我想在 tikz 中声明函数,以便在代码中多次使用同一个函数。
遗憾的是,tikz 的“声明函数”似乎与 babel 中的法语选项不兼容。事实上,以下代码(我故意简化的)运行良好:
\documentclass[english]{article}
\usepackage{babel}
\usepackage{tikz}
\begin{document}
\begin{tikzpicture}
\tikzset{declare function={Carre(\t)=\t*\t;}}
\draw plot [domain=-1:1] (\x,{Carre(\x)});
\end{tikzpicture}
\end{document}
但是当我更换
\documentclass[english]{article}
和
\documentclass[english,french]{article}
编译会产生错误。日志文件的内容如下:
缺失字符:nullfont 字体中没有 =! 缺失字符:nullfont 字体中没有 @! 缺失字符:nullfont 字体中没有 @!
失控参数?-1:1] (\x ,{Carre(\x )}); \end {tikzpicture} \end {document} ! 段落在 \pgfmath@local@@functions 完成之前结束。\par l.18
我怀疑你忘记了一个“}”,导致我将这个控制序列应用于太多文本。我们该如何恢复?我的计划是忘记整件事,并希望一切顺利。
在发布此文章之前,我更新了所有软件包但没有成功。
欢迎任何帮助!
答案1
分号由 french 选项激活babel
,这会使 TikZ 解析器关闭。您可以\shorthandoff{;}
在您的 中说tizpicture
来修复此问题。
您可以通过手动将代码\shorthandoff{;}
放在每个代码的开头来执行此操作tikzpicture
,也可以使用 TikZ 样式tikzpicture
通过设置自动将代码插入到每个代码中
\tikzset{
every picture/.prefix style={
execute at begin picture=\shorthandoff{;}
}
}
或者,正如 Tobi 在评论中指出的那样,您可以加载etoolbox
包并使用
\AtBeginEnvironment{tikzpicture}{\shorthandoff{;}}
修补tikzpicture
环境。
答案2
TikZ 3.0 引入了一个新的babel
tikzlibrary 来解决此类问题。
一个小型库,可使与 babel 包的交互更加容易。尽管名字如此,但它在其他情况下也可能有用,即当重要符号的 catcode 全局更改时。通常,使用此库始终是一个好主意;它并不总是默认加载,因为在极少数情况下它可能会破坏旧代码。
\documentclass[english]{article}
\usepackage[english,french]{babel}
\usepackage{tikz}
\usetikzlibrary{babel}
\begin{document}
\begin{tikzpicture}
\tikzset{declare function={Carre(\t)=\t*\t;}}
\draw plot [domain=-1:1] (\x,{Carre(\x)});
\end{tikzpicture}
\end{document}
更新:
正如所显示的Babel、活动字符、ifthenelse 和 tikz,babel
tikzlibrary 与 package 结合时有一些限制babel-spanish
。
答案3
与 Claudio 链接到的问题一样,问题出在 TikZ 加载的一些额外代码中,这些代码对活动字符的检查量不如主 TikZ 解析器那么多。由于 Babel;
直到文档开始前才更改的 catcode declare function
,因此例程中涉及的所有分号都是非活动的,因此与函数声明中的活动分号不匹配。同样,就像那个问题一样,一个解决方案就像 Jake 所说的那样:关闭;
tikzpicture 中的活动性。另一种方法是破解代码,使其在分号的 catcode 方面具有鲁棒性:
\documentclass[french]{article}
%\url{http://tex.stackexchange.com/q/86023/86}
\usepackage{babel}
\usepackage{tikz}
\makeatletter
\pgfkeys{%
/pgf/declare function/.code={%
\ifnum\the\catcode`\;=\active\relax%
\let\pgfmath@local@function@body=\pgfmath@local@function@body@active
\let\pgfmath@local@@functions=\pgfmath@local@@functions@active
\pgfmath@local@functions@active{#1}%
\else
\pgfmath@local@functions@notactive{#1}%
\fi
}
}
\def\pgfmath@local@functions@notactive#1{%
\pgfmath@local@functions#1@=@;%
}
\begingroup
\catcode`\;=\active\relax
\gdef\pgfmath@local@functions@active#1{%
\pgfmath@local@functions#1@=@;%
}
\gdef\pgfmath@local@@functions@active#1=#2;{%
\def\pgfmath@local@temp{#1}%
\ifx\pgfmath@local@temp\pgfmath@local@at%
\let\pgfmath@local@next=\relax%
\else%
\pgfmath@local@function#1=#2;%
\let\pgfmath@local@next=\pgfmath@local@functions%
\fi%
\pgfmath@local@next%
}
\gdef\pgfmath@local@function@body@active#1;{%
\def\pgfmath@local@body{#1}%
\begingroup%
\c@pgf@counta=0\relax%
\ifx\pgfmath@local@args\pgfmath@empty%
\expandafter\pgfmath@toks\expandafter=\expandafter{\pgfmath@local@body}%
\else%
\pgfmath@toks={}%
\expandafter\pgfmath@local@function@@body\pgfmath@local@args,,%
\fi%
\xdef\pgfmath@local@temp{%
\noexpand\pgfmathdeclarefunction{\pgfmath@local@name}{\the\c@pgf@counta}%
{\noexpand\pgfmathparse{\the\pgfmath@toks}}%
}%
\endgroup%
\pgfmath@local@temp%
}
\endgroup
\makeatother
\begin{document}
\begin{tikzpicture}
\tikzset{declare function={Carre(\t)=\t*\t;}}
\draw plot [domain=-1:1] (\x,{Carre(\x)});
\end{tikzpicture}
\shorthandoff{;}
\begin{tikzpicture}
\tikzset{declare function={Carre(\t)=\t*\t;}}
\draw plot [domain=-1:1] (\x,{Carre(\x)});
\end{tikzpicture}
\end{document}
与其他问题一样,这里的结果是可以编译的。为了证明这一点,下面是结果(将standalone
图片并排放置):
答案4
我用的是这个:
\usepackage[babel=true, kerning=true]{microtype}