使用 \newcommand 显示可能包含需要转义的特殊字符的用户输入

使用 \newcommand 显示可能包含需要转义的特殊字符的用户输入

我现在对 LaTeX 了解不多,但我需要能够使用它通过 C# 生成动态 PDF 文档。

在大多数情况下,一切都很酷并且按照我希望的方式运作。

有人给我一个静态的 LaTeX 文档作为基础模板,我使用 C# 写入来自 Web 服务器和数据库的所有动态数据。

例如,这是我从 LaTeX 开发人员那里得到的信息:

\documentclass[letter,landscape]{report}

\newcommand{\ReportTitle} {Summary Report }
\newcommand{\ReportAuthor}{Mister San }

\pdfinfo{
    /Title   (\ReportTitle)
    /Author  (\ReportAuthor)
    /Subject (Generated by \ReportAuthor on \today)
}

\begin{document}
    \ReportTitle \\
    By: \ReportAuthor \\
\end{document}

然后,我将获取该 LaTeX 代码(标记?)并使用 C# / ASP.NET MVC 使其动态化(我使用的技术对于这个问题来说并不重要)。完成后,它最终将看起来像这样:

\documentclass[letter,landscape]{report}

\newcommand{\ReportTitle} {@Model.ReportTitle }
\newcommand{\ReportAuthor}{@Model.ReportAuthor }

\pdfinfo{
    /Title   (\ReportTitle)
    /Author  (\ReportAuthor)
    /Subject (Generated by \ReportAuthor on \today)
}

\begin{document}
    \ReportTitle \\
    By: \ReportAuthor \\
\end{document}

现在,\ReportTitle 和 \ReportAuthor 是动态的,并且基于数据库中的内容。这通常按原样工作,但我遇到了一个特定问题,我不知道该怎么做才能解决它。

\ReportTitle 和 \ReportAuthor 字段中的文本来自用户输入的内容,他们可以使用任何他们想要的字符。如果用户输入了类似“~My_$uper_Report~”的 \ReportTitle - LaTeX 标记将变得无效,因为选择了保留字符。

我知道您可以转义保留字符,因此“Standard_Report”的 \ReportTitle 将变成:

\newcommand{\ReportTitle} {Standard\_Report }

我用 C# 编写了一个方法,将所有特殊的 LaTeX 字符替换为它们的转义字符。

这有时会有效(这很奇怪,通常事情要么有效,要么无效)。

好像我有太多这样的转义字符:

\newcommand{\ReportTitle} {\# \$ \% \& \~ \_ \^ \{ \} \backslash}

我收到内存不足错误。

我不知道为什么我无法在 \newcommand 中存储以空格分隔的转义特殊字符列表。

有人知道为什么我无法使前面的示例正常工作吗? 有没有更好的方法可以做到这一点?

是否存在现有的工具可以对用户输入进行编码,这样您不必自己逃避一切并检查 LaTeX 注入攻击?

顺便说一下,这是我收到的错误:

./main.tex:7: TeX capacity exceeded, sorry [input stack size=5000].
\@inmathwarn ...latex@warning {Command \protect #1
invalid in math mode}\fi l.7        /Title   (\ReportTitle)

****编辑:**** 一位用户发表了一条评论(但随后删除了)建议使用如下内容:

\detokenize\expandafter{\ReportTitle}

这实际上允许报告编译并显示保留字符,但不幸的是,它还在每个转义字符周围添加了双引号字符,这是不可接受的。不过还是谢谢你。我相信我最终会弄清楚的,或者这里的另一个用户会知道该怎么做。

答案1

\# \$ \% \& \~ \_ \^ \{ \} 

是非常不同的命令类型,\%会产生百分比但\^不会产生百分比,^它是一个接受\^{a}构造重音字母的参数的命令。

您可以使用

\detokenize{@Model.ReportTitle}

那么您基本上只需要引用\( \}\%确保构造具有平衡的括号。并添加

\usepackage[T1]{fontenc}

这样您就会获得稍微更正常的字体编码,其中的 ascii 字符可以像它们自己一样打印。

如果你永远不会在文档中插入注释,你可以%全局创建一个普通字符,这样你就不需要\%只添加

 \catcode`\%=12

到序言部分(在任何包加载之后,否则包中的注释将会被破坏)

相关内容