diff options
author | Philipp Gesang <phg42.2a@gmail.com> | 2013-04-23 03:07:32 +0200 |
---|---|---|
committer | Philipp Gesang <phg42.2a@gmail.com> | 2013-04-23 03:07:32 +0200 |
commit | c6a89a39cab64e09d530136e085383e7af3b05b8 (patch) | |
tree | 9fd1624ba632fbe951252178247b34427c9f0eaa | |
parent | 1faface747fdf8ca61c4f50518525e5d11bb1063 (diff) | |
download | luaotfload-c6a89a39cab64e09d530136e085383e7af3b05b8.tar.gz |
combine luaotfload-font-ltx -> luaotfload-features
-rw-r--r-- | luaotfload-features.lua | 229 | ||||
-rw-r--r-- | luaotfload-font-ltx.lua | 205 | ||||
-rw-r--r-- | tests/lookups.tex | 14 |
3 files changed, 243 insertions, 205 deletions
diff --git a/luaotfload-features.lua b/luaotfload-features.lua index aae0515..f954e72 100644 --- a/luaotfload-features.lua +++ b/luaotfload-features.lua @@ -1,3 +1,230 @@ +if not modules then modules = { } end modules ["features"] = { + version = 1.000, + comment = "companion to luaotfload.lua", + author = "Hans Hagen, PRAGMA-ADE, Hasselt NL", + copyright = "PRAGMA ADE / ConTeXt Development Team", + license = "see context related readme files" +} + +---[[ begin included font-ltx.lua ]] +--- this appears to be based in part on luatex-fonts-def.lua + +local fonts = fonts + +-- A bit of tuning for definitions. + +fonts.constructors.namemode = "specification" -- somehow latex needs this (changed name!) => will change into an overload + +-- tricky: we sort of bypass the parser and directly feed all into +-- the sub parser + +function fonts.definers.getspecification(str) + return "", str, "", ":", str +end + +local feature_list = { } + +local report = logs.names_report + +local stringlower = string.lower +local stringsub = string.sub +local stringgsub = string.gsub +local stringfind = string.find +local stringexplode = string.explode +local stringis_empty = string.is_empty + +local supported = { + b = "bold", + i = "italic", + bi = "bolditalic", + aat = false, + icu = false, + gr = false, +} + +--- this parses the optional flags after the slash +--- the original behavior is that multiple slashes +--- are valid but they might cancel prior settings +--- example: {name:Antykwa Torunska/I/B} -> bold + +local isstyle = function (request) + request = stringlower(request) + request = stringexplode(request, "/") + + for _,v in next, request do + local stylename = supported[v] + if stylename then + feature_list.style = stylename + elseif stringfind(v, "^s=") then + --- after all, we want everything after the second byte ... + local val = stringsub(v, 3) + feature_list.optsize = val + elseif stylename == false then + report("log", 0, + "load font", "unsupported font option: %s", v) + elseif not stringis_empty(v) then + feature_list.style = stringgsub(v, "[^%a%d]", "") + end + end +end + +local defaults = { + dflt = { + "ccmp", "locl", "rlig", "liga", "clig", + "kern", "mark", "mkmk", 'itlc', + }, + arab = { + "ccmp", "locl", "isol", "fina", "fin2", + "fin3", "medi", "med2", "init", "rlig", + "calt", "liga", "cswh", "mset", "curs", + "kern", "mark", "mkmk", + }, + deva = { + "ccmp", "locl", "init", "nukt", "akhn", + "rphf", "blwf", "half", "pstf", "vatu", + "pres", "blws", "abvs", "psts", "haln", + "calt", "blwm", "abvm", "dist", "kern", + "mark", "mkmk", + }, + khmr = { + "ccmp", "locl", "pref", "blwf", "abvf", + "pstf", "pres", "blws", "abvs", "psts", + "clig", "calt", "blwm", "abvm", "dist", + "kern", "mark", "mkmk", + }, + thai = { + "ccmp", "locl", "liga", "kern", "mark", + "mkmk", + }, + hang = { + "ccmp", "ljmo", "vjmo", "tjmo", + }, +} + +defaults.beng = defaults.deva +defaults.guru = defaults.deva +defaults.gujr = defaults.deva +defaults.orya = defaults.deva +defaults.taml = defaults.deva +defaults.telu = defaults.deva +defaults.knda = defaults.deva +defaults.mlym = defaults.deva +defaults.sinh = defaults.deva + +defaults.syrc = defaults.arab +defaults.mong = defaults.arab +defaults.nko = defaults.arab + +defaults.tibt = defaults.khmr + +defaults.lao = defaults.thai + +local function set_default_features(script) + local features + local script = script or "dflt" + report("log", 0, "load font", + "auto-selecting default features for script: %s", + script) + if defaults[script] then + features = defaults[script] + else + features = defaults["dflt"] + end + for _,v in next, features do + if feature_list[v] ~= false then + feature_list[v] = true + end + end +end + +local function issome () feature_list.lookup = 'name' end +local function isfile () feature_list.lookup = 'file' end +local function isname () feature_list.lookup = 'name' end +local function thename(s) feature_list.name = s end +local function issub (v) feature_list.sub = v end +local function istrue (s) feature_list[s] = true end +local function isfalse(s) feature_list[s] = false end +local function iskey (k,v) feature_list[k] = v end + +local P, S, R, C = lpeg.P, lpeg.S, lpeg.R, lpeg.C + +local spaces = P(" ")^0 +--local namespec = (1-S("/:("))^0 -- was: (1-S("/: ("))^0 +--[[phg-- this prevents matching of absolute paths as file names --]]-- +local namespec = (1-S("/:("))^1 +local filespec = (R("az", "AZ") * P(":"))^-1 * (1-S(":("))^1 +local stylespec = spaces * P("/") * (((1-P(":"))^0)/isstyle) * spaces +local filename = (P("file:")/isfile * (filespec/thename)) + (P("[") * P(true)/isname * (((1-P("]"))^0)/thename) * P("]")) +local fontname = (P("name:")/isname * (namespec/thename)) + P(true)/issome * (namespec/thename) +local sometext = (R("az","AZ","09") + S("+-.,"))^1 +local truevalue = P("+") * spaces * (sometext/istrue) +local falsevalue = P("-") * spaces * (sometext/isfalse) +local keyvalue = P("+") + (C(sometext) * spaces * P("=") * spaces * C(sometext))/iskey +local somevalue = sometext/istrue +local subvalue = P("(") * (C(P(1-S("()"))^1)/issub) * P(")") -- for Kim +local option = spaces * (keyvalue + falsevalue + truevalue + somevalue) * spaces +local options = P(":") * spaces * (P(";")^0 * option)^0 +local pattern = (filename + fontname) * subvalue^0 * stylespec^0 * options^0 + +local function colonized(specification) -- xetex mode + feature_list = { } + lpeg.match(pattern,specification.specification) + set_default_features(feature_list.script) + if feature_list.style then + specification.style = feature_list.style + feature_list.style = nil + end + if feature_list.optsize then + specification.optsize = feature_list.optsize + feature_list.optsize = nil + end + if feature_list.name then + if resolvers.findfile(feature_list.name, "tfm") then + feature_list.lookup = "file" + feature_list.name = file.addsuffix(feature_list.name, "tfm") + elseif resolvers.findfile(feature_list.name, "ofm") then + feature_list.lookup = "file" + feature_list.name = file.addsuffix(feature_list.name, "ofm") + end + + specification.name = feature_list.name + feature_list.name = nil + end + if feature_list.lookup then + specification.lookup = feature_list.lookup + feature_list.lookup = nil + end + if feature_list.sub then + specification.sub = feature_list.sub + feature_list.sub = nil + end + if not feature_list.mode then + -- if no mode is set, use our default + feature_list.mode = fonts.mode + end + specification.features.normal = fonts.handlers.otf.features.normalize(feature_list) + return specification +end + +fonts.definers.registersplit(":",colonized,"cryptic") +fonts.definers.registersplit("", colonized,"more cryptic") -- catches \font\text=[names] + +function fonts.definers.applypostprocessors(tfmdata) + local postprocessors = tfmdata.postprocessors + if postprocessors then + for i=1,#postprocessors do + local extrahash = postprocessors[i](tfmdata) -- after scaling etc + if type(extrahash) == "string" and extrahash ~= "" then + -- e.g. a reencoding needs this + extrahash = string.gsub(lower(extrahash),"[^a-z]","-") + tfmdata.properties.fullname = format("%s-%s",tfmdata.properties.fullname,extrahash) + end + end + end + return tfmdata +end +---[[ end included font-ltx.lua ]] + --[[doc-- Taken from the most recent branch of luaotfload. --doc]]-- @@ -108,3 +335,5 @@ registerotffeature { name = 'anum', description = 'arabic digits', } + +-- vim:tw=71:sw=4:ts=4:expandtab diff --git a/luaotfload-font-ltx.lua b/luaotfload-font-ltx.lua deleted file mode 100644 index afc8621..0000000 --- a/luaotfload-font-ltx.lua +++ /dev/null @@ -1,205 +0,0 @@ -if not modules then modules = { } end modules ['font-ltx'] = { - version = 1.001, - comment = "companion to luatex-*.tex", - author = "Hans Hagen, PRAGMA-ADE, Hasselt NL", - copyright = "PRAGMA ADE / ConTeXt Development Team", - license = "see context related readme files" -} ---- where have all the comments gone? - -local fonts = fonts - --- A bit of tuning for definitions. - -fonts.constructors.namemode = "specification" -- somehow latex needs this (changed name!) => will change into an overload - --- tricky: we sort of bypass the parser and directly feed all into --- the sub parser - -function fonts.definers.getspecification(str) - return "", str, "", ":", str -end - --- the generic name parser (different from context!) - -local feature_list = { } - -local report = logs.names_report - ---- ugh TODO use lpeg instead -local function isstyle(s) - local style = string.lower(s):split("/") - for _,v in next, style do - if v == "b" then - feature_list.style = "bold" - elseif v == "i" then - feature_list.style = "italic" - elseif v == "bi" or v == "ib" then - feature_list.style = "bolditalic" - elseif v:find("^s=") then - feature_list.optsize = v:split("=")[2] - elseif v == "aat" or v == "icu" or v == "gr" then - report("log", 0, - "load font", "unsupported font option: %s", v) - elseif not v:is_empty() then - feature_list.style = v:gsub("[^%a%d]", "") - end - end -end - -local defaults = { - dflt = { - "ccmp", "locl", "rlig", "liga", "clig", - "kern", "mark", "mkmk", 'itlc', - }, - arab = { - "ccmp", "locl", "isol", "fina", "fin2", - "fin3", "medi", "med2", "init", "rlig", - "calt", "liga", "cswh", "mset", "curs", - "kern", "mark", "mkmk", - }, - deva = { - "ccmp", "locl", "init", "nukt", "akhn", - "rphf", "blwf", "half", "pstf", "vatu", - "pres", "blws", "abvs", "psts", "haln", - "calt", "blwm", "abvm", "dist", "kern", - "mark", "mkmk", - }, - khmr = { - "ccmp", "locl", "pref", "blwf", "abvf", - "pstf", "pres", "blws", "abvs", "psts", - "clig", "calt", "blwm", "abvm", "dist", - "kern", "mark", "mkmk", - }, - thai = { - "ccmp", "locl", "liga", "kern", "mark", - "mkmk", - }, - hang = { - "ccmp", "ljmo", "vjmo", "tjmo", - }, -} - -defaults.beng = defaults.deva -defaults.guru = defaults.deva -defaults.gujr = defaults.deva -defaults.orya = defaults.deva -defaults.taml = defaults.deva -defaults.telu = defaults.deva -defaults.knda = defaults.deva -defaults.mlym = defaults.deva -defaults.sinh = defaults.deva - -defaults.syrc = defaults.arab -defaults.mong = defaults.arab -defaults.nko = defaults.arab - -defaults.tibt = defaults.khmr - -defaults.lao = defaults.thai - -local function set_default_features(script) - local features - local script = script or "dflt" - report("log", 0, "load font", - "auto-selecting default features for script: %s", - script) - if defaults[script] then - features = defaults[script] - else - features = defaults["dflt"] - end - for _,v in next, features do - if feature_list[v] ~= false then - feature_list[v] = true - end - end -end - -local function issome () feature_list.lookup = 'name' end -local function isfile () feature_list.lookup = 'file' end -local function isname () feature_list.lookup = 'name' end -local function thename(s) feature_list.name = s end -local function issub (v) feature_list.sub = v end -local function istrue (s) feature_list[s] = true end -local function isfalse(s) feature_list[s] = false end -local function iskey (k,v) feature_list[k] = v end - -local P, S, R, C = lpeg.P, lpeg.S, lpeg.R, lpeg.C - -local spaces = P(" ")^0 ---local namespec = (1-S("/:("))^0 -- was: (1-S("/: ("))^0 ---[[phg-- this prevents matching of absolute paths as file names --]]-- -local namespec = (1-S("/:("))^1 -local filespec = (R("az", "AZ") * P(":"))^-1 * (1-S(":("))^1 -local stylespec = spaces * P("/") * (((1-P(":"))^0)/isstyle) * spaces -local filename = (P("file:")/isfile * (filespec/thename)) + (P("[") * P(true)/isname * (((1-P("]"))^0)/thename) * P("]")) -local fontname = (P("name:")/isname * (namespec/thename)) + P(true)/issome * (namespec/thename) -local sometext = (R("az","AZ","09") + S("+-.,"))^1 -local truevalue = P("+") * spaces * (sometext/istrue) -local falsevalue = P("-") * spaces * (sometext/isfalse) -local keyvalue = P("+") + (C(sometext) * spaces * P("=") * spaces * C(sometext))/iskey -local somevalue = sometext/istrue -local subvalue = P("(") * (C(P(1-S("()"))^1)/issub) * P(")") -- for Kim -local option = spaces * (keyvalue + falsevalue + truevalue + somevalue) * spaces -local options = P(":") * spaces * (P(";")^0 * option)^0 -local pattern = (filename + fontname) * subvalue^0 * stylespec^0 * options^0 - -local function colonized(specification) -- xetex mode - feature_list = { } - lpeg.match(pattern,specification.specification) - set_default_features(feature_list.script) - if feature_list.style then - specification.style = feature_list.style - feature_list.style = nil - end - if feature_list.optsize then - specification.optsize = feature_list.optsize - feature_list.optsize = nil - end - if feature_list.name then - if resolvers.findfile(feature_list.name, "tfm") then - feature_list.lookup = "file" - feature_list.name = file.addsuffix(feature_list.name, "tfm") - elseif resolvers.findfile(feature_list.name, "ofm") then - feature_list.lookup = "file" - feature_list.name = file.addsuffix(feature_list.name, "ofm") - end - - specification.name = feature_list.name - feature_list.name = nil - end - if feature_list.lookup then - specification.lookup = feature_list.lookup - feature_list.lookup = nil - end - if feature_list.sub then - specification.sub = feature_list.sub - feature_list.sub = nil - end - if not feature_list.mode then - -- if no mode is set, use our default - feature_list.mode = fonts.mode - end - specification.features.normal = fonts.handlers.otf.features.normalize(feature_list) - return specification -end - -fonts.definers.registersplit(":",colonized,"cryptic") -fonts.definers.registersplit("", colonized,"more cryptic") -- catches \font\text=[names] - -function fonts.definers.applypostprocessors(tfmdata) - local postprocessors = tfmdata.postprocessors - if postprocessors then - for i=1,#postprocessors do - local extrahash = postprocessors[i](tfmdata) -- after scaling etc - if type(extrahash) == "string" and extrahash ~= "" then - -- e.g. a reencoding needs this - extrahash = string.gsub(lower(extrahash),"[^a-z]","-") - tfmdata.properties.fullname = format("%s-%s",tfmdata.properties.fullname,extrahash) - end - end - end - return tfmdata -end --- vim:tw=71:sw=4:ts=4:expandtab diff --git a/tests/lookups.tex b/tests/lookups.tex new file mode 100644 index 0000000..db26312 --- /dev/null +++ b/tests/lookups.tex @@ -0,0 +1,14 @@ +\input luaotfload.sty +%% lookup font by name (involving database) +\font\first=name:iwonaregular at 42pt +%% lookup font by file name (kpse) +\font\second=file:antpoltltsemiexpd-bolditalic.otf at 42pt +%% lookup font by name, with style in slash notation +\font\third={name:Antykwa torunska/I} at 42pt + +{\first foo \endgraf} +{\second bar \endgraf} +{\third baz \endgraf} + +\bye + |