+local ltjw_apply_ashift_math = ltjw.apply_ashift_math
+local ltjw_apply_ashift_disc = ltjw.apply_ashift_disc
+local min, max = math.min, math.max
+local function calc_np_aux_glyph_common(lp, acc_flag)
+ Np.nuc = lp
+ Np.first= (Np.first or lp)
+ if getfield(lp, 'lang') == lang_ja then
+ Np.id = id_jglyph
+ local m, mc, cls = set_np_xspc_jachar(Np, lp)
+ local npi, npf
+ lp, head, npi, npf = capsule_glyph(lp, m, mc[cls], head, tex_dir)
+ Np.first = (Np.first~=Np.nuc) and Np.first or npf or npi
+ Np.nuc = npi
+ return true, check_next_ickern(lp);
+ else
+ Np.id = id_glyph
+ set_np_xspc_alchar(Np, getchar(lp), lp, 1)
+ -- loop
+ local first_glyph, last_glyph = lp
+ set_attr(lp, attr_icflag, PROCESSED); Np.last = lp
+ local y_adjust = has_attr(lp,attr_ablshift) or 0
+ local node_depth = getfield(lp, 'depth') + min(y_adjust, 0)
+ local adj_depth = (y_adjust>0) and (getfield(lp, 'depth') + y_adjust) or 0
+ setfield(lp, 'yoffset', getfield(lp, 'yoffset') - y_adjust)
+ lp = node_next(lp)
+ for lx in traverse(lp) do
+ local lai = get_attr_icflag(lx)
+ if lx==last or lai>=PACKED then
+ lp=lx; break
+ else
+ local lid = getid(lx)
+ if lid==id_glyph and getfield(lx, 'lang') ~= lang_ja then
+ -- 欧文文字
+ last_glyph = lx; set_attr(lx, attr_icflag, PROCESSED); Np.last = lx
+ y_adjust = has_attr(lx,attr_ablshift) or 0
+ node_depth = max(getfield(lx, 'depth') + min(y_adjust, 0), node_depth)
+ adj_depth = (y_adjust>0) and max(getfield(lx, 'depth') + y_adjust, adj_depth) or adj_depth
+ setfield(lx, 'yoffset', getfield(lx, 'yoffset') - y_adjust)
+ elseif lid==id_kern then
+ local ls = getsubtype(lx)
+ if ls==2 then -- アクセント用の kern
+ set_attr(lx, attr_icflag, PROCESSED)
+ lx = node_next(lx) -- lx: アクセント本体
+ if getid(lx)==id_glyph then
+ setfield(lx, 'yoffset', getfield(lx, 'yoffset') - (has_attr(lx,attr_ablshift) or 0))
+ else -- アクセントは上下にシフトされている
+ setfield(lx, 'shift', getfield(lx, 'shift') + (has_attr(lx,attr_ablshift) or 0))
+ end
+ lx = node_next(node_next(lx))
+ elseif ls==0 then
+ Np.last = lx
+ elseif (ls==3) or (lai==ITALIC) then
+ Np.last = lx; set_attr(lx, attr_icflag, IC_PROCESSED)
+ else
+ lp=lx; break
+ end
+ else
+ lp=lx; break
+ end
+ end
+ end
+ local r
+ if adj_depth>node_depth then
+ r = node_new(id_rule,3)
+ setfield(r, 'width', 0); setfield(r, 'height', 0)
+ setfield(r, 'depth',adj_depth); setfield(r, 'dir', tex_dir)
+ set_attr(r, attr_icflag, PROCESSED)
+ end
+ if last_glyph then
+ Np.last_char = last_glyph
+ if r then insert_after(head, first_glyph, r) end
+ else
+ local npn = Np.nuc
+ Np.last_char = npn
+ if r then
+ local nf, nc = getfont(npn), getchar(npn)
+ local ct = (font.getfont(nf) or font.fonts[nf] ).characters[nc]
+ if not ct then -- variation selector
+ node_free(r)
+ elseif (ct.left_protruding or 0) == 0 then
+ head = insert_before(head, npn, r)
+ Np.first = acc_flag and Np.first or ((Np.first==npn) and r or npn)
+ elseif (ct.right_protruding or 0) == 0 then
+ insert_after(head, npn, r); Np.last, lp = r, r
+ else
+ ltjb.package_warning_no_line(
+ 'luatexja',
+ 'Check depth of glyph node ' .. tostring(npn) .. '(font=' .. nf
+ .. ', char=' .. nc .. '), because its \\lpcode is ' .. tostring(ct.left_protruding)
+ .. ' and its \\rpcode is ' .. tostring(ct.right_protruding)
+ ); node_free(r)
+ end
+ end
+ end
+ return true, lp
+ end
+end
+local calc_np_auxtable
+do
+local dir_tate = luatexja.dir_table.dir_tate
+calc_np_auxtable = {
+ [id_glyph] = calc_np_aux_glyph_common,