pack-obj.lua /size: 7370 b    last modification: 2020-07-01 14:35
1
if
not
modules
then
modules
=
{
}
end
modules
[
'
pack-obj
'
]
=
{
2
version
=
1
.
001
,
3
comment
=
"
companion to pack-obj.mkiv
"
,
4
author
=
"
Hans Hagen, PRAGMA-ADE, Hasselt NL
"
,
5
copyright
=
"
PRAGMA ADE / ConTeXt Development Team
"
,
6
license
=
"
see context related readme files
"
7
}
8 9
--[[ldx-- 10<p>We save object references in the main utility table. jobobjects are 11reusable components.</p> 12--ldx]]
--
13 14
local
context
=
context
15
local
codeinjections
=
backends
.
codeinjections
16
local
ctx_doifelse
=
commands
.
doifelse
17 18
local
report
=
logs
.
reporter
(
"
objects
"
)
19
local
trace
=
false
trackers
.
register
(
"
objects
"
,
function
(
v
)
trace
=
v
end
)
20 21
local
nuts
=
nodes
.
nuts
22 23
local
setlink
=
nuts
.
setlink
24
local
getlist
=
nuts
.
getlist
25
local
setbox
=
nuts
.
setbox
26 27
local
new_latelua
=
nuts
.
pool
.
latelua
28 29
local
settexdimen
=
tokens
.
setters
.
dimen
30 31
local
getcount
=
tex
.
getcount
32 33
local
implement
=
interfaces
.
implement
34
local
setmacro
=
interfaces
.
setmacro
35 36
local
allocate
=
utilities
.
storage
.
allocate
37 38
local
collected
=
allocate
(
)
39
local
tobesaved
=
allocate
(
)
40 41
local
jobobjects
=
{
42
collected
=
collected
,
43
tobesaved
=
tobesaved
,
44
}
45 46
job
.
objects
=
jobobjects
47 48
local
function
initializer
(
)
49
collected
=
jobobjects
.
collected
50
tobesaved
=
jobobjects
.
tobesaved
51
end
52 53
job
.
register
(
'
job.objects.collected
'
,
tobesaved
,
initializer
,
nil
)
54 55
local
function
saveobject
(
tag
,
number
,
page
)
56
local
data
=
{
number
,
page
}
57
tobesaved
[
tag
]
=
data
58
collected
[
tag
]
=
data
59
end
60 61
local
function
saveobjectspec
(
specification
)
62
local
tag
=
specification
.
tag
63
local
data
=
{
specification
.
number
,
specification
.
page
}
64
tobesaved
[
tag
]
=
data
65
collected
[
tag
]
=
data
66
end
67 68
local
function
setobject
(
tag
,
number
,
page
)
69
collected
[
tag
]
=
{
number
,
page
}
70
end
71 72
local
function
getobject
(
tag
)
73
return
collected
[
tag
]
or
tobesaved
[
tag
]
74
end
75 76
local
function
getobjectnumber
(
tag
,
default
)
77
local
o
=
collected
[
tag
]
or
tobesaved
[
tag
]
78
return
o
and
o
[
1
]
or
default
79
end
80 81
local
function
getobjectpage
(
tag
,
default
)
82
local
o
=
collected
[
tag
]
or
tobesaved
[
tag
]
83
return
o
and
o
[
2
]
or
default
84
end
85 86
jobobjects
.
save
=
saveobject
87
jobobjects
.
set
=
setobject
88
jobobjects
.
get
=
getobject
89
jobobjects
.
number
=
getobjectnumber
90
jobobjects
.
page
=
getobjectpage
91 92
-- implement {
93
-- name = "saveobject",
94
-- actions = saveobject
95
-- }
96
--
97
-- implement {
98
-- name = "setobject",
99
-- actions = setobject,
100
-- arguments = { "string", "integer", "integer" }
101
-- }
102
--
103
-- implement {
104
-- name = "objectnumber",
105
-- actions = { getobjectnumber, context },
106
-- arguments = "2 strings",
107
-- }
108
--
109
-- implement {
110
-- name = "objectpage",
111
-- actions = { getobjectpage, context },
112
-- arguments = "2 strings",
113
-- }
114
--
115
-- implement {
116
-- name = "doifelseobjectreferencefound",
117
-- actions = { getobject, commands.doifelse },
118
-- arguments = "string"
119
-- }
120 121
-- if false then
122
-- -- we can flush the inline ref ourselves now if we want
123
-- local flush = new_latelua("pdf.flushxform("..index..")")
124
-- flush.next = list
125
-- next.prev = flush
126
-- end
127 128
local
data
=
table
.
setmetatableindex
(
"
table
"
)
129 130
objects
=
{
131
data
=
data
,
132
n
=
0
,
133
}
134 135
local
objects
=
objects
136 137
function
objects
.
register
(
ns
,
id
,
b
,
referenced
,
offset
,
mode
)
138
local
n
=
objects
.
n
+
1
139
objects
.
n
=
n
140
nodes
.
handlers
.
finalizebox
(
b
)
141
if
mode
=
=
0
then
142
-- tex
143
data
[
ns
]
[
id
]
=
{
144
codeinjections
.
registerboxresource
(
b
)
,
-- a box number
145
offset
,
146
referenced
or
false
,
147
mode
,
148
}
149
else
150
-- box (backend)
151
data
[
ns
]
[
id
]
=
{
152
codeinjections
.
registerboxresource
(
b
,
offset
)
,
-- a box number
153
false
,
154
referenced
,
155
mode
,
156
}
157
end
158
if
trace
then
159
report
(
"
registering object %a (n=%i)
"
,
id
,
n
)
160
end
161
end
162 163
function
objects
.
restore
(
ns
,
id
)
-- why not just pass a box number here too (ok, we also set offset)
164
local
d
=
data
[
ns
]
[
id
]
165
if
d
then
166
local
index
=
d
[
1
]
167
local
offset
=
d
[
2
]
168
local
status
=
d
[
3
]
169
local
mode
=
d
[
4
]
170
local
hbox
=
codeinjections
.
restoreboxresource
(
index
)
-- a nut !
171
if
status
then
172
local
list
=
getlist
(
hbox
)
173
local
page
=
new_latelua
{
174
action
=
saveobjectspec
,
175
tag
=
ns
.
.
"
::
"
.
.
id
,
176
number
=
index
,
177
page
=
getcount
(
"
realpageno
"
)
,
178
}
179
setlink
(
list
,
page
)
180
end
181
setbox
(
"
objectbox
"
,
hbox
)
182
settexdimen
(
"
objectoff
"
,
offset
or
0
)
183
else
184
setbox
(
"
objectbox
"
,
nil
)
185
settexdimen
(
"
objectoff
"
,
0
)
-- for good old times
186
end
187
if
trace
then
188
report
(
"
restoring object %a
"
,
id
)
189
end
190
end
191 192
function
objects
.
dimensions
(
index
)
193
local
d
=
data
[
ns
]
[
id
]
194
if
d
then
195
return
codeinjections
.
boxresourcedimensions
(
d
[
1
]
)
196
else
197
return
0
,
0
,
0
,
0
198
end
199
end
200 201
function
objects
.
reference
(
ns
,
id
)
202
local
d
=
data
[
ns
]
[
id
]
203
if
d
then
204
return
d
[
1
]
205
else
206
return
getobjectnumber
(
ns
.
.
"
::
"
.
.
id
,
0
)
207
end
208
end
209 210
function
objects
.
page
(
ns
,
id
)
211
return
getobjectpage
(
ns
.
.
"
::
"
.
.
id
,
getcount
(
"
realpageno
"
)
)
212
end
213 214
function
objects
.
found
(
ns
,
id
)
215
return
data
[
ns
]
[
id
]
216
end
217 218
implement
{
219
name
=
"
registerreferencedobject
"
,
220
arguments
=
{
"
string
"
,
"
string
"
,
"
integer
"
,
true
,
"
dimension
"
,
"
integer
"
}
,
221
actions
=
objects
.
register
,
222
}
223 224
implement
{
225
name
=
"
registerobject
"
,
226
arguments
=
{
"
string
"
,
"
string
"
,
"
integer
"
,
false
,
"
dimension
"
,
"
integer
"
}
,
227
actions
=
objects
.
register
,
228
}
229 230
implement
{
231
name
=
"
restoreobject
"
,
232
arguments
=
"
2 strings
"
,
233
actions
=
objects
.
restore
,
234
}
235 236
implement
{
237
name
=
"
doifelseobject
"
,
238
arguments
=
"
2 strings
"
,
239
actions
=
function
(
ns
,
id
)
240
ctx_doifelse
(
data
[
ns
]
[
id
]
)
241
-- ctx_doifelse(objects.reference(ns,id))
242
end
,
243
}
244 245
implement
{
246
name
=
"
doifelseobjectreference
"
,
247
arguments
=
"
2 strings
"
,
248
actions
=
function
(
ns
,
id
)
249
-- ctx_doifelse(data[ns][id])
250
ctx_doifelse
(
objects
.
reference
(
ns
,
id
)
)
251
end
,
252
}
253 254
implement
{
255
name
=
"
getobjectreference
"
,
256
arguments
=
{
"
string
"
,
"
string
"
,
"
csname
"
}
,
257
actions
=
function
(
ns
,
id
,
target
)
258
setmacro
(
target
,
objects
.
reference
(
ns
,
id
)
,
"
global
"
)
259
end
260
}
261 262
implement
{
263
name
=
"
getobjectreferencepage
"
,
264
arguments
=
{
"
string
"
,
"
string
"
,
"
csname
"
}
,
265
actions
=
function
(
ns
,
id
,
target
)
266
setmacro
(
target
,
objects
.
page
(
ns
,
id
)
,
"
global
"
)
267
end
268
}
269 270
implement
{
271
name
=
"
getobjectdimensions
"
,
272
arguments
=
"
2 strings
"
,
273
actions
=
function
(
ns
,
id
)
274
local
object
=
data
[
ns
]
[
id
]
275
local
w
,
h
,
d
,
o
=
0
,
0
,
0
,
0
276
if
object
then
277
w
,
h
,
d
,
o
=
codeinjections
.
boxresourcedimensions
(
object
[
1
]
)
278
end
279
settexdimen
(
"
objectwd
"
,
w
or
0
)
280
settexdimen
(
"
objectht
"
,
h
or
0
)
281
settexdimen
(
"
objectdp
"
,
d
or
0
)
282
settexdimen
(
"
objectoff
"
,
o
or
#
objects
>
2
and
object
[
2
]
or
0
)
283
end
284
}
285 286
-- for the moment here:
287 288
implement
{
289
name
=
"
registerbackendsymbol
"
,
290
arguments
=
{
"
string
"
,
"
integer
"
}
,
291
actions
=
function
(
...
)
292
codeinjections
.
registersymbol
(
...
)
293
end
294
}
295