From 08e3b858401b56d97ff101295a3236fc8e0d47ef Mon Sep 17 00:00:00 2001 From: Philipp Gesang Date: Mon, 29 Dec 2014 23:38:05 +0100 Subject: [fontloader] sync with Context as of 2014-12-29 --- src/fontloader/misc/fontloader-font-afm.lua | 11 ++- src/fontloader/misc/fontloader-font-ini.lua | 2 +- src/fontloader/misc/fontloader-font-otf.lua | 24 +++-- src/fontloader/misc/fontloader-l-file.lua | 131 +++++++++++++++------------- src/fontloader/misc/fontloader-l-io.lua | 5 -- src/fontloader/misc/fontloader-l-lua.lua | 11 +++ src/fontloader/misc/fontloader-l-table.lua | 32 ++++--- src/fontloader/misc/fontloader-util-str.lua | 4 +- 8 files changed, 127 insertions(+), 93 deletions(-) (limited to 'src/fontloader/misc') diff --git a/src/fontloader/misc/fontloader-font-afm.lua b/src/fontloader/misc/fontloader-font-afm.lua index ca5616a..a96c668 100644 --- a/src/fontloader/misc/fontloader-font-afm.lua +++ b/src/fontloader/misc/fontloader-font-afm.lua @@ -48,6 +48,11 @@ local definers = fonts.definers local readers = fonts.readers local constructors = fonts.constructors +local fontloader = fontloader +local font_to_table = fontloader.to_table +local open_font = fontloader.open +local close_font = fontloader.close + local afm = constructors.newhandler("afm") local pfb = constructors.newhandler("pfb") @@ -222,10 +227,10 @@ end local function get_indexes(data,pfbname) data.resources.filename = resolvers.unresolve(pfbname) -- no shortcut - local pfbblob = fontloader.open(pfbname) + local pfbblob = open_font(pfbname) if pfbblob then local characters = data.characters - local pfbdata = fontloader.to_table(pfbblob) + local pfbdata = font_to_table(pfbblob) if pfbdata then local glyphs = pfbdata.glyphs if glyphs then @@ -251,7 +256,7 @@ local function get_indexes(data,pfbname) elseif trace_loading then report_afm("no data in pfb file %a",pfbname) end - fontloader.close(pfbblob) + close_font(pfbblob) elseif trace_loading then report_afm("invalid pfb file %a",pfbname) end diff --git a/src/fontloader/misc/fontloader-font-ini.lua b/src/fontloader/misc/fontloader-font-ini.lua index 884b224..c547f89 100644 --- a/src/fontloader/misc/fontloader-font-ini.lua +++ b/src/fontloader/misc/fontloader-font-ini.lua @@ -29,4 +29,4 @@ fonts.readers = { } fonts.definers = { methods = { } } fonts.loggers = { register = function() end } -fontloader.totable = fontloader.to_table +fontloader.totable = fontloader.to_table -- not used diff --git a/src/fontloader/misc/fontloader-font-otf.lua b/src/fontloader/misc/fontloader-font-otf.lua index 1bb608f..44ad893 100644 --- a/src/fontloader/misc/fontloader-font-otf.lua +++ b/src/fontloader/misc/fontloader-font-otf.lua @@ -56,13 +56,14 @@ otf.glists = { "gsub", "gpos" } otf.version = 2.802 -- beware: also sync font-mis.lua otf.cache = containers.define("fonts", "otf", otf.version, true) -local fontdata = fonts.hashes.identifiers -local chardata = characters and characters.data -- not used - +local hashes = fonts.hashes local definers = fonts.definers local readers = fonts.readers local constructors = fonts.constructors +local fontdata = hashes and hashes.identifiers +local chardata = characters and characters.data -- not used + local otffeatures = constructors.newfeatures("otf") local registerotffeature = otffeatures.register @@ -84,7 +85,12 @@ local applyruntimefixes = fonts.treatments and fonts.treatments.applyfixes local wildcard = "*" local default = "dflt" -local fontloaderfields = fontloader.fields +local fontloader = fontloader +local open_font = fontloader.open +local close_font = fontloader.close +local font_fields = fontloader.fields +local apply_featurefile = fontloader.apply_featurefile + local mainfields = nil local glyphfields = nil -- not used yet @@ -137,7 +143,7 @@ local function load_featurefile(raw,featurefile) if trace_loading then report_otf("using featurefile %a", featurefile) end - fontloader.apply_featurefile(raw, featurefile) + apply_featurefile(raw, featurefile) end end @@ -437,12 +443,12 @@ function otf.load(filename,sub,featurefile) -- second argument (format) is gone report_otf("loading %a, hash %a",filename,hash) local fontdata, messages if sub then - fontdata, messages = fontloader.open(filename,sub) + fontdata, messages = open_font(filename,sub) else - fontdata, messages = fontloader.open(filename) + fontdata, messages = open_font(filename) end if fontdata then - mainfields = mainfields or (fontloaderfields and fontloaderfields(fontdata)) + mainfields = mainfields or (font_fields and font_fields(fontdata)) end if trace_loading and messages and #messages > 0 then if type(messages) == "string" then @@ -526,7 +532,7 @@ function otf.load(filename,sub,featurefile) -- second argument (format) is gone report_otf("preprocessing and caching time %s, packtime %s", elapsedtime(data),packdata and elapsedtime(packtime) or 0) end - fontloader.close(fontdata) -- free memory + close_font(fontdata) -- free memory if cleanup > 3 then collectgarbage("collect") end diff --git a/src/fontloader/misc/fontloader-l-file.lua b/src/fontloader/misc/fontloader-l-file.lua index 2742e99..2c471d7 100644 --- a/src/fontloader/misc/fontloader-l-file.lua +++ b/src/fontloader/misc/fontloader-l-file.lua @@ -15,51 +15,53 @@ if not lfs then lfs = optionalrequire("lfs") end -if not lfs then - - lfs = { - getcurrentdir = function() - return "." - end, - attributes = function() - return nil - end, - isfile = function(name) - local f = io.open(name,'rb') - if f then - f:close() - return true - end - end, - isdir = function(name) - print("you need to load lfs") - return false - end - } - -elseif not lfs.isfile then - - local attributes = lfs.attributes - - function lfs.isdir(name) - return attributes(name,"mode") == "directory" - end - - function lfs.isfile(name) - return attributes(name,"mode") == "file" - end - - -- function lfs.isdir(name) - -- local a = attributes(name) - -- return a and a.mode == "directory" - -- end - - -- function lfs.isfile(name) - -- local a = attributes(name) - -- return a and a.mode == "file" - -- end - -end +-- -- see later +-- +-- if not lfs then +-- +-- lfs = { +-- getcurrentdir = function() +-- return "." +-- end, +-- attributes = function() +-- return nil +-- end, +-- isfile = function(name) +-- local f = io.open(name,'rb') +-- if f then +-- f:close() +-- return true +-- end +-- end, +-- isdir = function(name) +-- print("you need to load lfs") +-- return false +-- end +-- } +-- +-- elseif not lfs.isfile then +-- +-- local attributes = lfs.attributes +-- +-- function lfs.isdir(name) +-- return attributes(name,"mode") == "directory" +-- end +-- +-- function lfs.isfile(name) +-- return attributes(name,"mode") == "file" +-- end +-- +-- -- function lfs.isdir(name) +-- -- local a = attributes(name) +-- -- return a and a.mode == "directory" +-- -- end +-- +-- -- function lfs.isfile(name) +-- -- local a = attributes(name) +-- -- return a and a.mode == "file" +-- -- end +-- +-- end local insert, concat = table.insert, table.concat local match, find, gmatch = string.match, string.find, string.gmatch @@ -72,6 +74,28 @@ local checkedsplit = string.checkedsplit local P, R, S, C, Cs, Cp, Cc, Ct = lpeg.P, lpeg.R, lpeg.S, lpeg.C, lpeg.Cs, lpeg.Cp, lpeg.Cc, lpeg.Ct +-- better this way: + +local tricky = S("/\\") * P(-1) +local attributes = lfs.attributes + +if sandbox then + sandbox.redefine(lfs.isfile,"lfs.isfile") + sandbox.redefine(lfs.isdir, "lfs.isdir") +end + +function lfs.isdir(name) + if lpegmatch(tricky,name) then + return attributes(name,"mode") == "directory" + else + return attributes(name.."/.","mode") == "directory" + end +end + +function lfs.isfile(name) + return attributes(name,"mode") == "file" +end + local colon = P(":") local period = P(".") local periods = P("..") @@ -554,23 +578,6 @@ function file.collapsepath(str,anchor) -- anchor: false|nil, true, "." end end --- better this way: - -local tricky = S("/\\") * P(-1) -local attributes = lfs.attributes - -function lfs.isdir(name) - if lpegmatch(tricky,name) then - return attributes(name,"mode") == "directory" - else - return attributes(name.."/.","mode") == "directory" - end -end - -function lfs.isfile(name) - return attributes(name,"mode") == "file" -end - -- local function test(str,...) -- print(string.format("%-20s %-15s %-30s %-20s",str,file.collapsepath(str),file.collapsepath(str,true),file.collapsepath(str,"."))) -- end diff --git a/src/fontloader/misc/fontloader-l-io.lua b/src/fontloader/misc/fontloader-l-io.lua index 020e811..a91d44d 100644 --- a/src/fontloader/misc/fontloader-l-io.lua +++ b/src/fontloader/misc/fontloader-l-io.lua @@ -339,11 +339,6 @@ function io.readstring(f,n,m) return str end --- - -if not io.i_limiter then function io.i_limiter() end end -- dummy so we can test safely -if not io.o_limiter then function io.o_limiter() end end -- dummy so we can test safely - -- This works quite ok: -- -- function io.piped(command,writer) diff --git a/src/fontloader/misc/fontloader-l-lua.lua b/src/fontloader/misc/fontloader-l-lua.lua index 9565f48..1a2a987 100644 --- a/src/fontloader/misc/fontloader-l-lua.lua +++ b/src/fontloader/misc/fontloader-l-lua.lua @@ -165,3 +165,14 @@ end if lua then lua.mask = load([[τεχ = 1]]) and "utf" or "ascii" end + +local flush = io.flush + +if flush then + + local execute = os.execute if execute then function os.execute(...) flush() return execute(...) end end + local exec = os.exec if exec then function os.exec (...) flush() return exec (...) end end + local spawn = os.spawn if spawn then function os.spawn (...) flush() return spawn (...) end end + local popen = io.popen if popen then function io.popen (...) flush() return popen (...) end end + +end diff --git a/src/fontloader/misc/fontloader-l-table.lua b/src/fontloader/misc/fontloader-l-table.lua index 3eb8b85..97e0441 100644 --- a/src/fontloader/misc/fontloader-l-table.lua +++ b/src/fontloader/misc/fontloader-l-table.lua @@ -49,9 +49,19 @@ function table.keys(t) end end +-- local function compare(a,b) +-- local ta, tb = type(a), type(b) -- needed, else 11 < 2 +-- if ta == tb then +-- return a < b +-- else +-- return tostring(a) < tostring(b) -- not that efficient +-- end +-- end + local function compare(a,b) - local ta, tb = type(a), type(b) -- needed, else 11 < 2 - if ta == tb then + local ta = type(a) -- needed, else 11 < 2 + local tb = type(b) -- needed, else 11 < 2 + if ta == tb and ta == "number" then return a < b else return tostring(a) < tostring(b) -- not that efficient @@ -469,7 +479,7 @@ local function do_serialize(root,name,depth,level,indexed) end end -- we could check for k (index) being number (cardinal) - if root and next(root) then + if root and next(root) ~= nil then -- local first, last = nil, 0 -- #root cannot be trusted here (will be ok in 5.2 when ipairs is gone) -- if compact then -- -- NOT: for k=1,#root do (we need to quit at nil) @@ -513,7 +523,7 @@ local function do_serialize(root,name,depth,level,indexed) handle(format("%s %q,",depth,v)) end elseif tv == "table" then - if not next(v) then + if next(v) == nil then handle(format("%s {},",depth)) elseif inline then -- and #t > 0 local st = simple_table(v) @@ -597,7 +607,7 @@ local function do_serialize(root,name,depth,level,indexed) end end elseif tv == "table" then - if not next(v) then + if next(v) == nil then if tk == "number" then if hexify then handle(format("%s [0x%X]={},",depth,k)) @@ -683,7 +693,7 @@ local function do_serialize(root,name,depth,level,indexed) --~ end end end - if level > 0 then + if level > 0 then handle(format("%s},",depth)) end end @@ -748,7 +758,7 @@ local function serialize(_handle,root,name,specification) -- handle wins root._w_h_a_t_e_v_e_r_ = nil end -- Let's forget about empty tables. - if next(root) then + if next(root) ~= nil then do_serialize(root,name,"",0) end end @@ -928,7 +938,7 @@ local function sparse(old,nest,keeptables) if not (v == "" or v == false) then if nest and type(v) == "table" then v = sparse(v,nest) - if keeptables or next(v) then + if keeptables or next(v) ~= nil then new[k] = v end else @@ -1066,11 +1076,11 @@ end -- slower than #t on indexed tables (#t only returns the size of the numerically indexed slice) function table.is_empty(t) - return not t or not next(t) + return not t or next(t) == nil end function table.has_one_entry(t) - return t and not next(t,next(t)) + return t and next(t,next(t)) == nil end -- new @@ -1157,7 +1167,7 @@ function table.filtered(t,pattern,sort,cmp) else local n = next(t) local function iterator() - while n do + while n ~= nil do local k = n n = next(t,k) if find(k,pattern) then diff --git a/src/fontloader/misc/fontloader-util-str.lua b/src/fontloader/misc/fontloader-util-str.lua index a040b01..a677a82 100644 --- a/src/fontloader/misc/fontloader-util-str.lua +++ b/src/fontloader/misc/fontloader-util-str.lua @@ -361,10 +361,10 @@ strings.tracers = tracedchars function string.tracedchar(b) -- todo: table if type(b) == "number" then - return tracedchars[b] or (utfchar(b) .. " (U+" .. format('%05X',b) .. ")") + return tracedchars[b] or (utfchar(b) .. " (U+" .. format("%05X",b) .. ")") else local c = utfbyte(b) - return tracedchars[c] or (b .. " (U+" .. format('%05X',c) .. ")") + return tracedchars[c] or (b .. " (U+" .. (c and format("%05X",c) or "?????") .. ")") end end -- cgit v1.2.3 From a5998cb3add3331d4e44024bae4ec3c18777ca4f Mon Sep 17 00:00:00 2001 From: Philipp Gesang Date: Wed, 31 Dec 2014 18:06:47 +0100 Subject: [fontloader] sync with Context as of 2014-12-31 --- src/fontloader/misc/fontloader-l-file.lua | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'src/fontloader/misc') diff --git a/src/fontloader/misc/fontloader-l-file.lua b/src/fontloader/misc/fontloader-l-file.lua index 2c471d7..7ed6370 100644 --- a/src/fontloader/misc/fontloader-l-file.lua +++ b/src/fontloader/misc/fontloader-l-file.lua @@ -157,8 +157,8 @@ file.suffix = suffixonly file.suffixesonly = suffixesonly file.suffixes = suffixesonly -file.dirname = pathpart -- obsolete -file.extname = suffixonly -- obsolete +file.dirname = pathpart -- obsolete +file.extname = suffixonly -- obsolete -- actually these are schemes -- cgit v1.2.3 From f070e8b5b193c0ce686d2e6448b53338a499aecf Mon Sep 17 00:00:00 2001 From: Philipp Gesang Date: Wed, 11 Mar 2015 07:46:44 +0100 Subject: [fontloader] sync with Context as of 2015-03-11 --- src/fontloader/misc/fontloader-font-otf.lua | 2 +- src/fontloader/misc/fontloader-font-tfm.lua | 6 +- src/fontloader/misc/fontloader-fonts-cbk.lua | 13 +- src/fontloader/misc/fontloader-fonts-inj.lua | 385 +++++++++++++++------------ src/fontloader/misc/fontloader-fonts-otn.lua | 12 +- 5 files changed, 230 insertions(+), 188 deletions(-) (limited to 'src/fontloader/misc') diff --git a/src/fontloader/misc/fontloader-font-otf.lua b/src/fontloader/misc/fontloader-font-otf.lua index 44ad893..c7e83a4 100644 --- a/src/fontloader/misc/fontloader-font-otf.lua +++ b/src/fontloader/misc/fontloader-font-otf.lua @@ -53,7 +53,7 @@ local otf = fonts.handlers.otf otf.glists = { "gsub", "gpos" } -otf.version = 2.802 -- beware: also sync font-mis.lua +otf.version = 2.803 -- beware: also sync font-mis.lua otf.cache = containers.define("fonts", "otf", otf.version, true) local hashes = fonts.hashes diff --git a/src/fontloader/misc/fontloader-font-tfm.lua b/src/fontloader/misc/fontloader-font-tfm.lua index 49df94e..ab03788 100644 --- a/src/fontloader/misc/fontloader-font-tfm.lua +++ b/src/fontloader/misc/fontloader-font-tfm.lua @@ -72,15 +72,15 @@ local function read_from_tfm(specification) properties.filename = specification.filename properties.format = fonts.formats.tfm -- better than nothing parameters.size = size - shared.rawdata = { } - shared.features = features - shared.processes = next(features) and tfm.setfeatures(tfmdata,features) or nil -- tfmdata.properties = properties tfmdata.resources = resources tfmdata.parameters = parameters tfmdata.shared = shared -- + shared.rawdata = { } + shared.features = features + shared.processes = next(features) and tfm.setfeatures(tfmdata,features) or nil parameters.slant = parameters.slant or parameters[1] or 0 parameters.space = parameters.space or parameters[2] or 0 parameters.space_stretch = parameters.space_stretch or parameters[3] or 0 diff --git a/src/fontloader/misc/fontloader-fonts-cbk.lua b/src/fontloader/misc/fontloader-fonts-cbk.lua index 414cafb..ce19c88 100644 --- a/src/fontloader/misc/fontloader-fonts-cbk.lua +++ b/src/fontloader/misc/fontloader-fonts-cbk.lua @@ -116,13 +116,14 @@ function nodes.handlers.nodepass(head) if basepass and #basefonts > 0 then for i=1,#basefonts do local range = basefonts[i] - local start, stop = range[1], range[2] + local start = range[1] + local stop = range[2] if stop then - ligaturing(start,stop) - kerning(start,stop) - else - ligaturing(start) - kerning(start) + start, stop = ligaturing(start,stop) + start, stop = kerning(start,stop) + elseif start then + start = ligaturing(start) + start = kerning(start) end end end diff --git a/src/fontloader/misc/fontloader-fonts-inj.lua b/src/fontloader/misc/fontloader-fonts-inj.lua index 3b93382..cb9ed89 100644 --- a/src/fontloader/misc/fontloader-fonts-inj.lua +++ b/src/fontloader/misc/fontloader-fonts-inj.lua @@ -14,13 +14,12 @@ if not nodes.properties then return end local next, rawget = next, rawget local utfchar = utf.char +local fastcopy = table.fastcopy local trace_injections = false trackers.register("fonts.injections", function(v) trace_injections = v end) local report_injections = logs.reporter("fonts","injections") -report_injections("using experimental injector") - local attributes, nodes, node = attributes, nodes, node fonts = fonts @@ -81,19 +80,42 @@ function injections.resetcounts() keepregisteredcounts = false end +-- We need to make sure that a possible metatable will not kick in +-- unexpectedly. + function injections.reset(n) - local p = rawget(properties,start) - if p and p.injections then - -- todo: decrement counters? tricky as we then need to change the nof* to not increment - -- when we change a property - p.injections = nil -- should we keep the liga index? + local p = rawget(properties,n) + if p and rawget(p,"injections") then + p.injections = nil + end +end + +function injections.copy(target,source) + local sp = rawget(properties,source) + if sp then + local tp = rawget(properties,target) + local si = rawget(sp,"injections") + if si then + si = fastcopy(si) + if tp then + tp.injections = si + else + propertydata[target] = { + injections = si, + } + end + else + if tp then + tp.injections = nil + end + end end end function injections.setligaindex(n,index) local p = rawget(properties,n) if p then - local i = p.injections + local i = rawget(p,"injections") if i then i.ligaindex = index else @@ -113,9 +135,9 @@ end function injections.getligaindex(n,default) local p = rawget(properties,n) if p then - p = p.injections - if p then - return p.ligaindex or default + local i = rawget(p,"injections") + if i then + return i.ligaindex or default end end return default @@ -134,7 +156,7 @@ function injections.setcursive(start,nxt,factor,rlmode,exit,entry,tfmstart,tfmne -- local p = rawget(properties,start) if p then - local i = p.injections + local i = rawget(p,"injections") if i then i.cursiveanchor = true else @@ -151,7 +173,7 @@ function injections.setcursive(start,nxt,factor,rlmode,exit,entry,tfmstart,tfmne end local p = rawget(properties,nxt) if p then - local i = p.injections + local i = rawget(p,"injections") if i then i.cursivex = dx i.cursivey = dy @@ -185,14 +207,16 @@ function injections.setpair(current,factor,rlmode,r2lflag,spec,injection) -- r2l end local p = rawget(properties,current) if p then - local i = p.injections + local i = rawget(p,"injections") if i then - if leftkern ~= 0 or rightkern ~= 0 then - i.leftkern = i.leftkern or 0 + leftkern - i.rightkern = i.rightkern or 0 + rightkern + if leftkern ~= 0 then + i.leftkern = (i.leftkern or 0) + leftkern + end + if rightkern ~= 0 then + i.rightkern = (i.rightkern or 0) + rightkern end if yoffset ~= 0 then - i.yoffset = i.yoffset or 0 + yoffset + i.yoffset = (i.yoffset or 0) + yoffset end elseif leftkern ~= 0 or rightkern ~= 0 then p.injections = { @@ -240,9 +264,9 @@ function injections.setkern(current,factor,rlmode,x,injection) injection = "injections" end if p then - local i = p[injection] + local i = rawget(p,injection) if i then - i.leftkern = dx + i.leftkern or 0 + i.leftkern = dx + (i.leftkern or 0) else p[injection] = { leftkern = dx, @@ -270,7 +294,7 @@ function injections.setmark(start,base,factor,rlmode,ba,ma,tfmbase) -- ba=basean end local p = rawget(properties,start) if p then - local i = p.injections + local i = rawget(p,"injections") if i then i.markx = dx i.marky = dy @@ -313,18 +337,18 @@ local function show(n,what,nested,symbol) if n then local p = rawget(properties,n) if p then - local p = p[what] - if p then - local leftkern = p.leftkern or 0 - local rightkern = p.rightkern or 0 - local yoffset = p.yoffset or 0 - local markx = p.markx or 0 - local marky = p.marky or 0 - local markdir = p.markdir or 0 - local markbase = p.markbase or 0 -- will be markbasenode - local cursivex = p.cursivex or 0 - local cursivey = p.cursivey or 0 - local ligaindex = p.ligaindex or 0 + local i = rawget(p,what) + if i then + local leftkern = i.leftkern or 0 + local rightkern = i.rightkern or 0 + local yoffset = i.yoffset or 0 + local markx = i.markx or 0 + local marky = i.marky or 0 + local markdir = i.markdir or 0 + local markbase = i.markbase or 0 -- will be markbasenode + local cursivex = i.cursivex or 0 + local cursivey = i.cursivey or 0 + local ligaindex = i.ligaindex or 0 local margin = nested and 4 or 2 -- if rightkern ~= 0 or yoffset ~= 0 then @@ -355,9 +379,9 @@ local function showsub(n,what,where) report_injections("end subrun") end -local function trace(head) - report_injections("begin run: %s kerns, %s pairs, %s marks and %s cursives registered", - nofregisteredkerns,nofregisteredpairs,nofregisteredmarks,nofregisteredcursives) +local function trace(head,where) + report_injections("begin run %s: %s kerns, %s pairs, %s marks and %s cursives registered", + where or "",nofregisteredkerns,nofregisteredpairs,nofregisteredmarks,nofregisteredcursives) local n = head while n do local id = getid(n) @@ -414,10 +438,6 @@ local function collect_glyphs_1(head) local nf, tm = nil, nil for n in traverse_id(glyph_code,head) do -- only needed for relevant fonts if getsubtype(n) < 256 then - local pn = rawget(properties,n) - if pn then - pn = pn.injections - end local f = getfont(n) if f ~= nf then nf = f @@ -431,10 +451,14 @@ local function collect_glyphs_1(head) glyphs[nofglyphs] = n end -- yoffsets can influence curs steps - if pn then - local yoffset = pn.yoffset - if yoffset and yoffset ~= 0 then - setfield(n,"yoffset",yoffset) + local p = rawget(properties,n) + if p then + local i = rawget(p,"injections") + if i then + local yoffset = i.yoffset + if yoffset and yoffset ~= 0 then + setfield(n,"yoffset",yoffset) + end end end end @@ -470,18 +494,20 @@ local function inject_marks(marks,nofmarks) local n = marks[i] local pn = rawget(properties,n) if pn then - pn = pn.injections - end - if pn then - -- local markbase = pn.markbase - -- if markbase then - -- local p = markanchors[markbase] + pn = rawget(pn,"injections") + if pn then local p = pn.markbasenode if p then local px = getfield(p,"xoffset") local ox = 0 + local rightkern = nil local pp = rawget(properties,p) - local rightkern = pp and pp.rightkern + if pp then + pp = rawget(pp,"injections") + if pp then + rightkern = pp.rightkern + end + end if rightkern then -- x and w ~= 0 if pn.markdir < 0 then -- kern(w-x) glyph(p) kern(x) mark(n) @@ -490,8 +516,13 @@ local function inject_marks(marks,nofmarks) else -- kern(x) glyph(p) kern(w-x) mark(n) -- ox = px - getfield(p,"width") + pn.markx - pp.leftkern - ox = px - pn.markx - pp.leftkern - -- report_injections("l2r case 1: %p",ox) + local leftkern = pp.leftkern + if leftkern then + ox = px - pn.markx + else + ox = px - pn.markx - leftkern + end +-- report_injections("l2r case 1: %p",ox) end else -- we need to deal with fonts that have marks with width @@ -525,10 +556,10 @@ local function inject_marks(marks,nofmarks) end setfield(n,"yoffset",oy) else - -- normally this can't happen (only when in trace mode which is a special case anyway) + -- normally this can't happen (only when in trace mode which is a special case anyway) -- report_injections("missing mark anchor %i",pn.markbase or 0) end - -- end + end end end end @@ -540,14 +571,14 @@ local function inject_cursives(glyphs,nofglyphs) local n = glyphs[i] local pn = rawget(properties,n) if pn then - pn = pn.injections + pn = rawget(pn,"injections") end if pn then local cursivex = pn.cursivex if cursivex then if cursiveanchor then if cursivex ~= 0 then - pn.leftkern = pn.leftkern or 0 + cursivex + pn.leftkern = (pn.leftkern or 0) + cursivex end if lastanchor then if maxc == 0 then @@ -622,16 +653,16 @@ local function inject_kerns(head,glyphs,nofglyphs) local n = glyphs[i] local pn = rawget(properties,n) if pn then - pn = pn.injections - end - if pn then - local leftkern = pn.leftkern - if leftkern ~= 0 then - insert_node_before(head,n,newkern(leftkern)) -- type 0/2 - end - local rightkern = pn.rightkern - if rightkern and rightkern ~= 0 then - insert_node_after(head,n,newkern(rightkern)) -- type 0/2 + local i = rawget(pn,"injections") + if i then + local leftkern = i.leftkern + if leftkern and leftkern ~= 0 then + insert_node_before(head,n,newkern(leftkern)) -- type 0/2 + end + local rightkern = i.rightkern + if rightkern and rightkern ~= 0 then + insert_node_after(head,n,newkern(rightkern)) -- type 0/2 + end end end end @@ -640,7 +671,7 @@ end local function inject_everything(head,where) head = tonut(head) if trace_injections then - trace(head) + trace(head,"everything") end local glyphs, nofglyphs, marks, nofmarks if nofregisteredpairs > 0 then @@ -652,7 +683,7 @@ local function inject_everything(head,where) if nofregisteredcursives > 0 then inject_cursives(glyphs,nofglyphs) end - if nofregisteredmarks > 0 then + if nofregisteredmarks > 0 then -- and nofmarks > 0 inject_marks(marks,nofmarks) end inject_kerns(head,glyphs,nofglyphs) @@ -671,7 +702,7 @@ end local function inject_kerns_only(head,where) head = tonut(head) if trace_injections then - trace(head) + trace(head,"kerns") end local n = head local p = nil @@ -684,10 +715,10 @@ local function inject_kerns_only(head,where) if p then local d = getfield(p,"post") if d then - local pn = pn.postinjections - if pn then - local leftkern = pn.leftkern - if leftkern ~= 0 then + local i = rawget(pn,"postinjections") + if i then + local leftkern = i.leftkern + if leftkern and leftkern ~= 0 then local t = find_tail(d) insert_node_after(d,t,newkern(leftkern)) end @@ -695,28 +726,28 @@ local function inject_kerns_only(head,where) end local d = getfield(p,"replace") if d then - local pn = pn.replaceinjections - if pn then - local leftkern = pn.leftkern - if leftkern ~= 0 then + local i = rawget(pn,"replaceinjections") + if i then + local leftkern = i.leftkern + if leftkern and leftkern ~= 0 then local t = find_tail(d) insert_node_after(d,t,newkern(leftkern)) end end else - local pn = pn.injections - if pn then - local leftkern = pn.leftkern - if leftkern ~= 0 then + local i = rawget(pn,"injections") + if i then + local leftkern = i.leftkern + if leftkern and leftkern ~= 0 then setfield(p,"replace",newkern(leftkern)) end end end else - local pn = pn.injections - if pn then - local leftkern = pn.leftkern - if leftkern ~= 0 then + local i = rawget(pn,"injections") + if i then + local leftkern = i.leftkern + if leftkern and leftkern ~= 0 then head = insert_node_before(head,n,newkern(leftkern)) end end @@ -734,12 +765,12 @@ local function inject_kerns_only(head,where) if getsubtype(n) < 256 then local pn = rawget(properties,n) if pn then - pn = pn.preinjections - end - if pn then - local leftkern = pn.leftkern - if leftkern ~= 0 then - h = insert_node_before(h,n,newkern(leftkern)) + local i = rawget(pn,"preinjections") + if i then + local leftkern = i.leftkern + if leftkern and leftkern ~= 0 then + h = insert_node_before(h,n,newkern(leftkern)) + end end end else @@ -757,12 +788,12 @@ local function inject_kerns_only(head,where) if getsubtype(n) < 256 then local pn = rawget(properties,n) if pn then - pn = pn.postinjections - end - if pn then - local leftkern = pn.leftkern - if leftkern ~= 0 then - h = insert_node_before(h,n,newkern(leftkern)) + local i = rawget(pn,"postinjections") + if i then + local leftkern = i.leftkern + if leftkern and leftkern ~= 0 then + h = insert_node_before(h,n,newkern(leftkern)) + end end end else @@ -780,12 +811,12 @@ local function inject_kerns_only(head,where) if getsubtype(n) < 256 then local pn = rawget(properties,n) -- why can it be empty { } if pn then - pn = pn.replaceinjections - end - if pn then - local leftkern = pn.leftkern - if leftkern ~= 0 then - h = insert_node_before(h,n,newkern(leftkern)) + local i = rawget(pn,"replaceinjections") + if i then + local leftkern = i.leftkern + if leftkern and leftkern ~= 0 then + h = insert_node_before(h,n,newkern(leftkern)) + end end end else @@ -814,7 +845,7 @@ end local function inject_pairs_only(head,where) head = tonut(head) if trace_injections then - trace(head) + trace(head,"pairs") end -- local n = head @@ -828,14 +859,14 @@ local function inject_pairs_only(head,where) if p then local d = getfield(p,"post") if d then - local pn = pn.postinjections - if pn then - local leftkern = pn.leftkern - if leftkern ~= 0 then + local i = rawget(pn,"postinjections") + if i then + local leftkern = i.leftkern + if leftkern and leftkern ~= 0 then local t = find_tail(d) insert_node_after(d,t,newkern(leftkern)) end - -- local rightkern = pn.rightkern + -- local rightkern = i.rightkern -- if rightkern and rightkern ~= 0 then -- insert_node_after(head,n,newkern(rightkern)) -- n = getnext(n) -- to be checked @@ -844,27 +875,27 @@ local function inject_pairs_only(head,where) end local d = getfield(p,"replace") if d then - local pn = pn.replaceinjections - if pn then - local leftkern = pn.leftkern - if leftkern ~= 0 then + local i = rawget(pn,"replaceinjections") + if i then + local leftkern = i.leftkern + if leftkern and leftkern ~= 0 then local t = find_tail(d) insert_node_after(d,t,newkern(leftkern)) end - -- local rightkern = pn.rightkern + -- local rightkern = i.rightkern -- if rightkern and rightkern ~= 0 then -- insert_node_after(head,n,newkern(rightkern)) -- n = getnext(n) -- to be checked -- end end else - local pn = pn.injections - if pn then - local leftkern = pn.leftkern - if leftkern ~= 0 then + local i = rawget(pn,"injections") + if i then + local leftkern = i.leftkern + if leftkern and leftkern ~= 0 then setfield(p,"replace",newkern(leftkern)) end - -- local rightkern = pn.rightkern + -- local rightkern = i.rightkern -- if rightkern and rightkern ~= 0 then -- insert_node_after(head,n,newkern(rightkern)) -- n = getnext(n) -- to be checked @@ -873,17 +904,17 @@ local function inject_pairs_only(head,where) end else -- this is the most common case - local pn = pn.injections - if pn then - local yoffset = pn.yoffset + local i = rawget(pn,"injections") + if i then + local yoffset = i.yoffset if yoffset and yoffset ~= 0 then setfield(n,"yoffset",yoffset) end - local leftkern = pn.leftkern - if leftkern ~= 0 then + local leftkern = i.leftkern + if leftkern and leftkern ~= 0 then insert_node_before(head,n,newkern(leftkern)) end - local rightkern = pn.rightkern + local rightkern = i.rightkern if rightkern and rightkern ~= 0 then insert_node_after(head,n,newkern(rightkern)) n = getnext(n) -- to be checked @@ -901,23 +932,23 @@ local function inject_pairs_only(head,where) local h = d for n in traverse_id(glyph_code,d) do if getsubtype(n) < 256 then - local pn = rawget(properties,n) - if pn then - pn = pn.preinjections - end - if pn then - local yoffset = pn.yoffset - if yoffset and yoffset ~= 0 then - setfield(n,"yoffset",yoffset) - end - local leftkern = pn.leftkern - if leftkern ~= 0 then - h = insert_node_before(h,n,newkern(leftkern)) - end - local rightkern = pn.rightkern - if rightkern and rightkern ~= 0 then - insert_node_after(head,n,newkern(rightkern)) - n = getnext(n) -- to be checked + local p = rawget(properties,n) + if p then + local i = rawget(p,"preinjections") + if i then + local yoffset = i.yoffset + if yoffset and yoffset ~= 0 then + setfield(n,"yoffset",yoffset) + end + local leftkern = i.leftkern + if leftkern ~= 0 then + h = insert_node_before(h,n,newkern(leftkern)) + end + local rightkern = i.rightkern + if rightkern and rightkern ~= 0 then + insert_node_after(head,n,newkern(rightkern)) + n = getnext(n) -- to be checked + end end end else @@ -933,23 +964,23 @@ local function inject_pairs_only(head,where) local h = d for n in traverse_id(glyph_code,d) do if getsubtype(n) < 256 then - local pn = rawget(properties,n) - if pn then - pn = pn.postinjections - end - if pn then - local yoffset = pn.yoffset - if yoffset and yoffset ~= 0 then - setfield(n,"yoffset",yoffset) - end - local leftkern = pn.leftkern - if leftkern ~= 0 then - h = insert_node_before(h,n,newkern(leftkern)) - end - local rightkern = pn.rightkern - if rightkern and rightkern ~= 0 then - insert_node_after(head,n,newkern(rightkern)) - n = getnext(n) -- to be checked + local p = rawget(properties,n) + if p then + local i = rawget(p,"postinjections") + if i then + local yoffset = i.yoffset + if yoffset and yoffset ~= 0 then + setfield(n,"yoffset",yoffset) + end + local leftkern = i.leftkern + if leftkern and leftkern ~= 0 then + h = insert_node_before(h,n,newkern(leftkern)) + end + local rightkern = i.rightkern + if rightkern and rightkern ~= 0 then + insert_node_after(head,n,newkern(rightkern)) + n = getnext(n) -- to be checked + end end end else @@ -965,23 +996,23 @@ local function inject_pairs_only(head,where) local h = d for n in traverse_id(glyph_code,d) do if getsubtype(n) < 256 then - local pn = rawget(properties,n) - if pn then - pn = pn.replaceinjections - end - if pn then - local yoffset = pn.yoffset - if yoffset and yoffset ~= 0 then - setfield(n,"yoffset",yoffset) - end - local leftkern = pn.leftkern - if leftkern ~= 0 then - h = insert_node_before(h,n,newkern(leftkern)) - end - local rightkern = pn.rightkern - if rightkern and rightkern ~= 0 then - insert_node_after(head,n,newkern(rightkern)) - n = getnext(n) -- to be checked + local p = rawget(properties,n) + if p then + local i = rawget(pn,"replaceinjections") + if i then + local yoffset = i.yoffset + if yoffset and yoffset ~= 0 then + setfield(n,"yoffset",yoffset) + end + local leftkern = i.leftkern + if leftkern and leftkern ~= 0 then + h = insert_node_before(h,n,newkern(leftkern)) + end + local rightkern = i.rightkern + if rightkern and rightkern ~= 0 then + insert_node_after(head,n,newkern(rightkern)) + n = getnext(n) -- to be checked + end end end else diff --git a/src/fontloader/misc/fontloader-fonts-otn.lua b/src/fontloader/misc/fontloader-fonts-otn.lua index 32dc820..3f53078 100644 --- a/src/fontloader/misc/fontloader-fonts-otn.lua +++ b/src/fontloader/misc/fontloader-fonts-otn.lua @@ -6,6 +6,9 @@ if not modules then modules = { } end modules ['font-otn'] = { license = "see context related readme files", } +-- todo: looks like we have a leak somewhere (probably in ligatures) +-- todo: copy attributes to disc + -- this is a context version which can contain experimental code, but when we -- have serious patches we also need to change the other two font-otn files @@ -243,6 +246,7 @@ local setcursive = injections.setcursive local setkern = injections.setkern local setpair = injections.setpair local resetinjection = injections.reset +local copyinjection = injections.copy local setligaindex = injections.setligaindex local getligaindex = injections.getligaindex @@ -354,13 +358,19 @@ local function copy_glyph(g) -- next and prev are untouched ! if components then setfield(g,"components",nil) local n = copy_node(g) + copyinjection(n,g) -- we need to preserve the lig indices setfield(g,"components",components) return n else - return copy_node(g) + local n = copy_node(g) + copyinjection(n,g) -- we need to preserve the lig indices + return n end end +-- + + -- start is a mark and we need to keep that one local function markstoligature(kind,lookupname,head,start,stop,char) -- cgit v1.2.3