summaryrefslogtreecommitdiff
path: root/src/fontloader/misc/fontloader-fonts-cbk.lua
blob: 965b9689363caf09df96a15477a35f0b08083d63 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
if not modules then modules = { } end modules ['luatex-fonts-cbk'] = {
    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"
}

if context then
    texio.write_nl("fatal error: this module is not for context")
    os.exit()
end

local fonts = fonts
local nodes = nodes

-- Fonts: (might move to node-gef.lua)

local traverse_id = node.traverse_id
local glyph_code  = nodes.nodecodes.glyph
local disc_code   = nodes.nodecodes.disc

-- from now on we apply ligaturing and kerning here because it might interfere with complex
-- opentype discretionary handling where the base ligature pass expect some weird extra
-- pointers (which then confuse the tail slider that has some checking built in)

local ligaturing    = node.ligaturing
local kerning       = node.kerning

local basepass      = true

function nodes.handlers.setbasepass(v)
    basepass = v
end

function nodes.handlers.characters(head)
    local fontdata = fonts.hashes.identifiers
    if fontdata then
        local usedfonts = { }
        local basefonts = { }
        local prevfont  = nil
        local basefont  = nil
        for n in traverse_id(glyph_code,head) do
            local font = n.font
            if font ~= prevfont then
                if basefont then
                    basefont[2] = n.prev
                end
                prevfont = font
                local used = usedfonts[font]
                if not used then
                    local tfmdata = fontdata[font] --
                    if tfmdata then
                        local shared = tfmdata.shared -- we need to check shared, only when same features
                        if shared then
                            local processors = shared.processes
                            if processors and #processors > 0 then
                                usedfonts[font] = processors
                            elseif basepass then
                                basefont = { n, nil }
                                basefonts[#basefonts+1] = basefont
                            end
                        end
                    end
                end
            end
        end
        for d in traverse_id(disc_code,head) do
            local r = d.replace
            if r then
                for n in traverse_id(glyph_code,r) do
                    local font = n.font
                    if font ~= prevfont then
                        prevfont = font
                        local used = usedfonts[font]
                        if not used then
                            local tfmdata = fontdata[font] --
                            if tfmdata then
                                local shared = tfmdata.shared -- we need to check shared, only when same features
                                if shared then
                                    local processors = shared.processes
                                    if processors and #processors > 0 then
                                        usedfonts[font] = processors
                                    end
                                end
                            end
                        end
                    end
                end
            end
        end
        if next(usedfonts) then
            for font, processors in next, usedfonts do
                for i=1,#processors do
                    head = processors[i](head,font,0) or head
                end
            end
        end
        if basepass and #basefonts > 0 then
            for i=1,#basefonts do
                local range = basefonts[i]
                local start, stop = range[1], range[2]
                if stop then
                    ligaturing(start,stop)
                    kerning(start,stop)
                else
                    ligaturing(start)
                    kerning(start)
                end
            end
        end
        return head, true
    else
        return head, false
    end
end

function nodes.simple_font_handler(head)
 -- lang.hyphenate(head)
    head = nodes.handlers.characters(head)
    nodes.injections.handler(head)
    if not basepass then
        head = ligaturing(head)
        head = kerning(head)
    end
    nodes.handlers.protectglyphs(head)
    return head
end