我想编写一个处理一些多行字符串的 Lua 函数。
因此,我创建了一个新文件,test.lua
其中包含
userdata = userdata or {}
function userdata.surroundwithdashes(str)
str = str:gsub("\n", " (linebreak)\\\\ ")
tex.print("--" .. str .. "--")
end
并添加\directlua{dofile('test.lua')}
到我的 latex 序言中。为了调用该函数,我创建了一个宏\newcommand{\dash}[1]{\directlua{userdata.surroundwithdashes([[#1]])}}
。
这对于常规文本很有效
\dash{This is some test text}
但是,它不能识别换行符
\dash{This is some test text
with more than one line}
如果我手动插入它们,则会抛出错误(未定义的控制序列)
\dash{This is some test text \\
with more than one line}
此外,这还会在“TeX”后面产生一个额外的“m”,
\dash{This is some \TeX text}
如何可靠地解析输入字符串并检测其中的换行符?
答案1
这\\
扩展前它被传递给 Lua 函数userdata.surroundwithbraces
。由于扩展是类似 的扩展\edef
,而不是 LaTeX 的扩展\protected@edef
,因此宏\\
会中断。
可以通过 e-TeX 的 来阻止扩展\detokenize
。
此外,我更喜欢使用\luaescapestring
(或者 LuaLaTeX 的\luatexluaescapestring
) 来传递字符串参数,因为原语会处理必要的转义:
\RequirePackage{filecontents}
\begin{filecontents*}{dash.lua}
userdata = userdata or {}
function userdata.surroundwithdashes(str)
str = str:gsub("\n", " (linebreak)\\\\ ")
tex.print("--" .. str .. "--")
end
\end{filecontents*}
\directlua{dofile('dash.lua')}
\documentclass{article}
\newcommand*{\dash}[1]{%
\directlua{userdata.surroundwithdashes(%
"\luatexluaescapestring{\detokenize{#1}}")}%
}
\begin{document}
\dash{This is some test text}
\dash{This is some test text \\
with more than one line}
\end{document}
答案2
除了在 verbatim 或 obelines 等中,行尾被报告给宏层作为空格(或像\par
一个空白行),因此宏\dash
有一个带有单个空格标记的text
参数with