Skip to content

Commit

Permalink
Merge 899ea71 into fbfe5d4
Browse files Browse the repository at this point in the history
  • Loading branch information
Omikhleia committed Mar 29, 2023
2 parents fbfe5d4 + 899ea71 commit 6c89469
Show file tree
Hide file tree
Showing 24 changed files with 255 additions and 124 deletions.
15 changes: 6 additions & 9 deletions classes/base.lua
Expand Up @@ -430,19 +430,16 @@ function class:registerCommands ()
self:registerCommand("discretionary", function (options, _)
local discretionary = SILE.nodefactory.discretionary({})
if options.prebreak then
SILE.call("hbox", {}, function () SILE.typesetter:typeset(options.prebreak) end)
discretionary.prebreak = { SILE.typesetter.state.nodes[#SILE.typesetter.state.nodes] }
SILE.typesetter.state.nodes[#SILE.typesetter.state.nodes] = nil
local hbox = SILE.typesetter:makeHbox({ options.prebreak })
discretionary.prebreak = { hbox }
end
if options.postbreak then
SILE.call("hbox", {}, function () SILE.typesetter:typeset(options.postbreak) end)
discretionary.postbreak = { SILE.typesetter.state.nodes[#SILE.typesetter.state.nodes] }
SILE.typesetter.state.nodes[#SILE.typesetter.state.nodes] = nil
local hbox = SILE.typesetter:makeHbox({ options.postbreak })
discretionary.postbreak = { hbox }
end
if options.replacement then
SILE.call("hbox", {}, function () SILE.typesetter:typeset(options.replacement) end)
discretionary.replacement = { SILE.typesetter.state.nodes[#SILE.typesetter.state.nodes] }
SILE.typesetter.state.nodes[#SILE.typesetter.state.nodes] = nil
local hbox = SILE.typesetter:makeHbox({ options.replacement })
discretionary.replacement = { hbox }
end
table.insert(SILE.typesetter.state.nodes, discretionary)
end, "Inserts a discretionary node.")
Expand Down
74 changes: 19 additions & 55 deletions classes/plain.lua
Expand Up @@ -333,63 +333,27 @@ function class:registerCommands ()
end)
end)

local _rtl_pre_post = function (box, typesetter, line)
local advance = function () typesetter.frame:advanceWritingDirection(box:scaledWidth(line)) end
if typesetter.frame:writingDirection() == "RTL" then
advance()
return function () end
else
return advance
end
end

self:registerCommand("hbox", function (_, content)
local index = #(SILE.typesetter.state.nodes)+1
local recentContribution = {}
SILE.process(content)
local l = SILE.length()
local h, d = SILE.length(), SILE.length()
for i = index, #(SILE.typesetter.state.nodes) do
local node = SILE.typesetter.state.nodes[i]
if node.is_unshaped then
local shape = node:shape()
for _, attr in ipairs(shape) do
recentContribution[#recentContribution+1] = attr
h = attr.height > h and attr.height or h
d = attr.depth > d and attr.depth or d
l = l + attr:lineContribution():absolute()
end
else
recentContribution[#recentContribution+1] = node
l = l + node:lineContribution():absolute()
h = node.height > h and node.height or h
d = node.depth > d and node.depth or d
end
SILE.typesetter.state.nodes[i] = nil
end
local hbox = SILE.nodefactory.hbox({
height = h,
width = l,
depth = d,
value = recentContribution,
outputYourself = function (self_, typesetter, line)
local _post = _rtl_pre_post(self_, typesetter, line)
local ox = typesetter.frame.state.cursorX
local oy = typesetter.frame.state.cursorY
SILE.outputter:setCursor(typesetter.frame.state.cursorX, typesetter.frame.state.cursorY)
for _, node in ipairs(self_.value) do
node:outputYourself(typesetter, line)
end
typesetter.frame.state.cursorX = ox
typesetter.frame.state.cursorY = oy
_post()
SU.debug("hboxes", function ()
SILE.outputter:debugHbox(self_, self_:scaledWidth(line))
return "Drew debug outline around hbox"
end)
end
})
local hbox, hlist = SILE.typesetter:makeHbox(content)
-- HACK
-- Direct insertion in the typesetter node queue comes from
-- the original implementation.
-- It would likely be clearer to use: SILE.typesetter:pushHbox(hbox)
-- but the latter adds a zerohbox sometimes (on initline), so it will
-- break some non-regression test and possibly have some effect at
-- places... For now, therefore, keep that unchanged, but it should
-- be investigated.
table.insert(SILE.typesetter.state.nodes, hbox)

if #hlist > 0 then
SU.warn("Hbox has migrating content (ignored for now, but likely to break in future versions)")
-- Ugly shim:
-- One day we ought to do SILE.typesetter:pushHlist(hlist) here, so as to push
-- back the migrating contents from within the hbox'ed content.
-- However, old Lua code assumed the hbox to be returned, and sometimes removed it
-- from the typesetter queue (for measuring, etc.), assuming it was the last
-- element in the queue...
end
return hbox
end, "Compiles all the enclosed horizontal-mode material into a single hbox")

Expand Down
6 changes: 6 additions & 0 deletions core/nodefactory.lua
Expand Up @@ -335,6 +335,12 @@ function nodefactory.discretionary:replacementHeight ()
return self.replaceh
end

function nodefactory.discretionary:replacementDepth ()
if self.replaced then return self.replaced end
self.replaced = _maxnode(self.replacement, "depth")
return self.replaced
end

nodefactory.alternative = pl.class(nodefactory.hbox)

nodefactory.alternative.type = "alternative"
Expand Down
2 changes: 1 addition & 1 deletion documentation/c05-packages.sil
Expand Up @@ -162,7 +162,7 @@ basic functionality to other packages and classes. Classes such as the
\subsection{rebox}
\package-documentation{rebox}

\section{scalebox}
\subsection{scalebox}
\package-documentation{scalebox}

\subsection{tableofcontents}
Expand Down
11 changes: 6 additions & 5 deletions documentation/c12-tricks.sil
Expand Up @@ -199,15 +199,16 @@ function discovery:typesetProphecy (symbol)
\end{verbatim}

Next, we call another command to produce the symbol itself;
this allows the book designer to change the symbols at the SILE level rather than having to mess about with the Lua file.
We use the \command{\\hbox} command to wrap the output of the command into a hbox.
\command{\\hbox} returns its output, but also puts the box into the typesetter’s output node queue; we don’t want it to appear in the main typeblock, so we remove the node again, leaving our private copy in the \code{hbox} variable.
this allows the book designer to change the symbols at the SILE level rather than having to mess about with the Lua file.
We then wrap the output of the command into a hbox.
Here, note that we do not use the \command{\\hbox} command:
it would put the box into the typesetter’s output node queue, but we don’t want it to appear in the main typeblock.
So we just ask the typesetter to build the box and return it.

\begin{verbatim}
local hbox = SILE.call("hbox",\{\}, function()
local hbox = SILE.typesetter:makeHbox(function()
SILE.call("prophecy-"..symbol.."-mark")
end)
table.remove(SILE.typesetter.state.nodes)
\end{verbatim}

What we \em{do} want in the output queue is our special hbox node which will put the marking into the margin.
Expand Down
3 changes: 1 addition & 2 deletions packages/chordmode/init.lua
Expand Up @@ -29,8 +29,7 @@ end
function package:registerCommands ()

self:registerCommand("ch", function (options, content)
local chordBox = SILE.call("hbox", {}, { options.name })
SILE.typesetter.state.nodes[#(SILE.typesetter.state.nodes)] = nil
local chordBox = SILE.typesetter:makeHbox({ options.name })
local origWidth = chordBox.width
chordBox.width = SILE.length()
chordBox.height = SILE.settings:get("chordmode.lineheight")
Expand Down
7 changes: 4 additions & 3 deletions packages/cropmarks/init.lua
Expand Up @@ -16,15 +16,16 @@ local function outputMarks ()
SILE.outputter:drawRule(page:right() + 10, page:bottom(), 10, 0.5)
SILE.outputter:drawRule(page:right(), page:bottom() + 10, 0.5, 10)

SILE.call("hbox", {}, function ()
local hbox, hlist = SILE.typesetter:makeHbox(function ()
SILE.settings:temporarily(function ()
SILE.call("noindent")
SILE.call("font", { size="6pt" })
SILE.call("crop:header")
end)
end)
local hbox = SILE.typesetter.state.nodes[#SILE.typesetter.state.nodes]
SILE.typesetter.state.nodes[#SILE.typesetter.state.nodes] = nil
if #hlist > 0 then
SU.error("Forbidden migrating content in crop header")
end

SILE.typesetter.frame.state.cursorX = page:left() + 10
SILE.typesetter.frame.state.cursorY = page:top() - 13
Expand Down
3 changes: 1 addition & 2 deletions packages/dropcaps/init.lua
Expand Up @@ -13,10 +13,9 @@ local shapeHbox = function (options, content)
-- Clear irrelevant values before passing to font
options.lines, options.join, options.raise, options.shift, options.color, options.scale = nil, nil, nil, nil, nil, nil
SILE.call("noindent")
local hbox = SILE.call("hbox", {}, function ()
local hbox = SILE.typesetter:makeHbox(function ()
SILE.call("font", options, content)
end)
table.remove(SILE.typesetter.state.nodes)
return hbox
end

Expand Down
3 changes: 1 addition & 2 deletions packages/frametricks/init.lua
Expand Up @@ -183,8 +183,7 @@ function package:registerCommands ()

self:registerCommand("float", function (options, content)
SILE.typesetter:leaveHmode()
local hbox = SILE.call("hbox", {}, content)
table.remove(SILE.typesetter.state.nodes) -- steal it back
local hbox = SILE.typesetter:makeHbox(content) -- HACK What about migrating nodes here?
local heightOfPageSoFar = SILE.pagebuilder:collateVboxes(SILE.typesetter.state.outputQueue).height
local overshoot = SILE.length(heightOfPageSoFar + hbox.height - SILE.typesetter:getTargetLength())
if overshoot > SILE.length(0) then
Expand Down
7 changes: 5 additions & 2 deletions packages/gutenberg/init.lua
Expand Up @@ -12,8 +12,11 @@ function package:registerCommands ()
self:registerCommand("alternative", function (_, content)
local alts = {}
for _, fragment in ipairs(content) do
SILE.call("hbox", {}, { fragment })
table.insert(alts, table.remove(SILE.typesetter.state.nodes))
local hbox, hlist = SILE.typesetter:makeHbox({ fragment })
if #hlist > 0 then
SU.error("Forbidden migrating content in alternative")
end
table.insert(alts, hbox)
end
local alternative = SILE.nodefactory.alternative({
options = alts,
Expand Down
7 changes: 4 additions & 3 deletions packages/leaders/init.lua
Expand Up @@ -87,9 +87,10 @@ function package:registerCommands ()

self:registerCommand("leaders", function(options, content)
local width = options.width and SU.cast("glue", options.width) or SILE.nodefactory.hfillglue()
SILE.call("hbox", {}, content)
local hbox = SILE.typesetter.state.nodes[#SILE.typesetter.state.nodes]
SILE.typesetter.state.nodes[#SILE.typesetter.state.nodes] = nil
local hbox, hlist = SILE.typesetter:makeHbox(content)
if #hlist > 0 then
SU.error("Forbidden migrating content in leaders")
end
local l = leader({ width = width, value = hbox })
SILE.typesetter:pushExplicitGlue(l)
end)
Expand Down
3 changes: 1 addition & 2 deletions packages/lists/init.lua
Expand Up @@ -86,7 +86,7 @@ function package:doItem (options, content)
SILE.call("par")
end

local mark = SILE.call("hbox", {}, function ()
local mark = SILE.typesetter:makeHbox(function ()
if enumStyle.display then
if enumStyle.before then SILE.typesetter:typeset(enumStyle.before) end
SILE.typesetter:typeset(self.class.packages.counters:formatCounter({
Expand All @@ -99,7 +99,6 @@ function package:doItem (options, content)
SILE.typesetter:typeset(bullet)
end
end)
table.remove(SILE.typesetter.state.nodes) -- steal it back

local stepback
if enumStyle.display then
Expand Down
6 changes: 5 additions & 1 deletion packages/pdf/init.lua
Expand Up @@ -113,7 +113,11 @@ function package:registerCommands ()
pdf.begin_annotation()
end
})
local hbox = SILE.call("hbox", {}, content) -- hack

local hbox, hlist = SILE.typesetter:makeHbox(content) -- hack
SILE.typesetter:pushHbox(hbox)
SILE.typesetter:pushHlist(hlist)

SILE.typesetter:pushHbox({
value = nil,
height = SILE.measurement(0),
Expand Down
3 changes: 1 addition & 2 deletions packages/pullquote/init.lua
Expand Up @@ -14,8 +14,7 @@ local typesetMark = function (open, setback, scale, color, mark)
SILE.call("rebox", { width = setback, height = 0 }, { mark })
else
SILE.typesetter:pushGlue(SILE.nodefactory.hfillglue())
local hbox = SILE.call("hbox", {}, { mark })
table.remove(SILE.typesetter.state.nodes) -- steal it back
local hbox = SILE.typesetter:makeHbox({ mark }) -- for measuring
SILE.typesetter:pushGlue({ width = setback - hbox.width })
SILE.call("rebox", { width = hbox.width, height = 0 }, { mark })
SILE.typesetter:pushGlue({ width = -setback })
Expand Down
6 changes: 3 additions & 3 deletions packages/rebox/init.lua
Expand Up @@ -6,8 +6,7 @@ package._name = "rebox"
function package:registerCommands ()

self:registerCommand("rebox", function (options, content)
local hbox = SILE.call("hbox", {}, content)
table.remove(SILE.typesetter.state.nodes) -- steal it back
local hbox, hlist = SILE.typesetter:makeHbox(content)
if options.width then hbox.width = SILE.length(options.width) end
if options.height then hbox.height = SILE.length(options.height) end
if options.depth then hbox.depth = SILE.length(options.depth) end
Expand All @@ -16,7 +15,8 @@ function package:registerCommands ()
typesetter.frame:advanceWritingDirection(node:scaledWidth(line))
end
end
table.insert(SILE.typesetter.state.nodes, hbox)
SILE.typesetter:pushHbox(hbox)
SILE.typesetter:pushHlist(hlist)
end, "Place the output within a hbox of specified width, height, depth and visibility")

end
Expand Down
4 changes: 2 additions & 2 deletions packages/rotate/init.lua
Expand Up @@ -67,8 +67,7 @@ function package:registerCommands ()
self:registerCommand("rotate", function(options, content)
local angle = SU.required(options, "angle", "rotate command")
local theta = -math.rad(angle)
local origbox = SILE.call("hbox", {}, content)
SILE.typesetter.state.nodes[#SILE.typesetter.state.nodes] = nil
local origbox, hlist = SILE.typesetter:makeHbox(content)
local h = origbox.height + origbox.depth
local w = origbox.width.length
local st = math.sin(theta)
Expand Down Expand Up @@ -101,6 +100,7 @@ function package:registerCommands ()
depth = depth,
outputYourself = outputRotatedHbox
})
SILE.typesetter:pushHlist(hlist)
end)

end
Expand Down
6 changes: 2 additions & 4 deletions packages/ruby/init.lua
Expand Up @@ -65,14 +65,13 @@ function package:registerCommands ()

checkIfSpacerNeeded(reading)

SILE.call("hbox", {}, function ()
local rubybox = SILE.call("hbox", {}, function ()
SILE.settings:temporarily(function ()
SILE.call("noindent")
SILE.call("ruby:font")
SILE.typesetter:typeset(reading)
end)
end)
local rubybox = SILE.typesetter.state.nodes[#SILE.typesetter.state.nodes]
rubybox.outputYourself = function (box, typesetter, line)
local ox = typesetter.frame.state.cursorX
local oy = typesetter.frame.state.cursorY
Expand All @@ -87,8 +86,7 @@ function package:registerCommands ()
typesetter.frame.state.cursorY = oy
end
-- measure the content
SILE.call("hbox", {}, content)
local cbox = SILE.typesetter.state.nodes[#SILE.typesetter.state.nodes]
local cbox = SILE.call("hbox", {}, content)
SU.debug("ruby", "base box is", cbox)
SU.debug("ruby", "reading is", rubybox)
if cbox:lineContribution() > rubybox:lineContribution() then
Expand Down
15 changes: 6 additions & 9 deletions packages/rules/init.lua
Expand Up @@ -149,9 +149,7 @@ function package:registerCommands ()
self:registerCommand("underline", function (_, content)
local underlinePosition, underlineThickness = getUnderlineParameters()

local hbox = SILE.call("hbox", {}, content)
table.remove(SILE.typesetter.state.nodes) -- steal it back...

local hbox, hlist = SILE.typesetter:makeHbox(content)
-- Re-wrap the hbox in another hbox responsible for boxing it at output
-- time, when we will know the line contribution and can compute the scaled width
-- of the box, taking into account possible stretching and shrinking.
Expand All @@ -176,14 +174,13 @@ function package:registerCommands ()
SILE.outputter:drawRule(oldX, Y - underlinePosition, newX - oldX, underlineThickness)
end
})
SILE.typesetter:pushHlist(hlist)
end, "Underlines some content")

self:registerCommand("strikethrough", function (_, content)
local yStrikeoutPosition, yStrikeoutSize = getStrikethroughParameters()

local hbox = SILE.call("hbox", {}, content)
table.remove(SILE.typesetter.state.nodes) -- steal it back...

local hbox, hlist = SILE.typesetter:makeHbox(content)
-- Re-wrap the hbox in another hbox responsible for boxing it at output
-- time, when we will know the line contribution and can compute the scaled width
-- of the box, taking into account possible stretching and shrinking.
Expand All @@ -205,16 +202,15 @@ function package:registerCommands ()
SILE.outputter:drawRule(oldX, Y - yStrikeoutPosition - yStrikeoutSize / 2, newX - oldX, yStrikeoutSize)
end
})
SILE.typesetter:pushHlist(hlist)
end, "Strikes out some content")

self:registerCommand("boxaround", function (_, content)
-- This command was not documented and lacks feature.
-- Plan replacement with a better suited package.
SU.deprecated("\\boxaround (undocumented)", "\\framebox (package)", "0.12.0")

local hbox = SILE.call("hbox", {}, content)
table.remove(SILE.typesetter.state.nodes) -- steal it back...

local hbox, hlist = SILE.typesetter:makeHbox(content)
-- Re-wrap the hbox in another hbox responsible for boxing it at output
-- time, when we will know the line contribution and can compute the scaled width
-- of the box, taking into account possible stretching and shrinking.
Expand Down Expand Up @@ -245,6 +241,7 @@ function package:registerCommands ()
SILE.outputter:drawRule(oldX + w - thickness, Y - h, thickness, h + d)
end
})
SILE.typesetter:pushHlist(hlist)
end, "Draws a box around some content")

end
Expand Down

0 comments on commit 6c89469

Please sign in to comment.