You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
226 lines
6.1 KiB
226 lines
6.1 KiB
-----------------------------------------------------------------------
|
|
-- FILE: luaotfload-szss.lua
|
|
-- DESCRIPTION: part of luaotfload / szss
|
|
-----------------------------------------------------------------------
|
|
|
|
local ProvidesLuaModule = {
|
|
name = "luaotfload-szss",
|
|
version = "3.14", --TAGVERSION
|
|
date = "2020-05-06", --TAGDATE
|
|
description = "luaotfload submodule / color",
|
|
license = "GPL v2.0",
|
|
author = "Marcel Krüger"
|
|
}
|
|
|
|
if luatexbase and luatexbase.provides_module then
|
|
luatexbase.provides_module (ProvidesLuaModule)
|
|
end
|
|
|
|
local direct = node.direct
|
|
local otfregister = fonts.constructors.features.otf.register
|
|
|
|
local copy = direct.copy
|
|
local getdisc = direct.getdisc
|
|
local getnext = direct.getnext
|
|
local insert_after = direct.insert_after
|
|
local is_char = direct.is_char
|
|
local setchar = direct.setchar
|
|
local setdisc = direct.setdisc
|
|
|
|
local disc_t = node.id'disc'
|
|
|
|
local szsstable = setmetatable({}, { __index = function(t, i)
|
|
local v = font.getfont(i)
|
|
v = v and v.properties
|
|
v = v and v.transform_sz or false
|
|
t[i] = v
|
|
return v
|
|
end})
|
|
|
|
local function szssinitializer(tfmdata, value, features)
|
|
if value == 'auto' then
|
|
value = not tfmdata.characters[0x1E9E]
|
|
end
|
|
local properties = tfmdata.properties
|
|
properties.transform_sz = value
|
|
end
|
|
|
|
local function szssprocessor(head,font) -- ,attr,direction)
|
|
if not szsstable[font] then return end
|
|
local n = head
|
|
while n do
|
|
local c, id = is_char(n, font)
|
|
if c == 0x1E9E then
|
|
setchar(n, 0x53)
|
|
head, n = insert_after(head, n, copy(n))
|
|
elseif id == disc_t then
|
|
local pre, post, replace = getdisc(n)
|
|
pre = szssprocessor(pre, font)
|
|
post = szssprocessor(post, font)
|
|
replace = szssprocessor(replace, font)
|
|
setdisc(n, pre, post, replace)
|
|
end
|
|
n = getnext(n)
|
|
end
|
|
return head
|
|
end
|
|
|
|
otfregister {
|
|
name = 'szss',
|
|
description = 'Replace capital ß with SS',
|
|
default = 'auto',
|
|
initializers = {
|
|
node = szssinitializer,
|
|
plug = szssinitializer,
|
|
},
|
|
processors = {
|
|
position = 1,
|
|
node = szssprocessor,
|
|
plug = szssprocessor,
|
|
},
|
|
}
|
|
|
|
-- harf-only features (for node they are implemented in the fontloader
|
|
|
|
otfregister {
|
|
name = 'extend',
|
|
description = 'Fake extend',
|
|
default = false,
|
|
manipulators = {
|
|
plug = function(tfmdata, _, value)
|
|
value = tonumber(value)
|
|
if not value then
|
|
error[[Invalid extend value]]
|
|
end
|
|
tfmdata.extend = value * 1000
|
|
tfmdata.hb.hscale = tfmdata.units_per_em * value
|
|
local parameters = tfmdata.parameters
|
|
parameters.slant = parameters.slant * value
|
|
parameters.space = parameters.space * value
|
|
parameters.space_stretch = parameters.space_stretch * value
|
|
parameters.space_shrink = parameters.space_shrink * value
|
|
parameters.quad = parameters.quad * value
|
|
parameters.extra_space = parameters.extra_space * value
|
|
local done = {}
|
|
for _, char in next, tfmdata.characters do
|
|
if char.width and not done[char] then
|
|
char.width = char.width * value
|
|
done[char] = true
|
|
end
|
|
end
|
|
end,
|
|
},
|
|
}
|
|
|
|
otfregister {
|
|
name = 'slant',
|
|
description = 'Fake slant',
|
|
default = false,
|
|
manipulators = {
|
|
plug = function(tfmdata, _, value)
|
|
value = tonumber(value)
|
|
if not value then
|
|
error[[Invalid slant value]]
|
|
end
|
|
tfmdata.slant = value * 1000
|
|
local parameters = tfmdata.parameters
|
|
parameters.slant = parameters.slant + value * 65536
|
|
end,
|
|
},
|
|
}
|
|
|
|
otfregister {
|
|
name = 'squeeze',
|
|
description = 'Fake squeeze',
|
|
default = false,
|
|
manipulators = {
|
|
plug = function(tfmdata, _, value)
|
|
value = tonumber(value)
|
|
if not value then
|
|
error[[Invalid squeeze value]]
|
|
end
|
|
tfmdata.squeeze = value * 1000
|
|
tfmdata.hb.vscale = tfmdata.units_per_em * value
|
|
local parameters = tfmdata.parameters
|
|
parameters.slant = parameters.slant / value
|
|
parameters.x_height = parameters.x_height * value
|
|
parameters[8] = parameters[8] * value
|
|
local done = {}
|
|
for _, char in next, tfmdata.characters do
|
|
if not done[char] then
|
|
if char.height then
|
|
char.height = char.height * value
|
|
end
|
|
if char.depth then
|
|
char.depth = char.depth * value
|
|
end
|
|
done[char] = true
|
|
end
|
|
end
|
|
end,
|
|
},
|
|
}
|
|
|
|
-- Legacy TeX Input Method Disguised as Font Ligatures hack.
|
|
--
|
|
-- Single replacements, keyed by character to replace. Handled separately
|
|
-- because TeX ligaturing mechanism does not support one-to-one replacements.
|
|
local trep = {
|
|
[0x0022] = 0x201D, -- ["]
|
|
[0x0027] = 0x2019, -- [']
|
|
[0x0060] = 0x2018, -- [`]
|
|
}
|
|
|
|
-- Ligatures. The value is a character "ligature" table as described in the
|
|
-- manual.
|
|
local tlig ={
|
|
[0x2013] = { [0x002D] = { char = 0x2014 } }, -- [---]
|
|
[0x002D] = { [0x002D] = { char = 0x2013 } }, -- [--]
|
|
[0x0060] = { [0x0060] = { char = 0x201C } }, -- [``]
|
|
[0x0027] = { [0x0027] = { char = 0x201D } }, -- ['']
|
|
[0x0021] = { [0x0060] = { char = 0x00A1 } }, -- [!`]
|
|
[0x003F] = { [0x0060] = { char = 0x00BF } }, -- [?`]
|
|
[0x002C] = { [0x002C] = { char = 0x201E } }, -- [,,]
|
|
[0x003C] = { [0x003C] = { char = 0x00AB } }, -- [<<]
|
|
[0x003E] = { [0x003E] = { char = 0x00BB } }, -- [>>]
|
|
}
|
|
|
|
local function tligprocessor(head, font)
|
|
local n = head
|
|
while n do
|
|
local c, id = is_char(n, font)
|
|
local rep = trep[c]
|
|
if rep then
|
|
setchar(n, rep)
|
|
elseif id == disc_t then
|
|
local pre, post, replace = getdisc(n)
|
|
tligprocessor(pre, font)
|
|
tligprocessor(post, font)
|
|
tligprocessor(replace, font)
|
|
end
|
|
n = getnext(n)
|
|
end
|
|
end
|
|
|
|
otfregister {
|
|
name = 'tlig',
|
|
description = 'Traditional TeX ligatures',
|
|
default = false,
|
|
manipulators = {
|
|
plug = function(tfmdata, _, value)
|
|
local characters = tfmdata.characters
|
|
for codepoint, ligatures in next, tlig do
|
|
local char = characters[codepoint]
|
|
if char then
|
|
char.ligatures = ligatures
|
|
end
|
|
end
|
|
end,
|
|
},
|
|
processors = {
|
|
position=1,
|
|
plug = tligprocessor,
|
|
},
|
|
}
|
|
|
|
--- vim:sw=2:ts=2:expandtab:tw=71
|
|
|