
Estoy implementando operadores no estándar dibujándolos como imágenes usando el pict2e
paquete y luego escalándolos para que quepan en los distintos modos matemáticos. Almaceno los parámetros de la imagen en macros externas y los invoco en el picture
cuerpo.
Aquí hay un ejemplo mínimo:
\documentclass{article}
\usepackage{pict2e}
\def\num{3}
\def\decimal{3.2}
\newcommand*\testfigure{%
\begin{picture}(3,3)(0,0)
\put(0, 0){\line(0, \decimal){\num}}
\end{picture}
}
\begin{document}
\testfigure
\end{document}
Sin embargo, al compilar esto en el dorso y en mi instalación local de TeX Live, aparece un error:Falta = insertado para\ifnum
. A esto le sigue otro error:Número faltante, tratado como 0. Tenga en cuenta que este comportamiento se repite cuando defino la \decimal
macro con \newcommand
. También ocurre cuando el número tiene punto decimal pero no parte fraccionaria (por ejemplo, 3. y 3.0).
Este comportamiento se repite con \vector
, pero no con \qbezier
ninguno de los otros comandos de imagen.
Si reemplazo la \decimal
invocación con un número decimal literal, la compilación se realiza correctamente. Se pict2e
apoyan argumentos de pendiente real, a diferencia de la restricción de coprimalidad de picture
. También sé que \ifnum
actúa sólo sobre números enteros.
¿Por qué falla la compilación en este caso y por qué solo con \line
? ¿Cómo puedo dar correctamente \line
un argumento de pendiente decimal desde una macro?
Respuesta1
Esto fue un error en pict2e
. Envié un correo a los mantenedores y Rolf respondió positivamente. Incorporó los cambios a continuación y el problema debería solucionarse ahora (versión 0.3c, 20-08-2019).
La macro \pIIe@checkslopeargs
solía hacer:
\renewcommand*\pIIe@checkslopeargs[3]{%
\def\@tempa{#1}\expandafter\pIIe@checkslopearg\@tempa.:{#3}%
\def\@tempa{#2}\expandafter\pIIe@checkslopearg\@tempa.:{#3}%
\ifdim #1\p@=\z@ \ifdim #2\p@=\z@ \@badlinearg \fi\fi}
Almacena el primer argumento en una macro temporal ( \def\@tempa{#1}
), luego expande esa macro temporal y llama \pIIe@checkslopearg
con eso. Sin embargo la línea
\def\@tempa{#1}\expandafter\pIIe@checkslopearg\@tempa.:{#3}
hace exactamente lo mismo que el más simple
\pIIe@checkslopearg#1.:{#3}
y cuando \pIIe@checkslopearg
se expande, dividiéndolo #1
, .
no encuentra el punto si está oculto en su \decimal
macro, pero funciona si lo pasa explícitamente. Después de eso, un número decimal entra en una \ifnum
prueba, convirtiéndose esencialmente en \ifnum3.2<\z@
, que falla con Missing = inserted for \ifnum
.
El hecho de que el argumento esté almacenado en una macro temporal y el códigohaceadmite números decimales, me lleva a creer que esto es un error. Para solucionarlo puedes reemplazar los dos \def
por \edef
. También agregué un espacio faltante en una macro que provocaría una expansión innecesaria.
Pon esto en tu preámbulo, después de cargar pict2e
:
\makeatletter
\renewcommand*\pIIe@checkslopeargs[3]{%
% V \edef instead of \def
\edef\@tempa{#1}\expandafter\pIIe@checkslopearg\@tempa.:{#3}%
\edef\@tempa{#2}\expandafter\pIIe@checkslopearg\@tempa.:{#3}%
\ifdim #1\p@=\z@ \ifdim #2\p@=\z@ \@badlinearg \fi\fi}
\def\pIIe@checkslopearg #1.#2:#3{%
\def\@tempa{#1}%
\ifx\@tempa\empty\def\@tempa{0}\fi
\ifx\@tempa\space\def\@tempa{0}\fi% V added space
\ifnum\ifnum\@tempa<\z@-\fi\@tempa>#3 \@badlinearg \fi}
\makeatother