diff options
Diffstat (limited to 'Master/texmf-dist/tex/context/base/mkiv/typo-krn.lua')
-rw-r--r-- | Master/texmf-dist/tex/context/base/mkiv/typo-krn.lua | 130 |
1 files changed, 51 insertions, 79 deletions
diff --git a/Master/texmf-dist/tex/context/base/mkiv/typo-krn.lua b/Master/texmf-dist/tex/context/base/mkiv/typo-krn.lua index 7607fc5f509..24a91d6b61a 100644 --- a/Master/texmf-dist/tex/context/base/mkiv/typo-krn.lua +++ b/Master/texmf-dist/tex/context/base/mkiv/typo-krn.lua @@ -10,12 +10,12 @@ if not modules then modules = { } end modules ['typo-krn'] = { -- components: better split on tounicode local next, type, tonumber = next, type, tonumber -local utfchar = utf.char local nodes = nodes local fonts = fonts -local tasks = nodes.tasks +local enableaction = nodes.tasks.enableaction + local nuts = nodes.nuts local nodepool = nuts.pool @@ -25,27 +25,31 @@ local tonut = nuts.tonut -- check what is used local find_node_tail = nuts.tail -local free_node = nuts.free +local flush_node = nuts.flush_node local insert_node_before = nuts.insert_before local insert_node_after = nuts.insert_after local end_of_math = nuts.end_of_math +local use_components = nuts.use_components local getfield = nuts.getfield local getnext = nuts.getnext local getprev = nuts.getprev -local getboth = nuts.getboth local getid = nuts.getid local getfont = nuts.getfont local getsubtype = nuts.getsubtype local getchar = nuts.getchar local getdisc = nuts.getdisc +local getglue = nuts.getglue +local getkern = nuts.getkern local isglyph = nuts.isglyph local setfield = nuts.setfield local getattr = nuts.getattr -local setattr = nuts.setattr +local takeattr = nuts.takeattr local setlink = nuts.setlink -local setsubtype = nuts.setsubtype +local setdisc = nuts.setdisc +local setglue = nuts.setglue +local setkern = nuts.setkern local texsetattribute = tex.setattribute local unsetvalue = attributes.unsetvalue @@ -82,7 +86,6 @@ local spaceskip_code = skipcodes.spaceskip local xspaceskip_code = skipcodes.xspaceskip local fonthashes = fonts.hashes -local fontdata = fonthashes.identifiers local chardata = fonthashes.characters local quaddata = fonthashes.quads local markdata = fonthashes.marks @@ -104,11 +107,8 @@ typesetters.kerns = typesetters.kerns or { } local kerns = typesetters.kerns local report = logs.reporter("kerns") -local trace_ligatures = false trackers.register("typesetters.kerns.ligatures",function(v) trace_ligatures = v end) - --- use_advance is just an experiment: it makes copying glyphs (instead of new_glyph) dangerous - -local use_advance = false directives.register("typesetters.kerns.advance", function(v) use_advance = v end) +local trace_ligatures = false trackers.register("typesetters.kerns.ligatures", function(v) trace_ligatures = v end) +local trace_ligatures_d = false trackers.register("typesetters.kerns.ligatures.detail",function(v) trace_ligatures_d = v end) kerns.mapping = kerns.mapping or { } kerns.factors = kerns.factors or { } @@ -146,18 +146,24 @@ function kerns.keepligature(n) -- might become default local c = getchar(n) local d = fontdescriptions[f][c].name if a > 0 and contextsetups[a].keepligatures == v_auto then - report("font %!font:name!, glyph %a, slot %X -> ligature %s, by %s feature %a",f,d,c,"kept","dynamic","keepligatures") + if trace_ligatures_d then + report("font %!font:name!, glyph %a, slot %X -> ligature %s, by %s feature %a",f,d,c,"kept","dynamic","keepligatures") + end setcolor(n,"darkred") return true end local k = fontfeatures[f].keepligatures if k == v_auto then - report("font %!font:name!, glyph %a, slot %X -> ligature %s, by %s feature %a",f,d,c,"kept","static","keepligatures") + if trace_ligatures_d then + report("font %!font:name!, glyph %a, slot %X -> ligature %s, by %s feature %a",f,d,c,"kept","static","keepligatures") + end setcolor(n,"darkgreen") return true end if not k then - report("font %!font:name!, glyph %a, slot %X -> ligature %s, by %s feature %a",f,d,c,"split","static","keepligatures") + if trace_ligatures_d then + report("font %!font:name!, glyph %a, slot %X -> ligature %s, by %s feature %a",f,d,c,"split","static","keepligatures") + end resetcolor(n) return false end @@ -227,8 +233,7 @@ local function inject_begin(boundary,prev,keeptogether,krn,ok) -- prev is a glyp end if inject then -- not yet ok, as injected kerns can be overlays (from node-inj.lua) - setsubtype(boundary,userkern_code) - setfield(boundary,"kern",getfield(boundary,"kern") + quaddata[getfont(prev)]*krn) + setkern(boundary,getkern(boundary) + quaddata[getfont(prev)]*krn,userkern_code) return boundary, true end end @@ -264,8 +269,7 @@ local function inject_end(boundary,next,keeptogether,krn,ok) end if inject then -- not yet ok, as injected kerns can be overlays (from node-inj.lua) - setsubtype(tail,userkern_code) - setfield(tail,"kern",getfield(tail,"kern") + quaddata[getfont(next)]*krn) + setkern(tail,getkern(tail) + quaddata[getfont(next)]*krn,userkern_code) return boundary, true end end @@ -279,7 +283,7 @@ local function inject_end(boundary,next,keeptogether,krn,ok) local data = chardata[font][nextchar] local kerns = data and data.kerns local kern = (kerns and kerns[char] or 0) + quaddata[font]*krn - insert_node_after(boundary,tail,new_kern(kern)) + setlink(tail,new_kern(kern)) return boundary, true end end @@ -315,8 +319,7 @@ local function process_list(head,keeptogether,krn,font,okay) end if inject then -- not yet ok, as injected kerns can be overlays (from node-inj.lua) - setsubtype(prev,userkern_code) - setfield(prev,"kern",getfield(prev,"kern") + kern) + setkern(prev,getkern(prev) + kern,userkern_code) okay = true end end @@ -378,9 +381,8 @@ function kerns.handler(head) -- fontkerns don't get the attribute but they always sit between glyphs so -- are always valid bound .. disc nodes also somtimes don't get them local id = getid(start) - local attr = getattr(start,a_kerns) + local attr = takeattr(start,a_kerns) if attr and attr > 0 then - setattr(start,a_kerns,0) -- unsetvalue) local krn = mapping[attr] if krn == v_max then krn = .25 @@ -390,31 +392,13 @@ function kerns.handler(head) end if not krn or krn == 0 then bound = false - elseif id == glyph_code then -- we could use the subtype ligature - local c = getfield(start,"components") - if not c then - -- fine - elseif keepligature and keepligature(start) then + elseif id == glyph_code then + if keepligature and keepligature(start) then -- keep 'm - c = nil else - while c do - local s = start - local t = find_node_tail(c) - local p, n = getboth(s) - if p then - setlink(p,c) - else - head = c - end - if n then - setlink(t,n) - end - start = c - setfield(s,"components",nil) - free_node(s) - c = getfield(start,"components") - end + -- we could use the subtype ligature but that's also a call + -- todo: check tounicode and use that information to split + head, start = use_components(head,start) end local char = getchar(start) local font = getfont(start) @@ -433,8 +417,7 @@ function kerns.handler(head) end if inject then -- not yet ok, as injected kerns can be overlays (from node-inj.lua) - setsubtype(prev,userkern_code) - setfield(prev,"kern",getfield(prev,"kern") + quaddata[font]*krn) + setkern(prev,getkern(prev) + quaddata[font]*krn,userkern_code) done = true end end @@ -446,11 +429,7 @@ function kerns.handler(head) local data = chardata[font][prevchar] local kerns = data and data.kerns local kern = (kerns and kerns[char] or 0) + quaddata[font]*krn - if not fillup and use_advance then - setfield(prev,"xadvance",getfield(prev,"xadvance") + kern) - else - insert_node_before(head,start,kern_injector(fillup,kern)) - end + insert_node_before(head,start,kern_injector(fillup,kern)) done = true end else @@ -480,12 +459,7 @@ function kerns.handler(head) languages.expand(start,pglyph and prev) end local pre, post, replace = getdisc(start) - -- we really need to reasign the fields as luatex keeps track of - -- the tail in a temp preceding head .. kind of messy so we might - -- want to come up with a better solution some day like a real - -- pretail etc fields in a disc node - -- - -- maybe i'll merge the now split functions + local indeed = false if pre then local okay = false if not prev then @@ -497,8 +471,7 @@ function kerns.handler(head) end pre, okay = process_list(pre,keeptogether,krn,false,okay) if okay then - setfield(start,"pre",pre) - done = true + indeed = true end end if post then @@ -512,8 +485,7 @@ function kerns.handler(head) end post, okay = process_list(post,keeptogether,krn,false,okay) if okay then - setfield(start,"post",post) - done = true + indeed = true end end if replace then @@ -534,11 +506,14 @@ function kerns.handler(head) end replace, okay = process_list(replace,keeptogether,krn,false,okay) if okay then - setfield(start,"replace",replace) - done = true + indeed = true end elseif prevfont then - setfield(start,"replace",new_kern(quaddata[prevfont]*krn)) + replace = new_kern(quaddata[prevfont]*krn) + indeed = true + end + if indeed then + setdisc(start,pre,post,replace) done = true end bound = false @@ -549,21 +524,18 @@ function kerns.handler(head) elseif id == glue_code then local subtype = getsubtype(start) if subtype == userskip_code or subtype == xspaceskip_code or subtype == spaceskip_code then - local w = getfield(start,"width") - if w > 0 then - local width = w + gluefactor * w * krn - local stretch = getfield(start,"stretch") * width / w - local shrink = getfield(start,"shrink") * width / w + local width, stretch, shrink, stretch_order, shrink_order = getglue(start) + if width > 0 then + local w = width + gluefactor * width * krn + stretch = stretch * w / width + shrink = shrink * w / width if fillup then stretch = 2 * stretch shrink = 2 * shrink - setfield(start,"stretch_order",1) - -- shrink_order ? + stretch_order = 1 + -- shrink_order = 1 ? end - setfield(start,"width",width) - setfield(start,"stretch",stretch) - setfield(start,"shrink", shrink) - -- + setglue(start,w,stretch,shrink,stretch_order,shrink_order) done = true end end @@ -612,7 +584,7 @@ function kerns.set(factor) end if factor == v_max or factor ~= 0 then if not enabled then - tasks.enableaction("processors","typesetters.kerns.handler") + enableaction("processors","typesetters.kerns.handler") enabled = true end local a = factors[factor] |