Buffers in LuaTeX

From Wiki
Revision as of 13:31, 16 February 2021 by Jano Kula (talk | contribs) (buffers and boxes difference)
Jump to navigation Jump to search

A bit about buffers

Buffers are named chunks of text, saved by ConTeXt to be retrieved by the user later. They are meant for storing information not being typeset, yet. Typeset material is stored in Boxes. Buffers are usually defined as follows:

% Start a buffer with a custom name
\startbuffer[Marie]
This is the text in the buffer 'Marie'
\stopbuffer

% Define the \start...\stopPierre environment
\def\startPierre
    {\dostartbuffer[Pierre][startPierre][stopPierre]}

% Give \stopPierre some meaning if you want to do something with the buffer right away.
%\def\stopPierre
%   {\getbuffer[Pierre]}}

\startPierre
This is the text in the buffer 'Pierre'.
\stopPierre
\getbuffer[Pierre] % Print typeset contents

\startPierre
Now this is the text in the buffer 'Pierre', instead.
\stopPierre
\typebuffer[Pierre] % Print verbatim contents

The LuaTeX buffers.* commands

These commands were all found in the source code: buff-ini.lua

  • buffers.getcontent(b): Get the contents of the buffer b, or the empty string if the buffer does not exist.
  • buffers.raw(b): Synonym for buffers.getcontent(b).
  • buffers.getlines(b): Equivalent to splitlines(buffers.getcontent(b)).
  • buffers.erase(b): Delete the buffer b (not just its contents).
  • buffers.assign(b, text, catcodes): Set the contents of buffer b to text, using catcodetable catcodes
  • buffers.append(b, text): Append text to buffer b.
  • buffers.exists(b): Returns the name of the buffer if it exists, or else nil.
  • buffers.collectcontent(names, seperator): Returns the contents of the buffers in names, seperated by seperator ('\n' by default). Names can be either a table, or a comma-seperated string (surrounding braces are automatically removed — see parsers.settings_to_array in util-prs.lua.

Accessing buffer names

From the mailing list:

It's not easy to access buffer names from ConTeXt because ConTeXt stores the buffers in a local variable cache which is an upvalue for all the other functions. However, you can use the Lua debug library to access upvalues. The buffers.erase function only has a single upvalue which is cache, making it easy to extract all the buffer names from that. However, you can't get them in the order of declaration because cache is a hashmap and not an array. Moreover, ConTeXt is usually in sandboxing mode. To get access to the debug library you have to run ConTeXt with:

context --debug test.tex

MWE:

\starttext

\startbuffer[ex1]
Buffer 1
\stopbuffer

\startbuffer[ex2]
Buffer 2
\stopbuffer

\startluacode
local _, cache = debug.getupvalue(buffers.erase,1)
local names = {}
for name,_ in pairs(cache) do
    names[#names+1] = name
end
context(table.concat(names,", "))
\stopluacode
% Prints ex2, ex1 (but specific order is not guaranteed)

\stoptext