
¿Hay alguna forma de convertir pt
a TeX mm
o cm
en formato simple?
Respuesta1
Para convertir desde una dimensión dada en puntos, primero guarde la dimensión en un contador y luego realice la conversión a lo que necesita. Cuando TeX guarda la dimensión en un contador, la convierte a sp
unidades.
\catcode`@=11
\@tempdimb25.4mm
\@tempcnta=\@tempdimb
\the\@tempcnta
\divide\@tempcnta by65536\par
\the\@tempcnta pt
\bye
La conversión de cualquier unidad a un punto es un poco más complicada:
\catcode`@=11
\newdimen\@tempdimb
\newcount\@tempcnta
\def\topoint#1#2{%
\@tempdimb=#1
\@tempcnta=\@tempdimb
\multiply\@tempcnta by10
\divide\@tempcnta by18647 \advance\@tempcnta by1
\multiply\@tempcnta by72 \divide\@tempcnta by2540
\expandafter\def\expandafter#2\expandafter{\the\@tempcnta}}
\topoint{25.4mm}{\test}
\test pt
\bye
Respuesta2
Solución ampliable sin eTeX, utilizando el paquete de Heiko bigintcalc
. Realmente, esto es un desastre y deberías usar una de las soluciones que utilizan las extensiones eTeX.
\input bigintcalc.sty
\catcode`@=11
% Step 1: expand the number.
\def\pttocm#1{\romannumeral\expandafter\pttocm@i\romannumeral-`0#1pt;;;;}
\def\pttocm@i#1{\pttocm@clean\ifcat\relax#1\the\fi#1}
\def\pttocm@clean{\expandafter\pttocm@clean@\romannumeral-`0}
\def\pttocm@clean@#1{%
\ifcase\ifnum`#1<"2B 1\else\ifnum`#1>"39 1\else 2\fi\fi
\or\expandafter\pttocm@clean@end
\or\expandafter\pttocm@clean@do\fi #1}
\def\pttocm@clean@do#1#2;#3;{\pttocm@clean#2;#3#1;}
% Step 2: convert the decimal number to an integer/10^n
\def\pttocm@clean@end#1;#2;{\pttocm@clean@end@#2.;#2;.;!}
\def\pttocm@clean@end@#1.#2;#3.#4;#5!{\pttocm@decimal#4.;;#1#4}
\def\pttocm@decimal#1#2;{\ifx.#1\pttocm@decimal@\fi\pttocm@decimal#2;0}
% Step 3: convert from pt to nm (25400000nm=7227pt)
\def\pttocm@decimal@#1;0#2;#3;{\fi
\expandafter\expandafter\expandafter\pttocm@result
\bigintcalcDiv{\bigintcalcMul{25400000}{#3}}{7227#2}.;}
% Step 4: check the sign
\def\pttocm@result#1{%
\ifx-#1\expandafter\pttocm@result@neg
\else\expandafter\pttocm@result@pos\fi#1}
\def\pttocm@result@neg-{\expandafter\pttocm@rmstop
\expandafter-\romannumeral\pttocm@result@pos}
\chardef\pttocm@rmstop=0
% Step 5: shift the period 5 steps to the left, by reversing twice.
\def\pttocm@result@pos#1;{%
\pttocm@reverse 00000#1%
{?\pttocm@result@shift;}?;%
{?\pttocm@result@print;}?;}
\def\pttocm@reverse#1#2;{%
\pttocm@gobble#1%
\pttocm@reverse#2;#1}
\def\pttocm@gobble#1{}
\def\pttocm@result@shift#1;#2;#3;#4.#5#6#7#8#9%
{\pttocm@reverse #4#5#6#7#8#9.}
\def\pttocm@result@print#1;#2;#3;#4;{\pttocm@trimzeros{#4}}
% Step 6: remove spurious zeros.
\def\pttocm@trimzeros#1{\pttocm@trim@#1;\pttocm@trim@ 0;\pttocm@trim@@}
\def\pttocm@trim@#10;#2{#2#1;}
\def\pttocm@trim@@#1;#2;{\pttocm@trim@@@#1}
\def\pttocm@trim@@@#1{%
\ifx0#1\else\expandafter\pttocm@trim@end\expandafter#1\fi
\pttocm@trim@@@}
\def\pttocm@trim@end#1#2{%
\ifx.#1\expandafter\pttocm@rmstop\expandafter0%
\else\expandafter\pttocm@rmstop\fi #1}
\catcode`@=12
\pttocm{-12.1232pt}
\pttocm{283000000000}
\def\foo{23}
\pttocm{12\foo.1\foo2pt}
\newdimen\testdimen
\testdimen=1cm
\pttocm{\testdimen}
\testdimen=-1mm
\pttocm{\testdimen}
\bye
Respuesta3
Con la ayuda de eTeX \scantokens
, \strip@pt
también se puede:
\def\strip#1.#2pt{#1\ifnum#2>0.#2\fi}
\def\convertto#1#2{%
\expandafter\expandafter\expandafter\strip
\expandafter\expandafter\scantokens
\expandafter{\the\dimexpr#2*65536/\number\dimexpr1#1\relax\relax\endinput}}
\convertto{pt}{1pc}
\bye
Respuesta4
Aquí hay una combinación de la pregunta de Yiannis deEliminando el pt de una dimensióny la respuesta de Philippe Goutet de¿Cuáles son las distintas unidades (ej, em, in, pt, bp, dd, pc) expresadas en mm?:
\catcode`@=11
\begingroup
\catcode `P=12 % digits and punct. catcode
\catcode `T=12 % digits and punct. catcode
\lowercase{%
\def\x{\def\rem@pt##1.##2PT{##1\ifnum##2>\z@.##2\fi}}}
\expandafter\endgroup\x%
\def\strip@pt{\expandafter\rem@pt\the}
\def\convertto#1#2{\strip@pt\dimexpr #2*65536/\number\dimexpr 1#1\relax\relax}
\catcode`@=12
\convertto{mm}{10pt}
\bye
que requiere extensiones e-TeX.