diff options
50 files changed, 1694 insertions, 670 deletions
diff --git a/context/data/scite/context/lexers/data/scite-context-data-metafun.lua b/context/data/scite/context/lexers/data/scite-context-data-metafun.lua index 6f9723de1..b8aa47b38 100644 --- a/context/data/scite/context/lexers/data/scite-context-data-metafun.lua +++ b/context/data/scite/context/lexers/data/scite-context-data-metafun.lua @@ -1,4 +1,4 @@ return { - ["commands"]={ "transparency", "sqr", "log", "ln", "exp", "inv", "pow", "pi", "radian", "tand", "cotd", "sin", "cos", "tan", "cot", "atan", "asin", "acos", "invsin", "invcos", "invtan", "acosh", "asinh", "sinh", "cosh", "zmod", "paired", "tripled", "unitcircle", "fulldiamond", "unitdiamond", "fullsquare", "llcircle", "lrcircle", "urcircle", "ulcircle", "tcircle", "bcircle", "lcircle", "rcircle", "lltriangle", "lrtriangle", "urtriangle", "ultriangle", "uptriangle", "downtriangle", "lefttriangle", "righttriangle", "triangle", "smoothed", "cornered", "superellipsed", "randomized", "squeezed", "enlonged", "shortened", "punked", "curved", "unspiked", "simplified", "blownup", "stretched", "enlarged", "leftenlarged", "topenlarged", "rightenlarged", "bottomenlarged", "crossed", "laddered", "randomshifted", "interpolated", "paralleled", "cutends", "peepholed", "llenlarged", "lrenlarged", "urenlarged", "ulenlarged", "llmoved", "lrmoved", "urmoved", "ulmoved", "rightarrow", "leftarrow", "centerarrow", "boundingbox", "innerboundingbox", "outerboundingbox", "pushboundingbox", "popboundingbox", "bottomboundary", "leftboundary", "topboundary", "rightboundary", "xsized", "ysized", "xysized", "sized", "xyscaled", "intersection_point", "intersection_found", "penpoint", "bbwidth", "bbheight", "withshade", "withcircularshade", "withlinearshade", "defineshade", "shaded", "shadedinto", "withshadecolors", "withshadedomain", "withshademethod", "withshadefactor", "withshadevector", "withshadecenter", "withshadedirection", "withshadestep", "withshadefraction", "cmyk", "spotcolor", "multitonecolor", "namedcolor", "drawfill", "undrawfill", "inverted", "uncolored", "softened", "grayed", "greyed", "onlayer", "along", "graphictext", "loadfigure", "externalfigure", "figure", "register", "outlinetext", "checkedbounds", "checkbounds", "strut", "rule", "withmask", "bitmapimage", "colordecimals", "ddecimal", "dddecimal", "ddddecimal", "textext", "thetextext", "rawtextext", "textextoffset", "texbox", "thetexbox", "rawtexbox", "verbatim", "thelabel", "label", "autoalign", "transparent", "withtransparency", "property", "properties", "withproperties", "asgroup", "infont", "space", "crlf", "dquote", "percent", "SPACE", "CRLF", "DQUOTE", "PERCENT", "grayscale", "greyscale", "withgray", "withgrey", "colorpart", "readfile", "clearxy", "unitvector", "center", "epsed", "anchored", "originpath", "infinite", "break", "xstretched", "ystretched", "snapped", "pathconnectors", "function", "constructedfunction", "constructedpath", "constructedpairs", "straightfunction", "straightpath", "straightpairs", "curvedfunction", "curvedpath", "curvedpairs", "evenly", "oddly", "condition", "pushcurrentpicture", "popcurrentpicture", "arrowpath", "tensecircle", "roundedsquare", "colortype", "whitecolor", "blackcolor", "basiccolors", "complementary", "complemented", "normalfill", "normaldraw", "visualizepaths", "detailpaths", "naturalizepaths", "drawboundary", "drawwholepath", "drawpathonly", "visualizeddraw", "visualizedfill", "detaileddraw", "draworigin", "drawboundingbox", "drawpath", "drawpoint", "drawpoints", "drawcontrolpoints", "drawcontrollines", "drawpointlabels", "drawlineoptions", "drawpointoptions", "drawcontroloptions", "drawlabeloptions", "draworiginoptions", "drawboundoptions", "drawpathoptions", "resetdrawoptions", "undashed", "decorated", "redecorated", "undecorated", "passvariable", "passarrayvariable", "tostring", "format", "formatted", "startpassingvariable", "stoppassingvariable", "eofill", "eoclip", "nofill", "fillup", "eofillup", "area", "addbackground", "shadedup", "shadeddown", "shadedleft", "shadedright" }, + ["commands"]={ "transparency", "sqr", "log", "ln", "exp", "inv", "pow", "pi", "radian", "tand", "cotd", "sin", "cos", "tan", "cot", "atan", "asin", "acos", "invsin", "invcos", "invtan", "acosh", "asinh", "sinh", "cosh", "zmod", "paired", "tripled", "unitcircle", "fulldiamond", "unitdiamond", "fullsquare", "llcircle", "lrcircle", "urcircle", "ulcircle", "tcircle", "bcircle", "lcircle", "rcircle", "lltriangle", "lrtriangle", "urtriangle", "ultriangle", "uptriangle", "downtriangle", "lefttriangle", "righttriangle", "triangle", "smoothed", "cornered", "superellipsed", "randomized", "squeezed", "enlonged", "shortened", "punked", "curved", "unspiked", "simplified", "blownup", "stretched", "enlarged", "leftenlarged", "topenlarged", "rightenlarged", "bottomenlarged", "crossed", "laddered", "randomshifted", "interpolated", "paralleled", "cutends", "peepholed", "llenlarged", "lrenlarged", "urenlarged", "ulenlarged", "llmoved", "lrmoved", "urmoved", "ulmoved", "rightarrow", "leftarrow", "centerarrow", "boundingbox", "innerboundingbox", "outerboundingbox", "pushboundingbox", "popboundingbox", "bottomboundary", "leftboundary", "topboundary", "rightboundary", "xsized", "ysized", "xysized", "sized", "xyscaled", "intersection_point", "intersection_found", "penpoint", "bbwidth", "bbheight", "withshade", "withcircularshade", "withlinearshade", "defineshade", "shaded", "shadedinto", "withshadecolors", "withshadedomain", "withshademethod", "withshadefactor", "withshadevector", "withshadecenter", "withshadedirection", "withshadestep", "withshadefraction", "cmyk", "spotcolor", "multitonecolor", "namedcolor", "drawfill", "undrawfill", "inverted", "uncolored", "softened", "grayed", "greyed", "onlayer", "along", "graphictext", "loadfigure", "externalfigure", "figure", "register", "outlinetext", "checkedbounds", "checkbounds", "strut", "rule", "withmask", "bitmapimage", "colordecimals", "ddecimal", "dddecimal", "ddddecimal", "textext", "thetextext", "rawtextext", "textextoffset", "texbox", "thetexbox", "rawtexbox", "verbatim", "thelabel", "label", "autoalign", "transparent", "withtransparency", "property", "properties", "withproperties", "asgroup", "infont", "space", "crlf", "dquote", "percent", "SPACE", "CRLF", "DQUOTE", "PERCENT", "grayscale", "greyscale", "withgray", "withgrey", "colorpart", "readfile", "clearxy", "unitvector", "center", "epsed", "anchored", "originpath", "infinite", "break", "xstretched", "ystretched", "snapped", "pathconnectors", "function", "constructedfunction", "constructedpath", "constructedpairs", "straightfunction", "straightpath", "straightpairs", "curvedfunction", "curvedpath", "curvedpairs", "evenly", "oddly", "condition", "pushcurrentpicture", "popcurrentpicture", "arrowpath", "tensecircle", "roundedsquare", "colortype", "whitecolor", "blackcolor", "basiccolors", "complementary", "complemented", "resolvedcolor", "normalfill", "normaldraw", "visualizepaths", "detailpaths", "naturalizepaths", "drawboundary", "drawwholepath", "drawpathonly", "visualizeddraw", "visualizedfill", "detaileddraw", "draworigin", "drawboundingbox", "drawpath", "drawpoint", "drawpoints", "drawcontrolpoints", "drawcontrollines", "drawpointlabels", "drawlineoptions", "drawpointoptions", "drawcontroloptions", "drawlabeloptions", "draworiginoptions", "drawboundoptions", "drawpathoptions", "resetdrawoptions", "undashed", "decorated", "redecorated", "undecorated", "passvariable", "passarrayvariable", "tostring", "format", "formatted", "startpassingvariable", "stoppassingvariable", "eofill", "eoclip", "nofill", "fillup", "eofillup", "area", "addbackground", "shadedup", "shadeddown", "shadedleft", "shadedright" }, ["internals"]={ "nocolormodel", "greycolormodel", "graycolormodel", "rgbcolormodel", "cmykcolormodel", "shadefactor", "textextoffset", "normaltransparent", "multiplytransparent", "screentransparent", "overlaytransparent", "softlighttransparent", "hardlighttransparent", "colordodgetransparent", "colorburntransparent", "darkentransparent", "lightentransparent", "differencetransparent", "exclusiontransparent", "huetransparent", "saturationtransparent", "colortransparent", "luminositytransparent", "ahvariant", "ahdimple", "ahfactor", "metapostversion", "maxdimensions", "drawoptionsfactor" }, }
\ No newline at end of file diff --git a/context/data/scite/context/lexers/scite-context-lexer-mps.lua b/context/data/scite/context/lexers/scite-context-lexer-mps.lua index fa335eb3f..b4be44fe5 100644 --- a/context/data/scite/context/lexers/scite-context-lexer-mps.lua +++ b/context/data/scite/context/lexers/scite-context-lexer-mps.lua @@ -98,7 +98,8 @@ local primitive = token("primitive", exact_match(metapostprimitives)) local identifier = token("default", cstoken^1) local number = token("number", number) local grouping = token("grouping", S("()[]{}")) -- can be an option -local special = token("special", S("#()[]{}<>=:\"")) -- or else := <> etc split +local suffix = token("number", P("#@") + P("@#") + P("#")) +local special = token("special", P("#@") + P("@#") + S("#()[]{}<>=:\"")) -- or else := <> etc split local texlike = token("warning", P("\\") * cstokentex^1) local extra = token("extra", P("+-+") + P("++") + S("`~%^&_-+*/\'|\\")) @@ -134,6 +135,7 @@ metafunlexer._rules = { { "primitive", primitive }, { "luacall", luacall }, { "texstuff", texstuff }, + { "suffix", suffix }, { "identifier", identifier }, { "number", number }, { "quoted", quoted }, diff --git a/context/data/scite/context/scite-context-data-metafun.properties b/context/data/scite/context/scite-context-data-metafun.properties index d28a45aa5..b5d277dc7 100644 --- a/context/data/scite/context/scite-context-data-metafun.properties +++ b/context/data/scite/context/scite-context-data-metafun.properties @@ -42,17 +42,17 @@ constructedpath constructedpairs straightfunction straightpath straightpairs \ curvedfunction curvedpath curvedpairs evenly oddly \ condition pushcurrentpicture popcurrentpicture arrowpath tensecircle \ roundedsquare colortype whitecolor blackcolor basiccolors \ -complementary complemented normalfill normaldraw visualizepaths \ -detailpaths naturalizepaths drawboundary drawwholepath drawpathonly \ -visualizeddraw visualizedfill detaileddraw draworigin drawboundingbox \ -drawpath drawpoint drawpoints drawcontrolpoints drawcontrollines \ -drawpointlabels drawlineoptions drawpointoptions drawcontroloptions drawlabeloptions \ -draworiginoptions drawboundoptions drawpathoptions resetdrawoptions undashed \ -decorated redecorated undecorated passvariable passarrayvariable \ -tostring format formatted startpassingvariable stoppassingvariable \ -eofill eoclip nofill fillup eofillup \ -area addbackground shadedup shadeddown shadedleft \ -shadedright +complementary complemented resolvedcolor normalfill normaldraw \ +visualizepaths detailpaths naturalizepaths drawboundary drawwholepath \ +drawpathonly visualizeddraw visualizedfill detaileddraw draworigin \ +drawboundingbox drawpath drawpoint drawpoints drawcontrolpoints \ +drawcontrollines drawpointlabels drawlineoptions drawpointoptions drawcontroloptions \ +drawlabeloptions draworiginoptions drawboundoptions drawpathoptions resetdrawoptions \ +undashed decorated redecorated undecorated passvariable \ +passarrayvariable tostring format formatted startpassingvariable \ +stoppassingvariable eofill eoclip nofill fillup \ +eofillup area addbackground shadedup shadeddown \ +shadedleft shadedright keywordclass.metafun.internals=\ nocolormodel greycolormodel graycolormodel rgbcolormodel \ diff --git a/metapost/context/base/mpiv/mp-chem.mpiv b/metapost/context/base/mpiv/mp-chem.mpiv index b861d3f12..161568b02 100644 --- a/metapost/context/base/mpiv/mp-chem.mpiv +++ b/metapost/context/base/mpiv/mp-chem.mpiv @@ -50,24 +50,34 @@ pair chem_pair[], % scratch chem_sb_pair, chem_sb_pair.m, chem_sb_pair.p, chem_sb_pair.b ; + + picture - chem_pic, % scratch + chem_pic; % scratch % The use of dashpattern is found to dot the starting point with chem_sb_dash.m... %chem_sb_dash, chem_sb_dash.m, chem_sb_dash.p, chem_sb_dash.b, + +% nice hack but now redone +% +% picture chem_axis_color ; +% +% chem_axis_color := image(draw origin withcolor axiscolor) ; % so we handle all color models +% +% withpen pencircle scaled chem_axis_rulethickness withcolor colorpart(chem_axis_color) ; + +string chem_axis_color ; transform chem_t ; % scratch -color lightblue ; lightblue := (173/255,216/255,230/255) ; - % debugging boolean chem_trace_nesting ; chem_trace_nesting := false ; boolean chem_trace_text ; chem_trace_text := false ; boolean chem_trace_boundingbox ; chem_trace_boundingbox := false ; -chem_axis_color := image(draw origin withcolor lightblue) ; +chem_axis_color := "lightblue" ; chem_setting_axis := false ; chem_axis_rulethickness := 1pt ; chem_emwidth := 10pt ; % EmWidth or \the\emwidth does not work... @@ -333,7 +343,7 @@ def chem_start_structure(expr i, l, r, t, b, rotation, unit, bond, scale, offset chem_setting_offset := offset ; chem_setting_axis := if boolean axis : axis else : (axis<>0) fi ; chem_axis_rulethickness := .75*(rulethickness) ; % axis 50% thinner than frame and bonds. - chem_axis_color := image(draw origin withcolor axiscolor) ; % so we handle all color models + chem_axis_color := axiscolor ; chem_reset ; enddef ; @@ -367,24 +377,24 @@ vardef chem_stop_structure = % draw the axes to the bounding box of the entire structure, % not necessarily the bounding box of the final figure draw (l,0) -- (r,0) - withpen pencircle scaled chem_axis_rulethickness withcolor colorpart(chem_axis_color) ; + withpen pencircle scaled chem_axis_rulethickness withcolor chem_axis_color ; draw (0,b) -- (0,t) - withpen pencircle scaled chem_axis_rulethickness withcolor colorpart(chem_axis_color) ; + withpen pencircle scaled chem_axis_rulethickness withcolor chem_axis_color ; for i = 0 step chem_num0 until r : draw (i,-chem_num1) -- (i,chem_num1) - withpen pencircle scaled chem_axis_rulethickness withcolor colorpart(chem_axis_color) ; + withpen pencircle scaled chem_axis_rulethickness withcolor chem_axis_color ; endfor for i = 0 step -chem_num0 until l : draw (i,-chem_num1) -- (i,chem_num1) - withpen pencircle scaled chem_axis_rulethickness withcolor colorpart(chem_axis_color) ; + withpen pencircle scaled chem_axis_rulethickness withcolor chem_axis_color ; endfor for i = 0 step chem_num0 until t : draw (-chem_num1,i) -- (chem_num1,i) - withpen pencircle scaled chem_axis_rulethickness withcolor colorpart(chem_axis_color) ; + withpen pencircle scaled chem_axis_rulethickness withcolor chem_axis_color ; endfor for i = 0 step -chem_num0 until b : draw (-chem_num1,i) -- (chem_num1,i) - withpen pencircle scaled chem_axis_rulethickness withcolor colorpart(chem_axis_color) ; + withpen pencircle scaled chem_axis_rulethickness withcolor chem_axis_color ; endfor addto currentpicture also chem_pic ; fi ; @@ -406,9 +416,8 @@ vardef chem_stop_component = enddef ; vardef chem_pb = % PB : if chem_trace_nesting : - draw boundingbox currentpicture - withpen pencircle scaled 1mm withcolor colorpart(chem_axis_color) ; - draw origin withpen pencircle scaled 2mm withcolor colorpart(chem_axis_color) ; + draw boundingbox currentpicture withpen pencircle scaled 1mm withcolor chem_axis_color ; + draw origin withpen pencircle scaled 2mm withcolor chem_axis_color ; fi ; chem_doing_pb := true ; enddef ; @@ -507,21 +516,21 @@ enddef ; vardef chem_draw (expr what, r, c) (text extra) = draw what withpen pencircle scaled r - withcolor c %\MPcolor{c} + withcolor c extra ; enddef ; vardef chem_fill (expr what, r, c) (text extra) = fill what withpen pencircle scaled r - withcolor c %\MPcolor{c} + withcolor c extra ; enddef ; vardef chem_drawarrow (expr what, r, c) (text extra) = drawarrow what withpen pencircle scaled r - withcolor c %\MPcolor{c} + withcolor c extra ; enddef ; @@ -1691,14 +1700,14 @@ vardef chem_line (suffix $) (expr f, t, r, c) = % LINE draw if f=t : origin else : chem_marked(f) fi -- chem_marked(t) % no chem_transformed withpen pencircle scaled r - withcolor c %\MPcolor{c} + withcolor c enddef ; vardef chem_dash (suffix $) (expr f, t, r, c) = % DASH draw if f=t : origin else : chem_marked(f) fi -- chem_marked(t) % no chem_transformed withpen pencircle scaled r - withcolor c %\MPcolor{c} + withcolor c dashed evenly ; enddef ; @@ -1706,7 +1715,7 @@ vardef chem_arrow (suffix $) (expr f, t, r, c) = % ARROW drawarrow if f=t : origin else : chem_marked(f) fi -- chem_marked(t) % no chem_transformed withpen pencircle scaled r - withcolor c %\MPcolor{c} + withcolor c enddef ; diff --git a/metapost/context/base/mpiv/mp-mlib.mpiv b/metapost/context/base/mpiv/mp-mlib.mpiv index cac84a6fd..689995df7 100644 --- a/metapost/context/base/mpiv/mp-mlib.mpiv +++ b/metapost/context/base/mpiv/mp-mlib.mpiv @@ -54,6 +54,7 @@ vardef transparency_alternative_to_number(expr name) = fi enddef ; + def namedcolor (expr n) = 1 withprescript "sp_type=named" @@ -1534,3 +1535,12 @@ def nofill text t = fill t withpostscript "collect" enddef ; % def withrule expr r = % if (t = "even-odd") or (t = "evenodd") : withpostscript "evenodd" fi % enddef ; + +% so we can do: withcolor "red" + +def resolvedcolor(expr s) = + % lua.mp.namedcolor(s) % conflicts with macro namedcolor + % lua.mp.NamedColor(s) % okay but, can also be + % lua.mp("NamedColor",s) % which gives expansion mess + runscript("mp.NamedColor('" & s & "')") % faster anyway +enddef ; diff --git a/metapost/context/base/mpiv/mp-step.mpiv b/metapost/context/base/mpiv/mp-step.mpiv index 27bcffcdc..496eb0b20 100644 --- a/metapost/context/base/mpiv/mp-step.mpiv +++ b/metapost/context/base/mpiv/mp-step.mpiv @@ -11,7 +11,8 @@ %C therefore copyrighted by \PRAGMA. See licen-en.pdf for %C details. -% step prefixes .. no save needed +% maybe todo: step prefixes .. no save needed +% not todo : make it unreadable by lots of suffix compaction if known context_cell : endinput ; fi ; diff --git a/metapost/context/base/mpiv/mp-tool.mpiv b/metapost/context/base/mpiv/mp-tool.mpiv index 76459d25c..d5793d086 100644 --- a/metapost/context/base/mpiv/mp-tool.mpiv +++ b/metapost/context/base/mpiv/mp-tool.mpiv @@ -143,6 +143,8 @@ vardef colordecimals primary c = decimal cyanpart c & ":" & decimal magentapart c & ":" & decimal yellowpart c & ":" & decimal blackpart c elseif rgbcolor c : decimal redpart c & ":" & decimal greenpart c & ":" & decimal bluepart c + elseif string c: + colordecimals resolvedcolor(c) else : decimal c fi @@ -817,6 +819,16 @@ enddef ; %D Some colors. +def resolvedcolor(expr s) = + .5white +enddef ; + +let normalwithcolor = withcolor ; + +def withcolor primary c = + normalwithcolor if string c : resolvedcolor(c) else : c fi +enddef ; + def colortype(expr c) = if cmykcolor c : cmykcolor elseif rgbcolor c : rgbcolor else : grayscale fi enddef ; @@ -829,24 +841,26 @@ vardef blackcolor expr c = if cmykcolor c : (0,0,0,1) elseif rgbcolor c : (0,0,0) else : 0 fi enddef ; -vardef complementary expr c = ( - if cmykcolor c : (1,1,1,1) - - elseif rgbcolor c : (1,1,1) - - elseif pair c : (1,1) - - elseif numeric c : 1 - - fi c -) enddef ; +vardef complementary expr c = + if cmykcolor c : (1,1,1,1) - c + elseif rgbcolor c : (1,1,1) - c + elseif pair c : (1,1) - c + elseif numeric c : 1 - c + elseif string c : complementary resolvedcolor(c) + fi +enddef ; vardef complemented expr c = save m ; if cmykcolor c : m := max(cyanpart c, magentapart c, yellowpart c, blackpart c) ; - ( (m,m,m,m) - + (m,m,m,m) - c elseif rgbcolor c : m := max(redpart c, greenpart c, bluepart c) ; - ( (m,m,m) - + (m,m,m) - c elseif pair c : m := max(xpart c, ypart c) ; - ( (m,m) - - elseif numeric c : ( m - - fi c ) + (m,m) - c + elseif numeric c : m - c + elseif string c : complemented resolvedcolor(c) + fi enddef ; %D Well, this is the dangerous and naive version: @@ -1014,6 +1028,8 @@ primarydef p randomized s = ( else : ((uniformdeviate s) * p) fi + elseif string p : + resolvedcolor(p) randomized s else : p + uniformdeviate s fi @@ -1699,6 +1715,8 @@ vardef grayed primary p = tripled(.30*(1-cyanpart i)+.59*(1-magentapart i)+.11*(1-yellowpart i)+blackpart i) elseif greycolor p : p + elseif string p : + grayed resolvedcolor(p) elseif picture p : image ( for i within p : @@ -1854,14 +1872,16 @@ inner end ; % this will be redone (when needed) using scripts and backend handling -let normalwithcolor = withcolor ; +let mfun_remap_colors_normalwithcolor = normalwithcolor ; def remapcolors = - def withcolor primary c = normalwithcolor remappedcolor(c) enddef ; + def normalwithcolor primary c = + mfun_remap_colors_normalwithcolor remappedcolor(c) + enddef ; enddef ; def normalcolors = - let withcolor = normalwithcolor ; + let normalwithcolor = mfun_remap_colors_normalwithcolor ; enddef ; def resetcolormap = diff --git a/scripts/context/lua/mtxrun.lua b/scripts/context/lua/mtxrun.lua index 6f9e8239b..f1e1ab345 100644 --- a/scripts/context/lua/mtxrun.lua +++ b/scripts/context/lua/mtxrun.lua @@ -7065,7 +7065,7 @@ do -- create closure to overcome 200 locals limit package.loaded["util-prs"] = package.loaded["util-prs"] or true --- original size: 23411, stripped down to: 16177 +-- original size: 23253, stripped down to: 16177 if not modules then modules={} end modules ['util-prs']={ version=1.001, @@ -18783,8 +18783,8 @@ end -- of closure -- used libraries : l-lua.lua l-package.lua l-lpeg.lua l-function.lua l-string.lua l-table.lua l-io.lua l-number.lua l-set.lua l-os.lua l-file.lua l-gzip.lua l-md5.lua l-url.lua l-dir.lua l-boolean.lua l-unicode.lua l-math.lua util-str.lua util-tab.lua util-fil.lua util-sac.lua util-sto.lua util-prs.lua util-fmt.lua trac-set.lua trac-log.lua trac-inf.lua trac-pro.lua util-lua.lua util-deb.lua util-mrg.lua util-tpl.lua util-env.lua luat-env.lua lxml-tab.lua lxml-lpt.lua lxml-mis.lua lxml-aux.lua lxml-xml.lua trac-xml.lua data-ini.lua data-exp.lua data-env.lua data-tmp.lua data-met.lua data-res.lua data-pre.lua data-inp.lua data-out.lua data-fil.lua data-con.lua data-use.lua data-zip.lua data-tre.lua data-sch.lua data-lua.lua data-aux.lua data-tmf.lua data-lst.lua util-lib.lua luat-sta.lua luat-fmt.lua -- skipped libraries : - --- original bytes : 799032 --- stripped bytes : 290027 +-- original bytes : 798874 +-- stripped bytes : 289869 -- end library merge diff --git a/scripts/context/stubs/mswin/mtxrun.lua b/scripts/context/stubs/mswin/mtxrun.lua index 6f9e8239b..f1e1ab345 100644 --- a/scripts/context/stubs/mswin/mtxrun.lua +++ b/scripts/context/stubs/mswin/mtxrun.lua @@ -7065,7 +7065,7 @@ do -- create closure to overcome 200 locals limit package.loaded["util-prs"] = package.loaded["util-prs"] or true --- original size: 23411, stripped down to: 16177 +-- original size: 23253, stripped down to: 16177 if not modules then modules={} end modules ['util-prs']={ version=1.001, @@ -18783,8 +18783,8 @@ end -- of closure -- used libraries : l-lua.lua l-package.lua l-lpeg.lua l-function.lua l-string.lua l-table.lua l-io.lua l-number.lua l-set.lua l-os.lua l-file.lua l-gzip.lua l-md5.lua l-url.lua l-dir.lua l-boolean.lua l-unicode.lua l-math.lua util-str.lua util-tab.lua util-fil.lua util-sac.lua util-sto.lua util-prs.lua util-fmt.lua trac-set.lua trac-log.lua trac-inf.lua trac-pro.lua util-lua.lua util-deb.lua util-mrg.lua util-tpl.lua util-env.lua luat-env.lua lxml-tab.lua lxml-lpt.lua lxml-mis.lua lxml-aux.lua lxml-xml.lua trac-xml.lua data-ini.lua data-exp.lua data-env.lua data-tmp.lua data-met.lua data-res.lua data-pre.lua data-inp.lua data-out.lua data-fil.lua data-con.lua data-use.lua data-zip.lua data-tre.lua data-sch.lua data-lua.lua data-aux.lua data-tmf.lua data-lst.lua util-lib.lua luat-sta.lua luat-fmt.lua -- skipped libraries : - --- original bytes : 799032 --- stripped bytes : 290027 +-- original bytes : 798874 +-- stripped bytes : 289869 -- end library merge diff --git a/scripts/context/stubs/unix/mtxrun b/scripts/context/stubs/unix/mtxrun index 6f9e8239b..f1e1ab345 100644 --- a/scripts/context/stubs/unix/mtxrun +++ b/scripts/context/stubs/unix/mtxrun @@ -7065,7 +7065,7 @@ do -- create closure to overcome 200 locals limit package.loaded["util-prs"] = package.loaded["util-prs"] or true --- original size: 23411, stripped down to: 16177 +-- original size: 23253, stripped down to: 16177 if not modules then modules={} end modules ['util-prs']={ version=1.001, @@ -18783,8 +18783,8 @@ end -- of closure -- used libraries : l-lua.lua l-package.lua l-lpeg.lua l-function.lua l-string.lua l-table.lua l-io.lua l-number.lua l-set.lua l-os.lua l-file.lua l-gzip.lua l-md5.lua l-url.lua l-dir.lua l-boolean.lua l-unicode.lua l-math.lua util-str.lua util-tab.lua util-fil.lua util-sac.lua util-sto.lua util-prs.lua util-fmt.lua trac-set.lua trac-log.lua trac-inf.lua trac-pro.lua util-lua.lua util-deb.lua util-mrg.lua util-tpl.lua util-env.lua luat-env.lua lxml-tab.lua lxml-lpt.lua lxml-mis.lua lxml-aux.lua lxml-xml.lua trac-xml.lua data-ini.lua data-exp.lua data-env.lua data-tmp.lua data-met.lua data-res.lua data-pre.lua data-inp.lua data-out.lua data-fil.lua data-con.lua data-use.lua data-zip.lua data-tre.lua data-sch.lua data-lua.lua data-aux.lua data-tmf.lua data-lst.lua util-lib.lua luat-sta.lua luat-fmt.lua -- skipped libraries : - --- original bytes : 799032 --- stripped bytes : 290027 +-- original bytes : 798874 +-- stripped bytes : 289869 -- end library merge diff --git a/scripts/context/stubs/win64/mtxrun.lua b/scripts/context/stubs/win64/mtxrun.lua index 6f9e8239b..f1e1ab345 100644 --- a/scripts/context/stubs/win64/mtxrun.lua +++ b/scripts/context/stubs/win64/mtxrun.lua @@ -7065,7 +7065,7 @@ do -- create closure to overcome 200 locals limit package.loaded["util-prs"] = package.loaded["util-prs"] or true --- original size: 23411, stripped down to: 16177 +-- original size: 23253, stripped down to: 16177 if not modules then modules={} end modules ['util-prs']={ version=1.001, @@ -18783,8 +18783,8 @@ end -- of closure -- used libraries : l-lua.lua l-package.lua l-lpeg.lua l-function.lua l-string.lua l-table.lua l-io.lua l-number.lua l-set.lua l-os.lua l-file.lua l-gzip.lua l-md5.lua l-url.lua l-dir.lua l-boolean.lua l-unicode.lua l-math.lua util-str.lua util-tab.lua util-fil.lua util-sac.lua util-sto.lua util-prs.lua util-fmt.lua trac-set.lua trac-log.lua trac-inf.lua trac-pro.lua util-lua.lua util-deb.lua util-mrg.lua util-tpl.lua util-env.lua luat-env.lua lxml-tab.lua lxml-lpt.lua lxml-mis.lua lxml-aux.lua lxml-xml.lua trac-xml.lua data-ini.lua data-exp.lua data-env.lua data-tmp.lua data-met.lua data-res.lua data-pre.lua data-inp.lua data-out.lua data-fil.lua data-con.lua data-use.lua data-zip.lua data-tre.lua data-sch.lua data-lua.lua data-aux.lua data-tmf.lua data-lst.lua util-lib.lua luat-sta.lua luat-fmt.lua -- skipped libraries : - --- original bytes : 799032 --- stripped bytes : 290027 +-- original bytes : 798874 +-- stripped bytes : 289869 -- end library merge diff --git a/tex/context/base/context-version.pdf b/tex/context/base/context-version.pdf Binary files differindex 54e343a8c..51bce134d 100644 --- a/tex/context/base/context-version.pdf +++ b/tex/context/base/context-version.pdf diff --git a/tex/context/base/mkiv/chem-str.lua b/tex/context/base/mkiv/chem-str.lua index 0300aae02..9cf12c4c1 100644 --- a/tex/context/base/mkiv/chem-str.lua +++ b/tex/context/base/mkiv/chem-str.lua @@ -57,7 +57,6 @@ local v_fit = variables.fit local v_on = variables.on local v_none = variables.none -local mpnamedcolor = attributes.colors.mpnamedcolor local topoints = number.topoints local todimen = string.todimen @@ -324,12 +323,12 @@ local pattern = -- print(lpegmatch(pattern,"RZ13=x")) -- 1 RZ false false table x local f_initialize = 'if unknown context_chem : input mp-chem.mpiv ; fi ;' -local f_start_structure = formatters['chem_start_structure(%s,%s,%s,%s,%s,%s,%s,%s,%s,%s,%s,%s,%s);'] +local f_start_structure = formatters['chem_start_structure(%s,%s,%s,%s,%s,%s,%s,%s,%s,%s,%s,%s,%q);'] local f_set_trace_bounds = formatters['chem_trace_boundingbox := %l ;'] local f_stop_structure = 'chem_stop_structure;' local f_start_component = 'chem_start_component;' local f_stop_component = 'chem_stop_component;' -local f_line = formatters['chem_%s%s(%s,%s,%s,%s,%s);'] +local f_line = formatters['chem_%s%s(%s,%s,%s,%s,%q);'] local f_set = formatters['chem_set(%s);'] local f_number = formatters['chem_%s%s(%s,%s,"\\chemicaltext{%s}");'] local f_text = f_number @@ -337,8 +336,6 @@ local f_empty_normal = formatters['chem_%s(%s,%s,"");'] local f_empty_center = formatters['chem_c%s(%s,%s,"");'] local f_transform = formatters['chem_%s(%s,%s,%s);'] -local prepareMPvariable = commands and commands.prepareMPvariable - local function process(level,spec,text,n,rulethickness,rulecolor,offset,default_variant) insert(stack,{ spec = spec, text = text, n = n }) local txt = #stack @@ -379,7 +376,7 @@ local function process(level,spec,text,n,rulethickness,rulecolor,offset,default_ if t == v_default or t == v_normal or t == "" then rulecolor = saved_rulecolor elseif t then - rulecolor = mpnamedcolor(t) + rulecolor = t end elseif operation == "rulethickness" then local t = text @@ -685,8 +682,8 @@ function chemistry.start(settings) local unit = settings.unit or 655360 local bondlength = settings.factor or 3 local rulethickness = settings.rulethickness or 65536 - local rulecolor = settings.rulecolor or "" - local axiscolor = settings.framecolor or "" + local rulecolor = settings.rulecolor or "black" + local axiscolor = settings.framecolor or "black" local scale = settings.scale or "normal" local rotation = settings.rotation or 0 local offset = settings.offset or 0 @@ -751,7 +748,7 @@ function chemistry.start(settings) chemistry.structures, left, right, top, bottom, rotation, topoints(unit), bondlength, scale, topoints(offset), - tostring(settings.axis == v_on), topoints(rulethickness), tostring(axiscolor) + tostring(settings.axis == v_on), topoints(rulethickness), axiscolor ) metacode[#metacode+1] = f_set_trace_bounds(trace_boundingbox) ; -- diff --git a/tex/context/base/mkiv/chem-str.mkiv b/tex/context/base/mkiv/chem-str.mkiv index a0b0a9327..ec2067f60 100644 --- a/tex/context/base/mkiv/chem-str.mkiv +++ b/tex/context/base/mkiv/chem-str.mkiv @@ -172,8 +172,8 @@ scale {\chemicalparameter\c!scale}% rotation {\chemicalparameter\c!rotation}% symalign {\chemicalparameter\c!symalign}% - axis {\chemicalparameter\c!axis}% - framecolor {\MPcolor{\chemicalparameter\c!framecolor}}% + axis {\chemicalparameter\c!axis}% was \MPcolor{...} + framecolor {\chemicalparameter\c!framecolor}% rulethickness {\number\dimexpr\chemicalparameter\c!rulethickness}% offset {\number\dimexpr\chemicalparameter\c!offset}% unit {\number\dimexpr\chemicalparameter\c!unit}% @@ -228,7 +228,7 @@ {#2}% {\detokenize{#3}}% {\the\dimexpr\chemicalparameter\c!rulethickness}% todo: scaled points - {\MPcolor{\chemicalparameter\c!rulecolor}}% % we can precalculate this for speedup + {\chemicalparameter\c!rulecolor}% \relax \ignorespaces} @@ -237,7 +237,7 @@ {#1}% {\detokenize{#2}}% {\the\dimexpr\chemicalparameter\c!rulethickness}% todo: scaled points - {\MPcolor{\chemicalparameter\c!rulecolor}}% % we can precalculate this for speedup + {\chemicalparameter\c!rulecolor}% \relax \ignorespaces} diff --git a/tex/context/base/mkiv/colo-ini.lua b/tex/context/base/mkiv/colo-ini.lua index 1a055242b..a2e761eae 100644 --- a/tex/context/base/mkiv/colo-ini.lua +++ b/tex/context/base/mkiv/colo-ini.lua @@ -26,6 +26,9 @@ local context = context local commands = commands local implement = interfaces.implement +local getnamespace = interfaces.getnamespace + +local mark = utilities.storage.mark local settings_to_hash_strict = utilities.parsers.settings_to_hash_strict @@ -33,8 +36,11 @@ local colors = attributes.colors local transparencies = attributes.transparencies local colorintents = attributes.colorintents local registrations = backends.registrations + local texsetattribute = tex.setattribute local texgetattribute = tex.getattribute +local texgetcount = tex.getcount +local texgettoks = tex.gettoks local a_color = attributes.private('color') local a_transparency = attributes.private('transparency') @@ -46,12 +52,30 @@ local attributes_list = attributes.list local colorvalues = colors.values local transparencyvalues = transparencies.values -colors.sets = colors.sets or { } -- sets are mostly used for +colors.sets = mark(colors.sets or { }) -- sets are mostly used for local colorsets = colors.sets -- showing lists of defined local colorset = { } -- colors colorsets.default = colorset +local valid = mark(colors.valid or { }) +colors.valid = valid +local counts = mark(colors.counts or { }) +colors.counts = counts + +storage.register("attributes/colors/sets", colorsets, "attributes.colors.sets") +storage.register("attributes/colors/valid", valid, "attributes.colors.valid") +storage.register("attributes/colors/counts", counts, "attributes.colors.counts") -storage.register("attributes/colors/sets",colorsets,"attributes.colors.sets") +local function synccolor(name) + valid[name] = true +end + +local function synccolorclone(name,clone) + valid[name] = clone +end + +local function synccolorcount(name,n) + counts[name] = n +end local stack = { } @@ -585,10 +609,112 @@ local function mpcolor(model,ca,ta,default) return formatters["(%s,%s,%s)"](default,default,default) end +-- local function mpnamedcolor(name) +-- return mpcolor(texgetattribute(a_colorspace),l_color[name] or l_color.black,l_transparency[name] or false) +-- end + +local colornamespace = getnamespace("colornumber") +local paletnamespace = getnamespace("colorpalet") + +-- local function mpnamedcolor(name) +-- local prefix = texgettoks("t_colo_prefix") +-- local cn +-- if prefix ~= "" then +-- local v = valid[prefix..name] +-- if not v then +-- local n = paletnamespace .. prefix .. name +-- local p = valid[n] +-- if p == true then +-- cn = colornamespace .. n +-- elseif p then +-- cn = colornamespace .. p +-- else +-- cn = colornamespace .. name +-- end +-- elseif v == true then +-- cn = colornamespace .. paletnamespace .. prefix .. name +-- else +-- cn = colornamespace .. v +-- end +-- elseif valid[name] then +-- cn = colornamespace .. name +-- else +-- return mpcolor(texgetattribute(a_colorspace),l_color.black) +-- end +-- -- return mpcolor(texgetattribute(a_colorspace),l_color[name] or l_color.black) +-- return mpcolor(texgetattribute(a_colorspace),texgetcount(cn),l_transparency[name]) +-- end + +-- local function mpnamedcolor(name) +-- local colorspace = texgetattribute(a_colorspace) +-- local prefix = texgettoks("t_colo_prefix") +-- local cn +-- if prefix ~= "" then +-- local v = valid[prefix..name] +-- if not v then +-- local n = paletnamespace .. prefix .. name +-- local p = valid[n] +-- if p == true then +-- cn = n +-- elseif p then +-- cn = p +-- else +-- cn = name +-- end +-- elseif v == true then +-- cn = paletnamespace .. prefix .. name +-- else +-- cn = v +-- end +-- elseif valid[name] then +-- cn = name +-- else +-- return mpcolor(colorspace,l_color.black) +-- end +-- cn = counts[cn] +-- cn = cn and texgetcount(cn) or l_color[name] or l_color.black -- fall back to old method +-- return mpcolor(colorspace,cn,l_transparency[name]) +-- end + local function mpnamedcolor(name) - return mpcolor(texgetattribute(a_colorspace),l_color[name] or l_color.black) + local space = texgetattribute(a_colorspace) + local prefix = texgettoks("t_colo_prefix") + local color + if prefix ~= "" then + color = valid[prefix..name] + if not color then + local n = paletnamespace .. prefix .. name + color = valid[n] + if not color then + color = name + elseif color == true then + color = n + end + elseif color == true then + color = paletnamespace .. prefix .. name + end + elseif valid[name] then + color = name + else + return mpcolor(space,l_color.black) + end + color = counts[color] + if color then + color = texgetcount(color) + else + color = l_color[name] -- fall back on old method + end + if color then + return mpcolor(space,color,l_transparency[name]) + else + return mpcolor(space,l_color.black) + end end +-- mp.NamedColor = function(str) +-- mpprint(mpnamedcolor(str)) +-- end + local function mpoptions(model,ca,ta,default) -- will move to mlib-col return formatters["withcolor %s"](mpcolor(model,ca,ta,default)) end @@ -869,6 +995,24 @@ end local setcolormodel = colors.setmodel implement { + name = "synccolorcount", + actions = synccolorcount, + arguments = { "string", "integer" } +} + +implement { + name = "synccolor", + actions = synccolor, + arguments = "string", +} + +implement { + name = "synccolorclone", + actions = synccolorclone, + arguments = { "string", "string" }, +} + +implement { name = "setcolormodel", arguments = { "string", "boolean" }, actions = function(model,weight) diff --git a/tex/context/base/mkiv/colo-ini.mkiv b/tex/context/base/mkiv/colo-ini.mkiv index 26208edd4..f85f74c3a 100644 --- a/tex/context/base/mkiv/colo-ini.mkiv +++ b/tex/context/base/mkiv/colo-ini.mkiv @@ -21,6 +21,17 @@ %D This module implements color. Since \MKII\ and \MKIV\ use a completely %D different approach, this module only implements a few generic mechanisms. +\installcorenamespace{color} +\installcorenamespace{colorattribute} +\installcorenamespace{transparencyattribute} +\installcorenamespace{colorsetter} +\installcorenamespace{transparencysetter} +\installcorenamespace{colorpaletspecification} +\installcorenamespace{colorpalet} +\installcorenamespace{colorstack} +\installcorenamespace{colorconversions} +\installcorenamespace{colornumber} + \registerctxluafile{colo-ini}{1.000} \registerctxluafile{colo-icc}{1.000} @@ -58,16 +69,6 @@ \let\currentcolorpalet \empty \let\currentcolorprefix\empty % \currentcolorpalet: -\installcorenamespace{color} -\installcorenamespace{colorattribute} -\installcorenamespace{transparencyattribute} -\installcorenamespace{colorsetter} -\installcorenamespace{transparencysetter} -\installcorenamespace{colorpaletspecification} -\installcorenamespace{colorpalet} -\installcorenamespace{colorstack} -\installcorenamespace{colorconversions} - %D \macros %D {definecolor,defineglobalcolor,definenamedcolor,definespotcolor,definemultitonecolor, %D definetransparency} @@ -466,17 +467,37 @@ \unexpanded\def\setuppalet {\dosingleempty\colo_palets_setup} +% \def\colo_palets_setup[#1]% +% {\edef\currentcolorpalet{#1}% +% \ifx\currentcolorpalet\empty +% % seems to be a reset +% \let\currentcolorprefix\empty +% \else\ifcsname\??paletlist\currentcolorpalet\endcsname +% \edef\currentcolorprefix{#1:}% +% \else +% \colo_helpers_show_message\m!colors7\currentcolorpalet +% \let\currentcolorpalet\empty +% \let\currentcolorprefix\empty +% \fi\fi +% \the\everysetuppalet +% \colo_helpers_initialize_maintextcolor} + +\newtoks\t_colo_prefix % used in mp interface + \def\colo_palets_setup[#1]% {\edef\currentcolorpalet{#1}% \ifx\currentcolorpalet\empty % seems to be a reset \let\currentcolorprefix\empty + \t_colo_prefix\emptytoks \else\ifcsname\??paletlist\currentcolorpalet\endcsname \edef\currentcolorprefix{#1:}% + \t_colo_prefix\expandafter{\currentcolorprefix}% \else \colo_helpers_show_message\m!colors7\currentcolorpalet \let\currentcolorpalet\empty \let\currentcolorprefix\empty + \t_colo_prefix\emptytoks \fi\fi \the\everysetuppalet \colo_helpers_initialize_maintextcolor} @@ -732,6 +753,23 @@ % todo: check if color is overloading a non-color command +% \let\colo_basics_synchronize\gobbleoneargument % used in mp interface +% \let\colo_basics_inherit \gobbletwoarguments % used in mp interface + +\def\colo_basics_allocate#1% + {\expandafter\newcount\csname\??colornumber#1\endcsname + \clf_synccolorcount{#1}\c_syst_last_allocated_count} + +\def\colo_basics_synchronize#1% + {\ifcsname\??colornumber#1\endcsname\else + \colo_basics_allocate{#1}% + \fi + \clf_synccolor{#1}% + %\csname\??colornumber#1\endcsname\csname\??colorattribute#1\endcsname + \lastnamedcs\csname\??colorattribute#1\endcsname} + +\let\colo_basics_inherit\clf_synccolorclone + \newcount\c_colo_protection \unexpanded\def\startprotectedcolors @@ -742,30 +780,35 @@ \def\colo_basics_define[#1][#2]% {\clf_defineprocesscolorlocal{#1}{#2}\v_colo_freeze_state\relax + \colo_basics_synchronize{#1}% \ifcase\c_colo_protection \unexpanded\setvalue{#1}{\colo_helpers_activate{#1}}% \fi} \def\colo_basics_define_global[#1][#2]% {\clf_defineprocesscolorglobal{#1}{#2}\v_colo_freeze_state\relax + \colo_basics_synchronize{#1}% \ifcase\c_colo_protection \unexpanded\setgvalue{#1}{\colo_helpers_activate{#1}}% \fi} \def\colo_basics_define_named[#1][#2]% currently same as define {\clf_defineprocesscolorlocal{#1}{#2}\v_colo_freeze_state\relax + \colo_basics_synchronize{#1}% \ifcase\c_colo_protection \unexpanded\setvalue{#1}{\colo_helpers_activate{#1}}% \fi} \def\dodefinefastcolor[#1][#2]% still not fast but ok (might change) {\clf_defineprocesscolorlocal{#1}{#2}\v_colo_freeze_state\relax + \colo_basics_synchronize{#1}% \ifcase\c_colo_protection \unexpanded\setvalue{#1}{\colo_helpers_activate{#1}}% \fi} \def\colo_basics_defined_and_activated#1% - {\clf_defineprocesscolordummy{#1}% + {\clf_defineprocesscolordummy{#1}% we could pass dummy here too + \colo_basics_synchronize{d_u_m_m_y}% \colo_helpers_activate_dummy} \def\colo_basics_define_process @@ -777,12 +820,14 @@ \def\colo_basics_define_process_yes[#1][#2][#3]% {\clf_defineprocesscolorlocal{#1}{\processcolorcomponents{#2},#3}\v_colo_freeze_state\relax + \colo_basics_synchronize{#1}% \ifcase\c_colo_protection \unexpanded\setvalue{#1}{\colo_helpers_activate{#1}}% \fi} \def\colo_basics_define_process_nop[#1][#2][#3]% {\clf_defineprocesscolorlocal{#1}{#2}\v_colo_freeze_state\relax + \colo_basics_synchronize{#1}% \ifcase\c_colo_protection \unexpanded\setvalue{#1}{\colo_helpers_activate{#1}}% \fi} @@ -794,12 +839,14 @@ \def\colo_basics_define_spot[#1][#2][#3]% {\clf_definespotcolorglobal{#1}{#2}{#3}% + \colo_basics_synchronize{#1}% \ifcase\c_colo_protection \unexpanded\setgvalue{#1}{\colo_helpers_activate{#1}}% \fi} \def\colo_basics_define_multitone[#1][#2][#3][#4]% {\clf_definemultitonecolorglobal{#1}{#2}{#3}{#4}% + \colo_basics_synchronize{#1}% \ifcase\c_colo_protection \unexpanded\setgvalue{#1}{\colo_helpers_activate{#1}}% \fi} @@ -868,6 +915,7 @@ {#5}% \v_colo_freeze_state \relax + \colo_basics_synchronize{#1}% \unexpanded\setvalue{#1}{\colo_helpers_activate{#1}}} %D Here is a more efficient helper for pgf: @@ -1017,11 +1065,6 @@ \letvalue{\??colorsetter }\empty \letvalue{\??colorattribute }\!!zerocount \letvalue{\??transparencysetter}\empty \letvalue{\??transparencyattribute}\!!zerocount -%def\colo_helpers_inherited_direct_cs#1{\csname\??colorsetter \ifcsname\??colorsetter #1\endcsname#1\fi\endcsname} -%def\colo_helpers_inherited_direct_ca#1{\csname\??colorattribute \ifcsname\??colorattribute #1\endcsname#1\fi\endcsname} -%def\colo_helpers_inherited_direct_ts#1{\csname\??transparencysetter \ifcsname\??transparencysetter #1\endcsname#1\fi\endcsname} -%def\colo_helpers_inherited_direct_ta#1{\csname\??transparencyattribute\ifcsname\??transparencyattribute#1\endcsname#1\fi\endcsname} - \def\colo_helpers_inherited_direct_cs#1{\ifcsname\??colorsetter #1\endcsname\lastnamedcs\fi} \def\colo_helpers_inherited_direct_ca#1{\ifcsname\??colorattribute #1\endcsname\lastnamedcs\else\!!zerocount\fi} \def\colo_helpers_inherited_direct_ts#1{\ifcsname\??transparencysetter #1\endcsname\lastnamedcs\fi} @@ -1047,26 +1090,6 @@ \fi \to \everysetupcolors -% \def\colo_palets_define_set#1#2#3% -% {\doifelseassignment{#3}% \definepalet[test][xx={y=.4}] -% {\definecolor[\??colorpalet#1:#2][#3]% -% \colo_helpers_set_value{\??colorsetter #1:#2}{\colo_helpers_inherited_palet_ca{#1}{#2}}% -% \colo_helpers_set_value{\??colorattribute #1:#2}{\colo_helpers_inherited_palet_cs{#1}{#2}}% -% \colo_helpers_set_value{\??transparencysetter #1:#2}{\colo_helpers_inherited_palet_ta{#1}{#2}}% -% \colo_helpers_set_value{\??transparencyattribute#1:#2}{\colo_helpers_inherited_palet_ts{#1}{#2}}} -% {\ifcsname\??colorsetter#3\endcsname % \definepalet[test][xx=green] -% \colo_helpers_set_value{\??colorsetter #1:#2}{\colo_helpers_inherited_direct_cs{#3}}% -% \colo_helpers_set_value{\??colorattribute #1:#2}{\colo_helpers_inherited_direct_ca{#3}}% -% \colo_helpers_set_value{\??transparencysetter #1:#2}{\colo_helpers_inherited_direct_ts{#3}}% -% \colo_helpers_set_value{\??transparencyattribute#1:#2}{\colo_helpers_inherited_direct_ta{#3}}% -% \else -% % not entered when making format -% \localundefine{\??colorsetter #1:#2}% -% \localundefine{\??colorattribute #1:#2}% -% \localundefine{\??transparencysetter #1:#2}% -% \localundefine{\??transparencyattribute#1:#2}% -% \fi}} - \def\colo_palets_define_set#1#2#3% {\doifelseassignment{#3}% \definepalet[test][xx={y=.4}] {\colo_palets_define_assign}% @@ -1080,7 +1103,8 @@ {#1}{#2}{#3}} \def\colo_palets_define_inherit#1#2#3% - {\colo_helpers_set_value{\??colorsetter #1:#2}{\colo_helpers_inherited_direct_cs{#3}}% + {\colo_basics_inherit{#1:#2}{#3}% + \colo_helpers_set_value{\??colorsetter #1:#2}{\colo_helpers_inherited_direct_cs{#3}}% \colo_helpers_set_value{\??colorattribute #1:#2}{\colo_helpers_inherited_direct_ca{#3}}% \colo_helpers_set_value{\??transparencysetter #1:#2}{\colo_helpers_inherited_direct_ts{#3}}% \colo_helpers_set_value{\??transparencyattribute#1:#2}{\colo_helpers_inherited_direct_ta{#3}}} diff --git a/tex/context/base/mkiv/cont-new.mkiv b/tex/context/base/mkiv/cont-new.mkiv index 79bb68bd3..c81429b13 100644 --- a/tex/context/base/mkiv/cont-new.mkiv +++ b/tex/context/base/mkiv/cont-new.mkiv @@ -11,7 +11,7 @@ %C therefore copyrighted by \PRAGMA. See mreadme.pdf for %C details. -\newcontextversion{2016.06.26 19:00} +\newcontextversion{2016.07.01 16:28} %D This file is loaded at runtime, thereby providing an excellent place for %D hacks, patches, extensions and new features. diff --git a/tex/context/base/mkiv/context.mkiv b/tex/context/base/mkiv/context.mkiv index 425a152fa..9264d48ae 100644 --- a/tex/context/base/mkiv/context.mkiv +++ b/tex/context/base/mkiv/context.mkiv @@ -39,7 +39,7 @@ %D up and the dependencies are more consistent. \edef\contextformat {\jobname} -\edef\contextversion{2016.06.26 19:00} +\edef\contextversion{2016.07.01 16:28} \edef\contextkind {beta} %D For those who want to use this: diff --git a/tex/context/base/mkiv/font-afm.lua b/tex/context/base/mkiv/font-afm.lua index b2e942c8c..fe14059cb 100644 --- a/tex/context/base/mkiv/font-afm.lua +++ b/tex/context/base/mkiv/font-afm.lua @@ -1168,8 +1168,6 @@ registerafmfeature { -- readers -local check_tfm = readers.check_tfm - fonts.formats.afm = "type1" fonts.formats.pfb = "type1" @@ -1205,7 +1203,8 @@ function readers.afm(specification,method) tfmdata = check_afm(specification,specification.name .. "." .. forced) end if not tfmdata then - method = method or definers.method or "afm or tfm" + local check_tfm = readers.check_tfm + method = (check_tfm and (method or definers.method or "afm or tfm")) or "afm" if method == "tfm" then tfmdata = check_tfm(specification,specification.name) elseif method == "afm" then diff --git a/tex/context/base/mkiv/font-enc.lua b/tex/context/base/mkiv/font-enc.lua index ba957bdf2..1470f3b8d 100644 --- a/tex/context/base/mkiv/font-enc.lua +++ b/tex/context/base/mkiv/font-enc.lua @@ -78,24 +78,32 @@ function encodings.load(filename) if foundname and foundname ~= "" then local ok, encoding, size = resolvers.loadbinfile(foundname) if ok and encoding then - encoding = gsub(encoding,"%%(.-)\n","") - local unicoding = fonts.encodings.agl.unicodes - local tag, vec = match(encoding,"/(%w+)%s*%[(.*)%]%s*def") - local i = 0 - for ch in gmatch(vec,"/([%a%d%.]+)") do - if ch ~= ".notdef" then - vector[i] = ch - if not hash[ch] then - hash[ch] = i - else - -- duplicate, play safe for tex ligs and take first - end - local u = unicoding[ch] or enccodes[ch] -- enccodes have also context names - if u then - unicodes[u] = i + encoding = gsub(encoding,"%%(.-)[\n\r]+","") + if encoding then + local unicoding = fonts.encodings.agl.unicodes + local tag, vec = match(encoding,"[/]*(%w+)%s*%[(.*)%]%s*def") + if vec then + local i = 0 + for ch in gmatch(vec,"/([%a%d%.]+)") do + if ch ~= ".notdef" then + vector[i] = ch + if not hash[ch] then + hash[ch] = i + else + -- duplicate, play safe for tex ligs and take first + end + local u = unicoding[ch] or enccodes[ch] -- enccodes have also context names + if u then + unicodes[u] = i + end + end + i = i + 1 end + else + report_encoding("reading vector in encoding file %a fails",filename) end - i = i + 1 + else + report_encoding("reading encoding file %a fails",filename) end end end diff --git a/tex/context/base/mkiv/font-lib.mkvi b/tex/context/base/mkiv/font-lib.mkvi index f6bb734fd..3bfe308ff 100644 --- a/tex/context/base/mkiv/font-lib.mkvi +++ b/tex/context/base/mkiv/font-lib.mkvi @@ -33,7 +33,7 @@ \registerctxluafile{font-dsp}{1.001} % ... for this one \registerctxluafile{font-off}{1.001} % the old loader -\registerctxluafile{font-tfm}{1.001} +% \registerctxluafile{font-tfm}{1.001} \registerctxluafile{font-hsh}{1.001} % hashes used by context \registerctxluafile{font-nod}{1.001} @@ -60,6 +60,10 @@ %registerctxluafile{font-afm}{1.001} \registerctxluafile{font-afk}{1.001} +% tfm + +\registerctxluafile{font-tfm}{1.001} + % name database \registerctxluafile{font-syn}{1.001} diff --git a/tex/context/base/mkiv/font-map.lua b/tex/context/base/mkiv/font-map.lua index 6151b37f5..7f3b0f960 100644 --- a/tex/context/base/mkiv/font-map.lua +++ b/tex/context/base/mkiv/font-map.lua @@ -13,8 +13,8 @@ local P, R, S, C, Ct, Cc, lpegmatch = lpeg.P, lpeg.R, lpeg.S, lpeg.C, lpeg.Ct, l local floor = math.floor local formatters = string.formatters -local trace_loading = false trackers.register("fonts.loading", function(v) trace_loading = v end) -local trace_mapping = false trackers.register("fonts.mapping", function(v) trace_unimapping = v end) +local trace_loading = false trackers.register("fonts.loading", function(v) trace_loading = v end) +local trace_mapping = false trackers.register("fonts.mapping", function(v) trace_mapping = v end) local report_fonts = logs.reporter("fonts","loading") -- not otf only @@ -265,6 +265,9 @@ function mappings.addtounicode(data,filename,checklookups) local resources = data.resources local unicodes = resources.unicodes if not unicodes then + if trace_mapping then + report_fonts("no unicode list, quitting tounicode for %a",filename) + end return end local properties = data.properties @@ -474,11 +477,10 @@ function mappings.addtounicode(data,filename,checklookups) if trace_mapping and unicoded > 0 then report_fonts("%n ligature tounicode mappings deduced from gsub ligature features",unicoded) end - if trace_mapping then for unic, glyph in table.sortedhash(descriptions) do - local name = glyph.name - local index = glyph.index + local name = glyph.name or "-" + local index = glyph.index or 0 local unicode = glyph.unicode if unicode then if type(unicode) == "table" then diff --git a/tex/context/base/mkiv/font-one.lua b/tex/context/base/mkiv/font-one.lua index a6f47e87b..8629850de 100644 --- a/tex/context/base/mkiv/font-one.lua +++ b/tex/context/base/mkiv/font-one.lua @@ -86,7 +86,8 @@ local steps = { "add ligatures", "add extra kerns", "normalize features", - "fix names", + "check extra features", + "fix names", -- what a hack ... -- "add tounicode data", } @@ -318,6 +319,8 @@ enhancers["normalize features"] = function(data) data.resources.sequences = sequences end +enhancers["check extra features"] = otf.enhancers.enhance + enhancers["fix names"] = function(data) for k, v in next, data.descriptions do local n = v.name @@ -752,18 +755,12 @@ end <p>We have the usual two modes and related features initializers and processors.</p> --ldx]]-- -local function setmode(tfmdata,value) - if value then - tfmdata.properties.mode = lower(value) - end -end - registerafmfeature { name = "mode", description = "mode", initializers = { - base = setmode, - node = setmode, + base = otf.modeinitializer, + node = otf.modeinitializer, } } @@ -782,8 +779,6 @@ registerafmfeature { -- readers -local check_tfm = readers.check_tfm - fonts.formats.afm = "type1" fonts.formats.pfb = "type1" @@ -820,7 +815,8 @@ function readers.afm(specification,method) tfmdata = check_afm(specification,specification.name .. "." .. forced) end if not tfmdata then - method = method or definers.method or "afm or tfm" + local check_tfm = readers.check_tfm + method = (check_tfm and (method or definers.method or "afm or tfm")) or "afm" if method == "tfm" then tfmdata = check_tfm(specification,specification.name) elseif method == "afm" then diff --git a/tex/context/base/mkiv/font-onr.lua b/tex/context/base/mkiv/font-onr.lua index d03a9df89..dcf7445e5 100644 --- a/tex/context/base/mkiv/font-onr.lua +++ b/tex/context/base/mkiv/font-onr.lua @@ -35,9 +35,7 @@ local trace_loading = false trackers.register("afm.loading", function(v local report_afm = logs.reporter("fonts","afm loading") local report_pfb = logs.reporter("fonts","pfb loading") -fonts = fonts or { } -local handlers = fonts.handlers or { } -fonts.handlers = handlers +local handlers = fonts.handlers local afm = handlers.afm or { } handlers.afm = afm local readers = afm.readers or { } @@ -159,10 +157,15 @@ do local vector = lpegmatch(p_filternames,binary) - if vector[1] == ".notdef" then - -- tricky - vector[0] = table.remove(vector,1) +-- if vector[1] == ".notdef" then +-- -- tricky +-- vector[0] = table.remove(vector,1) +-- end + + for i=1,#vector do + vector[i-1] = vector[i] end + vector[#vector] = nil if not vector then report_pfb("no vector in %a",filename) diff --git a/tex/context/base/mkiv/font-otc.lua b/tex/context/base/mkiv/font-otc.lua index 30a58ad72..14afc5c50 100644 --- a/tex/context/base/mkiv/font-otc.lua +++ b/tex/context/base/mkiv/font-otc.lua @@ -92,11 +92,18 @@ local function addfeature(data,feature,specifications) -- todo: add some validator / check code so that we're more tolerant to -- user errors + if not specifications then + report_otf("missing specification") + return + end + local descriptions = data.descriptions local resources = data.resources local features = resources.features local sequences = resources.sequences + if not features or not sequences then + report_otf("missing specification") return end @@ -120,8 +127,9 @@ local function addfeature(data,feature,specifications) local skip = 0 local aglunicodes = false - local specifications = validspecification(specifications,name) + local specifications = validspecification(specifications,feature) if not specifications then + -- report_otf("invalid specification") return end @@ -650,7 +658,7 @@ local function enhance(data,filename,raw) end end --- otf.enhancers.enhance = enhance +otf.enhancers.enhance = enhance otf.enhancers.register("check extra features",enhance) diff --git a/tex/context/base/mkiv/font-oti.lua b/tex/context/base/mkiv/font-oti.lua index d74d2d502..5e812bb9e 100644 --- a/tex/context/base/mkiv/font-oti.lua +++ b/tex/context/base/mkiv/font-oti.lua @@ -34,6 +34,8 @@ local function setmode(tfmdata,value) end end +otf.modeinitializer = setmode + local function setlanguage(tfmdata,value) if value then local cleanvalue = lower(value) diff --git a/tex/context/base/mkiv/font-oto.lua b/tex/context/base/mkiv/font-oto.lua index 119977835..177382f58 100644 --- a/tex/context/base/mkiv/font-oto.lua +++ b/tex/context/base/mkiv/font-oto.lua @@ -120,7 +120,7 @@ local function registerbasehash(tfmdata) basehash[hash] = base end properties.basehash = base - properties.fullname = properties.fullname .. "-" .. base + properties.fullname = (properties.fullname or properties.name) .. "-" .. base -- report_prepare("fullname base hash '%a, featureset %a",tfmdata.properties.fullname,hash) applied = { } end @@ -225,6 +225,11 @@ local function preparesubstitutions(tfmdata,feature,value,validlookups,lookuplis local trace_alternatives = trace_baseinit and trace_alternatives local trace_ligatures = trace_baseinit and trace_ligatures + if not changed then + changed = { } + tfmdata.changed = changed + end + for i=1,#lookuplist do local sequence = lookuplist[i] local steps = sequence.steps @@ -392,7 +397,8 @@ local function featuresinitializer(tfmdata,value) local properties = tfmdata.properties local script = properties.script local language = properties.language - local rawfeatures = rawdata.resources.features + local rawresources = rawdata.resources + local rawfeatures = rawresources and rawresources.features local basesubstitutions = rawfeatures and rawfeatures.gsub local basepositionings = rawfeatures and rawfeatures.gpos -- diff --git a/tex/context/base/mkiv/font-oup.lua b/tex/context/base/mkiv/font-oup.lua index 571c69f13..c4945734f 100644 --- a/tex/context/base/mkiv/font-oup.lua +++ b/tex/context/base/mkiv/font-oup.lua @@ -848,6 +848,8 @@ function readers.getcomponents(fontdata) -- handy for resolving ligatures when n end end +readers.unifymissing = unifymissing + function readers.rehash(fontdata,hashmethod) -- TODO: combine loops in one if not (fontdata and fontdata.glyphs) then return diff --git a/tex/context/base/mkiv/font-tfm.lua b/tex/context/base/mkiv/font-tfm.lua index 3aee1bf53..d9b052388 100644 --- a/tex/context/base/mkiv/font-tfm.lua +++ b/tex/context/base/mkiv/font-tfm.lua @@ -7,7 +7,8 @@ if not modules then modules = { } end modules ['font-tfm'] = { } local next, type = next, type -local match = string.match +local match, format = string.match, string.format +local concat, sortedhash = table.concat, table.sortedhash local trace_defining = false trackers.register("fonts.defining", function(v) trace_defining = v end) local trace_features = false trackers.register("tfm.features", function(v) trace_features = v end) @@ -16,6 +17,7 @@ local report_defining = logs.reporter("fonts","defining") local report_tfm = logs.reporter("fonts","tfm loading") local findbinfile = resolvers.findbinfile +local setmetatableindex = table.setmetatableindex local fonts = fonts local handlers = fonts.handlers @@ -28,8 +30,10 @@ tfm.version = 1.000 tfm.maxnestingdepth = 5 tfm.maxnestingsize = 65536*1024 +local otf = fonts.handlers.otf + local tfmfeatures = constructors.features.tfm ------ registertfmfeature = tfmfeatures.register +local registertfmfeature = tfmfeatures.register constructors.resolvevirtualtoo = false -- wil be set in font-ctx.lua @@ -69,11 +73,68 @@ function tfm.setfeatures(tfmdata,features) end end -function tfm.reencode(tfmdata,specification) - return tfmdata +local depth = { } -- table.setmetatableindex("number") +local enhancers = { } + +local steps = { + "normalize features", + "check extra features" +} + +-- otf.enhancers.register("check extra features",enhance) + +enhancers["check extra features"] = otf.enhancers.enhance + +local function applyenhancers(data,filename) + for i=1,#steps do + local step = steps[i] + local enhancer = enhancers[step] + if enhancer then + if trace_loading then + report_tfm("applying enhancer %a",step) + end + enhancer(data,filename) + else + report_tfm("invalid enhancer %a",step) + end + end end -local depth = { } -- table.setmetatableindex("number") +-- Normally we just load the tfm data and go on. However there was some demand for +-- loading good old tfm /pfb files where afm files were lacking and even enc files +-- of dubious quality so we now support loading such (often messy) setups too. +-- +-- Because such fonts also use (ugly) tweaks achieve some purpose (like swapping +-- accents) we need to delay the unicoding actions till after the features have been +-- applied. +-- +-- It must be noted that in ConTeXt we don't expect this to be used at all. Here is +-- example: +-- +-- tfm metrics + pfb vector for index + pfb file for shapes +-- +-- \font\foo=file:csr10.tfm:reencode=auto;mode=node;liga=yes;kern=yes +-- +-- tfm metrics + pfb vector for index + enc file for tfm mapping + pfb file for shapes +-- +-- \font\foo=file:csr10.tfm:reencode=csr.enc;mode=node;liga=yes;kern=yes +-- +-- tfm metrics + enc file for mapping to tfm + bitmaps shapes +-- +-- \font\foo=file:csr10.tfm:reencode=csr.enc;bitmap=yes;mode=node;liga=yes;kern=yes +-- +-- One can add features: +-- +-- fonts.handlers.otf.addfeature { +-- name = "czechdqcheat", +-- type = "substitution", +-- data = { +-- quotedblright = "csquotedblright", +-- }, +-- } +-- +-- So "czechdqcheat=yes" is then a valid feature. And yes, it's a cheat. + local function read_from_tfm(specification) local filename = specification.filename @@ -85,29 +146,114 @@ local function read_from_tfm(specification) local tfmdata = font.read_tfm(filename,size) -- not cached, fast enough if tfmdata then - tfmdata = tfm.reencode(tfmdata,specification) -- not a manipulator, has to come earlier + local features = specification.features and specification.features.normal or { } + local features = constructors.checkedfeatures("tfm",features) + specification.features.normal = features + + -- If reencode returns a new table, we assume that we're doing something + -- special. An 'auto' reencode pickt up its vector from the pfb file. + + local newtfmdata = (depth[filename] == 1) and tfm.reencode(tfmdata,specification) + if newtfmdata then + tfmdata = newtfmdata + end - local features = specification.features and specification.features.normal or { } local resources = tfmdata.resources or { } local properties = tfmdata.properties or { } local parameters = tfmdata.parameters or { } local shared = tfmdata.shared or { } -- - properties.name = tfmdata.name - properties.fontname = tfmdata.fontname - properties.psname = tfmdata.psname - properties.filename = specification.filename - properties.format = fonts.formats.tfm -- better than nothing + shared.features = features + shared.resources = resources + -- + properties.name = tfmdata.name -- todo: fallback + properties.fontname = tfmdata.fontname -- todo: fallback + properties.psname = tfmdata.psname -- todo: fallback + properties.fullname = tfmdata.fullname -- todo: fallback + properties.filename = specification.filename -- todo: fallback + properties.format = fonts.formats.tfm -- better than nothing -- tfmdata.properties = properties tfmdata.resources = resources tfmdata.parameters = parameters tfmdata.shared = shared -- - shared.rawdata = { } + shared.rawdata = { resources = resources } shared.features = features + -- + -- The next branch is only entered when we have a proper encoded file i.e. + -- unicodes and such. It really nakes no sense to do feature juggling when + -- we have no names and unicodes. + -- + if newtfmdata then + -- + -- Some opentype processing assumes these to be present: + -- + if not resources.marks then + resources.marks = { } + end + if not resources.sequences then + resources.sequences = { } + end + if not resources.features then + resources.features = { + gsub = { }, + gpos = { }, + } + end + if not tfmdata.changed then + tfmdata.changed = { } + end + if not tfmdata.descriptions then + tfmdata.descriptions = tfmdata.characters + end + -- + -- It might be handy to have this: + -- + otf.readers.addunicodetable(tfmdata) + -- + -- We make a pseudo opentype font, e.g. kerns and ligatures etc: + -- + applyenhancers(tfmdata,filename) + -- + -- Now user stuff can kick in. + -- + constructors.applymanipulators("tfm",tfmdata,features,trace_features,report_tfm) + -- + -- As that can also mess with names and such, we are now ready for finalizing + -- the unicode information. This is a different order that for instance type one + -- (afm) files. First we try to deduce unicodes from already present information. + -- + otf.readers.unifymissing(tfmdata) + -- + -- Next we fill in the gaps, based on names from teh agl. Probably not much will + -- happen here. + -- + fonts.mappings.addtounicode(tfmdata,filename) + -- + -- The tounicode data is passed to the backend that constructs the vectors for us. + -- + tfmdata.tounicode = 1 + local tounicode = fonts.mappings.tounicode + for unicode, v in next, tfmdata.characters do + local u = v.unicode + if u then + v.tounicode = tounicode(u) + end + end + -- + -- However, when we use a bitmap font those vectors can't be constructed because + -- that information is not carried with those fonts (there is no name info, nor + -- proper index info, nor unicodes at that end). So, we provide it ourselves. + -- + if tfmdata.usedbitmap then + tfm.addtounicode(tfmdata) + end + end + -- shared.processes = next(features) and tfm.setfeatures(tfmdata,features) or nil -- + parameters.factor = 1 -- already scaled parameters.size = size parameters.slant = parameters.slant or parameters[1] or 0 parameters.space = parameters.space or parameters[2] or 0 @@ -119,7 +265,12 @@ local function read_from_tfm(specification) -- constructors.enhanceparameters(parameters) -- official copies for us -- - if constructors.resolvevirtualtoo then + if newtfmdata then + -- + -- We do nothing as we assume flat tfm files. It would become real messy + -- otherwise and I don't have something for testing on my system anyway. + -- + elseif constructors.resolvevirtualtoo then fonts.loggers.register(tfmdata,file.suffix(filename),specification) -- strange, why here local vfname = findbinfile(specification.name, 'ovf') if vfname and vfname ~= "" then @@ -154,21 +305,26 @@ local function read_from_tfm(specification) end end -- - local allfeatures = tfmdata.shared.features or specification.features.normal - constructors.applymanipulators("tfm",tfmdata,allfeatures,trace_features,report_tfm) - if not features.encoding then - local encoding, filename = match(properties.filename,"^(.-)%-(.*)$") -- context: encoding-name.* - if filename and encoding and encodings.known and encodings.known[encoding] then - features.encoding = encoding - end - end - -- let's play safe: + -- This is for old times sake (and context specific) so we comment it. It has + -- to do with encoding prefixes (a context naming that was later adopted by + -- the lm/gyre project) + -- + -- if not features.encoding then + -- local encoding, filename = match(properties.filename,"^(.-)%-(.*)$") + -- if filename and encoding and encodings.known and encodings.known[encoding] then + -- features.encoding = encoding + -- end + -- end + -- + -- Some afterthoughts: + -- properties.haskerns = true properties.hasligatures = true resources.unicodes = { } resources.lookuptags = { } -- depth[filename] = depth[filename] - 1 + -- return tfmdata else depth[filename] = depth[filename] - 1 @@ -209,7 +365,10 @@ end readers.ofm = readers.tfm --- bonus for old times sake: +-- The reencoding acts upon the 'reencode' feature which can have values 'auto' or +-- an enc file. You can also specify a 'pfbfile' feature (but it defaults to the +-- tfm filename) and a 'bitmap' feature. When no enc file is givven (auto) we will +-- get the vectors from the pfb file. do @@ -228,13 +387,13 @@ do local features = specification.features if not features then - return tfmdata + return end local features = features.normal if not features then - return tfmdata + return end local tfmfile = file.basename(tfmdata.name) @@ -243,7 +402,7 @@ do local bitmap = features.bitmap -- or features.pk if not encfile then - return tfmdata + return end local pfbfile = outfiles[tfmfile] @@ -256,7 +415,7 @@ do end if type(pfbfile) == "string" then pfbfile = file.addsuffix(pfbfile,"pfb") - pdf.mapline(tfmfile .. "<" .. pfbfile) + -- pdf.mapline(tfmfile .. "<" .. pfbfile) report_tfm("using type1 shapes from %a for %a",pfbfile,tfmfile) else report_tfm("using bitmap shapes for %a",tfmfile) @@ -266,26 +425,29 @@ do end local encoding = false + local vector = false - if type(encfile) == "string" and encfile ~= "auto" then - encoding = fonts.encodings.load(file.addsuffix(encfile,"enc")) - if encoding then - encoding = encoding.vector - end - elseif type(pfbfile) == "string" then + if type(pfbfile) == "string" then local pfb = fonts.constructors.handlers.pfb - -- report_tfm("using encoding from %a",pfbfile) if pfb and pfb.loadvector then local v, e = pfb.loadvector(pfbfile) + if v then + vector = v + end if e then encoding = e end end end - + if type(encfile) == "string" and encfile ~= "auto" then + encoding = fonts.encodings.load(file.addsuffix(encfile,"enc")) + if encoding then + encoding = encoding.vector + end + end if not encoding then report_tfm("bad encoding for %a, quitting",tfmfile) - return tfmdata + return end local unicoding = fonts.encodings.agl and fonts.encodings.agl.unicodes @@ -300,11 +462,16 @@ do -- create characters table - for index, name in table.sortedhash(encoding) do -- predictable order + local backmap = vector and table.swapped(vector) + local done = { } -- prevent duplicate + + for index, name in sortedhash(encoding) do -- predictable order local unicode = unicoding[name] local original = originals[index] if original then - if not unicode then + if unicode then + original.unicode = unicode + else unicode = private private = private + 1 if not reported then @@ -314,8 +481,14 @@ do characters[unicode] = original indices[index] = unicode original.name = name -- so one can lookup weird names - original.commands = { parentfont, { "char", index } } - else + if backmap then + original.index = backmap[name] + else -- probably bitmap + original.commands = { parentfont, { "char", index } } + original.oindex = index + end + done[name] = true + elseif not done[name] then report_tfm("bad index %a in font %a with name %a",index,tfmfile,name) end end @@ -352,10 +525,205 @@ do -- wrap up - tfmdata.fonts = { { id = virtualid } } - tfmdata.characters = characters + tfmdata.fonts = { { id = virtualid } } + tfmdata.characters = characters + tfmdata.fullname = tfmdata.fullname or tfmdata.name + tfmdata.psname = file.nameonly(pfbfile or tfmdata.name) + tfmdata.filename = pfbfile + tfmdata.encodingbytes = 2 + tfmdata.format = "type1" + tfmdata.tounicode = 1 + tfmdata.embedding = "subset" + tfmdata.usedbitmap = bitmap and virtualid return tfmdata end end + +-- This code adds a ToUnicode vector for bitmap fonts. We don't bother about +-- ranges because we have small fonts. it works ok with acrobat but fails with +-- the other viewers (they get confused by the bitmaps I guess). + +do + + local template = [[ +/CIDInit /ProcSet findresource begin + 12 dict begin + begincmap + /CIDSystemInfo << /Registry (TeX) /Ordering (bitmap-%s) /Supplement 0 >> def + /CMapName /TeX-bitmap-%s def + /CMapType 2 def + 1 begincodespacerange + <00> <FF> + endcodespacerange + %s beginbfchar +%s + endbfchar + endcmap +CMapName currentdict /CMap defineresource pop end +end +end +]] + + local flushstreamobject = lpdf and lpdf.flushstreamobject + local setfontattributes = pdf.setfontattributes + + if not flushstreamobject then + flushstreamobject = function(data) + return pdf.obj { + immediate = true, + type = "stream", + string = data, + } + end + end + + if not setfontattributes then + setfontattributes = function(id,data) + print(format("your luatex is too old so no tounicode bitmap font%i",id)) + end + end + + function tfm.addtounicode(tfmdata) + local id = tfmdata.usedbitmap + local map = { } + local char = { } -- no need for range, hardly used + for k, v in next, tfmdata.characters do + local index = v.oindex + local tounicode = v.tounicode + if index and tounicode then + map[index] = tounicode + end + end + for k, v in sortedhash(map) do + char[#char+1] = format("<%02X> <%s>",k,v) + end + char = concat(char,"\n") + local stream = format(template,id,id,#char,char) + local reference = flushstreamobject(stream,nil,true) + setfontattributes(id,format("/ToUnicode %i 0 R",reference)) + end + +end + +-- Now we implement the regular features handlers. We need to convert the +-- tfm specific structures to opentype structures. In basemode they are +-- converted back so that is a bti of a waste but it's fast enough. + +do + + local everywhere = { ["*"] = { ["*"] = true } } -- or: { ["*"] = { "*" } } + local noflags = { false, false, false, false } + + enhancers["normalize features"] = function(data) + local ligatures = setmetatableindex("table") + local kerns = setmetatableindex("table") + local characters = data.characters + for u, c in next, characters do + local l = c.ligatures + local k = c.kerns + if l then + ligatures[u] = l + for u, v in next, l do + l[u] = { ligature = v.char } + end + c.ligatures = nil + end + if k then + kerns[u] = k + for u, v in next, k do + k[u] = v -- { v, 0 } + end + c.kerns = nil + end + end + + for u, l in next, ligatures do + for k, v in next, l do + local vl = v.ligature + local dl = ligatures[vl] + if dl then + for kk, vv in next, dl do + v[kk] = vv -- table.copy(vv) + end + end + end + end + + local features = { + gpos = { }, + gsub = { }, + } + local sequences = { + -- only filled ones + } + if next(ligatures) then + features.gsub.liga = everywhere + data.properties.hasligatures = true + sequences[#sequences+1] = { + features = { + liga = everywhere, + }, + flags = noflags, + name = "s_s_0", + nofsteps = 1, + order = { "liga" }, + type = "gsub_ligature", + steps = { + { + coverage = ligatures, + }, + }, + } + end + if next(kerns) then + features.gpos.kern = everywhere + data.properties.haskerns = true + sequences[#sequences+1] = { + features = { + kern = everywhere, + }, + flags = noflags, + name = "p_s_0", + nofsteps = 1, + order = { "kern" }, + type = "gpos_pair", + steps = { + { + format = "kern", + coverage = kerns, + }, + }, + } + end + data.resources.features = features + data.resources.sequences = sequences + data.shared.resources = data.shared.resources or resources + end + +end + +-- As with type one (afm) loading, we just use the opentype ones: + +registertfmfeature { + name = "mode", + description = "mode", + initializers = { + base = otf.modeinitializer, + node = otf.modeinitializer, + } +} + +registertfmfeature { + name = "features", + description = "features", + default = true, + initializers = { + base = otf.basemodeinitializer, + node = otf.nodemodeinitializer, + }, + processors = { + node = otf.featuresprocessor, + } +} diff --git a/tex/context/base/mkiv/good-ini.lua b/tex/context/base/mkiv/good-ini.lua index f11b0f004..66f0e29d0 100644 --- a/tex/context/base/mkiv/good-ini.lua +++ b/tex/context/base/mkiv/good-ini.lua @@ -260,6 +260,9 @@ local function setextrafeatures(tfmdata) local f = g.features if f then for feature, specification in next, f do + -- not needed but nicer: + specification.name = specification.name or feature + -- addotffeature(tfmdata.shared.rawdata,feature,specification) registerotffeature { name = feature, diff --git a/tex/context/base/mkiv/lang-frq-pt.lua b/tex/context/base/mkiv/lang-frq-pt.lua new file mode 100644 index 000000000..ce4e7aa26 --- /dev/null +++ b/tex/context/base/mkiv/lang-frq-pt.lua @@ -0,0 +1,12 @@ +return { + language = "pt", + source = "https://pt.wikipedia.org/wiki/Frequência_de_letras", + frequencies = { + [0x61] = 14.63, [0x62] = 1.04, [0x63] = 3.88, [0x64] = 4.99, [0x65] = 12.57, + [0x66] = 1.02, [0x67] = 1.30, [0x68] = 1.28, [0x69] = 6.18, [0x6A] = 0.40, + [0x6B] = 0.02, [0x6C] = 2.78, [0x6D] = 4.74, [0x6E] = 5.05, [0x6F] = 10.73, + [0x70] = 2.52, [0x71] = 1.20, [0x72] = 6.53, [0x73] = 7.81, [0x74] = 4.74, + [0x75] = 4.63, [0x76] = 1.67, [0x77] = 0.01, [0x78] = 0.21, [0x79] = 0.01, + [0x7A] = 0.47, + } +} diff --git a/tex/context/base/mkiv/lang-ini.lua b/tex/context/base/mkiv/lang-ini.lua index 0677cb003..347cb0281 100644 --- a/tex/context/base/mkiv/lang-ini.lua +++ b/tex/context/base/mkiv/lang-ini.lua @@ -20,8 +20,8 @@ if not modules then modules = { } end modules ['lang-ini'] = { local type, tonumber = type, tonumber local utfbyte = utf.byte -local format, gsub = string.format, string.gsub -local concat, sortedkeys, sortedpairs = table.concat, table.sortedkeys, table.sortedpairs +local format, gsub, gmatch, find = string.format, string.gsub, string.gmatch, string.find +local concat, sortedkeys, sortedpairs, keys, insert = table.concat, table.sortedkeys, table.sortedpairs, table.keys, table.insert local utfbytes, strip = string.utfvalues, string.strip local context = context @@ -29,6 +29,7 @@ local commands = commands local implement = interfaces.implement local settings_to_array = utilities.parsers.settings_to_array +local settings_to_set = utilities.parsers.settings_to_set local trace_patterns = false trackers.register("languages.patterns", function(v) trace_patterns = v end) @@ -119,7 +120,7 @@ local function validdata(loaded,what,tag) if dataset then local data = dataset.data if not data or data == "" then - return nil + -- nothing elseif dataset.compression == "zlib" then data = zlib.decompress(data) if dataset.length and dataset.length ~= #data then @@ -157,14 +158,95 @@ local function sethjcodes(instance,loaded,what) end end +-- 2'2 conflicts with 4' ... and luatex barks on it + +local P, R, Cs, Ct, lpegmatch, lpegpatterns = lpeg.P, lpeg.R, lpeg.Cs, lpeg.Ct, lpeg.match, lpeg.patterns + +local utfsplit = utf.split + +local space = lpegpatterns.space +local whitespace = lpegpatterns.whitespace^1 +local nospace = lpegpatterns.utf8char - whitespace +local digit = lpegpatterns.digit +----- endofstring = #whitespace + P(-1) +local endofstring = #whitespace + +local word = (digit/"")^0 * (digit/"" * endofstring + digit/" " + nospace)^1 +local anyword = (1-whitespace)^1 +local analyze = Ct((whitespace + Cs(word))^1) + +local function unique(tag,requested,loaded) + local nofloaded = #loaded + if nofloaded == 0 then + return "" + elseif nofloaded == 1 then + return loaded[1] + else + insert(loaded,1," ") -- no need then for special first word + -- insert(loaded, " ") + loaded = concat(loaded," ") + local t = lpegmatch(analyze,loaded) or { } + local h = { } + local b = { } + for i=1,#t do + local ti = t[i] + local hi = h[ti] + if not hi then + h[ti] = 1 + elseif hi == 1 then + h[ti] = 2 + b[#b+1] = utfsplit(ti," ") + end + end + -- sort + local nofbad = #b + if nofbad > 0 then + local word + for i=1,nofbad do + local bi = b[i] + local p = P(bi[1]) + for i=2,#bi do + p = p * digit * P(bi[i]) + end + if word then + word = word + p + else + word = p + end + report_initialization("language %a, patterns %a, discarding conflict (0-9)%{[0-9]}t(0-9)",tag,requested,bi) + end + t, h, b = nil, nil, nil -- permit gc + local someword = digit^0 * word * digit^0 * endofstring / "" + -- local strip = Cs(someword^-1 * (someword + anyword + whitespace)^1) + local strip = Cs((someword + anyword + whitespace)^1) + return lpegmatch(strip,loaded) or loaded + else + return loaded + end + end +end + local function loaddefinitions(tag,specification) statistics.starttiming(languages) local data, instance = resolve(tag) - local definitions = settings_to_array(specification.patterns or "") + local requested = specification.patterns or "" + local definitions = settings_to_array(requested) if #definitions > 0 then if trace_patterns then report_initialization("pattern specification for language %a: %s",tag,specification.patterns) end + local ploaded = instance:patterns() + local eloaded = instance:hyphenation() + if not ploaded or ploaded == "" then + ploaded = { } + else + ploaded = { ploaded } + end + if not eloaded or eloaded == "" then + eloaded = { } + else + eloaded = { eloaded } + end local dataused = data.used local ok = false local resources = data.resources or { } @@ -178,6 +260,9 @@ local function loaddefinitions(tag,specification) report_initialization("clearing patterns for language %a",tag) end instance:clear_patterns() + instance:clear_hyphenation() + ploaded = { } + eloaded = { } elseif not dataused[definition] then dataused[definition] = definition local filename = "lang-" .. definition .. ".lua" @@ -195,8 +280,14 @@ local function loaddefinitions(tag,specification) ok, nofloaded = true, nofloaded + 1 sethjcodes(instance,loaded,"patterns") sethjcodes(instance,loaded,"exceptions") - instance:patterns (validdata(loaded,"patterns", tag) or "") - instance:hyphenation(validdata(loaded,"exceptions",tag) or "") + local p = validdata(loaded,"patterns",tag) + local e = validdata(loaded,"exceptions",tag) + if p and p ~= "" then + ploaded[#ploaded+1] = p + end + if e and e ~= "" then + eloaded[#eloaded+1] = e + end resources[#resources+1] = loaded -- so we can use them otherwise else report_initialization("invalid definition %a for language %a in %a",definition,tag,filename) @@ -208,6 +299,14 @@ local function loaddefinitions(tag,specification) report_initialization("definition %a for language %a already loaded",definition,tag) end end + if #ploaded > 0 then + instance:clear_patterns() + instance:patterns(unique(tag,requested,ploaded)) + end + if #eloaded > 0 then + instance:clear_hyphenation() + instance:hyphenation(concat(eloaded," ")) + end return ok elseif trace_patterns then report_initialization("no definitions for language %a",tag) diff --git a/tex/context/base/mkiv/mlib-lua.lua b/tex/context/base/mkiv/mlib-lua.lua index d348981e7..7b2c67220 100644 --- a/tex/context/base/mkiv/mlib-lua.lua +++ b/tex/context/base/mkiv/mlib-lua.lua @@ -87,7 +87,20 @@ end mp.print = mpprint -table.setmetatablecall(mp,function(t,k) mpprint(k) end) +-- We had this: +-- +-- table.setmetatablecall(mp,function(t,k) mpprint(k) end) +-- +-- but the next one is more interesting because we cannot use calls like: +-- +-- lua.mp.somedefdname("foo") +-- +-- which is due to expansion of somedefdname during suffix creation. So: +-- +-- lua.mp("somedefdname","foo") + + +table.setmetatablecall(mp,function(t,k,...) return t[k](...) end) function mp.boolean(n) n = n + 1 @@ -156,6 +169,12 @@ function mp.size(t) buffer[n] = type(t) == "table" and f_numeric(#t) or "0" end +local mpnamedcolor = attributes.colors.mpnamedcolor + +mp.NamedColor = function(str) + mpprint(mpnamedcolor(str)) +end + -- experiment: names can change local datasets = { } diff --git a/tex/context/base/mkiv/mult-fun.lua b/tex/context/base/mkiv/mult-fun.lua index d32776b96..1a083e366 100644 --- a/tex/context/base/mkiv/mult-fun.lua +++ b/tex/context/base/mkiv/mult-fun.lua @@ -107,6 +107,7 @@ return { -- "recolor", "refill", "redraw", "retext", "untext", "restroke", "reprocess", "repathed", "tensecircle", "roundedsquare", "colortype", "whitecolor", "blackcolor", "basiccolors", "complementary", "complemented", + "resolvedcolor", -- -- "swappointlabels", "normalfill", "normaldraw", "visualizepaths", "detailpaths", "naturalizepaths", diff --git a/tex/context/base/mkiv/mult-ini.lua b/tex/context/base/mkiv/mult-ini.lua index 76517f37e..19585a7fa 100644 --- a/tex/context/base/mkiv/mult-ini.lua +++ b/tex/context/base/mkiv/mult-ini.lua @@ -33,6 +33,7 @@ interfaces.formats = mark(interfaces.formats or { }) interfaces.translations = mark(interfaces.translations or { }) interfaces.setupstrings = mark(interfaces.setupstrings or { }) interfaces.corenamespaces = mark(interfaces.corenamespaces or { }) +interfaces.usednamespaces = mark(interfaces.usednamespaces or { }) local registerstorage = storage.register local sharedstorage = storage.shared @@ -44,6 +45,7 @@ local formats = interfaces.formats local translations = interfaces.translations local setupstrings = interfaces.setupstrings local corenamespaces = interfaces.corenamespaces +local usednamespaces = interfaces.usednamespaces local reporters = { } -- just an optimization registerstorage("interfaces/constants", constants, "interfaces.constants") @@ -53,6 +55,7 @@ registerstorage("interfaces/formats", formats, "interfaces.formats registerstorage("interfaces/translations", translations, "interfaces.translations") registerstorage("interfaces/setupstrings", setupstrings, "interfaces.setupstrings") registerstorage("interfaces/corenamespaces", corenamespaces, "interfaces.corenamespaces") +registerstorage("interfaces/usednamespaces", usednamespaces, "interfaces.usednamespaces") interfaces.interfaces = { "cs", "de", "en", "fr", "it", "nl", "ro", "pe", @@ -95,6 +98,11 @@ setmetatableindex(setupstrings, valueiskey) function interfaces.registernamespace(n,namespace) corenamespaces[n] = namespace + usednamespaces[namespace] = n +end + +function interfaces.getnamespace(n) + return usednamespaces[n] .. ">" end local function resolve(t,k) diff --git a/tex/context/base/mkiv/regi-ibm.lua b/tex/context/base/mkiv/regi-ibm.lua new file mode 100644 index 000000000..3b95333eb --- /dev/null +++ b/tex/context/base/mkiv/regi-ibm.lua @@ -0,0 +1,26 @@ +if not modules then modules = { } end modules ['regi-ibm'] = { -- 437 + version = 1.001, + comment = "companion to regi-ini.mkiv", + author = "Hans Hagen, PRAGMA-ADE, Hasselt NL", + copyright = "PRAGMA ADE / ConTeXt Development Team", + license = "see context related readme files" +} + +return { [0] = + 0x0000, 0x0001, 0x0002, 0x0003, 0x0004, 0x0005, 0x0006, 0x0007, 0x0008, 0x0009, 0x000A, 0x000B, 0x000C, 0x000D, 0x000E, 0x000F, + 0x0010, 0x0011, 0x0012, 0x0013, 0x0014, 0x0015, 0x0016, 0x0017, 0x0018, 0x0019, 0x001A, 0x001B, 0x001C, 0x001D, 0x001E, 0x001F, + 0x0020, 0x0021, 0x0022, 0x0023, 0x0024, 0x0025, 0x0026, 0x0027, 0x0028, 0x0029, 0x002A, 0x002B, 0x002C, 0x002D, 0x002E, 0x002F, + 0x0030, 0x0031, 0x0032, 0x0033, 0x0034, 0x0035, 0x0036, 0x0037, 0x0038, 0x0039, 0x003A, 0x003B, 0x003C, 0x003D, 0x003E, 0x003F, + 0x0040, 0x0041, 0x0042, 0x0043, 0x0044, 0x0045, 0x0046, 0x0047, 0x0048, 0x0049, 0x004A, 0x004B, 0x004C, 0x004D, 0x004E, 0x004F, + 0x0050, 0x0051, 0x0052, 0x0053, 0x0054, 0x0055, 0x0056, 0x0057, 0x0058, 0x0059, 0x005A, 0x005B, 0x005C, 0x005D, 0x005E, 0x005F, + 0x0060, 0x0061, 0x0062, 0x0063, 0x0064, 0x0065, 0x0066, 0x0067, 0x0068, 0x0069, 0x006A, 0x006B, 0x006C, 0x006D, 0x006E, 0x006F, + 0x0070, 0x0071, 0x0072, 0x0073, 0x0074, 0x0075, 0x0076, 0x0077, 0x0078, 0x0079, 0x007A, 0x007B, 0x007C, 0x007D, 0x007E, 0x007F, + 0x00C7, 0x00FC, 0x00E9, 0x00E2, 0x00E4, 0x00E0, 0x00E5, 0x00E7, 0x00EA, 0x00EB, 0x00E8, 0x00EF, 0x00EE, 0x00EC, 0x00C4, 0x00C5, + 0x00C9, 0x00E6, 0x00C6, 0x00F4, 0x00F6, 0x00F2, 0x00FB, 0x00F9, 0x00FF, 0x00D6, 0x00DC, 0x00A2, 0x00A3, 0x00A5, 0x20A7, 0x0192, + 0x00E1, 0x00ED, 0x00F3, 0x00FA, 0x00F1, 0x00D1, 0x00AA, 0x00BA, 0x00BF, 0x2310, 0x00AC, 0x00BD, 0x00BC, 0x00A1, 0x00AB, 0x00BB, + 0x2591, 0x2592, 0x2593, 0x2502, 0x2524, 0x2561, 0x2562, 0x2556, 0x2555, 0x2563, 0x2551, 0x2557, 0x255D, 0x255C, 0x255B, 0x2510, + 0x2514, 0x2534, 0x252C, 0x251C, 0x2500, 0x253C, 0x255E, 0x255F, 0x255A, 0x2554, 0x2569, 0x2566, 0x2560, 0x2550, 0x256C, 0x2567, + 0x2568, 0x2564, 0x2565, 0x2559, 0x2558, 0x2552, 0x2553, 0x256B, 0x256A, 0x2518, 0x250C, 0x2588, 0x2584, 0x258C, 0x2590, 0x2580, + 0x03B1, 0x00DF, 0x0393, 0x03C0, 0x03A3, 0x03C3, 0x00B5, 0x03C4, 0x03A6, 0x0398, 0x03A9, 0x03B4, 0x221E, 0x03C6, 0x03B5, 0x2229, + 0x2261, 0x00B1, 0x2265, 0x2264, 0x2320, 0x2321, 0x00F7, 0x2248, 0x00B0, 0x2219, 0x00B7, 0x221A, 0x207F, 0x00B2, 0x25A0, 0x00A0, +} diff --git a/tex/context/base/mkiv/regi-ini.lua b/tex/context/base/mkiv/regi-ini.lua index 37a88fd5f..be8fa1b1c 100644 --- a/tex/context/base/mkiv/regi-ini.lua +++ b/tex/context/base/mkiv/regi-ini.lua @@ -27,9 +27,6 @@ local sequencers = utilities.sequencers local textlineactions = resolvers.openers.helpers.textlineactions local setmetatableindex = table.setmetatableindex -local implement = interfaces.implement -local setmacro = interfaces.setmacro - --[[ldx-- <p>We will hook regime handling code into the input methods.</p> --ldx]]-- @@ -261,56 +258,6 @@ if sequencers then end --- interface: - -implement { - name = "enableregime", - arguments = "string", - actions = function(regime) setmacro("currentregime",enable(regime)) end -} - -implement { - name = "disableregime", - actions = function() setmacro("currentregime",disable()) end -} - -implement { - name = "pushregime", - actions = push -} - -implement { - name = "popregime", - actions = pop -} - -local stack = { } - -implement { - name = "startregime", - arguments = "string", - actions = function(regime) - insert(stack,currentregime) - if trace_translating then - report_translating("start using %a",regime) - end - setmacro("currentregime",enable(regime)) - end -} - -implement { - name = "stopregime", - actions = function() - if #stack > 0 then - local regime = remove(stack) - if trace_translating then - report_translating("stop using %a",regime) - end - setmacro("currentregime",enable(regime)) - end - end -} - -- Next we provide some hacks. Unfortunately we run into crappy encoded -- (read : mixed) encoded xml files that have these ë ä ö ü sequences -- instead of ë ä ö ü @@ -434,3 +381,60 @@ end -- local old = "Pozn" .. char(0xE1) .. "mky" -- local new = fromregime("cp1250",old) -- report_translating("%s -> %s",old,new) + +-- interface (might move to regi-tex.lua) + +if interfaces then + + local implement = interfaces.implement + local setmacro = interfaces.setmacro + + implement { + name = "enableregime", + arguments = "string", + actions = function(regime) setmacro("currentregime",enable(regime)) end + } + + implement { + name = "disableregime", + actions = function() setmacro("currentregime",disable()) end + } + + implement { + name = "pushregime", + actions = push + } + + implement { + name = "popregime", + actions = pop + } + + local stack = { } + + implement { + name = "startregime", + arguments = "string", + actions = function(regime) + insert(stack,currentregime) + if trace_translating then + report_translating("start using %a",regime) + end + setmacro("currentregime",enable(regime)) + end + } + + implement { + name = "stopregime", + actions = function() + if #stack > 0 then + local regime = remove(stack) + if trace_translating then + report_translating("stop using %a",regime) + end + setmacro("currentregime",enable(regime)) + end + end + } + +end diff --git a/tex/context/base/mkiv/spac-hor.mkiv b/tex/context/base/mkiv/spac-hor.mkiv index 7a275989a..ab877d1d1 100644 --- a/tex/context/base/mkiv/spac-hor.mkiv +++ b/tex/context/base/mkiv/spac-hor.mkiv @@ -767,14 +767,14 @@ \let\stopnarrow\spac_narrower_stop \newdimen\d_spac_effective_hsize \def\effectivehsize {\hsize} -\newdimen\d_spac_effective_leftskip \def\effectiveleftskip {\leftskip} -\newdimen\d_spac_effective_rightskip \def\effectiverightskip{\rightskip} +\newdimen\d_spac_effective_leftskip \def\effectiveleftskip {\dimexpr\leftskip \relax} +\newdimen\d_spac_effective_rightskip \def\effectiverightskip{\dimexpr\rightskip\relax} \unexpanded\def\seteffectivehsize {\setlocalhsize \d_spac_effective_hsize \localhsize - \d_spac_effective_leftskip \leftskip - \d_spac_effective_rightskip\rightskip + \d_spac_effective_leftskip 1\leftskip + \d_spac_effective_rightskip1\rightskip \let\effectivehsize \d_spac_effective_hsize \let\effectiveleftskip \d_spac_effective_leftskip \let\effectiverightskip\d_spac_effective_rightskip} diff --git a/tex/context/base/mkiv/status-files.pdf b/tex/context/base/mkiv/status-files.pdf Binary files differindex 03376e020..75e1b5aff 100644 --- a/tex/context/base/mkiv/status-files.pdf +++ b/tex/context/base/mkiv/status-files.pdf diff --git a/tex/context/base/mkiv/status-lua.pdf b/tex/context/base/mkiv/status-lua.pdf Binary files differindex 4c697e37e..0526d8fe5 100644 --- a/tex/context/base/mkiv/status-lua.pdf +++ b/tex/context/base/mkiv/status-lua.pdf diff --git a/tex/context/base/mkiv/strc-itm.mkvi b/tex/context/base/mkiv/strc-itm.mkvi index 48c8e1a30..fc05fc669 100644 --- a/tex/context/base/mkiv/strc-itm.mkvi +++ b/tex/context/base/mkiv/strc-itm.mkvi @@ -1118,6 +1118,7 @@ \dostarttagged\t!itemcontent\empty \strut \nobreak % else problems with intext items + \seteffectivehsize % NEW ! \hskip\d_strc_itemgroups_signal % concat \itemgroupparameter\c!command} diff --git a/tex/context/base/mkiv/syst-ini.mkiv b/tex/context/base/mkiv/syst-ini.mkiv index dc8300e7f..b2cc37f0c 100644 --- a/tex/context/base/mkiv/syst-ini.mkiv +++ b/tex/context/base/mkiv/syst-ini.mkiv @@ -200,6 +200,16 @@ \countdef \normalpagebox = 127 \normalpagebox = 255 % hardcoded in pdftex/xetex +% Only to be used by developers in very special cases! + +% \def\lastallocatedcount {\the\c_syst_last_allocated_count} +% \def\lastallocateddimen {\the\c_syst_last_allocated_dimen} +% \def\lastallocatedskip {\the\c_syst_last_allocated_skip} +% \def\lastallocatedmuskip {\the\c_syst_last_allocated_muskip} +% \def\lastallocatedbox {\the\c_syst_last_allocated_dimen} +% \def\lastallocatedtoks {\the\c_syst_last_allocated_toks} +% \def\lastallocatedattribute{\the\c_syst_last_allocated_attribute} + % A few traditional allocations (these might go): \countdef \count@ = 255 % hm, used in \newif .. todo: replace it there diff --git a/tex/context/base/mkiv/typo-brk.lua b/tex/context/base/mkiv/typo-brk.lua index 66615317b..2c21b97d4 100644 --- a/tex/context/base/mkiv/typo-brk.lua +++ b/tex/context/base/mkiv/typo-brk.lua @@ -170,7 +170,6 @@ methods[2] = function(head,start) -- ( => (- local tmp head, start, tmp = remove_node(head,start) head, start = insert_node_before(head,start,new_disc()) - -- setfield(start,"attr",copy_nodelist(getfield(tmp,"attr"))) -- just a copy will do setfield(start,"attr",getfield(tmp,"attr")) setfield(start,"replace",tmp) local tmp = copy_node(tmp) @@ -189,7 +188,6 @@ methods[3] = function(head,start) -- ) => -) local tmp head, start, tmp = remove_node(head,start) head, start = insert_node_before(head,start,new_disc()) - -- setfield(start,"attr",copy_nodelist(getfield(tmp,"attr"))) -- just a copy will do setfield(start,"attr",getfield(tmp,"attr")) setfield(start,"replace",tmp) local tmp = copy_node(tmp) @@ -208,7 +206,6 @@ methods[4] = function(head,start) -- - => - - - local tmp head, start, tmp = remove_node(head,start) head, start = insert_node_before(head,start,new_disc()) - -- setfield(start,"attr",copy_nodelist(getfield(tmp,"attr"))) -- just a copy will do setfield(start,"attr",getfield(tmp,"attr")) setdisc(start,copy_node(tmp),copy_node(tmp),tmp) insert_break(head,start,start,10000,10000) @@ -237,7 +234,6 @@ methods[5] = function(head,start,stop,settings) -- x => p q r middle = tonodes(tostring(middle),font,attr) end setdisc(start,left,right,middle) - -- setfield(start,"attr",copy_nodelist(attr)) -- todo: critical only -- just a copy will do setfield(start,"attr",attr) -- todo: critical only -- just a copy will do free_node(tmp) insert_break(head,start,start,10000,10000) @@ -272,6 +268,7 @@ function breakpoints.handler(head) if map then local cmap = map[char] if cmap then + setattr(current,a_breakpoints,unsetvalue) -- should not be needed -- for now we collect but when found ok we can move the handler here -- although it saves nothing in terms of performance local lang = getfield(current,"lang") @@ -301,7 +298,6 @@ function breakpoints.handler(head) else current = getnext(current) end - setattr(start,a_breakpoints,unsetvalue) -- should not be needed else current = getnext(current) end diff --git a/tex/context/base/mkiv/util-prs.lua b/tex/context/base/mkiv/util-prs.lua index 02729dd0e..82789ba3a 100644 --- a/tex/context/base/mkiv/util-prs.lua +++ b/tex/context/base/mkiv/util-prs.lua @@ -83,10 +83,6 @@ local pattern_b = spaces * comma^0 * spaces * (key * ((spaces * equal * spaces * -- "a=1, b=2, c=3, d={a{b,c}d}, e=12345, f=xx{a{b,c}d}xx, g={}" : outer {} removes, leading spaces ignored --- todo: rewrite to fold etc --- --- parse = lpeg.Cf(lpeg.Carg(1) * lpeg.Cg(key * equal * value) * separator^0,rawset)^0 -- lpeg.match(parse,"...",1,hash) - local hash = { } local function set(key,value) diff --git a/tex/context/interface/mkiv/i-context.pdf b/tex/context/interface/mkiv/i-context.pdf Binary files differindex 3d6d1b217..f6fe251b0 100644 --- a/tex/context/interface/mkiv/i-context.pdf +++ b/tex/context/interface/mkiv/i-context.pdf diff --git a/tex/context/interface/mkiv/i-readme.pdf b/tex/context/interface/mkiv/i-readme.pdf Binary files differindex e2209a67b..437fc541c 100644 --- a/tex/context/interface/mkiv/i-readme.pdf +++ b/tex/context/interface/mkiv/i-readme.pdf diff --git a/tex/context/modules/mkiv/m-steps.lua b/tex/context/modules/mkiv/m-steps.lua index f492c6c42..bba9ca8dd 100644 --- a/tex/context/modules/mkiv/m-steps.lua +++ b/tex/context/modules/mkiv/m-steps.lua @@ -10,11 +10,14 @@ if not modules then modules = { } end modules ['x-flow'] = { moduledata.steps = moduledata.steps or { } -local context = context -local variables = interfaces.variables +local context = context +local variables = interfaces.variables +local formatters = string.formatters +----- mpcolor = attributes.colors.mpnamedcolor +local concat = table.concat -local report = logs.reporter("stepcharts") -local trace = false +local report = logs.reporter("stepcharts") +local trace = false trackers.register("stepcharts",function(v) trace = v end) @@ -119,56 +122,93 @@ local function step_make_chart(settings) local textsettings = settings.text local cellsettings = settings.cell local linesettings = settings.line + + local start = context.startMPcode + local stop = context.stopMPcode + local flush = context + + if false then + + -- some 2% faster at most, so neglectable as this kind of graphics + -- is hardly used in quantity but it saves mem and tokens in tracing + -- and we lose some aspects, like outer color and so (currently) + + local mpcode = false + + local function start() + mpcode = { } + end + local function stop() + metapost.graphic { + instance = "metafun", + format = "metafun", + data = concat(mpcode,"\n"), + -- initializations = "", + -- extensions = "", + -- inclusions = "", + -- definitions = "", + -- figure = "", + method = "double", + } + mpcode = false + end + local function flush(fmt,first,...) + if first then + mpcode[#mpcode+1] = formatters[fmt](first,...) + else + mpcode[#mpcode+1] = fmt + end + end + + end -- - -- just process MP directly so that we can pass an array - -- - context.startMPcode() - context("if unknown context_cell : input mp-step.mpiv ; fi ;") - context("step_begin_chart ;") + start() + flush("if unknown context_cell : input mp-step.mpiv ; fi ;") + flush("step_begin_chart ;") -- local alternative = utilities.parsers.settings_to_hash(chartsettings.alternative) local vertical = alternative[variables.vertical] local align = alternative[variables.three] local category = chartsettings.category -- - context('chart_category := "%s" ;',category) + flush('chart_category := "%s" ;',category) -- if vertical then - context("chart_vertical := true ;") + flush("chart_vertical := true ;") end if align then - context("chart_align := true ;") + flush("chart_align := true ;") end -- - context("text_line_color := \\MPcolor{%s} ;", textsettings.framecolor) - context("text_line_width := %p ;", textsettings.rulethickness) - context("text_fill_color := \\MPcolor{%s} ;", textsettings.backgroundcolor) - context("text_offset := %p ;", textsettings.offset) - context("text_distance_set := %p ;", textsettings.distance) + flush("text_line_color := resolvedcolor(%q) ;", textsettings.framecolor) + flush("text_line_width := %p ;", textsettings.rulethickness) + flush("text_fill_color := resolvedcolor(%q) ;", textsettings.backgroundcolor) + flush("text_offset := %p ;", textsettings.offset) + flush("text_distance_set := %p ;", textsettings.distance) -- - context("cell_line_color := \\MPcolor{%s} ;", cellsettings.framecolor) - context("cell_line_width := %p ;", cellsettings.rulethickness) - context("cell_fill_color := \\MPcolor{%s} ;", cellsettings.backgroundcolor) - context("cell_offset := %p ;", cellsettings.offset) - context("cell_distance_x := %p ;", cellsettings.dx) - context("cell_distance_y := %p ;", cellsettings.dy) + flush("cell_line_color := resolvedcolor(%q) ;", cellsettings.framecolor) + flush("cell_line_width := %p ;", cellsettings.rulethickness) + flush("cell_fill_color := resolvedcolor(%q) ;", cellsettings.backgroundcolor) + flush("cell_offset := %p ;", cellsettings.offset) + flush("cell_distance_x := %p ;", cellsettings.dx) + flush("cell_distance_y := %p ;", cellsettings.dy) -- - context("line_line_color := \\MPcolor{%s} ;", linesettings.color) - context("line_line_width := %p ;", linesettings.rulethickness) - context("line_distance := %p ;", linesettings.distance) - context("line_offset := %p ;", linesettings.offset) - context("line_height := %p ;", linesettings.height) + flush("line_line_color := resolvedcolor(%q) ;", linesettings.color) + flush("line_line_width := %p ;", linesettings.rulethickness) + flush("line_distance := %p ;", linesettings.distance) + flush("line_offset := %p ;", linesettings.offset) + flush("line_height := %p ;", linesettings.height) -- for i=1,chart.count do local step = steps[i] - context("step_begin_cell ;") + flush("step_begin_cell ;") local ali = step.cell_ali local top = step.cell_top local bot = step.cell_bot if ali then local text = ali.text local shape = ali.shape - context('step_cell_ali(%s,%s,%s,\\MPcolor{%s},\\MPcolor{%s},%p,%i) ;', + flush('step_cell_ali(%s,%s,%s,resolvedcolor(%q),resolvedcolor(%q),%p,%i) ;', tonumber(text.left) or 0, tonumber(text.middle) or 0, tonumber(text.right) or 0, @@ -180,7 +220,7 @@ local function step_make_chart(settings) end if top then local shape = top.shape - context('step_cell_top(%s,\\MPcolor{%s},\\MPcolor{%s},%p,%i) ;', + flush('step_cell_top(%s,resolvedcolor(%q),resolvedcolor(%q),%p,%i) ;', tonumber(top.text.top) or 0, shape.framecolor, shape.backgroundcolor, @@ -190,7 +230,7 @@ local function step_make_chart(settings) end if bot then local shape = bot.shape - context('step_cell_bot(%s,\\MPcolor{%s},\\MPcolor{%s},%p,%i) ;', + flush('step_cell_bot(%s,resolvedcolor(%q),resolvedcolor(%q),%p,%i) ;', tonumber(bot.text.bot) or 0, shape.framecolor, shape.backgroundcolor, @@ -204,13 +244,10 @@ local function step_make_chart(settings) local s_t = step.start_t local s_m = step.start_m local s_b = step.start_b --- if vertical then --- top, bot, s_t, s_b = bot, top, s_b, s_t --- end if top then local shape = top.shape local line = top.line - context('step_text_top(%s,\\MPcolor{%s},\\MPcolor{%s},%p,%i,\\MPcolor{%s},%p,%i) ;', + flush('step_text_top(%s,resolvedcolor(%q),resolvedcolor(%q),%p,%i,resolvedcolor(%q),%p,%i) ;', tonumber(top.text.top) or 0, shape.framecolor, shape.backgroundcolor, @@ -224,7 +261,7 @@ local function step_make_chart(settings) if mid then -- used ? local shape = mid.shape local line = mid.line - context('step_text_mid(%s,\\MPcolor{%s},\\MPcolor{%s},%p,%i,\\MPcolor{%s},%p,%i) ;', + flush('step_text_mid(%s,resolvedcolor(%q),resolvedcolor(%q),%p,%i,resolvedcolor(%q),%p,%i) ;', tonumber(mid.text.mid) or 0, shape.framecolor, shape.backgroundcolor, @@ -238,7 +275,7 @@ local function step_make_chart(settings) if bot then local shape = bot.shape local line = bot.line - context('step_text_bot(%s,\\MPcolor{%s},\\MPcolor{%s},%p,%i,\\MPcolor{%s},%p,%i) ;', + flush('step_text_bot(%s,resolvedcolor(%q),resolvedcolor(%q),%p,%i,resolvedcolor(%q),%p,%i) ;', tonumber(bot.text.bot) or 0, shape.framecolor, shape.backgroundcolor, @@ -249,14 +286,14 @@ local function step_make_chart(settings) tonumber(line.alternative) or 1 ) end - context('start_t[%i] := %i ;',i,s_t) - context('start_m[%i] := %i ;',i,s_m) - context('start_b[%i] := %i ;',i,s_b) - context("step_end_cell ;") + flush('start_t[%i] := %i ;',i,s_t) + flush('start_m[%i] := %i ;',i,s_m) + flush('start_b[%i] := %i ;',i,s_b) + flush("step_end_cell ;") end -- - context("step_end_chart ;") - context.stopMPcode() + flush("step_end_chart ;") + stop() end local function step_cells(spec) @@ -302,16 +339,6 @@ local function step_text(spec) end end -local function step_textset(spec) - if count > 0 then - count = count + 1 - local step = steps[count] - step.text_top = spec - step.text_mid = spec - step.text_bot = spec - end -end - local function step_start_cell() count = count + 1 local step = steps[count] -- creates @@ -447,12 +474,6 @@ interfaces.implement { } interfaces.implement { - name = "step_textset", - arguments = step_spec, - actions = step_textset, -} - -interfaces.implement { name = "step_text_top", arguments = step_spec, actions = step_text_top, diff --git a/tex/context/modules/mkiv/m-steps.mkvi b/tex/context/modules/mkiv/m-steps.mkvi index 76aeed41f..841615d6e 100644 --- a/tex/context/modules/mkiv/m-steps.mkvi +++ b/tex/context/modules/mkiv/m-steps.mkvi @@ -247,7 +247,6 @@ \unexpanded\def\module_steps_texts {\dosingleempty\module_steps_texts_indeed} \unexpanded\def\module_steps_cell {\dosingleempty\module_steps_cell_indeed} \unexpanded\def\module_steps_text {\dosingleempty\module_steps_text_indeed} -%unexpanded\def\module_steps_textset {\dosingleempty\module_steps_textset_indeed} \unexpanded\def\module_steps_toptext {\dosingleempty\module_steps_toptext_indeed} \unexpanded\def\module_steps_bottext {\dosingleempty\module_steps_bottext_indeed} \unexpanded\def\module_steps_topcell {\dosingleempty\module_steps_topcell_indeed} @@ -358,22 +357,6 @@ }% \endgroup} -% \def\module_steps_textset_indeed[#category]#left#middle#right% -% {\begingroup -% \iffirstargument -% \module_steps_check_text{#category}% -% \fi -% \useSTEPtextstyleandcolor\c!style\c!color -% \setSTEPbox\module_steps_tag_a{#left}% -% \setSTEPbox\module_steps_tag_b{#middle}% -% \setSTEPbox\module_steps_tag_c{#right}% -% \clf_step_textset \module_steps_pass_data \STEPtextparameter { -% left {\module_steps_tag_a} -% middle {\module_steps_tag_a} -% right {\module_steps_tag_a} -% }% -% \endgroup} - \def\module_steps_toptext_indeed[#category]#top% {\begingroup \iffirstargument @@ -427,16 +410,13 @@ \let\texts \module_steps_texts \let\cell \module_steps_cell \let\text \module_steps_text - \let\textset\module_steps_textset \let\toptext\module_steps_toptext \let\bottext\module_steps_bottext \let\topcell\module_steps_topcell \let\botcell\module_steps_botcell \to \everySTEPchart -% todo: mapping can be done in lua - -% chart table cell text line +% The xml interface: \unexpanded\def\setSTEPxmldirective#1#2#3% {\begincsname setSTEP#1parameter\endcsname{#2}{#3}} @@ -558,14 +538,6 @@ \cells {five} {one} \stopSTEPchart -\startSTEPtable - \cell {one} \textset{$x$} {=}{$a+b+c$} - \cell {two} \textset{$c+d$}{=}{$y$} - \cell {three} -\stopSTEPtable - -\page - \startbuffer <stepchart> <cells> <top> some text </top> <bot> some text </bot> </cells> diff --git a/tex/generic/context/luatex/luatex-fonts-merged.lua b/tex/generic/context/luatex/luatex-fonts-merged.lua index 362aec0c3..59e985d64 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 : 06/26/16 19:00:04 +-- merge date : 07/01/16 16:28:20 do -- begin closure to overcome local limits and interference @@ -7025,7 +7025,7 @@ local P,R,S,C,Ct,Cc,lpegmatch=lpeg.P,lpeg.R,lpeg.S,lpeg.C,lpeg.Ct,lpeg.Cc,lpeg.m local floor=math.floor local formatters=string.formatters local trace_loading=false trackers.register("fonts.loading",function(v) trace_loading=v end) -local trace_mapping=false trackers.register("fonts.mapping",function(v) trace_unimapping=v end) +local trace_mapping=false trackers.register("fonts.mapping",function(v) trace_mapping=v end) local report_fonts=logs.reporter("fonts","loading") local force_ligatures=false directives.register("fonts.mapping.forceligatures",function(v) force_ligatures=v end) local fonts=fonts or {} @@ -7141,6 +7141,9 @@ function mappings.addtounicode(data,filename,checklookups) local resources=data.resources local unicodes=resources.unicodes if not unicodes then + if trace_mapping then + report_fonts("no unicode list, quitting tounicode for %a",filename) + end return end local properties=data.properties @@ -7329,8 +7332,8 @@ function mappings.addtounicode(data,filename,checklookups) end if trace_mapping then for unic,glyph in table.sortedhash(descriptions) do - local name=glyph.name - local index=glyph.index + local name=glyph.name or "-" + local index=glyph.index or 0 local unicode=glyph.unicode if unicode then if type(unicode)=="table" then @@ -7433,287 +7436,6 @@ end -- closure do -- begin closure to overcome local limits and interference -if not modules then modules={} end modules ['font-tfm']={ - version=1.001, - comment="companion to font-ini.mkiv", - author="Hans Hagen, PRAGMA-ADE, Hasselt NL", - copyright="PRAGMA ADE / ConTeXt Development Team", - license="see context related readme files" -} -local next,type=next,type -local match=string.match -local trace_defining=false trackers.register("fonts.defining",function(v) trace_defining=v end) -local trace_features=false trackers.register("tfm.features",function(v) trace_features=v end) -local report_defining=logs.reporter("fonts","defining") -local report_tfm=logs.reporter("fonts","tfm loading") -local findbinfile=resolvers.findbinfile -local fonts=fonts -local handlers=fonts.handlers -local readers=fonts.readers -local constructors=fonts.constructors -local encodings=fonts.encodings -local tfm=constructors.handlers.tfm -tfm.version=1.000 -tfm.maxnestingdepth=5 -tfm.maxnestingsize=65536*1024 -local tfmfeatures=constructors.features.tfm -constructors.resolvevirtualtoo=false -fonts.formats.tfm="type1" -fonts.formats.ofm="type1" -function tfm.setfeatures(tfmdata,features) - local okay=constructors.initializefeatures("tfm",tfmdata,features,trace_features,report_tfm) - if okay then - return constructors.collectprocessors("tfm",tfmdata,features,trace_features,report_tfm) - else - return {} - end -end -function tfm.reencode(tfmdata,specification) - return tfmdata -end -local depth={} -local function read_from_tfm(specification) - local filename=specification.filename - local size=specification.size - depth[filename]=(depth[filename] or 0)+1 - if trace_defining then - report_defining("loading tfm file %a at size %s",filename,size) - end - local tfmdata=font.read_tfm(filename,size) - if tfmdata then - tfmdata=tfm.reencode(tfmdata,specification) - local features=specification.features and specification.features.normal or {} - local resources=tfmdata.resources or {} - local properties=tfmdata.properties or {} - local parameters=tfmdata.parameters or {} - local shared=tfmdata.shared or {} - properties.name=tfmdata.name - properties.fontname=tfmdata.fontname - properties.psname=tfmdata.psname - properties.filename=specification.filename - properties.format=fonts.formats.tfm - tfmdata.properties=properties - tfmdata.resources=resources - tfmdata.parameters=parameters - tfmdata.shared=shared - shared.rawdata={} - shared.features=features - shared.processes=next(features) and tfm.setfeatures(tfmdata,features) or nil - parameters.size=size - parameters.slant=parameters.slant or parameters[1] or 0 - parameters.space=parameters.space or parameters[2] or 0 - parameters.space_stretch=parameters.space_stretch or parameters[3] or 0 - parameters.space_shrink=parameters.space_shrink or parameters[4] or 0 - parameters.x_height=parameters.x_height or parameters[5] or 0 - parameters.quad=parameters.quad or parameters[6] or 0 - parameters.extra_space=parameters.extra_space or parameters[7] or 0 - constructors.enhanceparameters(parameters) - if constructors.resolvevirtualtoo then - fonts.loggers.register(tfmdata,file.suffix(filename),specification) - local vfname=findbinfile(specification.name,'ovf') - if vfname and vfname~="" then - local vfdata=font.read_vf(vfname,size) - if vfdata then - local chars=tfmdata.characters - for k,v in next,vfdata.characters do - chars[k].commands=v.commands - end - properties.virtualized=true - tfmdata.fonts=vfdata.fonts - tfmdata.type="virtual" - local fontlist=vfdata.fonts - local name=file.nameonly(filename) - for i=1,#fontlist do - local n=fontlist[i].name - local s=fontlist[i].size - local d=depth[filename] - s=constructors.scaled(s,vfdata.designsize) - if d>tfm.maxnestingdepth then - report_defining("too deeply nested virtual font %a with size %a, max nesting depth %s",n,s,tfm.maxnestingdepth) - fontlist[i]={ id=0 } - elseif (d>1) and (s>tfm.maxnestingsize) then - report_defining("virtual font %a exceeds size %s",n,s) - fontlist[i]={ id=0 } - else - local t,id=fonts.constructors.readanddefine(n,s) - fontlist[i]={ id=id } - end - end - end - end - end - local allfeatures=tfmdata.shared.features or specification.features.normal - constructors.applymanipulators("tfm",tfmdata,allfeatures,trace_features,report_tfm) - if not features.encoding then - local encoding,filename=match(properties.filename,"^(.-)%-(.*)$") - if filename and encoding and encodings.known and encodings.known[encoding] then - features.encoding=encoding - end - end - properties.haskerns=true - properties.hasligatures=true - resources.unicodes={} - resources.lookuptags={} - depth[filename]=depth[filename]-1 - return tfmdata - else - depth[filename]=depth[filename]-1 - end -end -local function check_tfm(specification,fullname) - local foundname=findbinfile(fullname,'tfm') or "" - if foundname=="" then - foundname=findbinfile(fullname,'ofm') or "" - end - if foundname=="" then - foundname=fonts.names.getfilename(fullname,"tfm") or "" - end - if foundname~="" then - specification.filename=foundname - specification.format="ofm" - return read_from_tfm(specification) - elseif trace_defining then - report_defining("loading tfm with name %a fails",specification.name) - end -end -readers.check_tfm=check_tfm -function readers.tfm(specification) - local fullname=specification.filename or "" - if fullname=="" then - local forced=specification.forced or "" - if forced~="" then - fullname=specification.name.."."..forced - else - fullname=specification.name - end - end - return check_tfm(specification,fullname) -end -readers.ofm=readers.tfm -do - local outfiles={} - local tfmcache=table.setmetatableindex(function(t,tfmdata) - local id=font.define(tfmdata) - t[tfmdata]=id - return id - end) - local encdone=table.setmetatableindex("table") - function tfm.reencode(tfmdata,specification) - local features=specification.features - if not features then - return tfmdata - end - local features=features.normal - if not features then - return tfmdata - end - local tfmfile=file.basename(tfmdata.name) - local encfile=features.reencode - local pfbfile=features.pfbfile - local bitmap=features.bitmap - if not encfile then - return tfmdata - end - local pfbfile=outfiles[tfmfile] - if pfbfile==nil then - if bitmap then - pfbfile=false - elseif type(pfbfile)~="string" then - pfbfile=tfmfile - end - if type(pfbfile)=="string" then - pfbfile=file.addsuffix(pfbfile,"pfb") - pdf.mapline(tfmfile.."<"..pfbfile) - report_tfm("using type1 shapes from %a for %a",pfbfile,tfmfile) - else - report_tfm("using bitmap shapes for %a",tfmfile) - pfbfile=false - end - outfiles[tfmfile]=pfbfile - end - local encoding=false - if type(encfile)=="string" and encfile~="auto" then - encoding=fonts.encodings.load(file.addsuffix(encfile,"enc")) - if encoding then - encoding=encoding.vector - end - elseif type(pfbfile)=="string" then - local pfb=fonts.constructors.handlers.pfb - if pfb and pfb.loadvector then - local v,e=pfb.loadvector(pfbfile) - if e then - encoding=e - end - end - end - if not encoding then - report_tfm("bad encoding for %a, quitting",tfmfile) - return tfmdata - end - local unicoding=fonts.encodings.agl and fonts.encodings.agl.unicodes - local virtualid=tfmcache[tfmdata] - local tfmdata=table.copy(tfmdata) - local characters={} - local originals=tfmdata.characters - local indices={} - local parentfont={ "font",1 } - local private=fonts.constructors.privateoffset - local reported=encdone[tfmfile][encfile] - for index,name in table.sortedhash(encoding) do - local unicode=unicoding[name] - local original=originals[index] - if original then - if not unicode then - unicode=private - private=private+1 - if not reported then - report_tfm("glyph %a in font %a with encoding %a gets unicode %U",name,tfmfile,encfile,unicode) - end - end - characters[unicode]=original - indices[index]=unicode - original.name=name - original.commands={ parentfont,{ "char",index } } - else - report_tfm("bad index %a in font %a with name %a",index,tfmfile,name) - end - end - encdone[tfmfile][encfile]=true - for k,v in next,characters do - local kerns=v.kerns - if kerns then - local t={} - for k,v in next,kerns do - local i=indices[k] - if i then - t[i]=v - end - end - v.kerns=next(t) and t or nil - end - local ligatures=v.ligatures - if ligatures then - local t={} - for k,v in next,ligatures do - local i=indices[k] - if i then - t[i]=v - v.char=indices[v.char] - end - end - v.ligatures=next(t) and t or nil - end - end - tfmdata.fonts={ { id=virtualid } } - tfmdata.characters=characters - return tfmdata - end -end - -end -- closure - -do -- begin closure to overcome local limits and interference - if not modules then modules={} end modules ['font-oti']={ version=1.001, comment="companion to font-ini.mkiv", @@ -7740,6 +7462,7 @@ local function setmode(tfmdata,value) tfmdata.properties.mode=lower(value) end end +otf.modeinitializer=setmode local function setlanguage(tfmdata,value) if value then local cleanvalue=lower(value) @@ -14217,6 +13940,7 @@ function readers.getcomponents(fontdata) end end end +readers.unifymissing=unifymissing function readers.rehash(fontdata,hashmethod) if not (fontdata and fontdata.glyphs) then return @@ -16246,7 +15970,7 @@ local function registerbasehash(tfmdata) basehash[hash]=base end properties.basehash=base - properties.fullname=properties.fullname.."-"..base + properties.fullname=(properties.fullname or properties.name).."-"..base applied={} end local function registerbasefeature(feature,value) @@ -16314,6 +16038,10 @@ local function preparesubstitutions(tfmdata,feature,value,validlookups,lookuplis local trace_singles=trace_baseinit and trace_singles local trace_alternatives=trace_baseinit and trace_alternatives local trace_ligatures=trace_baseinit and trace_ligatures + if not changed then + changed={} + tfmdata.changed=changed + end for i=1,#lookuplist do local sequence=lookuplist[i] local steps=sequence.steps @@ -16467,7 +16195,8 @@ local function featuresinitializer(tfmdata,value) local properties=tfmdata.properties local script=properties.script local language=properties.language - local rawfeatures=rawdata.resources.features + local rawresources=rawdata.resources + local rawfeatures=rawresources and rawresources.features local basesubstitutions=rawfeatures and rawfeatures.gsub local basepositionings=rawfeatures and rawfeatures.gpos if basesubstitutions or basepositionings then @@ -23510,9 +23239,7 @@ local trace_indexing=false trackers.register("afm.indexing",function(v) trace_in local trace_loading=false trackers.register("afm.loading",function(v) trace_loading=v end) local report_afm=logs.reporter("fonts","afm loading") local report_pfb=logs.reporter("fonts","pfb loading") -fonts=fonts or {} -local handlers=fonts.handlers or {} -fonts.handlers=handlers +local handlers=fonts.handlers local afm=handlers.afm or {} handlers.afm=afm local readers=afm.readers or {} @@ -23585,9 +23312,10 @@ do end binary=decrypt(binary,4) local vector=lpegmatch(p_filternames,binary) - if vector[1]==".notdef" then - vector[0]=table.remove(vector,1) + for i=1,#vector do + vector[i-1]=vector[i] end + vector[#vector]=nil if not vector then report_pfb("no vector in %a",filename) return @@ -23823,6 +23551,7 @@ local steps={ "add ligatures", "add extra kerns", "normalize features", + "check extra features", "fix names", } local function applyenhancers(data,filename) @@ -24036,6 +23765,7 @@ enhancers["normalize features"]=function(data) data.resources.features=features data.resources.sequences=sequences end +enhancers["check extra features"]=otf.enhancers.enhance enhancers["fix names"]=function(data) for k,v in next,data.descriptions do local n=v.name @@ -24397,17 +24127,12 @@ local function read_from_afm(specification) end return tfmdata end -local function setmode(tfmdata,value) - if value then - tfmdata.properties.mode=lower(value) - end -end registerafmfeature { name="mode", description="mode", initializers={ - base=setmode, - node=setmode, + base=otf.modeinitializer, + node=otf.modeinitializer, } } registerafmfeature { @@ -24422,7 +24147,6 @@ registerafmfeature { node=otf.featuresprocessor, } } -local check_tfm=readers.check_tfm fonts.formats.afm="type1" fonts.formats.pfb="type1" local function check_afm(specification,fullname) @@ -24457,7 +24181,8 @@ function readers.afm(specification,method) tfmdata=check_afm(specification,specification.name.."."..forced) end if not tfmdata then - method=method or definers.method or "afm or tfm" + local check_tfm=readers.check_tfm + method=(check_tfm and (method or definers.method or "afm or tfm")) or "afm" if method=="tfm" then tfmdata=check_tfm(specification,specification.name) elseif method=="afm" then @@ -24665,6 +24390,529 @@ end -- closure do -- begin closure to overcome local limits and interference +if not modules then modules={} end modules ['font-tfm']={ + version=1.001, + comment="companion to font-ini.mkiv", + author="Hans Hagen, PRAGMA-ADE, Hasselt NL", + copyright="PRAGMA ADE / ConTeXt Development Team", + license="see context related readme files" +} +local next,type=next,type +local match,format=string.match,string.format +local concat,sortedhash=table.concat,table.sortedhash +local trace_defining=false trackers.register("fonts.defining",function(v) trace_defining=v end) +local trace_features=false trackers.register("tfm.features",function(v) trace_features=v end) +local report_defining=logs.reporter("fonts","defining") +local report_tfm=logs.reporter("fonts","tfm loading") +local findbinfile=resolvers.findbinfile +local setmetatableindex=table.setmetatableindex +local fonts=fonts +local handlers=fonts.handlers +local readers=fonts.readers +local constructors=fonts.constructors +local encodings=fonts.encodings +local tfm=constructors.handlers.tfm +tfm.version=1.000 +tfm.maxnestingdepth=5 +tfm.maxnestingsize=65536*1024 +local otf=fonts.handlers.otf +local tfmfeatures=constructors.features.tfm +local registertfmfeature=tfmfeatures.register +constructors.resolvevirtualtoo=false +fonts.formats.tfm="type1" +fonts.formats.ofm="type1" +function tfm.setfeatures(tfmdata,features) + local okay=constructors.initializefeatures("tfm",tfmdata,features,trace_features,report_tfm) + if okay then + return constructors.collectprocessors("tfm",tfmdata,features,trace_features,report_tfm) + else + return {} + end +end +local depth={} +local enhancers={} +local steps={ + "normalize features", + "check extra features" +} +enhancers["check extra features"]=otf.enhancers.enhance +local function applyenhancers(data,filename) + for i=1,#steps do + local step=steps[i] + local enhancer=enhancers[step] + if enhancer then + if trace_loading then + report_tfm("applying enhancer %a",step) + end + enhancer(data,filename) + else + report_tfm("invalid enhancer %a",step) + end + end +end +local function read_from_tfm(specification) + local filename=specification.filename + local size=specification.size + depth[filename]=(depth[filename] or 0)+1 + if trace_defining then + report_defining("loading tfm file %a at size %s",filename,size) + end + local tfmdata=font.read_tfm(filename,size) + if tfmdata then + local features=specification.features and specification.features.normal or {} + local features=constructors.checkedfeatures("tfm",features) + specification.features.normal=features + local newtfmdata=(depth[filename]==1) and tfm.reencode(tfmdata,specification) + if newtfmdata then + tfmdata=newtfmdata + end + local resources=tfmdata.resources or {} + local properties=tfmdata.properties or {} + local parameters=tfmdata.parameters or {} + local shared=tfmdata.shared or {} + shared.features=features + shared.resources=resources + properties.name=tfmdata.name + properties.fontname=tfmdata.fontname + properties.psname=tfmdata.psname + properties.fullname=tfmdata.fullname + properties.filename=specification.filename + properties.format=fonts.formats.tfm + tfmdata.properties=properties + tfmdata.resources=resources + tfmdata.parameters=parameters + tfmdata.shared=shared + shared.rawdata={ resources=resources } + shared.features=features + if newtfmdata then + if not resources.marks then + resources.marks={} + end + if not resources.sequences then + resources.sequences={} + end + if not resources.features then + resources.features={ + gsub={}, + gpos={}, + } + end + if not tfmdata.changed then + tfmdata.changed={} + end + if not tfmdata.descriptions then + tfmdata.descriptions=tfmdata.characters + end + otf.readers.addunicodetable(tfmdata) + applyenhancers(tfmdata,filename) + constructors.applymanipulators("tfm",tfmdata,features,trace_features,report_tfm) + otf.readers.unifymissing(tfmdata) + fonts.mappings.addtounicode(tfmdata,filename) + tfmdata.tounicode=1 + local tounicode=fonts.mappings.tounicode + for unicode,v in next,tfmdata.characters do + local u=v.unicode + if u then + v.tounicode=tounicode(u) + end + end + if tfmdata.usedbitmap then + tfm.addtounicode(tfmdata) + end + end + shared.processes=next(features) and tfm.setfeatures(tfmdata,features) or nil + parameters.factor=1 + parameters.size=size + parameters.slant=parameters.slant or parameters[1] or 0 + parameters.space=parameters.space or parameters[2] or 0 + parameters.space_stretch=parameters.space_stretch or parameters[3] or 0 + parameters.space_shrink=parameters.space_shrink or parameters[4] or 0 + parameters.x_height=parameters.x_height or parameters[5] or 0 + parameters.quad=parameters.quad or parameters[6] or 0 + parameters.extra_space=parameters.extra_space or parameters[7] or 0 + constructors.enhanceparameters(parameters) + if newtfmdata then + elseif constructors.resolvevirtualtoo then + fonts.loggers.register(tfmdata,file.suffix(filename),specification) + local vfname=findbinfile(specification.name,'ovf') + if vfname and vfname~="" then + local vfdata=font.read_vf(vfname,size) + if vfdata then + local chars=tfmdata.characters + for k,v in next,vfdata.characters do + chars[k].commands=v.commands + end + properties.virtualized=true + tfmdata.fonts=vfdata.fonts + tfmdata.type="virtual" + local fontlist=vfdata.fonts + local name=file.nameonly(filename) + for i=1,#fontlist do + local n=fontlist[i].name + local s=fontlist[i].size + local d=depth[filename] + s=constructors.scaled(s,vfdata.designsize) + if d>tfm.maxnestingdepth then + report_defining("too deeply nested virtual font %a with size %a, max nesting depth %s",n,s,tfm.maxnestingdepth) + fontlist[i]={ id=0 } + elseif (d>1) and (s>tfm.maxnestingsize) then + report_defining("virtual font %a exceeds size %s",n,s) + fontlist[i]={ id=0 } + else + local t,id=fonts.constructors.readanddefine(n,s) + fontlist[i]={ id=id } + end + end + end + end + end + properties.haskerns=true + properties.hasligatures=true + resources.unicodes={} + resources.lookuptags={} + depth[filename]=depth[filename]-1 + return tfmdata + else + depth[filename]=depth[filename]-1 + end +end +local function check_tfm(specification,fullname) + local foundname=findbinfile(fullname,'tfm') or "" + if foundname=="" then + foundname=findbinfile(fullname,'ofm') or "" + end + if foundname=="" then + foundname=fonts.names.getfilename(fullname,"tfm") or "" + end + if foundname~="" then + specification.filename=foundname + specification.format="ofm" + return read_from_tfm(specification) + elseif trace_defining then + report_defining("loading tfm with name %a fails",specification.name) + end +end +readers.check_tfm=check_tfm +function readers.tfm(specification) + local fullname=specification.filename or "" + if fullname=="" then + local forced=specification.forced or "" + if forced~="" then + fullname=specification.name.."."..forced + else + fullname=specification.name + end + end + return check_tfm(specification,fullname) +end +readers.ofm=readers.tfm +do + local outfiles={} + local tfmcache=table.setmetatableindex(function(t,tfmdata) + local id=font.define(tfmdata) + t[tfmdata]=id + return id + end) + local encdone=table.setmetatableindex("table") + function tfm.reencode(tfmdata,specification) + local features=specification.features + if not features then + return + end + local features=features.normal + if not features then + return + end + local tfmfile=file.basename(tfmdata.name) + local encfile=features.reencode + local pfbfile=features.pfbfile + local bitmap=features.bitmap + if not encfile then + return + end + local pfbfile=outfiles[tfmfile] + if pfbfile==nil then + if bitmap then + pfbfile=false + elseif type(pfbfile)~="string" then + pfbfile=tfmfile + end + if type(pfbfile)=="string" then + pfbfile=file.addsuffix(pfbfile,"pfb") + report_tfm("using type1 shapes from %a for %a",pfbfile,tfmfile) + else + report_tfm("using bitmap shapes for %a",tfmfile) + pfbfile=false + end + outfiles[tfmfile]=pfbfile + end + local encoding=false + local vector=false + if type(pfbfile)=="string" then + local pfb=fonts.constructors.handlers.pfb + if pfb and pfb.loadvector then + local v,e=pfb.loadvector(pfbfile) + if v then + vector=v + end + if e then + encoding=e + end + end + end + if type(encfile)=="string" and encfile~="auto" then + encoding=fonts.encodings.load(file.addsuffix(encfile,"enc")) + if encoding then + encoding=encoding.vector + end + end + if not encoding then + report_tfm("bad encoding for %a, quitting",tfmfile) + return + end + local unicoding=fonts.encodings.agl and fonts.encodings.agl.unicodes + local virtualid=tfmcache[tfmdata] + local tfmdata=table.copy(tfmdata) + local characters={} + local originals=tfmdata.characters + local indices={} + local parentfont={ "font",1 } + local private=fonts.constructors.privateoffset + local reported=encdone[tfmfile][encfile] + local backmap=vector and table.swapped(vector) + local done={} + for index,name in sortedhash(encoding) do + local unicode=unicoding[name] + local original=originals[index] + if original then + if unicode then + original.unicode=unicode + else + unicode=private + private=private+1 + if not reported then + report_tfm("glyph %a in font %a with encoding %a gets unicode %U",name,tfmfile,encfile,unicode) + end + end + characters[unicode]=original + indices[index]=unicode + original.name=name + if backmap then + original.index=backmap[name] + else + original.commands={ parentfont,{ "char",index } } + original.oindex=index + end + done[name]=true + elseif not done[name] then + report_tfm("bad index %a in font %a with name %a",index,tfmfile,name) + end + end + encdone[tfmfile][encfile]=true + for k,v in next,characters do + local kerns=v.kerns + if kerns then + local t={} + for k,v in next,kerns do + local i=indices[k] + if i then + t[i]=v + end + end + v.kerns=next(t) and t or nil + end + local ligatures=v.ligatures + if ligatures then + local t={} + for k,v in next,ligatures do + local i=indices[k] + if i then + t[i]=v + v.char=indices[v.char] + end + end + v.ligatures=next(t) and t or nil + end + end + tfmdata.fonts={ { id=virtualid } } + tfmdata.characters=characters + tfmdata.fullname=tfmdata.fullname or tfmdata.name + tfmdata.psname=file.nameonly(pfbfile or tfmdata.name) + tfmdata.filename=pfbfile + tfmdata.encodingbytes=2 + tfmdata.format="type1" + tfmdata.tounicode=1 + tfmdata.embedding="subset" + tfmdata.usedbitmap=bitmap and virtualid + return tfmdata + end +end +do + local template=[[ +/CIDInit /ProcSet findresource begin + 12 dict begin + begincmap + /CIDSystemInfo << /Registry (TeX) /Ordering (bitmap-%s) /Supplement 0 >> def + /CMapName /TeX-bitmap-%s def + /CMapType 2 def + 1 begincodespacerange + <00> <FF> + endcodespacerange + %s beginbfchar +%s + endbfchar + endcmap +CMapName currentdict /CMap defineresource pop end +end +end +]] + local flushstreamobject=lpdf and lpdf.flushstreamobject + local setfontattributes=pdf.setfontattributes + if not flushstreamobject then + flushstreamobject=function(data) + return pdf.obj { + immediate=true, + type="stream", + string=data, + } + end + end + if not setfontattributes then + setfontattributes=function(id,data) + print(format("your luatex is too old so no tounicode bitmap font%i",id)) + end + end + function tfm.addtounicode(tfmdata) + local id=tfmdata.usedbitmap + local map={} + local char={} + for k,v in next,tfmdata.characters do + local index=v.oindex + local tounicode=v.tounicode + if index and tounicode then + map[index]=tounicode + end + end + for k,v in sortedhash(map) do + char[#char+1]=format("<%02X> <%s>",k,v) + end + char=concat(char,"\n") + local stream=format(template,id,id,#char,char) + local reference=flushstreamobject(stream,nil,true) + setfontattributes(id,format("/ToUnicode %i 0 R",reference)) + end +end +do + local everywhere={ ["*"]={ ["*"]=true } } + local noflags={ false,false,false,false } + enhancers["normalize features"]=function(data) + local ligatures=setmetatableindex("table") + local kerns=setmetatableindex("table") + local characters=data.characters + for u,c in next,characters do + local l=c.ligatures + local k=c.kerns + if l then + ligatures[u]=l + for u,v in next,l do + l[u]={ ligature=v.char } + end + c.ligatures=nil + end + if k then + kerns[u]=k + for u,v in next,k do + k[u]=v + end + c.kerns=nil + end + end + for u,l in next,ligatures do + for k,v in next,l do + local vl=v.ligature + local dl=ligatures[vl] + if dl then + for kk,vv in next,dl do + v[kk]=vv + end + end + end + end + local features={ + gpos={}, + gsub={}, + } + local sequences={ + } + if next(ligatures) then + features.gsub.liga=everywhere + data.properties.hasligatures=true + sequences[#sequences+1]={ + features={ + liga=everywhere, + }, + flags=noflags, + name="s_s_0", + nofsteps=1, + order={ "liga" }, + type="gsub_ligature", + steps={ + { + coverage=ligatures, + }, + }, + } + end + if next(kerns) then + features.gpos.kern=everywhere + data.properties.haskerns=true + sequences[#sequences+1]={ + features={ + kern=everywhere, + }, + flags=noflags, + name="p_s_0", + nofsteps=1, + order={ "kern" }, + type="gpos_pair", + steps={ + { + format="kern", + coverage=kerns, + }, + }, + } + end + data.resources.features=features + data.resources.sequences=sequences + data.shared.resources=data.shared.resources or resources + end +end +registertfmfeature { + name="mode", + description="mode", + initializers={ + base=otf.modeinitializer, + node=otf.modeinitializer, + } +} +registertfmfeature { + name="features", + description="features", + default=true, + initializers={ + base=otf.basemodeinitializer, + node=otf.nodemodeinitializer, + }, + processors={ + node=otf.featuresprocessor, + } +} + +end -- closure + +do -- begin closure to overcome local limits and interference + if not modules then modules={} end modules ['font-lua']={ version=1.001, comment="companion to font-ini.mkiv", diff --git a/tex/generic/context/luatex/luatex-fonts.lua b/tex/generic/context/luatex/luatex-fonts.lua index 83d52d9a5..41b95d98c 100644 --- a/tex/generic/context/luatex/luatex-fonts.lua +++ b/tex/generic/context/luatex/luatex-fonts.lua @@ -230,7 +230,6 @@ if non_generic_context.luatex_fonts.skip_loading ~= true then loadmodule('luatex-fonts-syn.lua') - loadmodule('font-tfm.lua') loadmodule('font-oti.lua') -- These are the old loader and processing modules. These use the built-in font loader and @@ -266,6 +265,10 @@ if non_generic_context.luatex_fonts.skip_loading ~= true then loadmodule('font-one.lua') -- was font-afm.lua loadmodule('font-afk.lua') + -- traditional code + + loadmodule('font-tfm.lua') + -- common code loadmodule('font-lua.lua') |