From b47e8c2cdeeab0bcdb1c4c32328c933f3f8599de Mon Sep 17 00:00:00 2001 From: Hans Hagen Date: Tue, 24 Jan 2023 15:11:58 +0100 Subject: 2023-01-24 13:50:00 --- tex/context/base/mkii/cont-new.mkii | 2 +- tex/context/base/mkii/context.mkii | 2 +- tex/context/base/mkii/mult-it.mkii | 3 + tex/context/base/mkii/mult-ro.mkii | 3 + tex/context/base/mkiv/back-exp.lua | 4 +- tex/context/base/mkiv/colo-ini.lua | 54 ++- tex/context/base/mkiv/cont-new.mkiv | 2 +- tex/context/base/mkiv/context.mkiv | 2 +- tex/context/base/mkiv/mult-def.lua | 4 + tex/context/base/mkiv/mult-prm.lua | 16 +- tex/context/base/mkiv/status-files.pdf | Bin 24557 -> 24608 bytes tex/context/base/mkiv/status-lua.pdf | Bin 265035 -> 265525 bytes tex/context/base/mkiv/strc-doc.lua | 102 +++- tex/context/base/mkxl/back-exp-imp-mth.lmt | 5 +- tex/context/base/mkxl/back-exp.lmt | 33 +- tex/context/base/mkxl/catc-def.mkxl | 5 + tex/context/base/mkxl/colo-ini.mkxl | 3 + tex/context/base/mkxl/cont-new.mkxl | 2 +- tex/context/base/mkxl/context.mkxl | 2 +- tex/context/base/mkxl/driv-shp.lmt | 45 +- tex/context/base/mkxl/file-job.lmt | 6 +- tex/context/base/mkxl/file-job.mklx | 3 +- tex/context/base/mkxl/font-con.lmt | 2 + tex/context/base/mkxl/font-imp-effects.lmt | 62 ++- tex/context/base/mkxl/font-mat.mklx | 22 +- tex/context/base/mkxl/grph-rul.lmt | 25 +- tex/context/base/mkxl/grph-trf.lmt | 11 + tex/context/base/mkxl/grph-trf.mkxl | 33 +- tex/context/base/mkxl/lpdf-lmt.lmt | 1 + tex/context/base/mkxl/lpdf-rul.lmt | 372 +++++++------- tex/context/base/mkxl/lpdf-tag.lmt | 73 ++- tex/context/base/mkxl/math-acc.mklx | 2 + tex/context/base/mkxl/math-act.lmt | 15 +- tex/context/base/mkxl/math-ali.mkxl | 11 +- tex/context/base/mkxl/math-fnt.lmt | 26 +- tex/context/base/mkxl/math-ini.lmt | 143 +++--- tex/context/base/mkxl/math-ini.mkxl | 80 ++- tex/context/base/mkxl/math-spa.lmt | 24 +- tex/context/base/mkxl/math-tag.lmt | 79 +-- tex/context/base/mkxl/node-fin.lmt | 15 +- tex/context/base/mkxl/node-ini.lmt | 3 +- tex/context/base/mkxl/node-nut.lmt | 1 + tex/context/base/mkxl/node-ref.lmt | 21 +- tex/context/base/mkxl/node-res.lmt | 14 +- tex/context/base/mkxl/node-rul.mkxl | 28 +- tex/context/base/mkxl/node-shp.lmt | 2 +- tex/context/base/mkxl/pack-rul.mkxl | 60 ++- tex/context/base/mkxl/page-lay.mkxl | 3 + tex/context/base/mkxl/spac-ali.mkxl | 4 + tex/context/base/mkxl/spac-prf.lmt | 538 +++++++++++++++++---- tex/context/base/mkxl/spac-prf.mklx | 44 +- tex/context/base/mkxl/spac-ver.lmt | 4 +- tex/context/base/mkxl/spac-ver.mkxl | 7 +- tex/context/base/mkxl/strc-mat.mkxl | 7 - tex/context/base/mkxl/strc-tag.lmt | 47 +- tex/context/base/mkxl/supp-box.lmt | 21 +- tex/context/base/mkxl/supp-box.mkxl | 14 +- tex/context/base/mkxl/tabl-tbl.mkxl | 21 +- tex/context/base/mkxl/tabl-xtb.lmt | 60 ++- tex/context/base/mkxl/task-ini.lmt | 2 + tex/context/base/mkxl/trac-vis.lmt | 84 +++- tex/context/base/mkxl/trac-vis.mkxl | 4 +- tex/context/base/mkxl/typo-ada.lmt | 17 +- tex/context/base/mkxl/typo-ada.mkxl | 4 +- tex/context/base/mkxl/typo-chr.lmt | 4 +- tex/context/base/mkxl/typo-chr.mkxl | 4 +- tex/context/fonts/mkiv/lucida-math.lfg | 20 +- tex/context/fonts/mkiv/type-imp-lucida.mkiv | 2 +- tex/context/interface/mkii/keys-it.xml | 3 + tex/context/interface/mkii/keys-ro.xml | 3 + tex/context/modules/mkiv/s-math-repertoire.mkiv | 6 +- tex/generic/context/luatex/luatex-fonts-merged.lua | 2 +- 72 files changed, 1650 insertions(+), 698 deletions(-) (limited to 'tex') diff --git a/tex/context/base/mkii/cont-new.mkii b/tex/context/base/mkii/cont-new.mkii index be7fd9234..0766c82c3 100644 --- a/tex/context/base/mkii/cont-new.mkii +++ b/tex/context/base/mkii/cont-new.mkii @@ -11,7 +11,7 @@ %C therefore copyrighted by \PRAGMA. See mreadme.pdf for %C details. -\newcontextversion{2023.01.15 13:53} +\newcontextversion{2023.01.24 13:47} %D This file is loaded at runtime, thereby providing an %D excellent place for hacks, patches, extensions and new diff --git a/tex/context/base/mkii/context.mkii b/tex/context/base/mkii/context.mkii index 407cde6ad..3234da7b6 100644 --- a/tex/context/base/mkii/context.mkii +++ b/tex/context/base/mkii/context.mkii @@ -20,7 +20,7 @@ %D your styles an modules. \edef\contextformat {\jobname} -\edef\contextversion{2023.01.15 13:53} +\edef\contextversion{2023.01.24 13:47} %D For those who want to use this: diff --git a/tex/context/base/mkii/mult-it.mkii b/tex/context/base/mkii/mult-it.mkii index 3526f81f1..d9a553cea 100644 --- a/tex/context/base/mkii/mult-it.mkii +++ b/tex/context/base/mkii/mult-it.mkii @@ -450,6 +450,7 @@ \setinterfacevariable{printable}{stampabile} \setinterfacevariable{process}{process} \setinterfacevariable{product}{prodotto} +\setinterfacevariable{profile}{profile} \setinterfacevariable{program}{programma} \setinterfacevariable{project}{progetto} \setinterfacevariable{protected}{protetto} @@ -719,6 +720,7 @@ \setinterfaceconstant{bookmark}{segnalibro} \setinterfaceconstant{bottom}{fondo} \setinterfaceconstant{bottomafter}{bottomafter} +\setinterfaceconstant{bottomalign}{bottomalign} \setinterfaceconstant{bottombefore}{bottombefore} \setinterfaceconstant{bottomcolor}{bottomcolor} \setinterfaceconstant{bottomcommand}{bottomcommand} @@ -1333,6 +1335,7 @@ \setinterfaceconstant{toffset}{toffset} \setinterfaceconstant{tolerance}{tolleranza} \setinterfaceconstant{top}{cima} +\setinterfaceconstant{topalign}{topalign} \setinterfaceconstant{topcolor}{topcolor} \setinterfaceconstant{topcommand}{topcommand} \setinterfaceconstant{topdistance}{distanzacima} diff --git a/tex/context/base/mkii/mult-ro.mkii b/tex/context/base/mkii/mult-ro.mkii index f08babafd..914ea076f 100644 --- a/tex/context/base/mkii/mult-ro.mkii +++ b/tex/context/base/mkii/mult-ro.mkii @@ -450,6 +450,7 @@ \setinterfacevariable{printable}{tiparibil} \setinterfacevariable{process}{process} \setinterfacevariable{product}{produs} +\setinterfacevariable{profile}{profile} \setinterfacevariable{program}{program} \setinterfacevariable{project}{proiect} \setinterfacevariable{protected}{protejat} @@ -719,6 +720,7 @@ \setinterfaceconstant{bookmark}{semncarte} \setinterfaceconstant{bottom}{jos} \setinterfaceconstant{bottomafter}{bottomafter} +\setinterfaceconstant{bottomalign}{bottomalign} \setinterfaceconstant{bottombefore}{bottombefore} \setinterfaceconstant{bottomcolor}{bottomcolor} \setinterfaceconstant{bottomcommand}{bottomcommand} @@ -1333,6 +1335,7 @@ \setinterfaceconstant{toffset}{toffset} \setinterfaceconstant{tolerance}{toleranta} \setinterfaceconstant{top}{sus} +\setinterfaceconstant{topalign}{topalign} \setinterfaceconstant{topcolor}{topcolor} \setinterfaceconstant{topcommand}{topcommand} \setinterfaceconstant{topdistance}{distantasus} diff --git a/tex/context/base/mkiv/back-exp.lua b/tex/context/base/mkiv/back-exp.lua index 4f29e09d6..1abe9164a 100644 --- a/tex/context/base/mkiv/back-exp.lua +++ b/tex/context/base/mkiv/back-exp.lua @@ -3438,8 +3438,8 @@ end for n, subtype in nexthlist, head do if subtype == linelist_code then setattr(n,a_textblock,noftextblocks) - elseif subtype == glue_code or subtype == kern_code then -- no need to set fontkerns - setattr(n,a_textblock,0) +-- elseif subtype == glue_code or subtype == kern_code then -- weird, no list +-- setattr(n,a_textblock,0) end end return false diff --git a/tex/context/base/mkiv/colo-ini.lua b/tex/context/base/mkiv/colo-ini.lua index de319be46..136f5b435 100644 --- a/tex/context/base/mkiv/colo-ini.lua +++ b/tex/context/base/mkiv/colo-ini.lua @@ -889,7 +889,7 @@ local function formatcolor(ca,separator) end return concat(c,separator) else - return format("%0.3f",0) + return "0.000" -- format("%0.3f",0) end end @@ -1365,3 +1365,55 @@ implement { context((s < 0 and 0) or (s > 1 and 1) or s) end } + +-- playground for MS and HH + +do + + -- https://www.w3.org/TR/WCAG21/#dfn-contrast-ratio + -- https://www.w3.org/TR/WCAG21/#dfn-relative-luminance + + local function crap(v) + return v <= 0.03928 and v/12.92 or (v+0.055/1.055)^2.4 + end + + local function luminance(color) + color = values[color] + if color then + return (0.2126 * crap(color[2]) + 0.7152 * crap(color[3]) + 0.0722 * crap(color[4])) + 0.05 + end + end + + local function formatluminance(color) + local l = luminance(color) + if l then + return format("%0.3f",l) + end + end + + local function formatluminanceratio(one,two) + local one = luminance(one) + local two = luminance(two) + if one and two then + return format("%0.3f",one > two and one/two or two/one) + end + end + + colors.formatluminance = formatluminance + colors.formatluminanceratio = formatluminanceratio + + implement { + name = "formatluminance", + -- protected = true, + arguments = "integer", + actions = { formatluminance, context }, + } + + implement { + name = "formatluminanceratio", + -- protected = true, + arguments = { "integer", "integer" }, + actions = { formatluminanceratio, context }, + } + +end diff --git a/tex/context/base/mkiv/cont-new.mkiv b/tex/context/base/mkiv/cont-new.mkiv index 05a4a397c..34d9b4ed0 100644 --- a/tex/context/base/mkiv/cont-new.mkiv +++ b/tex/context/base/mkiv/cont-new.mkiv @@ -13,7 +13,7 @@ % \normalend % uncomment this to get the real base runtime -\newcontextversion{2023.01.15 13:53} +\newcontextversion{2023.01.24 13:47} %D This file is loaded at runtime, thereby providing an excellent place for hacks, %D patches, extensions and new features. There can be local overloads in cont-loc diff --git a/tex/context/base/mkiv/context.mkiv b/tex/context/base/mkiv/context.mkiv index a48bbf9cd..9e556a542 100644 --- a/tex/context/base/mkiv/context.mkiv +++ b/tex/context/base/mkiv/context.mkiv @@ -49,7 +49,7 @@ %D {YYYY.MM.DD HH:MM} format. \edef\contextformat {\jobname} -\edef\contextversion{2023.01.15 13:53} +\edef\contextversion{2023.01.24 13:47} %D Kind of special: diff --git a/tex/context/base/mkiv/mult-def.lua b/tex/context/base/mkiv/mult-def.lua index f73d41e93..4ac851371 100644 --- a/tex/context/base/mkiv/mult-def.lua +++ b/tex/context/base/mkiv/mult-def.lua @@ -17894,6 +17894,10 @@ return { ["pe"]="محصول", ["ro"]="produs", }, + ["profile"]={ + ["en"]="profile", + ["fr"]="profil", + }, ["program"]={ ["cs"]="program", ["de"]="programm", diff --git a/tex/context/base/mkiv/mult-prm.lua b/tex/context/base/mkiv/mult-prm.lua index 410d67a69..14035ad5a 100644 --- a/tex/context/base/mkiv/mult-prm.lua +++ b/tex/context/base/mkiv/mult-prm.lua @@ -509,7 +509,9 @@ return { "mathatomskip", "mathbackwardpenalties", "mathbeginclass", + "mathbinary", "mathcheckfencesmode", + "mathclose", "mathdictgroup", "mathdictproperties", "mathdirection", @@ -525,13 +527,20 @@ return { "mathghost", "mathgluemode", "mathgroupingmode", + "mathinner", "mathleftclass", "mathlimitsmode", "mathmainstyle", "mathmiddle", "mathnolimitsmode", + "mathopen", + "mathoperator", + "mathordinary", + "mathoverline", "mathpenaltiesmode", + "mathpunct", "mathradical", + "mathrelation", "mathrightclass", "mathrulesfam", "mathrulesmode", @@ -545,6 +554,7 @@ return { "mathsurroundmode", "mathsurroundskip", "maththreshold", + "mathunderline", "meaningasis", "meaningfull", "meaningless", @@ -665,6 +675,8 @@ return { "untraced", "unvpack", "variablefam", + "virtualhrule", + "virtualvrule", "vpack", "wordboundary", "wrapuppar", @@ -957,13 +969,9 @@ return { "mathchar", "mathchardef", "mathchoice", - "mathclose", "mathcode", - "mathinner", "mathop", - "mathopen", "mathord", - "mathpunct", "mathrel", "mathsurround", "maxdeadcycles", diff --git a/tex/context/base/mkiv/status-files.pdf b/tex/context/base/mkiv/status-files.pdf index d1ff492f2..10fca5828 100644 Binary files a/tex/context/base/mkiv/status-files.pdf and b/tex/context/base/mkiv/status-files.pdf differ diff --git a/tex/context/base/mkiv/status-lua.pdf b/tex/context/base/mkiv/status-lua.pdf index a28499680..45f201541 100644 Binary files a/tex/context/base/mkiv/status-lua.pdf and b/tex/context/base/mkiv/status-lua.pdf differ diff --git a/tex/context/base/mkiv/strc-doc.lua b/tex/context/base/mkiv/strc-doc.lua index 7a79a7121..0592ad7d5 100644 --- a/tex/context/base/mkiv/strc-doc.lua +++ b/tex/context/base/mkiv/strc-doc.lua @@ -526,26 +526,76 @@ end -- this one will become: return catcode, d (etc) +-- function sections.structuredata(depth,key,default,honorcatcodetable) -- todo: spec table and then also depth +-- if depth then +-- depth = levelmap[depth] or tonumber(depth) +-- end +-- if not depth or depth == 0 then +-- depth = data.depth +-- end +-- local data = data.status[depth] +-- local d +-- if data then +-- if find(key,".",1,true) then +-- d = accesstable(key,data) +-- else +-- d = data.titledata +-- d = d and d[key] +-- end +-- end +-- if d and type(d) ~= "table" then +-- if honorcatcodetable == true or honorcatcodetable == v_auto then +-- local metadata = data.metadata +-- local catcodes = metadata and metadata.catcodes +-- if catcodes then +-- ctx_sprint(catcodes,d) +-- else +-- context(d) +-- end +-- elseif not honorcatcodetable or honorcatcodetable == "" then +-- context(d) +-- else +-- local catcodes = catcodenumbers[honorcatcodetable] +-- if catcodes then +-- ctx_sprint(catcodes,d) +-- else +-- context(d) +-- end +-- end +-- elseif default then +-- context(default) +-- end +-- end + function sections.structuredata(depth,key,default,honorcatcodetable) -- todo: spec table and then also depth + local detail = false + if type(depth) == "string" then + depth, detail = string.splitup(depth,":") + end if depth then depth = levelmap[depth] or tonumber(depth) end if not depth or depth == 0 then depth = data.depth end - local data = data.status[depth] + local useddata + if detail == "+" then + useddata = structures.lists.collected[#structures.lists.tobesaved+1] + else + useddata = data.status[depth] + end local d - if data then + if useddata then if find(key,".",1,true) then - d = accesstable(key,data) + d = accesstable(key,useddata) else - d = data.titledata + d = useddata.titledata d = d and d[key] end end if d and type(d) ~= "table" then if honorcatcodetable == true or honorcatcodetable == v_auto then - local metadata = data.metadata + local metadata = useddata.metadata local catcodes = metadata and metadata.catcodes if catcodes then ctx_sprint(catcodes,d) @@ -567,20 +617,50 @@ function sections.structuredata(depth,key,default,honorcatcodetable) -- todo: sp end end +-- function sections.userdata(depth,key,default) +-- if depth then +-- depth = levelmap[depth] or tonumber(depth) +-- end +-- if not depth or depth == 0 then +-- depth = data.depth +-- end +-- if depth > 0 then +-- local userdata = data.status[depth] +-- userdata = userdata and userdata.userdata +-- userdata = (userdata and userdata[key]) or default +-- if userdata then +-- context(userdata) +-- end +-- end +-- end + function sections.userdata(depth,key,default) + local detail = false + if type(depth) == "string" then + depth, detail = string.splitup(depth,":") + end if depth then - depth = levelmap[depth] or tonumber(depth) + depth = levelmap[depth] + end + if not depth then + depth = tonumber(depth) end if not depth or depth == 0 then depth = data.depth end - if depth > 0 then - local userdata = data.status[depth] - userdata = userdata and userdata.userdata - userdata = (userdata and userdata[key]) or default + local userdata + if detail == "+" then + userdata = structures.lists.collected[#structures.lists.tobesaved+1] if userdata then - context(userdata) + userdata = userdata.userdata end + elseif depth > 0 then + userdata = data.status[depth] + userdata = userdata and userdata.userdata + end + userdata = (userdata and userdata[key]) or default + if userdata then + context(userdata) end end diff --git a/tex/context/base/mkxl/back-exp-imp-mth.lmt b/tex/context/base/mkxl/back-exp-imp-mth.lmt index 5f1554e65..4df109b54 100644 --- a/tex/context/base/mkxl/back-exp-imp-mth.lmt +++ b/tex/context/base/mkxl/back-exp-imp-mth.lmt @@ -175,9 +175,8 @@ do maxsize = 1 } end - elseif roottg == "msubsup" then - -- kind of tricky: we have a diufferent order in display mode + -- kind of tricky: we have a different order in display mode local nucleus, superscript, subscript if ndata > 3 then -- error @@ -263,7 +262,7 @@ do local tg = d.tg if automathrows and (roottg == "mrow" or roottg == "mtext") then -- maybe just always ! check spec first - -- or we can have chesks.* for each as we then can flatten + -- or we can have checks.* for each as we then can flatten if no_mrow[tg] then root.skip = "comment" end diff --git a/tex/context/base/mkxl/back-exp.lmt b/tex/context/base/mkxl/back-exp.lmt index 622aae435..e5e2e9dab 100644 --- a/tex/context/base/mkxl/back-exp.lmt +++ b/tex/context/base/mkxl/back-exp.lmt @@ -1880,18 +1880,25 @@ local collectresults do -- too many locals otherwise end end + local enabled = true + + updaters.register("tagging.state.disable",function() enabled = false end) + updaters.register("tagging.state.enable", function() enabled = true end) + function nodes.handlers.export(head) -- hooks into the page builder - starttiming(treehash) - if trace_export then - report_export("%w",currentdepth) - end - -- continueexport() - restart = true - collectresults(head) - if trace_export then - report_export("%w",currentdepth) + if enabled then + starttiming(treehash) + if trace_export then + report_export("%w",currentdepth) + end + -- continueexport() + restart = true + collectresults(head) + if trace_export then + report_export("%w",currentdepth) + end + stoptiming(treehash) end - stoptiming(treehash) return head end @@ -1900,13 +1907,15 @@ local collectresults do -- too many locals otherwise return p end + -- needs checking! + function builders.paragraphs.tag(head) noftextblocks = noftextblocks + 1 for n, subtype in nexthlist, head do if subtype == linelist_code then setattr(n,a_textblock,noftextblocks) - elseif subtype == glue_code or subtype == kern_code then -- no need to set fontkerns - setattr(n,a_textblock,0) + -- elseif subtype == glue_code or subtype == kern_code then -- weird, no list + -- setattr(n,a_textblock,0) end end return false diff --git a/tex/context/base/mkxl/catc-def.mkxl b/tex/context/base/mkxl/catc-def.mkxl index e24aa9cb3..1bde98774 100644 --- a/tex/context/base/mkxl/catc-def.mkxl +++ b/tex/context/base/mkxl/catc-def.mkxl @@ -281,4 +281,9 @@ \amcode \barasciicode \othercatcode \amcode \tildeasciicode \othercatcode +% \amcode "002C \activecatcode % comma +% \amcode "002E \activecatcode % period +% \amcode "003A \activecatcode % colon +% \amcode "003B \activecatcode % semicolon + \endinput diff --git a/tex/context/base/mkxl/colo-ini.mkxl b/tex/context/base/mkxl/colo-ini.mkxl index 6b9b8a5f8..807fdfad1 100644 --- a/tex/context/base/mkxl/colo-ini.mkxl +++ b/tex/context/base/mkxl/colo-ini.mkxl @@ -1300,6 +1300,9 @@ \permanent\def\colorvalue #1{\clf_formatcolor\rawcolorattribute{#1}{\colorformatseparator}} \permanent\def\grayvalue #1{\clf_formatgray \rawcolorattribute{#1}{\colorformatseparator}} +\permanent\def\colorluminance #1{\clf_formatluminance \rawcolorattribute{#1} } +\permanent\def\colorluminanceratio #1#2{\clf_formatluminanceratio\rawcolorattribute{#1} \rawcolorattribute{#2} } + \permanent\def\doifelseblack #1{\clf_doifelseblack\rawcolorattribute{#1}} \permanent\def\doifelsedrawingblack {\clf_doifelsedrawingblack} diff --git a/tex/context/base/mkxl/cont-new.mkxl b/tex/context/base/mkxl/cont-new.mkxl index 26913598c..ac65d70cc 100644 --- a/tex/context/base/mkxl/cont-new.mkxl +++ b/tex/context/base/mkxl/cont-new.mkxl @@ -13,7 +13,7 @@ % \normalend % uncomment this to get the real base runtime -\newcontextversion{2023.01.15 13:53} +\newcontextversion{2023.01.24 13:47} %D This file is loaded at runtime, thereby providing an excellent place for hacks, %D patches, extensions and new features. There can be local overloads in cont-loc diff --git a/tex/context/base/mkxl/context.mkxl b/tex/context/base/mkxl/context.mkxl index 38c897e6d..ec204055b 100644 --- a/tex/context/base/mkxl/context.mkxl +++ b/tex/context/base/mkxl/context.mkxl @@ -29,7 +29,7 @@ %D {YYYY.MM.DD HH:MM} format. \immutable\edef\contextformat {\jobname} -\immutable\edef\contextversion{2023.01.15 13:53} +\immutable\edef\contextversion{2023.01.24 13:47} %overloadmode 1 % check frozen / warning %overloadmode 2 % check frozen / error diff --git a/tex/context/base/mkxl/driv-shp.lmt b/tex/context/base/mkxl/driv-shp.lmt index 7bc2f54c5..2a2b14850 100644 --- a/tex/context/base/mkxl/driv-shp.lmt +++ b/tex/context/base/mkxl/driv-shp.lmt @@ -49,6 +49,7 @@ local getfont = nuts.getfont local getglyphdimensions = nuts.getglyphdimensions local getkerndimension = nuts.getkerndimension local getlistdimensions = nuts.getlistdimensions +local getruledimensions = nuts.getruledimensions local setdirection = nuts.setdirection local setlink = nuts.setlink @@ -85,6 +86,8 @@ local math_code = nodecodes.math local rule_code = nodecodes.rule local whatsit_code = nodecodes.whatsit +local virtualrule_code = nodes.rulecodes.virtual + local leaders_code = gluecodes.leaders local cleaders_code = gluecodes.cleaders local xleaders_code = gluecodes.xleaders @@ -1132,7 +1135,7 @@ local hlist_out, vlist_out do end end elseif id == rule_code then - local width, height, depth = getwhd(current) + local width, height, depth, virtual = getruledimensions(current) if width > 0 then if height == runningrule then height = boxheight @@ -1147,18 +1150,22 @@ local hlist_out, vlist_out do pos_h = pos_h - width xoffset = - xoffset end - if top ~= 0 then - -- height = height - top - total = total - top - end - if bottom ~= 0 then - depth = depth - bottom - total = total - bottom + if not virtual then + if top ~= 0 then + -- height = height - top + total = total - top + end + if bottom ~= 0 then + depth = depth - bottom + total = total - bottom + end end pos_v = pos_v - depth flushrule(current,pos_h + xoffset,pos_v + yoffset,pos_r,width,total,subtype) end - cur_h = cur_h + width + if not virtual then + cur_h = cur_h + width + end end elseif id == math_code then -- local kern = getkern(current) @@ -1518,7 +1525,7 @@ local hlist_out, vlist_out do elseif id == kern_code then cur_v = cur_v + getkern(current) elseif id == rule_code then - local width, height, depth = getwhd(current) + local width, height, depth, virtual = getruledimensions(current) local total = height + depth if total > 0 then if width == runningrule then @@ -1526,19 +1533,23 @@ local hlist_out, vlist_out do end if width > 0 then local xoffset, yoffset, left, right = getoffsets(current) - if left ~= 0 then - width = width - left - xoffset = left - end - if right ~= 0 then - width = width - right + if not virtual then + if left ~= 0 then + width = width - left + xoffset = left + end + if right ~= 0 then + width = width - right + end end if pos_r == righttoleft_code then xoffset = - xoffset - width end flushrule(current,pos_h + xoffset,pos_v - total - yoffset,pos_r,width,total,subtype) end - cur_v = cur_v + total + if not virtual then + cur_v = cur_v + total + end end elseif id == whatsit_code then flushwhatsit[subtype](current,pos_h,pos_v) diff --git a/tex/context/base/mkxl/file-job.lmt b/tex/context/base/mkxl/file-job.lmt index be2886fba..e117b914e 100644 --- a/tex/context/base/mkxl/file-job.lmt +++ b/tex/context/base/mkxl/file-job.lmt @@ -397,6 +397,8 @@ end local textlevel = 0 -- inaccessible for user, we need to define counter textlevel at the tex end +local c_textlevel = tex.iscount("textlevel") + local function dummyfunction() end local function startstoperror() @@ -414,7 +416,7 @@ local function starttext() context.dostarttext() end textlevel = textlevel + 1 - texsetcount("global","textlevel",textlevel) + texsetcount("global",c_textlevel,textlevel) end local function stoptext() @@ -424,7 +426,7 @@ local function stoptext() elseif textlevel > 0 then textlevel = textlevel - 1 end - texsetcount("global","textlevel",textlevel) + texsetcount("global",c_textlevel,textlevel) if textlevel <= 0 then if trace_jobfiles then report_jobfiles("stopping text") diff --git a/tex/context/base/mkxl/file-job.mklx b/tex/context/base/mkxl/file-job.mklx index 6272b551f..76b679bd6 100644 --- a/tex/context/base/mkxl/file-job.mklx +++ b/tex/context/base/mkxl/file-job.mklx @@ -18,6 +18,8 @@ %D This module delegates most of the work to \LUA\ and therefore also let it %D define the commands, which is more efficient. +\ifdefined\textlevel \else \newinteger\textlevel \fi % used at lua end + \registerctxluafile{data-hsh}{autosuffix} \registerctxluafile{file-job}{autosuffix} @@ -78,7 +80,6 @@ % document structure -\ifdefined\textlevel \else \newinteger\textlevel \fi % might go away \ifdefined\strc_pagenumbers_flush_final_page \else \let\strc_pagenumbers_flush_final_page\relax \fi % ugly \permanent\protected\def\dostarttext diff --git a/tex/context/base/mkxl/font-con.lmt b/tex/context/base/mkxl/font-con.lmt index 117e81a66..073af7d2e 100644 --- a/tex/context/base/mkxl/font-con.lmt +++ b/tex/context/base/mkxl/font-con.lmt @@ -415,6 +415,7 @@ function constructors.scale(tfmdata,specification) if extendfactor ~= 0 and extendfactor ~= 1 then hdelta = hdelta * extendfactor target.extend = extendfactor * 1000 +-- target.extend = round(target.extend) else target.extend = 1000 -- extent ? end @@ -423,6 +424,7 @@ function constructors.scale(tfmdata,specification) if squeezefactor ~= 0 and squeezefactor ~= 1 then vdelta = vdelta * squeezefactor target.squeeze = squeezefactor * 1000 +-- target.squeeze = round(target.squeeze) else target.squeeze = 1000 -- extent ? end diff --git a/tex/context/base/mkxl/font-imp-effects.lmt b/tex/context/base/mkxl/font-imp-effects.lmt index 8dce81087..f366bc89e 100644 --- a/tex/context/base/mkxl/font-imp-effects.lmt +++ b/tex/context/base/mkxl/font-imp-effects.lmt @@ -121,6 +121,28 @@ local effects = { hidden = 3, } +local rules = { + "RadicalRuleThickness", + "OverbarRuleThickness", + "FractionRuleThickness", + "UnderbarRuleThickness", +} + +-- radicals are not yet ok + +local function setmathparameters(tfmdata,characters,mathparameters,dx,dy,squeeze,multiplier) + -- hm, this was "if delta ~= 0 then" but delta was gone + if dy ~= 0 then + for i=1,#rules do + local name = rules[i] + local value = mathparameters[name] + if value then + mathparameters[name] = (squeeze or 1) * (value + dy) + end + end + end +end + local function initializeeffect(tfmdata,value) local spec if type(value) == "number" then @@ -170,7 +192,7 @@ local function initializeeffect(tfmdata,value) if squeeze then initializesqueeze(tfmdata,squeeze) end - properties.effect = { + effect = { effect = effect, width = width, factor = factor, @@ -184,28 +206,7 @@ local function initializeeffect(tfmdata,value) extend = tfmdata.parameters.extendfactor, squeeze = tfmdata.parameters.squeezefactor, } - end -end - -local rules = { - "RadicalRuleThickness", - "OverbarRuleThickness", - "FractionRuleThickness", - "UnderbarRuleThickness", -} - --- radicals are not yet ok - -local function setmathparameters(tfmdata,characters,mathparameters,dx,dy,squeeze,multiplier) - -- hm, this was "if delta ~= 0 then" but delta was gone - if dy ~= 0 then - for i=1,#rules do - local name = rules[i] - local value = mathparameters[name] - if value then - mathparameters[name] = (squeeze or 1) * (value + dy) - end - end + properties.effect = effect end end @@ -237,6 +238,21 @@ local function manipulateeffect(tfmdata) local vfactor = (1 + effect.vfactor) * vfactor parameters.hshift = hshift parameters.vshift = vshift + -- + -- For now we assume that the properties of parts wrt advance and such still + -- apply and that the extensible piece kicks in if needed. Beware of creating + -- virtual extensibles because these could get squeeze twice. + -- + -- local allparts = { } + -- for unicode, character in next, characters do + -- local parts = character.parts + -- if parts then + -- for i=1,#parts do + -- allparts[parts[i].glyph] = true + -- end + -- end + -- end + -- for unicode, character in next, characters do local oldwidth = character.width local oldheight = character.height diff --git a/tex/context/base/mkxl/font-mat.mklx b/tex/context/base/mkxl/font-mat.mklx index 33a9f3623..942c2fecd 100644 --- a/tex/context/base/mkxl/font-mat.mklx +++ b/tex/context/base/mkxl/font-mat.mklx @@ -384,10 +384,12 @@ \to \everymathematics \protected\def\font_helpers_synchronize_math_family_mr - {\c_attr_mathfamily\zerocount} + {\c_attr_mathfamily\zerocount + \font_helpers_synchronize_math_parameters_normal} \protected\def\font_helpers_synchronize_math_family_mb - {\c_attr_mathfamily\ifconditional\c_font_pseudo_bold_math_state\plussix\else\plusthree\fi} + {\c_attr_mathfamily\ifconditional\c_font_pseudo_bold_math_state\plussix\else\plusthree\fi + \font_helpers_synchronize_math_parameters_bold} \installcorenamespace{fontmathsynchronizer} \installcorenamespace{fontmathstoredstrategy} @@ -535,15 +537,21 @@ %D This is nasty, as the engine only stores the last set family parameters (per style) which %D in our case can be bold. -\def\font_helpers_synchronize_math_parameters +\def\font_helpers_synchronize_math_parameters_normal {\c_math_last_family_used\mathstylefontid\textstyle\zerocount - \textfont \zerocount\textfont \zerocount - \scriptfont \zerocount\scriptfont \zerocount - \scriptscriptfont\zerocount\scriptscriptfont\zerocount} + \textfont \c_font_fam_mr\textfont \c_font_fam_mr + \scriptfont \c_font_fam_mr\scriptfont \c_font_fam_mr + \scriptscriptfont\c_font_fam_mr\scriptscriptfont\c_font_fam_mr} + +\def\font_helpers_synchronize_math_parameters_bold + {\c_math_last_family_used\mathstylefontid\textstyle\zerocount + \textfont \c_attr_mathfamily\textfont \c_attr_mathfamily + \scriptfont \c_attr_mathfamily\scriptfont \c_attr_mathfamily + \scriptscriptfont\c_attr_mathfamily\scriptscriptfont\c_attr_mathfamily} \appendtoks \ifnum\c_math_last_family_used=\mathstylefontid\textstyle\zerocount\else - \font_helpers_synchronize_math_parameters + \font_helpers_synchronize_math_parameters_normal \fi \to\everybodyfont diff --git a/tex/context/base/mkxl/grph-rul.lmt b/tex/context/base/mkxl/grph-rul.lmt index b1de3a6a6..c33319658 100644 --- a/tex/context/base/mkxl/grph-rul.lmt +++ b/tex/context/base/mkxl/grph-rul.lmt @@ -56,7 +56,7 @@ interfaces.implement { { "radius", "dimension" }, { "corner", "string" }, } } , - actions = function(t,...) + actions = function(t) local rule = userrule(t) if t.type == "mp" then t.ma = getattribute(a_colormodel) or 1 @@ -65,22 +65,23 @@ interfaces.implement { else setattrlist(rule,true) end - context(nuts.tonode(rule)) + context(tonode(rule)) end } interfaces.implement { - name = "outlinerule", - public = true, + name = "roundedoutline", protected = true, - arguments = { { - { "width", "dimension" }, - { "height", "dimension" }, - { "depth", "dimension" }, - { "line", "dimension" }, - } } , - actions = function(t) - local rule = outlinerule(t.width,t.height,t.depth,t.line) + arguments = { "dimension", "dimension", "dimension", "dimension", "dimension", "string" }, + actions = function(w,h,d,l,r,c) + local rule = userrule { + width = w, + height = h, + depth = d, + line = l, + radius = r, + corner = c, + } setattrlist(rule,true) context(tonode(rule)) end diff --git a/tex/context/base/mkxl/grph-trf.lmt b/tex/context/base/mkxl/grph-trf.lmt index f68d6a6a8..7ca15e2a0 100644 --- a/tex/context/base/mkxl/grph-trf.lmt +++ b/tex/context/base/mkxl/grph-trf.lmt @@ -10,8 +10,19 @@ if not modules then modules = { } end modules ['grph-trf'] = { local sind, cosd, tand, abs = math.sind, math.cosd, math.tand, math.abs +local isdimen = tex.isdimen local setdimension = tex.setdimensionvalue +local d_grph_rotate_x_size = isdimen("d_grph_rotate_x_size") +local d_grph_rotate_y_size = isdimen("d_grph_rotate_y_size") +local d_grph_rotate_x_position = isdimen("d_grph_rotate_x_position") +local d_grph_rotate_y_position = isdimen("d_grph_rotate_y_position") +local d_grph_rotate_x_offset = isdimen("d_grph_rotate_x_offset") +local d_grph_rotate_y_offset = isdimen("d_grph_rotate_y_offset") +local d_grph_rotate_new_width = isdimen("d_grph_rotate_new_width") +local d_grph_rotate_new_height = isdimen("d_grph_rotate_new_height") +local d_grph_rotate_new_depth = isdimen("d_grph_rotate_new_depth") + local function analyzerotate(rotation,width,height,depth,total,notfit,obeydepth) -- -- print(rotation,width,height,depth,notfit,obeydepth) diff --git a/tex/context/base/mkxl/grph-trf.mkxl b/tex/context/base/mkxl/grph-trf.mkxl index 4cac29282..53080b6a1 100644 --- a/tex/context/base/mkxl/grph-trf.mkxl +++ b/tex/context/base/mkxl/grph-trf.mkxl @@ -26,6 +26,19 @@ \registerctxluafile{grph-trf}{autosuffix} +% See below + +\newdimension\d_grph_rotate_x_size +\newdimension\d_grph_rotate_y_size +\newdimension\d_grph_rotate_x_offset +\newdimension\d_grph_rotate_y_offset +\newdimension\d_grph_rotate_x_position +\newdimension\d_grph_rotate_y_position + +\newdimension\d_grph_rotate_new_width +\newdimension\d_grph_rotate_new_height +\newdimension\d_grph_rotate_new_depth + % local: \newdimension\d_grph_scale_x_size @@ -758,16 +771,16 @@ %D register and these are actually kind of constants not used in further %D calculations): -\mutable\dimendef\d_grph_rotate_x_size \zeropoint -\mutable\dimendef\d_grph_rotate_y_size \zeropoint -\mutable\dimendef\d_grph_rotate_x_offset \zeropoint -\mutable\dimendef\d_grph_rotate_y_offset \zeropoint -\mutable\dimendef\d_grph_rotate_x_position\zeropoint -\mutable\dimendef\d_grph_rotate_y_position\zeropoint - -\mutable\dimendef\d_grph_rotate_new_width \zeropoint -\mutable\dimendef\d_grph_rotate_new_height\zeropoint -\mutable\dimendef\d_grph_rotate_new_depth \zeropoint +% mutable\dimendef\d_grph_rotate_x_size \zeropoint +% mutable\dimendef\d_grph_rotate_y_size \zeropoint +% mutable\dimendef\d_grph_rotate_x_offset \zeropoint +% mutable\dimendef\d_grph_rotate_y_offset \zeropoint +% mutable\dimendef\d_grph_rotate_x_position\zeropoint +% mutable\dimendef\d_grph_rotate_y_position\zeropoint +% +% mutable\dimendef\d_grph_rotate_new_width \zeropoint +% mutable\dimendef\d_grph_rotate_new_height\zeropoint +% mutable\dimendef\d_grph_rotate_new_depth \zeropoint %D These aren't: diff --git a/tex/context/base/mkxl/lpdf-lmt.lmt b/tex/context/base/mkxl/lpdf-lmt.lmt index a8608cc7b..784654c06 100644 --- a/tex/context/base/mkxl/lpdf-lmt.lmt +++ b/tex/context/base/mkxl/lpdf-lmt.lmt @@ -1124,6 +1124,7 @@ local flushimage do local fractionrule_code = rulecodes.fraction local radicalrule_code = rulecodes.radical local outlinerule_code = rulecodes.outline + ----- virtualrule_code = rulecodes.virtual local processrule = nodes.rules.process diff --git a/tex/context/base/mkxl/lpdf-rul.lmt b/tex/context/base/mkxl/lpdf-rul.lmt index dfa5d1a89..391fd0ad1 100644 --- a/tex/context/base/mkxl/lpdf-rul.lmt +++ b/tex/context/base/mkxl/lpdf-rul.lmt @@ -9,7 +9,7 @@ if not modules then modules = { } end modules ['lpdf-rul'] = { -- todo: split backend and pdf local tonumber, next, type = tonumber, next, type -local concat = table.concat +local concat, setmetatableindex = table.concat, table.setmetatableindex local attributes = attributes local nodes = nodes @@ -34,11 +34,20 @@ local getrandom = utilities.randomizer.get local formatters = string.formatters local setdimen = tex.setdimen -local setcount = tex.setcount +local isdimen = tex.isdimen local setmacro = tokens.setters.macro local codeinjections = backends.registered.pdf.codeinjections +local d_rule_width = isdimen("d_rule_width") +local d_rule_height = isdimen("d_rule_height") +local d_rule_depth = isdimen("d_rule_depth") +local d_rule_h = isdimen("d_rule_h") +local d_rule_v = isdimen("d_rule_v") +local d_rule_line = isdimen("d_rule_line") +local d_rule_offset = isdimen("d_rule_offset") +local d_rule_factor = isdimen("d_rule_factor") + -- This is very pdf specific. Maybe move some to lpdf-rul.lua some day. local pdfprint ; pdfprint = function(...) pdfprint = lpdf.print return pdfprint(...) end @@ -54,7 +63,7 @@ do -- local maxcachesize = 8*1024 -- local cachethreshold = 1024/2 - local cache = table.setmetatableindex(function(t,k) + local cache = setmetatableindex(function(t,k) local v = simplemetapost("rulefun",k) -- w, h, d cachesize = cachesize + #v if cachesize > maxcachesize then @@ -178,178 +187,212 @@ do -- course one can use mp instead. It could be improved but at the cost of more -- code than I'm willing to add for something hardly used. - local function round(p,kind) - local method = tonumber(p.corner) or 0 - if method < 0 or method > 27 then - method = 0 - end + local linemapping = { + [interfaces.variables.round] = "ltrb", + ["0"] = "ltrb", ["trbl"] = "ltrb", ["rblt"] = "ltrb", ["bltr"] = "ltrb", + -- + ["1"] = "ltrb", ["2"] = "ltrb", ["3"] = "ltrb", ["4"] = "ltrb", + ["5"] = "ltrb", ["6"] = "ltrb", ["7"] = "ltrb", ["8"] = "ltrb", + -- + [ "9"] = "lbr", ["rbl"] = "lbr", + ["10"] = "tlb", ["blt"] = "tlb", + ["11"] = "ltr", ["rtl"] = "lrt", + ["12"] = "lbr", ["rbl"] = "lbr", + -- + ["13"] = "rt", ["tr"] = "rt", + ["14"] = "rb", ["br"] = "rb", + ["15"] = "bl", ["lb"] = "bl", + ["16"] = "tl", ["lt"] = "tl", + -- + ["32"] = "lr", ["rl"] = "lr", + ["33"] = "tb", ["bt"] = "tb", + -- + ["28"] = "l", + ["29"] = "r", + ["30"] = "b", + ["31"] = "t", + } + + local roundmapping = { + [interfaces.variables.round] = "ltrb", + [ "0"] = "ltrb", ["trbl"] = "ltrb", ["rblt"] = "ltrb", ["bltr"] = "ltrb", + -- + [ "9"] = "lbr", ["rbl"] = "lbr", + ["10"] = "tlb", ["blt"] = "tlb", + ["11"] = "ltr", ["rtl"] = "lrt", + ["12"] = "lbr", ["rbl"] = "lbr", + -- + ["13"] = "rt", ["tr"] = "rt", + ["14"] = "rb", ["br"] = "rb", + ["15"] = "bl", ["lb"] = "bl", + ["16"] = "tl", ["lt"] = "tl", + -- + ["32"] = "lr", ["rl"] = "lr", + ["33"] = "tb", ["bt"] = "tb", + -- + ["28"] = "l", + ["29"] = "r", + ["30"] = "b", + ["31"] = "t", + } + + setmetatableindex(linemapping,function(t,k) + local v = tonumber(k) and k or "ltrb" + t[k] = v + return v + end) + + setmetatableindex(roundmapping,function(t,k) + local v = tonumber(k) and k or "ltrb" + t[k] = v + return v + end) + + local function round(p,kind,corner) local width = p.width or 0 local height = p.height or 0 local depth = p.depth or 0 - local total = height + depth local radius = p.radius or 655360 - local line = p.line or 65536 - local how = (method > 8 or kind ~= "fill") and "S" or "f" + local line = (p.line or 65536) * bpfactor local half = line / 2 - local xmin = half * bpfactor - local xmax = ( width - half) * bpfactor - local ymax = ( height - half) * bpfactor - local ymin = (-depth + half) * bpfactor - local full = ( radius + half) - local xxmin = full * bpfactor - local xxmax = ( width - full) * bpfactor - local yymax = ( height - full) * bpfactor - local yymin = (-depth + full) * bpfactor - line = line * bpfactor - if xxmin <= xxmax and yymin <= yymax then - local list = nil - if method == 0 then - list = { - "q", line, "w", xxmin, ymin, "m", xxmax, ymin, "l", xmax, ymin, xmax, yymin, "y", - xmax, yymax, "l", xmax, ymax, xxmax, ymax, "y", xxmin, ymax, "l", xmin, ymax, - xmin, yymax, "y", xmin, yymin, "l", xmin, ymin, xxmin, ymin, "y", "h", how, "Q", - } - elseif method == 1 then - list = { - "q", line, "w", xxmin, ymin, "m", xxmax, ymin, "l", xmax, ymin, xmax, yymin, "y", - xmax, ymax, "l", xmin, ymax, "l", xmin, yymin, "l", xmin, ymin, xxmin, ymin, "y", - "h", how, "Q", - } - elseif method == 2 then - list = { - "q", line, "w", xxmin, ymin, "m", xmax, ymin, "l", xmax, ymax, "l", xxmin, ymax, - "l", xmin, ymax, xmin, yymax, "y", xmin, yymin, "l", xmin, ymin, xxmin, ymin, - "y", "h", how, "Q", - } - elseif method == 3 then - list = { - "q", line, "w", xmin, ymin, "m", xmax, ymin, "l", xmax, yymax, "l", xmax, ymax, - xxmax, ymax, "y", xxmin, ymax, "l", xmin, ymax, xmin, yymax, "y", xmin, ymin, - "l", "h", how, "Q", - } - - elseif method == 4 then - list = { - "q", line, "w", xmin, ymin, "m", xxmax, ymin, "l", xmax, ymin, xmax, yymin, "y", - xmax, yymax, "l", xmax, ymax, xxmax, ymax, "y", xmin, ymax, "l", xmin, ymin, "l", - "h", how, "Q", - } - elseif method == 5 then - list = { - "q", line, "w", xmin, ymin, "m", xmax, ymin, "l", xmax, yymax, "l", xmax, ymax, - xxmax, ymax, "y", xmin, ymax, "l", xmin, ymin, "l", "h", how, "Q", - } - elseif method == 6 then - list = { - "q", line, "w", xmin, ymin, "m", xxmax, ymin, "l", xmax, ymin, xmax, yymin, "y", - xmax, ymax, "l", xmin, ymax, "l", xmin, ymin, "l", "h", how, "Q", - } - elseif method == 7 then - list = { - "q", line, "w", xxmin, ymin, "m", xmax, ymin, "l", xmax, ymax, "l", xmin, ymax, - "l", xmin, yymin, "l", xmin, ymin, xxmin, ymin, "y", "h", how, "Q", - } - elseif method == 8 then + local xxmin = 0 + local xxmax = width * bpfactor + local yymax = height * bpfactor + local yymin = -depth * bpfactor + local xmin = xxmin + half + local xmax = xxmax - half + local ymax = yymax - half + local ymin = yymin + half + local list = nil + if radius == 0 then + local method = linemapping[corner] + if method == "ltrb" then list = { - "q", line, "w", xmin, ymin, "m", xmax, ymin, "l", xmax, ymax, "l", xxmin, ymax, - "l", xmin, ymax, xmin, yymax, "y", xmin, ymin, "l", "h", how, "Q", + "q", line, "w", xmin, ymin, "m", xmax, ymin, "l", xmax, ymax, "l", xmin, ymax, + kind == "fill" and "l h f Q" or "l h S Q" } - elseif method == 9 then - list = { - "q", line, "w", xmin, ymax, "m", xmin, yymin, "l", xmin, ymin, xxmin, ymin, "y", - xxmax, ymin, "l", xmax, ymin, xmax, yymin, "y", xmax, ymax, "l", how, "Q", - } - elseif method == 10 then - list = { - "q", line, "w", xmax, ymax, "m", xxmin, ymax, "l", xmin, ymax, xmin, yymax, "y", - xmin, yymin, "l", xmin, ymin, xxmin, ymin, "y", xmax, ymin, "l", how, "Q", - } - elseif method == 11 then - list = { - "q", line, "w", xmax, ymin, "m", xmax, yymax, "l", xmax, ymax, xxmax, ymax, "y", - xxmin, ymax, "l", xmin, ymax, xmin, yymax, "y", xmin, ymin, "l", how, "Q", - } - elseif method == 12 then - list = { - "q", line, "w", xmin, ymax, "m", xxmax, ymax, "l", xmax, ymax, xmax, yymax, "y", - xmax, yymin, "l", xmax, ymin, xxmax, ymin, "y", xmin, ymin, "l", how, "Q", - } - elseif method == 13 then - list = { - "q", line, "w", xmin, ymax, "m", xxmax, ymax, "l", xmax, ymax, xmax, yymax, "y", - xmax, ymin, "l", how, "Q", - } - elseif method == 14 then - list = { - "q", line, "w", xmax, ymax, "m", xmax, yymin, "l", xmax, ymin, xxmax, ymin, "y", - xmin, ymin, "l", how, "Q", - } - elseif method == 15 then - list = { - "q", line, "w", xmax, ymin, "m", xxmin, ymin, "l", xmin, ymin, xmin, yymin, "y", - xmin, ymax, "l", how, "Q", - } - elseif method == 16 then - list = { - "q", line, "w", xmin, ymin, "m", xmin, yymax, "l", xmin, ymax, xxmin, ymax, "y", - xmax, ymax, "l", how, "Q", - } - elseif method == 17 then - list = { - "q", line, "w", xxmax, ymax, "m", xmax, ymax, xmax, yymax, "y", how, "Q", - } - elseif method == 18 then - list = { - "q", line, "w", xmax, yymin, "m", xmax, ymin, xxmax, ymin, "y", how, "Q", - } - elseif method == 19 then - list = { - "q", line, "w", xxmin, ymin, "m", xmin, ymin, xmin, yymin, "y", how, "Q", - } - elseif method == 20 then - list = { - "q", line, "w", xmin, yymax, "m", xmin, ymax, xxmin, ymax, "y", how, "Q", - } - elseif method == 21 then - list = { - "q", line, "w", xxmax, ymax, "m", xmax, ymax, xmax, yymax, "y", xmin, yymax, "m", - xmin, ymax, xxmin, ymax, "y", how, "Q", - } - elseif method == 22 then - list = { - "q", line, "w", xxmax, ymax, "m", xmax, ymax, xmax, yymax, "y", xmax, yymin, "m", - xmax, ymin, xxmax, ymin, "y", how, "Q", - } - elseif method == 23 then - list = { - "q", line, "w", xmax, yymin, "m", xmax, ymin, xxmax, ymin, "y", xxmin, ymin, "m", - xmin, ymin, xmin, yymin, "y", how, "Q", - } - elseif method == 24 then - list = { - "q", line, "w", xxmin, ymin, "m", xmin, ymin, xmin, yymin, "y", xmin, yymax, "m", - xmin, ymax, xxmin, ymax, "y", how, "Q", - } - elseif method == 25 then - list = { - "q", line, "w", xxmax, ymax, "m", xmax, ymax, xmax, yymax, "y", xmax, yymin, "m", - xmax, ymin, xxmax, ymin, "y", xxmin, ymin, "m", xmin, ymin, xmin, yymin, "y", - xmin, yymax, "m", xmin, ymax, xxmin, ymax, "y", how, "Q", - } - elseif method == 26 then + elseif method == "l" then + list = { "q", line, "w", xmin, yymin, "m", xmin, yymax, "l S Q" } + elseif method == "r" then + list = { "q", line, "w", xmax, yymin, "m", xmax, yymax, "l S Q" } + elseif method == "b" then + list = { "q", line, "w", xxmin, ymin, "m", xxmax, ymin, "l S Q" } + elseif method == "t" then + list = { "q", line, "w", xxmin, ymax, "m", xxmax, ymax, "l S Q" } + elseif method == "lr" then + list = { "q", line, "w", xmin, yymin, "m", xmin, yymax, "l", xmax, yymin, "m", xmax, yymax, "l S Q" } + elseif method == "tb" then + list = { "q", line, "w", xxmin, ymin, "m", xxmax, ymin, "l", xxmin, ymax, "m", xxmax, ymax, "l S Q" } + elseif method == "lbr" then + list = { "q", line, "w", xmin, yymax, "m", xmin, ymin, "l", xmax, ymin, "l", xmax, yymax, "l S Q" } + elseif method == "tlb" then + list = { "q", line, "w", xxmax, ymax, "m", xmin, ymax, "l", xmin, ymin, "l", xxmax, ymin, "l S Q" } + elseif method == "ltr" then + list = { "q", line, "w", xmin, yymin, "m", xmin, ymax, "l", xmax, ymax, "l", xmax, yymin, "l S Q" } + elseif method == "lbr" then + list = { "q", line, "w", xxmin, ymax, "m", xmax, ymax, "l", xmax, ymin, "l", xxmin, ymin, "l S Q" } + elseif method == "rt" then + list = { "q", line, "w", xxmin, ymax, "m", xmax, ymax, "l", xmax, yymin, "l S Q" } + elseif method == "rb" then + list = { "q", line, "w", xmax, yymax, "m", xmax, ymin, "l", xxmin, ymin, "l S Q" } + elseif method == "bl" then + list = { "q", line, "w", xxmax, ymin, "m", xmin, ymin, "l", xmin, yymax, "l S Q" } + elseif method == "tl" then + list = { "q", line, "w", xmin, yymin, "m", xmin, ymax, "l", xxmax, ymax, "l S Q" } + else + return + end + else + local method = roundmapping[corner] + local done = kind ~= "fill" and "h S Q" or "h f Q" -- todo + local full = ( radius + half) + local xxxmin = full * bpfactor + local xxxmax = ( width - full) * bpfactor + local yyymax = ( height - full) * bpfactor + local yyymin = (-depth + full) * bpfactor + if xxxmin > xxxmax or yyymin > yyymax then + return + elseif method == "ltrb" then list = { - "q", line, "w", xmax, yymin, "m", xmax, ymin, xxmax, ymin, "y", xmin, yymax, "m", - xmin, ymax, xxmin, ymax, "y", how, "Q", + "q", line, "w", xxxmin, ymin, "m", xxxmax, ymin, "l", xmax, ymin, xmax, yyymin, "y", xmax, yyymax, "l", xmax, ymax, xxxmax, ymax, "y", + xxxmin, ymax, "l", xmin, ymax, xmin, yyymax, "y", xmin, yyymin, "l", xmin, ymin, xxxmin, ymin, "y", done, } - - elseif method == 27 then + elseif method == "1" then -- ll lr + list = { "q", line, "w", xxxmin, ymin, "m", xxxmax, ymin, "l", xmax, ymin, xmax, yyymin, "y", xmax, ymax, "l", xmin, ymax, "l", xmin, yyymin, "l", xmin, ymin, xxxmin, ymin, "y", done } + elseif method == "2" then -- ll ul + list = { "q", line, "w", xxxmin, ymin, "m", xmax, ymin, "l", xmax, ymax, "l", xxxmin, ymax, "l", xmin, ymax, xmin, yyymax, "y", xmin, yyymin, "l", xmin, ymin, xxxmin, ymin, "y", done } + elseif method == "3" then -- ul ur + list = { "q", line, "w", xmin, ymin, "m", xmax, ymin, "l", xmax, yyymax, "l", xmax, ymax, xxxmax, ymax, "y", xxxmin, ymax, "l", xmin, ymax, xmin, yyymax, "y", xmin, ymin, "l", done } + elseif method == "4" then -- ur lr + list = { "q", line, "w", xmin, ymin, "m", xxxmax, ymin, "l", xmax, ymin, xmax, yyymin, "y", xmax, yyymax, "l", xmax, ymax, xxxmax, ymax, "y", xmin, ymax, "l", xmin, ymin, "l", done } + elseif method == "5" then -- ur + list = { "q", line, "w", xmin, ymin, "m", xmax, ymin, "l", xmax, yyymax, "l", xmax, ymax, xxxmax, ymax, "y", xmin, ymax, "l", xmin, ymin, "l", done } + elseif method == "6" then -- lr + list = { "q", line, "w", xmin, ymin, "m", xxxmax, ymin, "l", xmax, ymin, xmax, yyymin, "y", xmax, ymax, "l", xmin, ymax, "l", xmin, ymin, "l", done } + elseif method == "7" then -- + list = { "q", line, "w", xxxmin, ymin, "m", xmax, ymin, "l", xmax, ymax, "l", xmin, ymax, "l", xmin, yyymin, "l", xmin, ymin, xxxmin, ymin, "y", done } -- outlier + elseif method == "8" then -- ul + list = { "q", line, "w", xmin, ymin, "m", xmax, ymin, "l", xmax, ymax, "l", xxxmin, ymax, "l", xmin, ymax, xmin, yyymax, "y", xmin, ymin, "l", done } + elseif method == "lbr" then + list = { "q", line, "w", xmin, yymax, "m", xmin, yyymin, "l", xmin, ymin, xxxmin, ymin, "y", xxxmax, ymin, "l", xmax, ymin, xmax, yyymin, "y", xmax, yymax, "l S Q" } + elseif method == "tlb" then + list = { "q", line, "w", xxmax, ymax, "m", xxxmin, ymax, "l", xmin, ymax, xmin, yyymax, "y", xmin, yyymin, "l", xmin, ymin, xxxmin, ymin, "y", xxmax, ymin, "l S Q" } + elseif method == "ltr" then + list = { "q", line, "w", xmax, yymin, "m", xmax, yyymax, "l", xmax, ymax, xxxmax, ymax, "y", xxxmin, ymax, "l", xmin, ymax, xmin, yyymax, "y", xmin, yymin, "l S Q" } + elseif method == "lbr" then + list = { "q", line, "w", xxmin, ymax, "m", xxxmax, ymax, "l", xmax, ymax, xmax, yyymax, "y", xmax, yyymin, "l", xmax, ymin, xxxmax, ymin, "y", xxmin, ymin, "l S Q" } + elseif method == "lr" then + list = { "q", line, "w", xxxmin, ymin, "m", xmin, ymin, xmin, yyymin, "y", xmin, yyymax, "l", xmin, ymax, xxxmin, ymax, "y", + xxxmax, ymax, "m", xmax, ymax, xmax, yyymax, "y", xmax, yyymin, "l", xmax, ymin, xxxmax, ymin, "y S Q" } + elseif method == "tb" then + list = { "q", line, "w", xmax, yyymin, "m", xmax, ymin, xxxmax, ymin, "y", xxxmin, ymin, "l", xmin, ymin, xmin, yyymin, "y", + xmax, yyymax, "m", xmax, ymax, xxxmax, ymax, "y", xxxmin, ymax, "l", xmin, ymax, xmin, yyymax, "y S Q" } + elseif method == "rt" then + list = { "q", line, "w", xxmin, ymax, "m", xxxmax, ymax, "l", xmax, ymax, xmax, yyymax, "y", xmax, yymin, "l S Q" } + elseif method == "rb" then + list = { "q", line, "w", xmax, yymax, "m", xmax, yyymin, "l", xmax, ymin, xxxmax, ymin, "y", xxmin, ymin, "l S Q" } + elseif method == "bl" then + list = { "q", line, "w", xxmax, ymin, "m", xxxmin, ymin, "l", xmin, ymin, xmin, yyymin, "y", xmin, yymax, "l S Q" } + elseif method == "tl" then + list = { "q", line, "w", xmin, yymin, "m", xmin, yyymax, "l", xmin, ymax, xxxmin, ymax, "y", xxmax, ymax, "l S Q" } + elseif method == "17" then -- urx + list = { "q", line, "w", xxxmax, ymax, "m", xmax, ymax, xmax, yyymax, "y S Q" } + elseif method == "18" then -- lrt + list = { "q", line, "w", xmax, yyymin, "m", xmax, ymin, xxxmax, ymin, "y S Q" } + elseif method == "19" then -- llx + list = { "q", line, "w", xxxmin, ymin, "m", xmin, ymin, xmin, yyymin, "y S Q" } + elseif method == "20" then -- urx + list = { "q", line, "w", xmin, yyymax, "m", xmin, ymax, xxxmin, ymax, "y S Q" } + elseif method == "21" then -- ulx urx + list = { "q", line, "w", xmax, yyymax, "m", xmax, ymax, xxxmax, ymax, "y", xxxmin, ymax, "m", xmin, ymax, xmin, yyymax, "y S Q" } + elseif method == "22" then -- urt lrt + list = { "q", line, "w", xxxmax, ymax, "m", xmax, ymax, xmax, yyymax, "y", xmax, yyymin, "m", xmax, ymin, xxxmax, ymin, "y S Q" } + elseif method == "23" then -- llx lrx + list = { "q", line, "w", xmax, yyymin, "m", xmax, ymin, xxxmax, ymin, "y", xxxmin, ymin, "m", xmin, ymin, xmin, yyymin, "y S Q" } + elseif method == "24" then -- ulx llx + list = { "q", line, "w", xxxmin, ymin, "m", xmin, ymin, xmin, yyymin, "y", xmin, yyymax, "m", xmin, ymax, xxxmin, ymax, "y S Q" } + elseif method == "25" then -- llx lrx urx ulx list = { - "q", line, "w", xxmax, ymax, "m", xmax, ymax, xmax, yymax, "y", xxmin, ymin, "m", - xmin, ymin, xmin, yymin, "y", how, "Q", + "q", line, "w", xxxmax, ymax, "m", xmax, ymax, xmax, yyymax, "y", xmax, yyymin, "m", xmax, ymin, xxxmax, ymin, "y", xxxmin, ymin, "m", + xmin, ymin, xmin, yyymin, "y", xmin, yyymax, "m", xmin, ymax, xxxmin, ymax, "y S Q", } + elseif method == "26" then + list = { "q", line, "w", xmax, yyymin, "m", xmax, ymin, xxxmax, ymin, "y", xmin, yyymax, "m", xmin, ymax, xxxmin, ymax, "y S Q" } + elseif method == "27" then + list = { "q", line, "w", xxxmax, ymax, "m", xmax, ymax, xmax, yyymax, "y", xxxmin, ymin, "m", xmin, ymin, xmin, yyymin, "y S Q" } + elseif method == "l" then + list = { "q", line, "w", xxxmin, ymin, "m", xmin, ymin, xmin, yyymin, "y", xmin, yyymax, "l", xmin, ymax, xxxmin, ymax, "y S Q" } + elseif method == "r" then + list = { "q", line, "w", xxxmax, ymax, "m", xmax, ymax, xmax, yyymax, "y", xmax, yyymin, "l", xmax, ymin, xxxmax, ymin, "y S Q" } + elseif method == "b" then + list = { "q", line, "w", xmax, yyymin, "m", xmax, ymin, xxxmax, ymin, "y", xxxmin, ymin, "l", xmin, ymin, xmin, yyymin, "y S Q" } + elseif method == "t" then + list = { "q", line, "w", xmax, yyymax, "m", xmax, ymax, xxxmax, ymax, "y", xxxmin, ymax, "l", xmin, ymax, xmin, yyymax, "y S Q" } + else + return end - pdfprint("direct",concat(list," ")) end + pdfprint("direct",concat(list," ")) end local f_rectangle = formatters["q %.6N w %.6N %.6N %.6N %.6N re %s Q"] @@ -366,8 +409,9 @@ h %s Q]] ] local rule_any = function(p,h,v,i,n) - if p.corner then - return round(p,i) + local corner = p.corner + if corner then + return round(p,i,corner) else local l = (p.line or 65536)*bpfactor local r = p and (p.radius or 0)*bpfactor or 0 diff --git a/tex/context/base/mkxl/lpdf-tag.lmt b/tex/context/base/mkxl/lpdf-tag.lmt index 7aa9edb9b..f6a881208 100644 --- a/tex/context/base/mkxl/lpdf-tag.lmt +++ b/tex/context/base/mkxl/lpdf-tag.lmt @@ -134,6 +134,12 @@ end -- mostly the same as the annotations tree +local usenamespace = false experiments.register("structures.tags.namespaces", function(v) usenamespace = v end) + +local namespaceurls = { + mathml = "http://www.w3.org/1998/Math/MathML", +} + local function finishstructure() if root and #structure_kids > 0 then local nums = pdfarray() @@ -152,11 +158,35 @@ local function finishstructure() } local idtree = pdfmakenametree(names) -- - local rolemap = pdfdictionary() + local rolemaps = usenamespace and { } + local rolemap = pdfdictionary() -- main one for k, v in next, usedmapping do k = usedlabels[k] or k local p = properties[k] - rolemap[k] = pdfconstant(p and p.pdf or "Span") -- or "Div" + if not p then + print("UNDEFINED", k) + end + local n = p and p.namespace + if rolemaps and n then + local r = rolemaps[n] + if not r then + r = pdfdictionary() + rolemaps[n] = r + end + r[k] = pdfconstant(k) -- maybe other tag + else + rolemap[k] = pdfconstant(p and p.pdf or "Span") -- or "Div" + end + end + local namespaces = rolemaps and next(rolemaps) and pdfarray { } or nil + if namespaces then + for k, v in table.sortedhash(rolemaps) do + namespaces[#namespaces+1] = pdfdictionary { + Type = pdfconstant("Namespace"), + NS = pdfunicode(namespaceurls[k] or k), + RoleMapNS = v, + } + end end local structuretree = pdfdictionary { Type = pdfconstant("StructTreeRoot"), @@ -164,6 +194,7 @@ local function finishstructure() ParentTree = pdfreference(pdfflushobject(parent_ref,parenttree)), IDTree = idtree, RoleMap = rolemap, -- sorted ? + Namespaces = namespaces, } pdfflushobject(structure_ref,structuretree) addtocatalog("StructTreeRoot",pdfreference(structure_ref)) @@ -406,15 +437,25 @@ end local EMCliteral = nil local visualize = nil +local enabled = true + +updaters.register("tagging.state.disable",function() enabled = false end) +updaters.register("tagging.state.enable", function() enabled = true end) + function nodeinjections.addtags(head) + if not enabled then + return + end + if not EMCliteral then EMCliteral = register(setstate("EMC")) end - local last = nil - local ranges = { } - local range = nil + local last = nil + local ranges = { } + local range = nil + local nofranges = 0 if not root then structure_kids = pdfarray() @@ -430,12 +471,10 @@ function nodeinjections.addtags(head) -- maybe also disc if getchar(n) ~= 0 then local at = getattr(n,a_tagged) or false -- false: pagebody or so, so artifact - -- if not at then - -- range = nil - -- elseif ... if last ~= at then range = { at, "glyph", n, n, list } -- attr id start stop list - ranges[#ranges+1] = range + nofranges = nofranges + 1 + ranges[nofranges] = range last = at elseif range then range[4] = n -- stop @@ -445,11 +484,8 @@ function nodeinjections.addtags(head) local at = getattr(n,a_image) if at then local at = getattr(n,a_tagged) or false -- false: pagebody or so, so artifact - -- if not at then - -- range = nil - -- else - ranges[#ranges+1] = { at, "image", n, n, list } -- attr id start stop list - -- end + nofranges = nofranges + 1 + ranges[nofranges] = { at, "image", n, n, list } -- attr id start stop list last = nil else local list = getlist(n) @@ -469,7 +505,7 @@ function nodeinjections.addtags(head) -- inspect(ranges) if trace_tags then - for i=1,#ranges do + for i=1,nofranges do local range = ranges[i] local attr = range[1] local id = range[2] @@ -511,7 +547,12 @@ function nodeinjections.addtags(head) end end - for i=1,#ranges do +-- local function inject(start,stop,list,literal,left,right) +-- setlink(getprev(start) or list or true,literal,left or true,start) +-- setlink(stop,right or true,copy_node(EMCliteral),getnext(stop)) +-- end + + for i=1,nofranges do local range = ranges[i] local attr = range[1] diff --git a/tex/context/base/mkxl/math-acc.mklx b/tex/context/base/mkxl/math-acc.mklx index 9d51ba697..6e25c413f 100644 --- a/tex/context/base/mkxl/math-acc.mklx +++ b/tex/context/base/mkxl/math-acc.mklx @@ -157,6 +157,8 @@ \definemathtopaccent[\v!top:\v!stretch][widetilde]["0303] \definemathtopaccent[\v!top:\v!stretch][widedddot]["20DB] +\definemathtopaccent[\v!top:\v!stretch][vec] ["20D7] % clumsy notation for vectors + \aliased\let\mathring\ring % for a while \popoverloadmode diff --git a/tex/context/base/mkxl/math-act.lmt b/tex/context/base/mkxl/math-act.lmt index adfb5712c..a55331c46 100644 --- a/tex/context/base/mkxl/math-act.lmt +++ b/tex/context/base/mkxl/math-act.lmt @@ -33,6 +33,7 @@ local context = context local commands = commands local mathematics = mathematics local texsetdimen = tex.setdimen +local texisdimen = tex.isdimen local abs = math.abs local blocks = characters.blocks @@ -55,6 +56,9 @@ local fontproperties = fonts.hashes.properties local mathgaps = mathematics.gaps +local d_scratchleftoffset = texisdimen("scratchleftoffset") +local d_scratchrightoffset = texisdimen("scratchrightoffset") + local use_math_goodies = true directives.register("math.nogoodies", function(v) use_math_goodies = not v end) local checkitalics = false trackers .register("math.checkitalics", function(v) checkitalics = v end) @@ -136,6 +140,11 @@ local how = { AccentBottomOvershoot = "unscaled", AccentSuperscriptPercent = "unscaled", DelimiterPercent = "unscaled", + -- + RadicalRuleThickness = "vertical", + OverbarRuleThickness = "vertical", + FractionRuleThickness = "vertical", + UnderbarRuleThickness = "vertical", } local function scaleparameters(mathparameters,parameters) @@ -149,7 +158,7 @@ local function scaleparameters(mathparameters,parameters) -- kept elseif h == "horizontal" then value = value * hfactor - elseif h == "vertical"then + elseif h == "vertical" then value = value * vfactor else value = value * factor @@ -3744,8 +3753,8 @@ interfaces.implement { -- can be public with two times "integerargument" arguments = { "integer", "integer" }, actions = function(family,unicode) local kind, loffset, roffset = horizontalcode(family,unicode) - texsetdimen("scratchleftoffset", loffset) - texsetdimen("scratchrightoffset",roffset) + texsetdimen(d_scratchleftoffset, loffset) + texsetdimen(d_scratchrightoffset,roffset) context(kind) end } diff --git a/tex/context/base/mkxl/math-ali.mkxl b/tex/context/base/mkxl/math-ali.mkxl index 7789dcb60..20ea1d279 100644 --- a/tex/context/base/mkxl/math-ali.mkxl +++ b/tex/context/base/mkxl/math-ali.mkxl @@ -2112,8 +2112,8 @@ %D $<\limits^a$ %D \stoptyping -\permanent\protected\def\overset #1#2{#2\limits\normalsuperscript{#1}} -\permanent\protected\def\underset#1#2{#2\limits\normalsubscript {#1}} +\permanent\protected\def\overset #1#2{\mathrel{#2}\limits\normalsuperscript{#1}} +\permanent\protected\def\underset#1#2{\mathrel{#2}\limits\normalsubscript {#1}} %D The following code comes from \type {math-str.mkiv}. %D @@ -2133,13 +2133,14 @@ \def\strc_math_flush_number_box{\box\b_strc_formulas_number} +% \newdimension \d_strc_math_display_width +% \newdimension \d_strc_math_indent +% \newconditional\c_strc_math_indent + \newconditional\c_strc_math_display_overflow \newconstant \c_strc_math_number_location \newconstant \c_strc_math_number_variant -\newdimension \d_strc_math_display_width \newconstant \c_strc_formulas_frame_mode -\newdimension \d_strc_math_indent -\newconditional\c_strc_math_indent \newdimension \d_strc_math_framed_width \defcsname\??formulaoption\v!frame\endcsname diff --git a/tex/context/base/mkxl/math-fnt.lmt b/tex/context/base/mkxl/math-fnt.lmt index cd4976900..af180b6e4 100644 --- a/tex/context/base/mkxl/math-fnt.lmt +++ b/tex/context/base/mkxl/math-fnt.lmt @@ -6,6 +6,8 @@ if not modules then modules = { } end modules ['math-fnt'] = { license = "see context related readme files" } +local round = math.round + local nuts = nodes.nuts local tonut = nodes.tonut local tonode = nodes.tonode @@ -33,7 +35,9 @@ local addcharacters = font.addcharacters local function register_extensible(font,char,style,box) -- We don't share (yet)! local bx = tonut(box) + updaters.apply("tagging.state.disable") -- fast enough nodes.handlers.finalizelist(bx) + updaters.apply("tagging.state.enable") local id = getid(bx) local al = getattrlst(bx) local wd, ht, dp = getwhd(bx) @@ -49,10 +53,24 @@ local function register_extensible(font,char,style,box) -- local private = fonts.helpers.setboxdirectly(font,unicode,box) -- we saved a scaled glyph stream so we now use an unscaled one ... - local g = new_glyph(font,private,al) - if fonts.hashes.properties[font].compactmath then - nuts.setscales(g,1000,1000,1000) - end + local p = fonts.hashes.parameters[font] + local g = new_glyph(font,private,al) +-- if fonts.hashes.properties[font].compactmath then +-- nuts.setscales(g,1000,1000,1000) +-- end + -- nasty, testcase: bold math sqrt extensible + local sx = round(1000/p.extendfactor) + local sy = round(1000/p.squeezefactor) + nuts.setscales(g,1000,sx,sy) + -- horrible +if sx ~= 1000 then + wd = wd * 7200/7227 +end +if sy ~= 1000 then + ht = ht * 7200/7227 + dp = dp * 7200/7227 +end + -- local n = new_hlist(g) -- if newcommands then diff --git a/tex/context/base/mkxl/math-ini.lmt b/tex/context/base/mkxl/math-ini.lmt index fb98ce35b..f26f24c93 100644 --- a/tex/context/base/mkxl/math-ini.lmt +++ b/tex/context/base/mkxl/math-ini.lmt @@ -30,7 +30,6 @@ local context = context local commands = commands local implement = interfaces.implement -local ctx_sprint = context.sprint local ctx_doifelsesomething = commands.doifelsesomething local trace_defining = false trackers.register("math.defining", function(v) trace_defining = v end) @@ -287,12 +286,12 @@ local lastengineclass = 0 local lastprivateclass = maxengineclass for k, v in next, nodes.noadcodes do - if type(k) == "string"then + if type(k) == "string" then classes[k] = v - local n = classnames[v] - if not n or #k < #n then - classnames[v] = k - end +-- local n = classnames[v] +-- if not n or #k < #n then +-- classnames[v] = k +-- end elseif k > lastengineclass then lastengineclass = k end @@ -314,6 +313,8 @@ local over_class = classes.over local fenced_class = classes.fenced local ghost_class = classes.ghost +-- these will go + classes.ord = ordinary_class classes.op = operator_class classes.bin = binary_class @@ -326,6 +327,8 @@ classes.rad = radical_class classes.fen = fenced_class classes.gst = ghost_class +-- these will go too + classes.limop = operator_class classes.limoperator = operator_class classes.nolop = operator_class @@ -333,7 +336,7 @@ classes.nolimoperator = operator_class classes.large = operator_class classes.largeoperator = operator_class --- special in the engine : variable active inner vcenter +-- special in the engine : variable active inner vcenter local function registerengineclass(name,short) local class = classes[name] @@ -345,11 +348,38 @@ local function registerengineclass(name,short) else class = ordinary_class end - classes[name] = class + else + classnames[class] = short or name end + classes[class] = name + classes[name] = class return class end +-- predefined classes + +registerengineclass("ordinary", "ord") +registerengineclass("operator", "ope") +registerengineclass("binary", "bin") +registerengineclass("relation", "rel") +registerengineclass("open", "ope") +registerengineclass("close", "clo") +registerengineclass("punctuation", "pun") +registerengineclass("variable", "var") -- not used +registerengineclass("active", "act") -- not used +registerengineclass("inner", "inn") -- not used +registerengineclass("middle", "mid") +registerengineclass("accent", "acc") +registerengineclass("radical", "rad") +registerengineclass("fraction", "fra") +registerengineclass("under", "und") +registerengineclass("over", "ove") +registerengineclass("fenced", "fen") +registerengineclass("ghost", "gho") +registerengineclass("vcenter", "vce") -- not used + +-- additional classes + registerengineclass("explicit", "xpl") registerengineclass("imaginary", "img") registerengineclass("differential", "dif") @@ -365,19 +395,19 @@ registerengineclass("construct", "con") registerengineclass("dimension", "dim") registerengineclass("unary", "una") registerengineclass("textpunctuation", "tpu") -registerengineclass("unspaced") -registerengineclass("experimental") -registerengineclass("fake") +registerengineclass("unspaced", "uns") +registerengineclass("experimental", "exp") +registerengineclass("fake", "fak") registerengineclass("numbergroup", "ngr") -registerengineclass("maybeordinary") -registerengineclass("mayberelation") -registerengineclass("maybebinary") +registerengineclass("maybeordinary", "mor") +registerengineclass("mayberelation", "mre") +registerengineclass("maybebinary", "mbi") local specialclasses = tex.specialmathclasscodes classes["all"] = specialclasses["all"] classnames[specialclasses["all"] ] = "all" -classes["begin"] = specialclasses["begin"] classnames[specialclasses["begin"]] = "begin" +classes["begin"] = specialclasses["begin"] classnames[specialclasses["begin"]] = "beg" classes["end"] = specialclasses["end"] classnames[specialclasses["end"] ] = "end" callback.register("get_noad_class", function(n) return classnames[n] end) @@ -506,6 +536,16 @@ mathematics.virtualized = virtualized do + local skip = { + [accent_class] = true, + [topaccent_class] = true, + [bottomaccent_class] = true, + [over_class] = true, + [under_class] = true, + [radical_class] = true, + [root_class] = true, + } + local registercharacter = mathematics.dictionaries.registercharacter local groupnames = mathematics.dictionaries.names @@ -514,10 +554,10 @@ do setmathcode("global",slot,class,family,unicode) mset = false end - if dset and (class == open_class or class == close_class or class == middle_class or class == division_class) then - setdelcode("global",slot,family,unicode,0,0) - dset = false - end + -- if dset and (class == open_class or class == close_class or class == middle_class or class == division_class) then + -- setdelcode("global",slot,family,unicode,0,0) + -- dset = false + -- end if group then group = groupnames[group] or 0 if group ~= 0 then @@ -540,47 +580,36 @@ do end end - -- local f_accent = formatters[ [[\defUmathtopaccent \%s{%X}{%X}{%X}]] ] - -- local f_fixedtopaccent = formatters[ [[\defUmathfixedtopaccent \%s{%X}{%X}{%X}]] ] - -- local f_fixedbottomaccent = formatters[ [[\defUmathfixedbottomaccent \%s{%X}{%X}{%X}]] ] - -- local f_topaccent = formatters[ [[\defUmathtopaccent \%s{%X}{%X}{%X}]] ] - -- local f_bottomaccent = formatters[ [[\defUmathbottomaccent \%s{%X}{%X}{%X}]] ] - -- local f_over = formatters[ [[\defUdelimiterover \%s{%X}{%X}{%X}]] ] - -- local f_under = formatters[ [[\defUdelimiterunder\%s{%X}{%X}{%X}]] ] - -- local f_fence = formatters[ [[\defUdelimiter \%s{%X}{%X}{%X}]] ] - -- local f_delimiter = formatters[ [[\defUdelimiter \%s{%X}{%X}{%X}]] ] - -- local f_radical = formatters[ [[\defUradical \%s{%X}{%X}]] ] - -- local f_root = formatters[ [[\defUroot \%s{%X}{%X}]] ] - -- local f_char = formatters[ [[\defUmathchar \%s{%X}{%X}{%X}]] ] - local texmathchardef = tex.mathchardef + -- local setmathsymbol = function(name,class,family,slot,stretch,group) -- hex is nicer for tracing + -- if skip[class] then + -- return -- only in mkiv + -- elseif class == open_class or class == close_class or class == middle_class then + -- setdelcode("global",slot,family,slot,0,0) -- can go + -- elseif class == delimiter_class then -- open close or middle (bars) + -- setdelcode("global",slot,family,slot,0,0) -- can go + -- class = 0 + -- else + -- if group then + -- group = groupnames[group] or 0 + -- if group ~= 0 then + -- texmathchardef(name,class,family,slot,"permanent",0x1,group,slot) + -- return + -- end + -- end + -- end + -- texmathchardef(name,class,family,slot,"permanent") + -- end + local setmathsymbol = function(name,class,family,slot,stretch,group) -- hex is nicer for tracing - if class == accent_class then - -- ctx_sprint(f_accent(name,0,family,slot)) - elseif class == topaccent_class then - -- ctx_sprint((stretch and f_topaccent or f_fixedtopaccent)(name,0,family,slot)) - elseif class == bottomaccent_class then - -- ctx_sprint((stretch and f_bottomaccent or f_fixedbottomaccent)(name,0,family,slot)) - elseif class == over_class then -- only in mkiv - -- ctx_sprint(f_over(name,0,family,slot)) - elseif class == under_class then -- only in mkiv - -- ctx_sprint(f_under(name,0,family,slot)) - elseif class == open_class or class == close_class or class == middle_class then - setdelcode("global",slot,family,slot,0,0) -- can go - -- ctx_sprint(f_fence(name,class,family,slot)) - -- ctx_sprint(f_char(name,class,family,slot)) - texmathchardef(name,class,family,slot,"permanent") - elseif class == delimiter_class then -- open close or middle (bars) - setdelcode("global",slot,family,slot,0,0) -- can go - -- ctx_sprint(f_delimiter(name,0,family,slot)) - -- ctx_sprint(f_char(name,0,family,slot)) - texmathchardef(name,0,family,slot,"permanent") - elseif class == radical_class then -- only in mkiv - -- ctx_sprint(f_radical(name,family,slot)) - elseif class == root_class then -- only in mkiv - -- ctx_sprint(f_root(name,family,slot)) - elseif texmathchardef then + if skip[class] then + return -- only in mkiv + -- elseif class == open_class or class == close_class or class == middle_class then + else + if class == delimiter_class then -- open close or middle (bars) + class = ordinary_class + end if group then group = groupnames[group] or 0 if group ~= 0 then diff --git a/tex/context/base/mkxl/math-ini.mkxl b/tex/context/base/mkxl/math-ini.mkxl index dfa8a18ef..901d187b0 100644 --- a/tex/context/base/mkxl/math-ini.mkxl +++ b/tex/context/base/mkxl/math-ini.mkxl @@ -51,33 +51,19 @@ \unprotect -\newdimension\mathstrutht -\newdimension\mathstrutdp -\newinteger \mathnestinglevel - -% For now: - -%protected\def\Umathaccent_top {\Umathaccent top } -%protected\def\Umathaccent_bottom {\Umathaccent bottom } -%protected\def\Umathaccent_top_fixed {\Umathaccent top fixed } -%protected\def\Umathaccent_bottom_fixed{\Umathaccent bottom fixed } - -%permanent\protected\def\defUmathfixedtopaccent #1#2#3#4{\global\immutable\protected\def#1{\Umathaccent_top_fixed "#2 "#3 "#4 }} -%permanent\protected\def\defUmathfixedbottomaccent#1#2#3#4{\global\immutable\protected\def#1{\Umathaccent_bottom_fixed "#2 "#3 "#4 }} -%permanent\protected\def\defUmathtopaccent #1#2#3#4{\global\immutable\protected\def#1{\Umathaccent_top "#2 "#3 "#4 }} -%permanent\protected\def\defUmathbottomaccent #1#2#3#4{\global\immutable\protected\def#1{\Umathaccent_bottom "#2 "#3 "#4 }} - -%permanent\protected\def\defUmathchar #1#2#3#4{\global\immutable\Umathchardef #1 "#2 "#3 "#4 } -%permanent\protected\def\defUdelimiter #1#2#3#4{\global\immutable\protected\def#1{\Udelimiter "#2 "#3 "#4 }} -%permanent\protected\def\defUdelimiter #1#2#3#4{\global\immutable\Umathchardef #1 "#2 "#3 "#4 } - -%permanent\protected\def\defUradical #1#2#3{\global\immutable\protected\def#1{\Uradical "#2 "#3 }} -%permanent\protected\def\defUroot #1#2#3{\global\immutable\protected\def#1{\Uroot "#2 "#3 }} - -%permanent\protected\def\defUdelimiterover #1#2#3#4{\global\immutable\protected\def#1{\Udelimiterover "#2 "#3 }} % radicals -%permanent\protected\def\defUdelimiterunder #1#2#3#4{\global\immutable\protected\def#1{\Udelimiterunder "#2 "#3 }} % radicals - -% So: +\newdimension \mathstrutht +\newdimension \mathstrutdp +\newinteger \mathnestinglevel + +\newcount \c_strc_math_n_of_lines +\newdimension \d_strc_math_max_width +\newdimension \d_strc_math_first_width +\newdimension \d_strc_math_last_width +\newdimension \d_strc_math_first_height +\newdimension \d_strc_math_last_depth +\newdimension \d_strc_math_display_width +\newdimension \d_strc_math_indent +\newconditional\c_strc_math_indent \registerctxluafile{math-ini}{autosuffix} \registerctxluafile{math-dim}{autosuffix} @@ -2682,6 +2668,15 @@ % todo: use \Umathclass\c_math_comma\mathpunctcode etc for temporary switching +%D This is a dirty trick. In order to prevent a loop due to reinjection, when a +%D active one is seen, the amcode is set to other. So, afterwards we need to +%D reactivate. Eventually this feature will be dropped in favor of a more modern +%D mechanism. + +\def\math_activeate_comma {\amcode\c_math_comma \activecatcode} +\def\math_activeate_period {\amcode\c_math_period \activecatcode} +\def\math_activeate_semicolon{\amcode\c_math_semicolon\activecatcode} + \def\math_set_o_comma {\Umathcode\c_math_comma \mathordinarycode \zerocount\c_math_comma} \def\math_set_p_comma {\Umathcode\c_math_comma \mathpunctuationcode\zerocount\c_math_comma} \def\math_set_o_period {\Umathcode\c_math_period \mathordinarycode \zerocount\c_math_period} @@ -2692,9 +2687,9 @@ \edef\math_set_o_both {\math_set_o_period\math_set_o_comma} \edef\math_set_p_both {\math_set_p_period\math_set_p_comma} -\protected\def\math_punctuation_nop_comma {\begingroup\math_set_p_comma ,\endgroup} -\protected\def\math_punctuation_nop_period {\begingroup\math_set_o_period .\endgroup} -\protected\def\math_punctuation_nop_semicolon{\begingroup\math_set_p_semicolon;\endgroup} +\protected\def\math_punctuation_nop_comma {\begingroup\math_set_p_comma ,\endgroup\math_activeate_comma } +\protected\def\math_punctuation_nop_period {\begingroup\math_set_o_period .\endgroup\math_activeate_period } +\protected\def\math_punctuation_nop_semicolon{\begingroup\math_set_p_semicolon;\endgroup\math_activeate_semicolon} % todo: use new lookahead stuff @@ -2706,9 +2701,9 @@ \let\math_punctuation_yes_period \math_punctuation_nop_period \let\math_punctuation_yes_semicolon\math_punctuation_all_semicolon -\def\math_punctuation_comma_next {\begingroup\Umathcode\c_math_comma \ifx\nexttoken\blankspace\mathpunctuationcode\else\mathordinarycode\fi\zerocount\c_math_comma ,\endgroup} -\def\math_punctuation_period_next {\begingroup\Umathcode\c_math_period \ifx\nexttoken\blankspace\mathpunctuationcode\else\mathordinarycode\fi\zerocount\c_math_period .\endgroup} -\def\math_punctuation_semicolon_next{\begingroup\Umathcode\c_math_semicolon\ifx\nexttoken\blankspace\mathpunctuationcode\else\mathordinarycode\fi\zerocount\c_math_semicolon;\endgroup} +\def\math_punctuation_comma_next {\begingroup\Umathcode\c_math_comma \ifx\nexttoken\blankspace\mathpunctuationcode\else\mathordinarycode\fi\zerocount\c_math_comma ,\endgroup\math_activeate_comma } +\def\math_punctuation_period_next {\begingroup\Umathcode\c_math_period \ifx\nexttoken\blankspace\mathpunctuationcode\else\mathordinarycode\fi\zerocount\c_math_period .\endgroup\math_activeate_period } +\def\math_punctuation_semicolon_next{\begingroup\Umathcode\c_math_semicolon\ifx\nexttoken\blankspace\mathpunctuationcode\else\mathordinarycode\fi\zerocount\c_math_semicolon;\endgroup\math_activeate_semicolon} \installcorenamespace {mathautopunctuation} @@ -2725,12 +2720,6 @@ \let.\math_punctuation_nop_period \let;\math_punctuation_nop_semicolon} - % more efficient list: - % - % \gdefcsname\??mathautopunctuation\v!no\endcsname - % {\Umathcode\c_math_period\mathordcode \zerocount\c_math_period - % \Umathcode\c_math_comma \mathpunctcode\zerocount\c_math_comma } - \gdefcsname\??mathautopunctuation\v!yes\endcsname {\let,\math_punctuation_yes_comma \let.\math_punctuation_yes_period @@ -2773,10 +2762,17 @@ % \activatemathcharacter\c_math_period % \activatemathcharacter\c_math_semicolon +% \appendtoks +% \mathcode\c_math_comma \c_math_special +% \mathcode\c_math_period \c_math_special +% \mathcode\c_math_semicolon\c_math_special +% \begincsname\??mathautopunctuation\mathematicsparameter\c!autopunctuation\endcsname +% \to \everymathematics + \appendtoks - \mathcode\c_math_comma \c_math_special - \mathcode\c_math_period \c_math_special - \mathcode\c_math_semicolon\c_math_special + \math_activeate_comma + \math_activeate_period + \math_activeate_semicolon \begincsname\??mathautopunctuation\mathematicsparameter\c!autopunctuation\endcsname \to \everymathematics diff --git a/tex/context/base/mkxl/math-spa.lmt b/tex/context/base/mkxl/math-spa.lmt index 5fa1a3742..9840a6aef 100644 --- a/tex/context/base/mkxl/math-spa.lmt +++ b/tex/context/base/mkxl/math-spa.lmt @@ -49,11 +49,21 @@ local nextnode = nuts.traversers.node local texgetdimen = tex.getdimen local texsetdimen = tex.setdimen local texsetcount = tex.setcount +local texisdimen = tex.isdimen +local texiscount = tex.iscount local boundary = tex.boundaries.system("mathalign") local stages = { } local initial = { } +local c_strc_math_n_of_lines = texiscount("c_strc_math_n_of_lines") +local d_strc_math_max_width = texisdimen("d_strc_math_max_width") +local d_strc_math_first_width = texisdimen("d_strc_math_first_width") +local d_strc_math_last_width = texisdimen("d_strc_math_last_width") +local d_strc_math_first_height = texisdimen("d_strc_math_first_height") +local d_strc_math_last_depth = texisdimen("d_strc_math_last_depth") +local d_strc_math_indent = texisdimen("d_strc_math_indent") + stages[1] = function(specification,stage) local box = getbox(specification.box) local head = getlist(box) @@ -91,7 +101,7 @@ stages[1] = function(specification,stage) break end end - texsetdimen("global","d_strc_math_indent",distance) + texsetdimen("global",d_strc_math_indent,distance) if align == 2 then for n in nextglue, head do setglue(n,getwidth(n),0,0,0,0) @@ -149,12 +159,12 @@ stages[2] = function(specification,stage) end end end - texsetcount("global","c_strc_math_n_of_lines",cnt) - texsetdimen("global","d_strc_math_max_width",maxwidth) - texsetdimen("global","d_strc_math_first_width",firstwidth) - texsetdimen("global","d_strc_math_last_width",lastwidth) - texsetdimen("global","d_strc_math_first_height",firstheight) - texsetdimen("global","d_strc_math_last_depth",lastdepth) + texsetcount("global",c_strc_math_n_of_lines,cnt) + texsetdimen("global",d_strc_math_max_width,maxwidth) + texsetdimen("global",d_strc_math_first_width,firstwidth) + texsetdimen("global",d_strc_math_last_width,lastwidth) + texsetdimen("global",d_strc_math_first_height,firstheight) + texsetdimen("global",d_strc_math_last_depth,lastdepth) end stages[3] = stages[2] diff --git a/tex/context/base/mkxl/math-tag.lmt b/tex/context/base/mkxl/math-tag.lmt index 128b85249..eaba1ea54 100644 --- a/tex/context/base/mkxl/math-tag.lmt +++ b/tex/context/base/mkxl/math-tag.lmt @@ -26,6 +26,7 @@ local nuts = nodes.nuts local tonut = nuts.tonut local getchar = nuts.getchar +local getprev = nuts.getprev local getcharspec = nuts.getcharspec local getdata = nuts.getdata local getlist = nuts.getlist @@ -105,11 +106,15 @@ local restart_tagged = tags.restart local stop_tagged = tags.stop local taglist = tags.taglist -local chardata = characters.data +----- chardata = characters.data -local getmathcodes = tex.getmathcodes -local mathcodes = mathematics.codes -local ordinary_mathcode = mathcodes.ordinary +local getmathcodes = tex.getmathcodes +----- mathcodes = mathematics.codes +local mathcodes = mathematics.classes +local ordinary_mathcode = mathcodes.ordinary +local digit_mathcode = mathcodes.digit +local punctuation_mathcode = mathcodes.punctuation +local active_mathcode = mathcodes.active local fromunicode16 = fonts.mappings.fromunicode16 local fontcharacters = fonts.hashes.characters @@ -223,7 +228,7 @@ end -- only focus on structure and let the engine deal with the details. Another reason -- to update this is that we can add some tracing (lmtx only). --- This has been working ok for quite but in 2023 it's tiem to have a look at it +-- This has been working ok for quite but in 2023 it's time to have a look at it -- again and see to what extend we need to adapt to new features. Around the time -- PG's Panopticom was put on youtube. @@ -245,19 +250,32 @@ process = function(start) -- we cannot use the processor as we have no finalizer if id == mathchar_code then local char = getchar(start) local code = getmathcodes(char) - local ch = chardata[char] - local mc = ch and ch.mathclass +-- local ch = chardata[char] +-- local mc = ch and ch.mathclass local tag - local properties= { class = mc } + local properties= { class = code } + -- we're a bit early so we can have active here and no rules get applied + -- so maybe we have to correct some later on -- todo: we have way more now +-- if code == ordinary_mathcode then +-- if mc == "number" then +-- tag = "mn" +-- elseif mc == "variable" or not mc then -- variable is default +-- tag = "mi" +-- else +-- tag = "mo" +-- end +-- else +-- tag = "mo" +-- end +-- print(code,mathematics.classes[code]) +-- print(ordinary_mathcode,digit_mathcode,active_mathcode) if code == ordinary_mathcode then - if mc == "number" then - tag = "mn" - elseif mc == "variable" or not mc then -- variable is default - tag = "mi" - else - tag = "mo" - end + tag = "mi" + elseif code == digit_mathcode then + tag = "mn" +-- elseif code == punctuation_mathcode or code == active_mathcode then +-- tag = "mo" else tag = "mo" end @@ -316,7 +334,8 @@ process = function(start) -- we cannot use the processor as we have no finalizer process(list) end else - if tag ~= "mstackertop" and tag ~= "mstackermid" and tag ~= "mstackerbot" then +if tag ~= "mtable" and tag ~= "mstackertop" and tag ~= "mstackermid" and tag ~= "mstackerbot" then +-- if tag ~= "mstackertop" and tag ~= "mstackermid" and tag ~= "mstackerbot" then tag = "mtext" end local text = start_tagged(tag) @@ -343,12 +362,12 @@ process = function(start) -- we cannot use the processor as we have no finalizer -- local keep = { } -- win case we might need to move keep outside for n, id, subtype in nextnode, list do local mth = id == math_code and subtype - if mth == 0 then -- hm left_code - -- insert(keep,text) - keep = text - text = start_tagged("mrow") - common = common + 1 - end +if mth == 0 then -- begin in line + -- insert(keep,text) + keep = text + text = start_tagged("mrow") + common = common + 1 +end local aa = getattr(n,a_tagged) if aa then local ac = cache[aa] @@ -392,12 +411,12 @@ process = function(start) -- we cannot use the processor as we have no finalizer runner(replace,depth+1) end end - if mth == 1 then - stop_tagged() - -- text = remove(keep) - text = keep - common = common - 1 - end +if mth == 1 then -- end in line + stop_tagged() + -- text = remove(keep) + text = keep + common = common - 1 +end end end runner(list,0) @@ -488,6 +507,7 @@ process = function(start) -- we cannot use the processor as we have no finalizer end elseif id == fence_code then local delimiter = getdelimiter(start) +-- print(subtype,fencecodes[subtype],delimiter) if subtype == leftfence_code then local properties = { } insert(fencesstack,properties) @@ -623,7 +643,8 @@ process = function(start) -- we cannot use the processor as we have no finalizer end stop_tagged() else - setattr(start,a_tagged,start_tagged("merror", { detail = nodecodes[i] })) + --rule boundary + setattr(start,a_tagged,start_tagged("merror", { detail = nodecodes[id] })) stop_tagged() end end diff --git a/tex/context/base/mkxl/node-fin.lmt b/tex/context/base/mkxl/node-fin.lmt index 7093638de..88050af8a 100644 --- a/tex/context/base/mkxl/node-fin.lmt +++ b/tex/context/base/mkxl/node-fin.lmt @@ -44,6 +44,7 @@ local rulecodes = nodes.rulecodes local boxrule_code = rulecodes.box local imagerule_code = rulecodes.image local emptyrule_code = rulecodes.empty +local virtualrule_code = rulecodes.virtual local container_code = nodes.listcodes.container @@ -211,7 +212,7 @@ local function process(attribute,head,inheritance,default) -- one attribute setlist(stack,list) end elseif id == rule_code then - check = hasdimensions(stack) + check = subtype == virtualrule_code or hasdimensions(stack) end -- much faster this way than using a check() and nested() function if check then @@ -291,7 +292,7 @@ local function simple(attribute,head) setlist(stack,list) end elseif id == rule_code then - check = hasdimensions(stack) + check = subtype == virtualrule_code or hasdimensions(stack) end if check then local c = getattr(stack,attribute) @@ -386,7 +387,9 @@ local function selective(attribute,head,inheritance,default) -- two attributes setlist(stack,list) end elseif id == rule_code then - if subtype == boxrule_code or subtype == imagerule_code or subtype == emptyrule_code then + if subtype == virtualrule_code then + check = true + elseif subtype == boxrule_code or subtype == imagerule_code or subtype == emptyrule_code then -- so no redundant color stuff (only here, layers for instance should obey) check = false else @@ -494,7 +497,7 @@ local function stacked(attribute,head,default) -- no inheritance, but list-wise end end elseif id == rule_code then - check = hasdimensions(stack) + check = subtype == virtualrule_code or hasdimensions(stack) end if check then local a = getattr(stack,attribute) @@ -576,7 +579,9 @@ local function stacker(attribute,head,default) -- no inheritance, but list-wise end end elseif id == rule_code then - if subtype == boxrule_code or subtype == imagerule_code or subtype == emptyrule_code then + if subtype == virtualrule_code then + check = true + elseif subtype == boxrule_code or subtype == imagerule_code or subtype == emptyrule_code then -- so no redundant color stuff (only here, layers for instance should obey) check = false else diff --git a/tex/context/base/mkxl/node-ini.lmt b/tex/context/base/mkxl/node-ini.lmt index 34028fa2e..f1b9bb452 100644 --- a/tex/context/base/mkxl/node-ini.lmt +++ b/tex/context/base/mkxl/node-ini.lmt @@ -245,7 +245,8 @@ nodes.specialskipcodes = { table.setmetatableindex(listcodes,function(t,k) -- fully qualified as yet unknown - local v = mathematics.classnames[k - 0x100] or listcodes.unknown +-- local v = mathematics.classnames[k - 0x100] or listcodes.unknown + local v = mathematics.classes[k - 0x100] or mathematics.classnames[k - 0x100] or listcodes.unknown t[k] = v return v end) diff --git a/tex/context/base/mkxl/node-nut.lmt b/tex/context/base/mkxl/node-nut.lmt index 89c1fbac6..f17c5ce7a 100644 --- a/tex/context/base/mkxl/node-nut.lmt +++ b/tex/context/base/mkxl/node-nut.lmt @@ -138,6 +138,7 @@ local nuts = { getreplace = direct.getreplace, getrightdelimiter = direct.getrightdelimiter, getruledata = direct.getdata, -- obsolete when we have the split + getruledimensions = direct.getruledimensions, getscale = direct.getscale, getscales = direct.getscales, getscript = direct.getscript, diff --git a/tex/context/base/mkxl/node-ref.lmt b/tex/context/base/mkxl/node-ref.lmt index 36715c067..15c35cba9 100644 --- a/tex/context/base/mkxl/node-ref.lmt +++ b/tex/context/base/mkxl/node-ref.lmt @@ -42,6 +42,7 @@ local report_reference = logs.reporter("backend","references") local report_destination = logs.reporter("backend","destinations") local report_area = logs.reporter("backend","areas") +local texiscount = tex.iscount local texsetcount = tex.setcount ----- texsetattribute = tex.setattribute @@ -55,6 +56,8 @@ updaters.register("backends.injections.latebindings",function() prerollreference = backends.codeinjections.prerollreference end) +local c_lastreferenceattribute = texiscount("lastreferenceattribute") + local nuts = nodes.nuts local nodepool = nuts.pool @@ -246,7 +249,7 @@ local inject_areas do end end - -- Setting these once and not passign them each nested call is faster and this injector is + -- Setting these once and not passing them each nested call is faster and this injector is -- actually one of the more costly calls in a run (when we have lots of references to -- check) and it's also a bti less code. @@ -313,7 +316,7 @@ local inject_areas do local function inject(head,skip,parent,pardir,txtdir) local first, last, firstdir, reference local current = head - while current do + while current do -- tod: check with loop local id = getid(current) if id == hlist_code or id == vlist_code then local r = getattr(current,attribute) @@ -366,6 +369,7 @@ local inject_areas do end goto NEXT elseif id == glue_code then + -- local skiptype = ... 0=regular 1=left 2=right local subtype = getsubtype(current) if subtype == leftskip_code or subtype == lefthang_code or subtype == parfillleftskip_code then goto NEXT @@ -402,8 +406,8 @@ local inject_areas do -- print("!!!!!!!!") end else - -- todo: safeguard when we have a glyph or dics or ... so we might as well - -- then scan for all possibel content nodes + -- todo: safeguard when we have a glyph or disc or ... so we might as well + -- then scan for all possible content nodes reference = r first = current last = current @@ -456,6 +460,7 @@ local colorize, justadd do str = str .. " " shift = (shift or 2) * exheight end + -- todo: virtual rule, zero width hbox, offsets local text = typesetters.tohpack(str,infofont) local rule = new_rule(emwidth/5,4*exheight,3*exheight) setshift(text,shift) @@ -493,12 +498,12 @@ local colorize, justadd do height = 65536/2 depth = height end + -- todo: use virtual rules local rule = setcoloring(new_rule(width,height,depth),1,u_color,u_transparency) -- gray color model if width < 0 then local kern = new_kern(width) setwidth(rule,-width) - setnext(kern,rule) - setprev(rule,kern) + setlink(kern,rule) return kern elseif sr and sr ~= "" then local text = addstring(what,sr,shift) @@ -549,7 +554,7 @@ do -- so some part of the backend work is already done here stack[topofstack] = { r, h or false, d or false, codeinjections.prerollreference(r) } -- texsetattribute(attribute,topofstack) -- todo -> at tex end - texsetcount("lastreferenceattribute",topofstack) + texsetcount(c_lastreferenceattribute,topofstack) end function references.get(n) -- not public so functionality can change @@ -761,7 +766,7 @@ do if result then setlink(current,annot) else - result = annot + result = annot end current = find_node_tail(annot) end diff --git a/tex/context/base/mkxl/node-res.lmt b/tex/context/base/mkxl/node-res.lmt index daf0187e8..6fed08b63 100644 --- a/tex/context/base/mkxl/node-res.lmt +++ b/tex/context/base/mkxl/node-res.lmt @@ -77,7 +77,7 @@ local setleader = nuts.setleader local setclass = nuts.setclass local setdata = nuts.setdata -local setruledata = nuts.setruledata +local setoffsets = nuts.setoffsets local setvalue = nuts.setvalue local copy_nut = nuts.copyonly @@ -188,6 +188,7 @@ local userrule = register_nut(new_nut(rule_code,rulecodes.user)) -- local outlinerule = register_nut(new_nut(rule_code,rulecodes.outline)) -- setdirection(rule, lefttoright_code) local imagerule = register_nut(new_nut(rule_code,rulecodes.image)) -- setdirection(rule, lefttoright_code) local boxrule = register_nut(new_nut(rule_code,rulecodes.box)) -- setdirection(rule, lefttoright_code) +local virtualrule = register_nut(new_nut(rule_code,rulecodes.virtual)) -- setdirection(rule, lefttoright_code) local hlist = register_nut(new_nut(nodecodes.hlist)) setdirection(hlist,lefttoright_code) local vlist = register_nut(new_nut(nodecodes.vlist)) setdirection(vlist,lefttoright_code) @@ -382,7 +383,7 @@ function nutpool.outlinerule(width,height,depth,line) -- w/h/d == nil will let t setwhd(n,width,height,depth) end if line then - setruledata(n,round(line)) -- has to be an integer + setdata(n,round(line)) -- has to be an integer end return n end @@ -403,6 +404,15 @@ function nutpool.boxrule(width,height,depth) -- w/h/d == nil will let them adapt return n end +function nutpool.virtualrule(width,height,depth) -- w/h/d == nil will let them adapt + local n = copy_nut(virtualrule) + if width or height or depth then + setdata(n,width) + setoffsets(n,nil,nil,height,depth) + end + return n +end + local function new_leader(width,list) local n = copy_nut(cleader) if width then diff --git a/tex/context/base/mkxl/node-rul.mkxl b/tex/context/base/mkxl/node-rul.mkxl index 24b7d5ef0..5253c8008 100644 --- a/tex/context/base/mkxl/node-rul.mkxl +++ b/tex/context/base/mkxl/node-rul.mkxl @@ -71,6 +71,20 @@ %definesystemattribute[ruled] %definesystemattribute[shifted] +\newdimension\d_rule_width +\newdimension\d_rule_height +\newdimension\d_rule_depth +\newdimension\d_rule_h +\newdimension\d_rule_v +\newdimension\d_rule_line +\newdimension\d_rule_offset +\newdimension\d_rule_factor + +\mutable\lettonothing\m_rule_direction +%mutable\lettonothing\m_rule_factor +\mutable\lettonothing\m_rule_option +\mutable\lettonothing\m_rule_color + \registerctxluafile{node-rul}{autosuffix,optimize} \installcorenamespace{bar} @@ -289,20 +303,6 @@ %D %D \typebuffer \getbuffer -\newdimension\d_rule_width -\newdimension\d_rule_height -\newdimension\d_rule_depth -\newdimension\d_rule_h -\newdimension\d_rule_v -\newdimension\d_rule_line -\newdimension\d_rule_offset -\newdimension\d_rule_factor - -\mutable\lettonothing\m_rule_direction -%mutable\lettonothing\m_rule_factor -\mutable\lettonothing\m_rule_option -\mutable\lettonothing\m_rule_color - \startuseMPgraphic{rules:under:random} draw ((0,RuleDepth) ... (RuleWidth,RuleDepth)) randomized (4*RuleThickness) diff --git a/tex/context/base/mkxl/node-shp.lmt b/tex/context/base/mkxl/node-shp.lmt index 7d73d9390..fc149330b 100644 --- a/tex/context/base/mkxl/node-shp.lmt +++ b/tex/context/base/mkxl/node-shp.lmt @@ -38,7 +38,7 @@ function handlers.finalizebox(box) actions(getbox(box)) -- nut end -function handlers.finalizelist(list) +function handlers.finalizelist(list) -- beware of export: block it if needed actions(list) -- nut end diff --git a/tex/context/base/mkxl/pack-rul.mkxl b/tex/context/base/mkxl/pack-rul.mkxl index 9b87d95b0..baaab17a5 100644 --- a/tex/context/base/mkxl/pack-rul.mkxl +++ b/tex/context/base/mkxl/pack-rul.mkxl @@ -273,32 +273,56 @@ corner {\p_framed_backgroundcorner} \relax}} +% we keep this as reference (should still work when uncommented) +% +% \def\pack_framed_stroked_box +% {\edef\p_framed_framecorner{\framedparameter\c!framecorner}% +% \ifx\p_framed_framecorner\v!rectangular +% \pack_framed_stroked_box_normal +% \else +% \pack_framed_stroked_box_radius +% \fi} +% +% \def\pack_framed_stroked_box_radius +% {\edef\p_framed_frameradius{\framedparameter\c!frameradius}% +% \ifzeropt\dimexpr\p_framed_frameradius\relax % just in case of .x\bodyfontsize +% \pack_framed_stroked_box_normal +% \orelse\ifx\p_framed_frame\v!on +% \pack_framed_stroked_box_round +% \fi} +% +% % \pack_framed_stroked_box_normal % later +% +% \def\pack_framed_stroked_box_round +% {\raise\d_framed_target_dp\hpack{\frule +% width \d_framed_target_wd +% height \d_framed_target_ht +% depth \d_framed_target_dp +% line \d_framed_linewidth +% radius \p_framed_frameradius\space +% corner {\p_framed_framecorner} +% \relax}} +% +% corner is the parent of framecorner and backgroundcorner (round value never checked) +% when 'round' is passed it is not a number and therefore we get four sides + \def\pack_framed_stroked_box {\edef\p_framed_framecorner{\framedparameter\c!framecorner}% \ifx\p_framed_framecorner\v!rectangular \pack_framed_stroked_box_normal - \else - \pack_framed_stroked_box_radius - \fi} - -\def\pack_framed_stroked_box_radius - {\edef\p_framed_frameradius{\framedparameter\c!frameradius}% - \ifzeropt\dimexpr\p_framed_frameradius\relax % just in case of .x\bodyfontsize - \pack_framed_stroked_box_normal \orelse\ifx\p_framed_frame\v!on \pack_framed_stroked_box_round \fi} -% \pack_framed_stroked_box_normal % later - -\def\pack_framed_stroked_box_round - {\raise\d_framed_target_dp\hpack{\frule - width \d_framed_target_wd - height \d_framed_target_ht - depth \d_framed_target_dp - line \d_framed_linewidth - radius \p_framed_frameradius\space - corner {\p_framed_framecorner} +\def\pack_framed_stroked_box_round % todo: variant without keywords + {\raise\d_framed_target_dp + \hpack{\clf_roundedoutline % we could access these at the lua end! + \d_framed_target_wd + \d_framed_target_ht + \d_framed_target_dp + \d_framed_linewidth + \framedparameter\c!frameradius + {\p_framed_framecorner} \relax}} % a lot of weird corners diff --git a/tex/context/base/mkxl/page-lay.mkxl b/tex/context/base/mkxl/page-lay.mkxl index d56becbc6..5e2281a2f 100644 --- a/tex/context/base/mkxl/page-lay.mkxl +++ b/tex/context/base/mkxl/page-lay.mkxl @@ -814,6 +814,9 @@ \permanent\def\layoutcolumnoffset#1% can travel around so we can't use \lastnamedcs {\csname\??layoutcolumn\ifcsname\??layoutcolumn#1\endcsname#1\else0\fi\endcsname} +\permanent\protected\def\layoutlineoffset#1% + {\the\dimexpr\topskip-\strutht+#1\lineheight-\lineheight\relax} + \def\page_layouts_synchronize_at_start {\ifdim\makeupheight=\layoutlines\lineheight \else % weird check \page_layouts_synchronize diff --git a/tex/context/base/mkxl/spac-ali.mkxl b/tex/context/base/mkxl/spac-ali.mkxl index 6ca9e5e55..c7d2fb657 100644 --- a/tex/context/base/mkxl/spac-ali.mkxl +++ b/tex/context/base/mkxl/spac-ali.mkxl @@ -827,6 +827,10 @@ \defcsname\??aligncommand\v!always\endcsname{\toksapp\t_spac_align_collected{\bitwiseflip\hyphenationmode\forcecheckhyphenationcode}} +% experiment + +\defcsname\??aligncommand\v!profile\endcsname{\toksapp\t_spac_align_collected{\setmainlineprofile}} + \definehspace [\v!final] [\emspaceamount] \def\spac_align_flush_parfill diff --git a/tex/context/base/mkxl/spac-prf.lmt b/tex/context/base/mkxl/spac-prf.lmt index c38cdc97b..66a75cba0 100644 --- a/tex/context/base/mkxl/spac-prf.lmt +++ b/tex/context/base/mkxl/spac-prf.lmt @@ -16,7 +16,6 @@ local formatters = string.formatters local nodecodes = nodes.nodecodes local gluecodes = nodes.gluecodes -local listcodes = nodes.listcodes local glyph_code = nodecodes.glyph local disc_code = nodecodes.disc @@ -34,10 +33,14 @@ local leaders_code = gluecodes.leaders local lineskip_code = gluecodes.lineskip local baselineskip_code = gluecodes.baselineskip -local linelist_code = listcodes.line +local strutrule_code = nodes.rulecodes.strut +local linelist_code = nodes.listcodes.line local texlists = tex.lists local settexattribute = tex.setattribute +local texgetdimen = tex.getdimen + +local newindex = lua.newindex local nuts = nodes.nuts local tonut = nodes.tonut @@ -46,6 +49,7 @@ local tonode = nuts.tonode local getreplace = nuts.getreplace local getattr = nuts.getattr local getid = nuts.getid +local getboth = nuts.getboth local getnext = nuts.getnext local getprev = nuts.getprev local getsubtype = nuts.getsubtype @@ -59,6 +63,11 @@ local getwidth = nuts.getwidth local getheight = nuts.getheight local getdepth = nuts.getdepth local getboxglue = nuts.getboxglue +local effectiveglue = nuts.effectiveglue +local findattribute = nuts.findattribute + +local nextnode = nuts.traversers.node +local nextglue = nuts.traversers.glue local setlink = nuts.setlink local setlist = nuts.setlist @@ -76,6 +85,8 @@ local theprop = nuts.theprop local floor = math.floor local ceiling = math.ceil +local min = math.min +local max = math.max local new_rule = nuts.pool.rule local new_glue = nuts.pool.glue @@ -119,7 +130,7 @@ local function getprofile(line,step) return end - local glue_set, glue_order, glue_sign = getboxglue(line) +-- local glue_set, glue_order, glue_sign = getboxglue(line) local heights = { } local depths = { } @@ -140,71 +151,24 @@ local function getprofile(line,step) -- remember p - local function progress() - position = width - width = position + wd - p = floor((position - margin)/step + 0.5) - w = floor((width + margin)/step - 0.5) - if p < 0 then - p = 0 - end - if w < 0 then - w = 0 - end - if p > w then - w, p = p, w - end - if w > max then - for i=max+1,w+1 do - heights[i] = 0 - depths [i] = 0 - end - max = w - end - for i=p,w do - if ht > heights[i] then - heights[i] = ht - end - if dp > depths[i] then - depths[i] = dp - end - end - end - local function process(current) -- called nested in disc replace - while current do - local id = getid(current) + for current, id, subtype in nextnode, current do if id == glyph_code then wd, ht, dp = getwhd(current) - progress() elseif id == kern_code then wd = getkern(current) ht = 0 dp = 0 - progress() elseif id == disc_code then local replace = getreplace(current) if replace then process(replace) end + goto done elseif id == glue_code then - local width, stretch, shrink, stretch_order, shrink_order = getglue(current) - if glue_sign == 1 then - if stretch_order == glue_order then - wd = width + stretch * glue_set - else - wd = width - end - elseif glue_sign == 2 then - if shrink_order == glue_order then - wd = width - shrink * glue_set - else - wd = width - end - else - wd = width - end - if getsubtype(current) >= leaders_code then + wd = effectiveglue(current, line) -- geteffectivewhd + -- tricky + if subtype >= leaders_code then local leader = getleader(current) local w w, ht, dp = getwhd(leader) -- can become getwhd(current) after 1.003 @@ -212,12 +176,11 @@ local function getprofile(line,step) ht = 0 dp = 0 end - progress() elseif id == hlist_code then + -- maybe: offsets -- we could do a nested check .. but then we need to push / pop glue local shift = getshift(current) local w, h, d = getwhd(current) - -- if getattr(current,a_specialcontent) then if getprop(current,"specialcontent") then -- like a margin note, maybe check for wd wd = w @@ -228,29 +191,49 @@ local function getprofile(line,step) ht = h - shift dp = d + shift end - progress() elseif id == vlist_code or id == unset_code then local shift = getshift(current) -- todo - wd, ht, dp = getwhd(current) - progress() + wd, ht, dp = getwhd(current) -- todo: use combined getter elseif id == rule_code then wd, ht, dp = getwhd(current) - progress() elseif id == math_code then + -- todo get glue wd = getkern(current) + getwidth(current) -- surround ht = 0 dp = 0 - progress() - elseif id == marginkern_code then - -- not in lmtx - wd = getwidth(current) - ht = 0 - dp = 0 - progress() else --- print(nodecodes[id]) + goto done end - current = getnext(current) + -- progress + position = width + width = position + wd + p = floor((position - margin)/step + 0.5) + w = floor((width + margin)/step - 0.5) + if p < 0 then + p = 0 + end + if w < 0 then + w = 0 + end + if p > w then + w, p = p, w + end + if w > max then + for i=max+1,w+1 do + heights[i] = 0 + depths [i] = 0 + end + max = w + end + for i=p,w do + if ht > heights[i] then + heights[i] = ht + end + if dp > depths[i] then + depths[i] = dp + end + end + ::done:: end end @@ -362,6 +345,7 @@ local function addprofile(node,profile,step) return end local what = nil + -- beware: basically end of line so we actually need to put it elsewhere if lastht == 0 and lastdp == 0 then what = new_kern(lastwd) else @@ -470,12 +454,17 @@ end -- lineskip | lineskiplimit local function inject(top,bot,amount) -- todo: look at penalties - local glue = new_glue(amount) - -- - setattr(glue,a_profilemethod,0) - setattr(glue,a_visual,getattr(top,a_visual)) - -- - setlink(top,glue,bot) + if amount ~= 0 then + local glue = new_glue(amount) + -- + setattr(glue,a_profilemethod,0) + -- setattr(glue,a_visual,getattr(top,a_visual)) + setattr(glue,a_visual,nodes.visualizers.modes.glue) + -- + setlink(top,glue,bot) + -- + report("injected correction %p at page",amount,tex.getcount("realpageno")) + end end methods[v_none] = function() @@ -487,8 +476,8 @@ methods[v_strict] = function(top,bot,t_profile,b_profile,specification) local top = tonut(top) local bot = tonut(bot) - local strutht = specification.height or texdimen.strutht - local strutdp = specification.depth or texdimen.strutdp + local strutht = specification.height or texgetdimen.strutht + local strutdp = specification.depth or texgetdimen.strutdp local lineheight = strutht + strutdp local depth = getdepth(top) @@ -523,8 +512,8 @@ methods[v_fixed] = function(top,bot,t_profile,b_profile,specification) local top = tonut(top) local bot = tonut(bot) - local strutht = specification.height or texdimen.strutht - local strutdp = specification.depth or texdimen.strutdp + local strutht = specification.height or texgetdimen.strutht + local strutdp = specification.depth or texgetdimen.strutdp local lineheight = strutht + strutdp local depth = getdepth(top) @@ -545,7 +534,7 @@ methods[v_fixed] = function(top,bot,t_profile,b_profile,specification) return true end - local delta = getdelta(t_profile,b_profile) + local delta = getdelta(t_profile,b_profile) local dp = strutdp while depth > lineheight - strutdp do @@ -642,8 +631,6 @@ end local function profilelist(line,mvl) - local current = line - local top = nil local bot = nil @@ -666,11 +653,8 @@ local function profilelist(line,mvl) pagehead, pagetail = getpagelist() if pagetail then - local current = pagetail - while current do - local id = getid(current) + for current, id, subtype in nextnode, pagetail do if id == hlist_code then - local subtype = getsubtype(current) if subtype == linelist_code then t_profile = hasprofile(current) if t_profile then @@ -690,13 +674,12 @@ local function profilelist(line,mvl) else break end - current = getnext(current) end end end - while current do + for current, id, subtype in nextnode, line do local attr = getattr(current,a_profilemethod) @@ -709,10 +692,7 @@ local function profilelist(line,mvl) lastattr = attr end - local id = getid(current) - if id == hlist_code then -- check subtype - local subtype = getsubtype(current) if subtype == linelist_code then if top == current then -- skip @@ -751,7 +731,6 @@ local function profilelist(line,mvl) end elseif id == glue_code then if top then - local subtype = getsubtype(current) -- if subtype == lineskip_code or subtype == baselineskip_code then local wd = getwidth(current) if wd > 0 then @@ -781,7 +760,6 @@ local function profilelist(line,mvl) top = nil bot = nil end - current = getnext(current) end if top then t_profile = setprofile(top) @@ -795,6 +773,8 @@ profiling.list = profilelist local enabled = false +-- todo: use attribute storage + function profiling.set(specification) if not enabled then enableaction("mvlbuilders", "builders.profiling.pagehandler") @@ -818,10 +798,8 @@ function profiling.profilebox(specification) local action = method and methods[method] or methods[v_strict] local lastglue = nil local distance = 0 - while current do - local id = getid(current) + for current, id, subtype in nextnode, current do if id == hlist_code then - local subtype = getsubtype(current) if subtype == linelist_code then if top then bot = current @@ -855,7 +833,6 @@ function profiling.profilebox(specification) bot = nil end elseif id == glue_code then - local subtype = getsubtype(current) if subtype == lineskip_code or subtype == baselineskip_code then if top then local wd = getwidth(current) @@ -882,7 +859,6 @@ function profiling.profilebox(specification) top = nil bot = nil end - current = getnext(current) end if top then @@ -947,3 +923,367 @@ interfaces.implement { } } } + +-- The following is an experiment that I picked up after demoing this already old but never +-- used feature and in the process it got applied to document of hundreds of pages. Actually +-- performance is quite okay but this mechanism is not really meant for that scenario. We'll +-- see where this ends. We could (an d might) integrate it in the above but the next is more +-- lightweight while the previous was basically some exploration with lots of options. + +do + + -- we could share the two arrays if needed + + local a_lineprofile = attributes.private("lineprofile") + + local registervalue = attributes.registervalue + local getvalue = attributes.getvalue + local texsetattribute = tex.setattribute + + local function getdepthprofile(line,step,margin,max,list) + + local width = 0 + local position = 0 + local profile = newindex(max+2,0) + local wd = 0 + local ht = 0 + local dp = 0 + + profile[0] = 0 + + local function process(current) -- called nested in disc replace + for current, id, subtype in nextnode, current do + if id == glyph_code then + wd, ht, dp = getwhd(current) + elseif id == kern_code then + wd = getkern(current) + dp = 0 + elseif id == disc_code then + local replace = getreplace(current) + if replace then + process(replace) + end + goto done + elseif id == glue_code then + wd = effectiveglue(current, line) -- geteffectivewhd + -- tricky + if subtype >= leaders_code then + local leader = getleader(current) + local w + w, ht, dp = getwhd(leader) -- can become getwhd(current) after 1.003 + else + dp = 0 + end + elseif id == hlist_code then + -- maybe: offsets + -- we could do a nested check .. but then we need to push / pop glue + local shift = getshift(current) + local w, h, d = getwhd(current) + if getprop(current,"specialcontent") then + -- like a margin note, maybe check for wd + wd = w + dp = 0 + else + wd = w + dp = d + shift + end + elseif id == vlist_code then + local shift = getshift(current) -- todo + wd, ht, dp = getwhd(current) -- todo: use combined getter + elseif id == rule_code then + if subtype == strutrule_code then + dp = 0 + else + wd, ht, dp = getwhd(current) + end + elseif id == math_code then + -- todo get glue + wd = getkern(current) + getwidth(current) -- surround + dp = 0 + else + goto done + end + -- progress + position = width + width = position + wd + p = floor((position - margin)/step + 0.5) + w = floor((width + margin)/step - 0.5) + if p < 0 then + p = 0 + end + if w < 0 then + w = 0 + end + if p > w then + w, p = p, w + end + if w > max then + for i=max+1,w+1 do + profile[i] = 0 + end + max = w + end + for i=p,w do + if dp > profile[i] then + profile[i] = dp + end + end + ::done:: + end + end + + process(list) + + return profile + + end + + local function getheightprofile(line,step,margin,max,list) + + local width = 0 + local position = 0 + local profile = newindex(max+2,0) + local wd = 0 + local ht = 0 + local dp = 0 + + profile[0] = 0 + + local function process(current) -- called nested in disc replace + for current, id, subtype in nextnode, current do + if id == glyph_code then + wd, ht, dp = getwhd(current) + elseif id == kern_code then + wd = getkern(current) + ht = 0 + elseif id == disc_code then + local replace = getreplace(current) + if replace then + process(replace) + end + goto done + elseif id == glue_code then + wd = effectiveglue(current, line) -- geteffectivewhd + -- tricky + if subtype >= leaders_code then + local leader = getleader(current) + local w + w, ht, dp = getwhd(leader) -- can become getwhd(current) after 1.003 + else + ht = 0 + end + elseif id == hlist_code then + -- maybe: offsets + -- we could do a nested check .. but then we need to push / pop glue + local shift = getshift(current) + local w, h, d = getwhd(current) + if getprop(current,"specialcontent") then + -- like a margin note, maybe check for wd + wd = w + ht = 0 + else + wd = w + ht = h - shift + end + elseif id == vlist_code then + local shift = getshift(current) -- todo + wd, ht, dp = getwhd(current) -- todo: use combined getter + elseif id == rule_code then + if subtype == strutrule_code then + ht = 0 + else + wd, ht, dp = getwhd(current) + end + elseif id == math_code then + -- todo get glue + wd = getkern(current) + getwidth(current) -- surround + ht = 0 + else + goto done + end + -- progress + position = width + width = position + wd + p = floor((position - margin)/step + 0.5) + w = floor((width + margin)/step - 0.5) + if p < 0 then + p = 0 + end + if w < 0 then + w = 0 + end + if p > w then + w, p = p, w + end + if w > max then + for i=max+1,w+1 do + profile[i] = 0 + end + max = w + end + for i=p,w do + if ht > profile[i] then + profile[i] = ht + end + end + ::done:: + end + end + + process(list) + + return profile + + end + + local show_lineprofile = false + local show_linedetails = false + + trackers.register("profiling.lines.show", function(v) + local visualizers = nodes.visualizers + glue_mode = visualizers.modes.glue + line_mode = visualizers.modes.line + show_lineprofile = v + visualizers.enable() + end) + + trackers.register("profiling.lines.details", function(v) + show_linedetail = v + end) + + local defaultstep = 65536 * 2 -- 2pt + local defaultmethod = "a" + local defaultfactor = 1 + + -- I played with different methods (like only get depths and then on the fly check with heights + -- but there is no gain and it is also fuzzy. So for now we just do the whole scan. + + function profilelines(list) + + if not list then + return + end + + local _, start = findattribute(list,a_lineprofile) + if not start then + return + end + + -- no height or depth ... skip + + for current, subtype in nextglue, start do + if subtype == lineskip_code and not getprop(current,"profiled") then + local detail = getattr(current,a_lineprofile) + if detail then + -- + local amount = getwidth(current) + -- + local top, bot = getboth(current) + setprop(current,"profiled",amount) -- original amount + if top then + if getid(top) == penalty_code then + top = getprev(top) + end + if top and bot then + if getid(top) == hlist_code and getsubtype(top) == linelist_code then + if getid(bot) == hlist_code and getsubtype(bot) == linelist_code then + local toplist = getlist(top) + local botlist = getlist(bot) + if toplist and botlist then + -- + local detail = getvalue(a_lineprofile,detail) or { } + local step = detail.step or defaultstep + local factor = tonumber(detail.factor) or defaultfactor + local method = detail.method or defaultmethod + local margin = step / 4 + -- + if factor > 1 then + factor = 1 + elseif factor <= 0 then + factor = 0 -- we could actually go the other way + end + -- + local natural = getdepth(top) + getheight(bot) + local added = factor * amount + local possible = natural - added + local overshoot = 0 + local topmax = ceiling(getwidth(top)/step) + 1 + local botmax = ceiling(getwidth(bot)/step) + 1 + -- if method == "a" then + local depths = getdepthprofile (top,step,margin,topmax,toplist) + local heights = getheightprofile(bot,step,margin,botmax,botlist) + local steps = min(#depths,#heights) + for i=1,steps do + local o = heights[i] + depths[i] - possible + if o > overshoot then + -- we can quit when >= added + overshoot = o +-- if overshoot > added then +-- break +-- end + end + end + -- end + -- if overshoot < added / 2 then + -- overshoot = added / 2 + -- end + if overshoot ~= amount then -- shouldn't we round + setwidth(current,overshoot) + if show_lineprofile then + setattr(current,a_visual,glue_mode) + setattr(bot,a_visual,line_mode) + setattr(top,a_visual,line_mode) + end + if show_linedetail then + report("lineskip changed from %p to %p on page %i",amount,overshoot,tex.getcount("realpageno")) + end + end + end + end + end + end + end + end + end + end + end + + builders.profiling.profilelines = profilelines + + function profiling.boxlinehandler(head) + if head then + profilelines(head) + end + return head + end + + function profiling.pagelinehandler(head) + if head then + profilelines(head) + end + return head + end + + function profiling.setlines(specification) + if not enabled then + enableaction("mvlbuilders", "builders.profiling.pagelinehandler") + enableaction("vboxbuilders", "builders.profiling.boxlinehandler") + enabled = true + end + texsetattribute(a_lineprofile,registervalue(a_lineprofile,specification)) + end + + interfaces.implement { + name = "setlineprofile", + actions = profiling.setlines, + arguments = { + { + { "name" }, + { "method" }, + { "step", "dimension" }, + { "factor" }, + } + } + } + +end diff --git a/tex/context/base/mkxl/spac-prf.mklx b/tex/context/base/mkxl/spac-prf.mklx index 824b14ca7..fc3e4ae22 100644 --- a/tex/context/base/mkxl/spac-prf.mklx +++ b/tex/context/base/mkxl/spac-prf.mklx @@ -20,11 +20,7 @@ \unprotect -\doiffileelse{spac-prf-new.lmt}{ - \registerctxluafile{spac-prf-new}{autosuffix} -} { - \registerctxluafile{spac-prf}{autosuffix} -} +\registerctxluafile{spac-prf}{autosuffix} \definesystemattribute[profilemethod][public] @@ -86,7 +82,7 @@ \edef\currentprofile{#profile}% \fi \spac_profile_set - \par + \profileparameter\c!before} \protected\def\spac_profile_stop @@ -150,4 +146,40 @@ \defineprofile[quarterfixed][\v!fixed][\c!factor=\plusfour] \defineprofile[eightsfixed] [\v!fixed][\c!factor=\pluseight] +% Finally some follow up on this experiment: + +\definesystemattribute[lineprofile] [public] + +\installcorenamespace {lineprofile} + +\installcommandhandler \??lineprofile {lineprofile} \??lineprofile + +\setuplineprofile + [\c!method=\v!a, + \c!step=.5\emwidth, % maybe 2pt + \c!factor=.125] % maybe 0.250 + +\def\spac_line_profile_set + {\clf_setlineprofile + name {\currentlineprofile}% + step \dimexpr\lineprofileparameter\c!step\relax + factor {\lineprofileparameter\c!factor} + method {\lineprofileparameter\c!method}% + \relax} + +\permanent\tolerant\protected\def\setlineprofile[#profile]% + {\edef\currentlineprofile{#profile}% + \spac_line_profile_set} + +\permanent\protected\def\resetlineprofile + {\c_attr_lineprofile\attributeunsetvalue} + +\permanent\protected\def\setmainlineprofile + {\lettonothing\currentlineprofile + \clf_setlineprofile} + +\appendtoks + \c_attr_lineprofile\attributeunsetvalue % or in general resetter +\to \everyforgetall + \protect \endinput diff --git a/tex/context/base/mkxl/spac-ver.lmt b/tex/context/base/mkxl/spac-ver.lmt index 01690b7ae..a0b1d5a94 100644 --- a/tex/context/base/mkxl/spac-ver.lmt +++ b/tex/context/base/mkxl/spac-ver.lmt @@ -117,6 +117,8 @@ local d_globalbodyfontstrutdepth = tex.isdimen("globalbodyfontstrutdepth") ----- d_strutht = tex.isdimen("strutht") local d_strutdp = tex.isdimen("strutdp") +local d_spac_overlay = tex.isdimen("d_spac_overlay") + local nuts = nodes.nuts local tonut = nuts.tonut @@ -1455,7 +1457,7 @@ do end -- local delta = n_ht + skips + p_dp - texsetdimen("global","d_spac_overlay",-delta) -- for tracing + texsetdimen("global",d_spac_overlay,-delta) -- for tracing -- we should adapt pagetotal ! (need a hook for that) .. now we have the wrong pagebreak local k = new_kern(-delta) setvisual(k) diff --git a/tex/context/base/mkxl/spac-ver.mkxl b/tex/context/base/mkxl/spac-ver.mkxl index 89632bd84..76dc97dc5 100644 --- a/tex/context/base/mkxl/spac-ver.mkxl +++ b/tex/context/base/mkxl/spac-ver.mkxl @@ -20,10 +20,11 @@ \newdimen \bodyfontstrutdepth \newgluespec\globalbodyfontlineheight % why a skip -\newdimen \globalbodyfontstrutheight +\newdimen \globalbodyfontstrutheight \newdimen \globalbodyfontstrutdepth -\newgluespec\s_spac_vspacing_predefined +\newgluespec \s_spac_vspacing_predefined +\newdimension\d_spac_overlay % \overloaded\let\strutht \undefined \newdimen\strutht % already defined % \overloaded\let\strutdp \undefined \newdimen\strutdp @@ -2020,8 +2021,6 @@ %D used in itemize \unknown\ always test this: -\newdimension\d_spac_overlay - \def\spac_overlay_lines {\directcheckedvspacing{\v!back,\v!overlay}% \blank[\v!back,\v!overlay]% \nointerlineskip} diff --git a/tex/context/base/mkxl/strc-mat.mkxl b/tex/context/base/mkxl/strc-mat.mkxl index 025021edb..86e77e63c 100644 --- a/tex/context/base/mkxl/strc-mat.mkxl +++ b/tex/context/base/mkxl/strc-mat.mkxl @@ -1352,13 +1352,6 @@ % a limitation is that this only works in a regular setting, so no shapes -\newinteger \c_strc_math_n_of_lines -\newdimension\d_strc_math_max_width -\newdimension\d_strc_math_first_width -\newdimension\d_strc_math_last_width -\newdimension\d_strc_math_first_height -\newdimension\d_strc_math_last_depth - \appendtoks \global\d_strc_math_indent \zeropoint \global\c_strc_math_n_of_lines \zerocount diff --git a/tex/context/base/mkxl/strc-tag.lmt b/tex/context/base/mkxl/strc-tag.lmt index 2a0699924..ec6455cc6 100644 --- a/tex/context/base/mkxl/strc-tag.lmt +++ b/tex/context/base/mkxl/strc-tag.lmt @@ -182,34 +182,34 @@ local properties = allocate { -- todo: more "record = true" to improve forma margintext = { pdf = "Span", nature = "inline" }, marginanchor = { pdf = "Span", nature = "inline" }, - math = { pdf = "Div", nature = "inline" }, -- no display - mn = { pdf = "Span", nature = "mixed" }, - mi = { pdf = "Span", nature = "mixed" }, - mo = { pdf = "Span", nature = "mixed" }, - ms = { pdf = "Span", nature = "mixed" }, - mrow = { pdf = "Span", nature = "display" }, - msubsup = { pdf = "Span", nature = "display" }, - msub = { pdf = "Span", nature = "display" }, - msup = { pdf = "Span", nature = "display" }, - merror = { pdf = "Span", nature = "mixed" }, - munderover = { pdf = "Span", nature = "display" }, - munder = { pdf = "Span", nature = "display" }, - mover = { pdf = "Span", nature = "display" }, - mtext = { pdf = "Span", nature = "mixed" }, - mfrac = { pdf = "Span", nature = "display" }, - mroot = { pdf = "Span", nature = "display" }, - msqrt = { pdf = "Span", nature = "display" }, - mfenced = { pdf = "Span", nature = "display" }, - maction = { pdf = "Span", nature = "display" }, + math = { pdf = "Div", nature = "inline", namespace = "mathml" }, -- no display + mn = { pdf = "Span", nature = "mixed", namespace = "mathml" }, + mi = { pdf = "Span", nature = "mixed", namespace = "mathml" }, + mo = { pdf = "Span", nature = "mixed", namespace = "mathml" }, + ms = { pdf = "Span", nature = "mixed", namespace = "mathml" }, + mrow = { pdf = "Span", nature = "display", namespace = "mathml" }, + msubsup = { pdf = "Span", nature = "display", namespace = "mathml" }, + msub = { pdf = "Span", nature = "display", namespace = "mathml" }, + msup = { pdf = "Span", nature = "display", namespace = "mathml" }, + merror = { pdf = "Span", nature = "mixed", namespace = "mathml" }, + munderover = { pdf = "Span", nature = "display", namespace = "mathml" }, + munder = { pdf = "Span", nature = "display", namespace = "mathml" }, + mover = { pdf = "Span", nature = "display", namespace = "mathml" }, + mtext = { pdf = "Span", nature = "mixed", namespace = "mathml" }, + mfrac = { pdf = "Span", nature = "display", namespace = "mathml" }, + mroot = { pdf = "Span", nature = "display", namespace = "mathml" }, + msqrt = { pdf = "Span", nature = "display", namespace = "mathml" }, + mfenced = { pdf = "Span", nature = "display", namespace = "mathml" }, + maction = { pdf = "Span", nature = "display", namespace = "mathml" }, mstacker = { pdf = "Span", nature = "display" }, -- these are only internally used mstackertop = { pdf = "Span", nature = "display" }, -- these are only internally used mstackerbot = { pdf = "Span", nature = "display" }, -- these are only internally used mstackermid = { pdf = "Span", nature = "display" }, -- these are only internally used - mtable = { pdf = "Table", nature = "display" }, -- might change - mtr = { pdf = "TR", nature = "display" }, -- might change - mtd = { pdf = "TD", nature = "display" }, -- might change + mtable = { pdf = "Table", nature = "display", namespace = "mathml" }, -- might change + mtr = { pdf = "TR", nature = "display", namespace = "mathml" }, -- might change + mtd = { pdf = "TD", nature = "display", namespace = "mathml" }, -- might change ignore = { pdf = "Span", nature = "mixed" }, -- used internally private = { pdf = "Span", nature = "mixed" }, -- for users (like LS) when they need it @@ -576,7 +576,8 @@ implement { public = true, protected = true, actions = tags.setproperty, - arguments = { "optional", "'backend'", "optional" }, +-- arguments = { "optional", "'backend'", "optional" }, + arguments = { "optional", "'pdf'", "optional" }, } implement { diff --git a/tex/context/base/mkxl/supp-box.lmt b/tex/context/base/mkxl/supp-box.lmt index 28c1d44f9..a5bfe1394 100644 --- a/tex/context/base/mkxl/supp-box.lmt +++ b/tex/context/base/mkxl/supp-box.lmt @@ -101,9 +101,18 @@ local setlistcolor = nodes.tracers.colors.setlist local texget = tex.get local texgetbox = tex.getbox +local texisdimen = tex.isdimen local texsetdimen = tex.setdimen local texgetnest = tex.getnest +local d_lastnaturalboxwd = texisdimen("lastnaturalboxwd") +local d_lastnaturalboxht = texisdimen("lastnaturalboxht") +local d_lastnaturalboxdp = texisdimen("lastnaturalboxdp") + +local d_givenwidth = texisdimen("givenwidth") +local d_givenheight = texisdimen("givenheight") +local d_givendepth = texisdimen("givendepth") + local function hyphenatedlist(head,usecolor) local current = head and tonut(head) while current do @@ -409,9 +418,9 @@ do if l then w, h, d = getdimensions(l) end - texsetdimen("lastnaturalboxwd",w) - texsetdimen("lastnaturalboxht",h) - texsetdimen("lastnaturalboxdp",d) + texsetdimen(d_lastnaturalboxwd,w) + texsetdimen(d_lastnaturalboxht,h) + texsetdimen(d_lastnaturalboxdp,d) return w, h, d end @@ -845,9 +854,9 @@ implement { }, }, actions = function(t) - texsetdimen("givenwidth", t.width or 0) - texsetdimen("givenheight",t.height or 0) - texsetdimen("givendepth", t.depth or 0) + texsetdimen(d_givenwidth, t.width or 0) + texsetdimen(d_givenheight,t.height or 0) + texsetdimen(d_givendepth, t.depth or 0) end, } diff --git a/tex/context/base/mkxl/supp-box.mkxl b/tex/context/base/mkxl/supp-box.mkxl index bbbc7591e..802815416 100644 --- a/tex/context/base/mkxl/supp-box.mkxl +++ b/tex/context/base/mkxl/supp-box.mkxl @@ -15,8 +15,6 @@ \unprotect -\registerctxluafile{supp-box}{autosuffix,optimize} - \permanent\integerdef\negatelistsigncode\numexpr \negatexlistsigncode +\negateylistsigncode @@ -32,6 +30,12 @@ \newdimension\givenheight \newdimension\givendepth +\newdimension\lastnaturalboxwd % maybe alias ! +\newdimension\lastnaturalboxht +\newdimension\lastnaturalboxdp + +\registerctxluafile{supp-box}{autosuffix,optimize} + % \fixupboxesmode\plusone % gone: is now the default %D This module implements some box manipulation macros. Some are quite simple, some @@ -2761,9 +2765,9 @@ %D \setbox0\hbox to 10cm{foo} \the\naturalwd0 %D \stoptyping -\newdimension\lastnaturalboxwd -\newdimension\lastnaturalboxht -\newdimension\lastnaturalboxdp +% \newdimension\lastnaturalboxwd +% \newdimension\lastnaturalboxht +% \newdimension\lastnaturalboxdp %D We can define these public in lua: diff --git a/tex/context/base/mkxl/tabl-tbl.mkxl b/tex/context/base/mkxl/tabl-tbl.mkxl index eec1edf9c..d4ad013d5 100644 --- a/tex/context/base/mkxl/tabl-tbl.mkxl +++ b/tex/context/base/mkxl/tabl-tbl.mkxl @@ -1227,8 +1227,11 @@ \def\tabl_tabulate_start_foot_yes[#1]% {\processcontent{\e!stop\v!tabulatetail}\m_tabl_tabulate_data{\letcsname\??tabulatefoot#1\endcsname\m_tabl_tabulate_data}} -\def\tabl_tabulate_start_head_nop{\tabl_tabulate_start_head_yes[\v!tabulate]} -\def\tabl_tabulate_start_foot_nop{\tabl_tabulate_start_foot_yes[\v!tabulate]} +% \def\tabl_tabulate_start_head_nop{\tabl_tabulate_start_head_yes[\v!tabulate]} +% \def\tabl_tabulate_start_foot_nop{\tabl_tabulate_start_foot_yes[\v!tabulate]} + +\def\tabl_tabulate_start_head_nop{\tabl_tabulate_start_head_yes[]} +\def\tabl_tabulate_start_foot_nop{\tabl_tabulate_start_foot_yes[]} \protected\def\tabl_start_defined[#1]% {\bgroup @@ -2100,7 +2103,16 @@ % % can we omit the next one in the first run? probably % \noalign{\the\t_tabl_tabulate_every_after_row#2}} -\permanent\tolerant\protected\def\tabl_tabulate_NR_common#1#2#.#3% #. gobbles pars and spaces +% test case for ignorepar error +% +% \starttabulatehead +% \NC A \NC B \NC \NR +% \stoptabulatehead +% \starttabulate[|l|l|] +% \NC 1 \NC 2 \NC \NR +% \stoptabulate + +\permanent\tolerant\protected\def\tabl_tabulate_NR_common#1#2% #. gobbles pars and spaces {\global\advanceby\c_tabl_tabulate_noflines\plusone \global\setfalse\c_tabl_tabulate_firstflushed \global\setfalse\c_tabl_tabulate_equal @@ -2111,7 +2123,8 @@ \tabl_tabulate_pheight_reset \unskip\unskip\crcr\tabl_tabulate_flush_collected % can we omit the next one in the first run? probably - \noalign{\the\t_tabl_tabulate_every_after_row#2}#3} + % todo: move \ignorepars ourside so no alignment error then + \noalign{\the\t_tabl_tabulate_every_after_row#2\ignorepars}} \def\tabl_tabulate_check_penalties {\ifconditional\c_tabl_tabulate_tolerant_break\else diff --git a/tex/context/base/mkxl/tabl-xtb.lmt b/tex/context/base/mkxl/tabl-xtb.lmt index 3d91ccb85..2a3b9a3b0 100644 --- a/tex/context/base/mkxl/tabl-xtb.lmt +++ b/tex/context/base/mkxl/tabl-xtb.lmt @@ -37,8 +37,10 @@ local implement = interfaces.implement local tex = tex local texgetcount = tex.getcount local texsetcount = tex.setcount +local texiscount = tex.iscount local texgetdimen = tex.getdimen local texsetdimen = tex.setdimen +local texisdimen = tex.isdimen local texget = tex.get local format = string.format @@ -108,7 +110,19 @@ local report_xtable = logs.reporter("xtable") trackers.register("xtable.construct", function(v) trace_xtable = v end) -local null_mode = 0 +local c_tabl_x_nx = texiscount("c_tabl_x_nx") +local c_tabl_x_ny = texiscount("c_tabl_x_ny") +local c_tabl_x_state = texiscount("c_tabl_x_state") +local c_tabl_x_mode = texiscount("c_tabl_x_mode") +local c_tabl_x_skip_mode = texiscount("c_tabl_x_skip_mode") +local d_tabl_x_final_width = texisdimen("d_tabl_x_final_width") +local d_tabl_x_distance = texisdimen("d_tabl_x_distance") +local d_tabl_x_width = texisdimen("d_tabl_x_width") +local d_tabl_x_height = texisdimen("d_tabl_x_height") +local d_tabl_x_depth = texisdimen("d_tabl_x_depth") + +local c_frameddimensionstate = texiscount("frameddimensionstate") + local head_mode = 1 local foot_mode = 2 local more_mode = 3 @@ -228,10 +242,10 @@ function xtables.initialize_reflow_width(option,width) local r = data.currentrow local c = data.currentcolumn + 1 local drc = data.rows[r][c] - drc.nx = texgetcount("c_tabl_x_nx") - drc.ny = texgetcount("c_tabl_x_ny") + drc.nx = texgetcount(c_tabl_x_nx) + drc.ny = texgetcount(c_tabl_x_ny) local distances = data.distances - local distance = texgetdimen("d_tabl_x_distance") + local distance = texgetdimen(d_tabl_x_distance) if distance > distances[c] then distances[c] = distance end @@ -419,21 +433,21 @@ function xtables.initialize_reflow_height() for x=1,drc.nx-1 do w = w + widths[c+x] end - texsetdimen("d_tabl_x_width",w) + texsetdimen(d_tabl_x_width,w) local dimensionstate = drc.dimensionstate or 0 if dimensionstate == 1 or dimensionstate == 3 then -- width was fixed so height is known - texsetcount("c_tabl_x_skip_mode",1) + texsetcount(c_tabl_x_skip_mode,1) elseif dimensionstate == 2 then -- height is enforced - texsetcount("c_tabl_x_skip_mode",1) + texsetcount(c_tabl_x_skip_mode,1) elseif data.autowidths[c] then -- width has changed so we need to recalculate the height - texsetcount("c_tabl_x_skip_mode",0) + texsetcount(c_tabl_x_skip_mode,0) elseif data.fixedcolumns[c] then - texsetcount("c_tabl_x_skip_mode",0) -- new + texsetcount(c_tabl_x_skip_mode,0) -- new else - texsetcount("c_tabl_x_skip_mode",1) + texsetcount(c_tabl_x_skip_mode,1) end end @@ -524,9 +538,9 @@ function xtables.initialize_construct() end end -- - texsetdimen("d_tabl_x_width",width) - texsetdimen("d_tabl_x_height",total) - texsetdimen("d_tabl_x_depth",0) -- for now + texsetdimen(d_tabl_x_width,width) + texsetdimen(d_tabl_x_height,total) + texsetdimen(d_tabl_x_depth,0) -- for now end function xtables.set_construct() @@ -936,11 +950,11 @@ function xtables.construct() [body_mode] = body, } if #body == 0 then - texsetcount("global","c_tabl_x_state",0) - texsetdimen("global","d_tabl_x_final_width",0) + texsetcount("global",c_tabl_x_state,0) + texsetdimen("global",d_tabl_x_final_width,0) else - texsetcount("global","c_tabl_x_state",1) - texsetdimen("global","d_tabl_x_final_width",getwidth(body[1][1])) + texsetcount("global",c_tabl_x_state,1) + texsetdimen("global",d_tabl_x_final_width,getwidth(body[1][1])) end end @@ -1105,7 +1119,7 @@ function xtables.flush(directives) -- todo split by size / no inbetween then .. results[foot_mode] = { } end results[body_mode] = { } - texsetcount("global","c_tabl_x_state",0) + texsetcount("global",c_tabl_x_state,0) else -- some is left so footer is delayed -- todo: try to flush a few more lines @@ -1119,7 +1133,7 @@ function xtables.flush(directives) -- todo split by size / no inbetween then .. else -- todo: try to fit more of body end - texsetcount("global","c_tabl_x_state",2) + texsetcount("global",c_tabl_x_state,2) end else if firstsize > height then @@ -1130,10 +1144,10 @@ function xtables.flush(directives) -- todo split by size / no inbetween then .. bodystart = bodystart + 1 end end - texsetcount("global","c_tabl_x_state",2) -- 1 + texsetcount("global",c_tabl_x_state,2) -- 1 end else - texsetcount("global","c_tabl_x_state",0) + texsetcount("global",c_tabl_x_state,0) end data.bodystart = bodystart data.bodystop = bodystop @@ -1179,7 +1193,7 @@ function xtables.flush(directives) -- todo split by size / no inbetween then .. results[head_mode] = { } results[body_mode] = { } results[foot_mode] = { } - texsetcount("global","c_tabl_x_state",0) + texsetcount("global",c_tabl_x_state,0) end end @@ -1209,7 +1223,7 @@ end function xtables.next_row(specification) local r = data.currentrow + 1 - data.modes[r] = texgetcount("c_tabl_x_mode") + data.modes[r] = texgetcount(c_tabl_x_mode) data.currentrow = r data.currentcolumn = 0 data.rowproperties[r] = specification diff --git a/tex/context/base/mkxl/task-ini.lmt b/tex/context/base/mkxl/task-ini.lmt index 17555d7e2..0e96c1e8e 100644 --- a/tex/context/base/mkxl/task-ini.lmt +++ b/tex/context/base/mkxl/task-ini.lmt @@ -149,6 +149,7 @@ appendaction("vboxbuilders", "normalizers", "nodes.handlers.backgroundsvbox", ------------("vboxbuilders", "normalizers", "typesetters.margins.localhandler", nil, "nut", "disabled" ) appendaction("vboxbuilders", "normalizers", "builders.vspacing.vboxhandler", nil, "nut", "enabled" ) appendaction("vboxbuilders", "normalizers", "builders.profiling.vboxhandler", nil, "nut", "disabled" ) +appendaction("vboxbuilders", "normalizers", "builders.profiling.boxlinehandler", nil, "nut", "disabled" ) appendaction("vboxbuilders", "normalizers", "typesetters.checkers.handler", nil, "nut", "disabled" ) appendaction("vboxbuilders", "normalizers", "typesetters.synchronize.handler", nil, "nut", "disabled" ) @@ -157,6 +158,7 @@ appendaction("mvlbuilders", "normalizers", "typesetters.margins.globalhandler", appendaction("mvlbuilders", "normalizers", "nodes.handlers.migrate", nil, "nut", "disabled" ) appendaction("mvlbuilders", "normalizers", "builders.vspacing.pagehandler", nil, "nut", "enabled" ) appendaction("mvlbuilders", "normalizers", "builders.profiling.pagehandler", nil, "nut", "disabled" ) +appendaction("mvlbuilders", "normalizers", "builders.profiling.pagelinehandler", nil, "nut", "disabled" ) appendaction("mvlbuilders", "normalizers", "typesetters.checkers.handler", nil, "nut", "disabled" ) appendaction("mvlbuilders", "normalizers", "typesetters.synchronize.handler", nil, "nut", "disabled" ) diff --git a/tex/context/base/mkxl/trac-vis.lmt b/tex/context/base/mkxl/trac-vis.lmt index 0cf6cb6a3..68310ef69 100644 --- a/tex/context/base/mkxl/trac-vis.lmt +++ b/tex/context/base/mkxl/trac-vis.lmt @@ -93,6 +93,7 @@ local pt_factor = number.dimenfactors.pt local nodepool = nuts.pool local new_rule = nodepool.rule +local new_virtual_rule = nodepool.virtualrule local new_kern = nodepool.kern local new_glue = nodepool.glue local new_hlist = nodepool.hlist @@ -249,6 +250,12 @@ local function enable() tex.setcount("global","c_syst_visualizers_state",1) -- so that we can optimize at the tex end end +function visualizers.enable() + if not enabled then + enable() + end +end + local function setvisual(n,a,what,list) -- this will become more efficient when we have the bit lib linked in if not n or n == "reset" then return unsetvalue @@ -400,33 +407,88 @@ directives.register("visualizers.fraction", function(v) fraction = (v and tonumb -- ... if okay it will replace the current hpack_string in node_typ +-- local function sometext(str,layer,color,textcolor,lap,variant) +-- local text = hpack_string(str,usedfont) +-- local size = getwidth(text) +-- local rule = new_rule(size,2*exheight,exheight/2) +-- local kern = new_kern(-size) +-- if color then +-- setcolor(rule,color) +-- end +-- if textcolor then +-- setlistcolor(getlist(text),textcolor) +-- end +-- local info = setlink(rule,kern,text) +-- setlisttransparency(info,"trace:g") +-- info = hpack_nodes(info) +-- local width = getwidth(info) +-- if variant then +-- setoffsets(info,0,variant*exheight) +-- end +-- if lap then +-- info = new_hlist(setlink(new_kern(-width),info)) -- use xoffset and set info wd to 0 +-- else +-- info = new_hlist(info) -- a bit overkill: double wrapped +-- end +-- if layer then +-- setattr(info,a_layer,layer) +-- end +-- return info, width +-- end + +-- local function sometext(str,layer,color,textcolor,lap,variant) +-- local text = hpack_string(str,usedfont) +-- local size = getwidth(text) +-- local rule = new_virtual_rule(size,2*exheight,exheight/2) +-- if color then +-- setcolor(rule,color) +-- end +-- if textcolor then +-- setlistcolor(getlist(text),textcolor) +-- end +-- local info = setlink(rule,text) +-- setlisttransparency(info,"trace:g") +-- info = hpack_nodes(info) +-- if variant then +-- setoffsets(info,0,variant*exheight) +-- end +-- info = new_hlist(info) -- a bit overkill: double wrapped +-- if lap then +-- setoffsets(info,-size) +-- end +-- if layer then +-- setattr(info,a_layer,layer) +-- end +-- return info, size +-- end + local function sometext(str,layer,color,textcolor,lap,variant) local text = hpack_string(str,usedfont) local size = getwidth(text) - local rule = new_rule(size,2*exheight,exheight/2) - local kern = new_kern(-size) + local rule = new_virtual_rule(size,2*exheight,exheight/2) if color then setcolor(rule,color) end if textcolor then setlistcolor(getlist(text),textcolor) end - local info = setlink(rule,kern,text) + local info = setlink(rule,text) setlisttransparency(info,"trace:g") - info = hpack_nodes(info) - local width = getwidth(info) + info = new_hlist(info) + local x, y + if lap then + x = -size + end if variant then - setoffsets(info,0,variant*exheight) + y = variant * exheight end - if lap then - info = new_hlist(setlink(new_kern(-width),info)) - else - info = new_hlist(info) -- a bit overkill: double wrapped + if x or y then + setoffsets(info,x,y) end if layer then setattr(info,a_layer,layer) end - return info, width + return info, size end local function someblob(str,layer,color,textcolor,width) diff --git a/tex/context/base/mkxl/trac-vis.mkxl b/tex/context/base/mkxl/trac-vis.mkxl index 3b088d05f..ec51ad4b0 100644 --- a/tex/context/base/mkxl/trac-vis.mkxl +++ b/tex/context/base/mkxl/trac-vis.mkxl @@ -32,13 +32,13 @@ \writestatus{loading}{ConTeXt Tracing Macros / Visualization} -\registerctxluafile{trac-vis}{autosuffix} - \unprotect \newconstant\c_syst_visualizers_state \newtoks \t_syst_visualizers_optimize +\registerctxluafile{trac-vis}{autosuffix} + % \definesystemattribute[visual][public,global] % already defined % no, but can become an option: diff --git a/tex/context/base/mkxl/typo-ada.lmt b/tex/context/base/mkxl/typo-ada.lmt index 17e18f01e..37393ca77 100644 --- a/tex/context/base/mkxl/typo-ada.lmt +++ b/tex/context/base/mkxl/typo-ada.lmt @@ -8,7 +8,7 @@ if not modules then modules = { } end modules ['typo-adj'] = { } local setdimen = tex.setdimen -local setcount = tex.setcount +local isdimen = tex.isdimen local setmacro = tokens.setters.macro local expandmacro = token.expandmacro @@ -46,7 +46,12 @@ local adaptive = nodes.adaptive or { } nodes.adaptive = adaptive local enabled = false -local enableaction = nodes.tasks.enableaction +local enableaction = nodes.tasks.enableaction + +local d_adaptive_width = isdimen("d_adaptive_width") +local d_adaptive_height = isdimen("d_adaptive_height") +local d_adaptive_depth = isdimen("d_adaptive_depth") +local d_adaptive_line = isdimen("d_adaptive_line") function adaptive.set(settings) if not enabled then @@ -58,10 +63,10 @@ function adaptive.set(settings) end local function setadaptive(w,h,d,l,c) - setdimen("d_adaptive_width",w) - setdimen("d_adaptive_height",h) - setdimen("d_adaptive_depth",d) - setdimen("d_adaptive_line",l) + setdimen(d_adaptive_width,w) + setdimen(d_adaptive_height,h) + setdimen(d_adaptive_depth,d) + setdimen(d_adaptive_line,l) setmacro("m_adaptive_color",c) end diff --git a/tex/context/base/mkxl/typo-ada.mkxl b/tex/context/base/mkxl/typo-ada.mkxl index 6e686a932..733b2ca5b 100644 --- a/tex/context/base/mkxl/typo-ada.mkxl +++ b/tex/context/base/mkxl/typo-ada.mkxl @@ -13,8 +13,6 @@ \writestatus{loading}{ConTeXt Typesetting Macros / Adaptive} -\registerctxluafile{typo-ada}{autosuffix} - % Musical timestamp: the postponed by COVID concert of Gazpacho in Zwolle NL: a joy % to see dedicated and talented musicians perform their work in perfection and as a % well balanced and equiped team. @@ -36,6 +34,8 @@ \aliasdimension\usedadaptiveline \d_adaptive_line \aliasdimension\usedadaptivehsize \d_adaptive_hsize +\registerctxluafile{typo-ada}{autosuffix} + \aliased\let\usedadaptivebox\b_adaptive_box \mutable\lettonothing\m_adaptive_color diff --git a/tex/context/base/mkxl/typo-chr.lmt b/tex/context/base/mkxl/typo-chr.lmt index 160981ab7..56218440f 100644 --- a/tex/context/base/mkxl/typo-chr.lmt +++ b/tex/context/base/mkxl/typo-chr.lmt @@ -228,6 +228,8 @@ interfaces.implement { -- not needed in lmtx ... +local c_syst_last_node_id = tex.iscount("c_syst_last_node_id") + interfaces.implement { name = "lastnodeid", actions = function() @@ -239,7 +241,7 @@ interfaces.implement { okay = tail.id end end - texsetcount("c_syst_last_node_id",okay) + texsetcount(c_syst_last_node_id,okay) end, } diff --git a/tex/context/base/mkxl/typo-chr.mkxl b/tex/context/base/mkxl/typo-chr.mkxl index e59be1e29..ad5314801 100644 --- a/tex/context/base/mkxl/typo-chr.mkxl +++ b/tex/context/base/mkxl/typo-chr.mkxl @@ -33,6 +33,8 @@ %D for instance when combining bit and pieces where keeping a state is complex compared %D to cleaning up unwanted stuff. +\newinteger\c_syst_last_node_id + \registerctxluafile{typo-chr}{autosuffix} \definesystemattribute[marked][public] @@ -78,8 +80,6 @@ %D test test\number\lastnodeid test %D \stoptyping -\newinteger\c_syst_last_node_id - \permanent\protected\def\doifelselastnode {\clf_lastnodeequals} % can be public implementors \permanent\protected\def\doifelseatwordboundary{\clf_atwordboundary} % can be public implementors \permanent\protected\def\lastnodeid {\clf_lastnodeid\c_syst_last_node_id} % can be public implementors diff --git a/tex/context/fonts/mkiv/lucida-math.lfg b/tex/context/fonts/mkiv/lucida-math.lfg index c95a32c5d..31589f5b3 100644 --- a/tex/context/fonts/mkiv/lucida-math.lfg +++ b/tex/context/fonts/mkiv/lucida-math.lfg @@ -13,10 +13,10 @@ return { copyright = "ConTeXt development team", mathematics = { parameters = { - FractionRuleThickness = 55, - AccentBaseDepth = 250, - DelimiterPercent = 90, - DelimiterShortfall = 400, + FractionRuleThickness = 55, + AccentBaseDepth = 250, + DelimiterPercent = 90, + DelimiterShortfall = 400, SuperscriptBottomMaxWithSubscript = 325, PrimeShiftUp = "1.4*SuperscriptShiftUp", PrimeShiftUpCramped = "1.4*SuperscriptShiftUp", @@ -32,6 +32,18 @@ return { tweak = "fixoldschool", version = "Version 1.802", }, +{ + tweak = "parameters", + feature = "boldmath", + list = { +-- RadicalRuleThickness = 55, + RadicalRuleThickness = 60, +-- RadicalRuleThickness = "1.09*RadicalRuleThickness", +-- FractionRuleThickness = 65, +-- OverRuleThickness = 65, +-- UnderRuleThickness = 65, + } +}, { tweak = "addmirrors", }, diff --git a/tex/context/fonts/mkiv/type-imp-lucida.mkiv b/tex/context/fonts/mkiv/type-imp-lucida.mkiv index 363b0d223..1e4c35abc 100644 --- a/tex/context/fonts/mkiv/type-imp-lucida.mkiv +++ b/tex/context/fonts/mkiv/type-imp-lucida.mkiv @@ -21,7 +21,7 @@ \starttypescriptcollection[lucida-opentype] - \doifunknownfontfeature {lucida-math-bold} {\definefontfeature[lucida-math-bold][boldened]} + \doifunknownfontfeature {lucida-math-bold} {\definefontfeature[lucida-math-bold][boldened][boldmath=yes]} \starttypescript [lucida,lucidaot,lucidadk,lucidaot-nt,lucida-nt] \loadfontgoodies[lucida-opentype-math] diff --git a/tex/context/interface/mkii/keys-it.xml b/tex/context/interface/mkii/keys-it.xml index ffffb9611..e456732ef 100644 --- a/tex/context/interface/mkii/keys-it.xml +++ b/tex/context/interface/mkii/keys-it.xml @@ -453,6 +453,7 @@ + @@ -725,6 +726,7 @@ + @@ -1339,6 +1341,7 @@ + diff --git a/tex/context/interface/mkii/keys-ro.xml b/tex/context/interface/mkii/keys-ro.xml index 9cd8c0431..2abf5c5b9 100644 --- a/tex/context/interface/mkii/keys-ro.xml +++ b/tex/context/interface/mkii/keys-ro.xml @@ -453,6 +453,7 @@ + @@ -725,6 +726,7 @@ + @@ -1339,6 +1341,7 @@ + diff --git a/tex/context/modules/mkiv/s-math-repertoire.mkiv b/tex/context/modules/mkiv/s-math-repertoire.mkiv index 59a2b828b..56d56bb6a 100644 --- a/tex/context/modules/mkiv/s-math-repertoire.mkiv +++ b/tex/context/modules/mkiv/s-math-repertoire.mkiv @@ -541,7 +541,7 @@ % \enabledirectives[math.nogoodies] % \showmathcharacterssetbodyfonts{lucidaot,cambria,xits,stixtwo,modern,pagella,termes,bonum,schola,dejavu} -\showmathcharacterssetbodyfonts{lucidaot,cambria,stixtwo,modern,pagella,termes,bonum,schola,ebgaramond,dejavu,modernlatin} +\showmathcharacterssetbodyfonts{lucida,cambria,stixtwo,modern,pagella,termes,bonum,schola,ebgaramond,dejavu}% ,modernlatin} % \showmathcharacterssetbodyfonts{newcomputermodern-book,lucidaot,cambria,stixtwo,modern,pagella,termes,bonum,schola,dejavu} % \showmathcharacterssetbodyfonts{newcomputermodern-book,stixtwo,modern,pagella,termes,bonum,schola,dejavu} % \showmathcharacterssetbodyfonts{newcomputermodern-book,lucidaot,cambria,stixtwo,modern,pagella,termes,schola,dejavu} @@ -551,7 +551,7 @@ \doifelse {\getdocumentargument{bodyfont}} {} { - \setupbodyfont[cambria, 12pt] + % \setupbodyfont[cambria, 12pt] % \setupbodyfont[modern, 12pt] % \setupbodyfont[lmvirtual, 12pt] % \setupbodyfont[pxvirtual, 12pt] @@ -566,7 +566,7 @@ % \setupbodyfont[bonum, 12pt] % \setupbodyfont[schola, 12pt] % \setupbodyfont[dejavu, 12pt] - % \setupbodyfont[lucidaot, 12pt] + \setupbodyfont[lucida, 12pt] % \setupbodyfont[newcomputermodern-book, 12pt] } { diff --git a/tex/generic/context/luatex/luatex-fonts-merged.lua b/tex/generic/context/luatex/luatex-fonts-merged.lua index 71dafd320..045081e2b 100644 --- a/tex/generic/context/luatex/luatex-fonts-merged.lua +++ b/tex/generic/context/luatex/luatex-fonts-merged.lua @@ -1,6 +1,6 @@ -- merged file : c:/data/develop/context/sources/luatex-fonts-merged.lua -- parent file : c:/data/develop/context/sources/luatex-fonts.lua --- merge date : 2023-01-15 13:53 +-- merge date : 2023-01-24 13:47 do -- begin closure to overcome local limits and interference -- cgit v1.2.3