介绍
目前,我正在准备一个自定义类,该类可能会使用 XeTeX 或 LuaTeX 进行编译。它用于需要专业打印的书籍布局,因此我想设置TrimBox
输出 PDF 的。问题是出血的大小是由 key-val 类选项定义的。因此,我需要能够使用宏作为\special
/\pdfpageattr
命令的一部分。
大概的概念
一般的想法是使用\special
s (XeTeX) 或\pdfpageattr
(LuaTeX、PDFTeX) 来设置 TrimBox。编译器的区分可以用 LaTeX3 来完成\sys_if_engine_
,而且 TrimBox 字符串也可以定义为标记列表。然后我使用这些标记列表的变量内容 () 定义一个宏,:V
将正确的值写入 PDF。
代码
这是我提出的最小示例代码。
\documentclass{article}
\usepackage{xparse}
\ExplSyntaxOn\makeatletter %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%% bleed value (keyval class option in real document)
\dim_new:N \g_@@_bleed_dim
\dim_set:Nn \g_@@_bleed_dim { 3mm }
%% set page size (and other stuff in the real document)
\usepackage { geometry }
\geometry { papersize = { 185mm , 245mm } }
%% set crop size
\usepackage [ center ] { crop }
\CROP@size {
\dim_eval:n { \paperwidth + 2 \g_@@_bleed_dim }
} {
\dim_eval:n { \paperheight + 2 \g_@@_bleed_dim }
}
%% new variant
\cs_generate_variant:Nn \dim_to_decimal_in_bp:n { N }
% values for the rim box
\tl_new:N \g_@@_trim_box_quadruple_tl
\tl_set:Nx \g_@@_trim_box_quadruple_tl {
\dim_to_decimal_in_bp:N \g_@@_bleed_dim \c_space_token
\dim_to_decimal_in_bp:N \g_@@_bleed_dim \c_space_token
\dim_to_decimal_in_bp:n { \paperwidth + \g_@@_bleed_dim } \c_space_token
\dim_to_decimal_in_bp:n { \paperheight + \g_@@_bleed_dim }
}
%% special for use with XeTeX
\tl_new:N \g_@@_trim_special_tl
\tl_set:Nx \g_@@_trim_special_tl {
pdf: \c_space_token put \c_space_token @thispage \c_space_token
<< \c_space_token /TrimBox \c_space_token [ \g_@@_trim_box_quadruple_tl ] \c_space_token >>
}
%% page attribute for use with LuaTeX and PDFTeX
\tl_new:N \g_@@_trim_pageattr_tl
\tl_set:Nx \g_@@_trim_pageattr_tl {
/TrimBox \c_space_token [ \g_@@_trim_box_quadruple_tl ]
}
%% command to set the specials for xetex
\cs_new:Npn \@@_special:n #1 {
\AtBeginShipout { \immediate \special { #1 } }
\immediate \special { #1 }
}
%% command to set the page attributes for pdftex/luatex
\cs_new:Npn \@@_pdfpageattr:n #1 {
\pdfpageattr { #1 }
}
%% make a variants to make sure we get the expaned content
\cs_generate_variant:Nn \@@_special:n { V }
\cs_generate_variant:Nn \@@_pdfpageattr:n { V }
%% [A] THIS DOES NOT WORK!
%% set the trim box according to engine
%\bool_if:nTF { \sys_if_engine_luatex_p: || \sys_if_engine_pdftex_p: } {
% \@@_pdfpageattr:V \g_@@_trim_pageattr_tl
%} {
% \sys_if_engine_xetex:TF {
% \usepackage{atbegshi}
% \@@_special:V \g_@@_trim_special_tl
% } { ERROR: UNKOWN MACHINE! }
%}
%% just a macro to show some debug info
\NewDocumentCommand { \debuginfo } { } {
\par\noindent
Machine: ~ \texttt{ \c_sys_engine_str }
\par\bigskip\noindent
special: \\
\mbox { \texttt { \g_@@_trim_special_tl } }
\par\medskip\noindent
pageattribute: \\
\mbox { \texttt { \g_@@_trim_pageattr_tl } }
}
\ExplSyntaxOff\makeatother %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%% [B] THIS WORKS!
%% for pdftex and luatex
%\pdfpageattr { /TrimBox [8.50392 8.50392 532.91336 702.99211] }
%% for xetex
%\usepackage{atbegshi}
%\AtBeginShipout { \special { pdf: put @thispage << /TrimBox [8.50392 8.50392 532.91336 702.99211] >> } }
%\special { pdf: put @thispage << /TrimBox [8.50392 8.50392 532.91336 702.99211] >> }
\begin{document}
\section*{Test Document}
\debuginfo \clearpage Just another page \ldots
\end{document}
结果
不幸的是我的想法没有达到预期的效果。
使用手动设置([B]
在代码中)时,一切都很好,并且 TrimBox 已针对 PDFTeX、LuaTeX 和 XeTeX 正确设置。但是,当使用自动生成的标记列表([A]
在代码中)时,它不起作用:使用 XeTeX 我得到了一个 PDF,但没有任何 TrimBox 设置,而使用 PDFTeX 或 LuaTeX 时,PDF 文件已损坏,无法使用查看器打开,甚至解压缩失败cpdf
。
问题
简单:我犯了什么错误?
笔记
如果这个问题导致一个强大的代码,我会将它打包并在 CTAN 上发布。
在研究过程中,我发现了以下问题,并想澄清一下这不是一个重复的问题;-)
- 在 pdf 中嵌入打印机设置– 据我所知
pdfprintclip
这只是一个 vier 设置,但说实话我没有测试它,因为我不知道如何使用它。 - 在 xelatex 中使用“几何”设置正确的自定义页面大小时出现问题– 仅与视觉页面布局有关,与 PDF-TrimBox 无关
- 如何在 \pdfpageattr 中使用宏– 实际上展示了如何使用宏(又称动态值)来实现TrimBox,但我无法将答案转移到我的LaTeX3方法中
- 使用 XeLaTeX 生成符合 PDF/X 标准的文档– 仅包含有关使用 XeTeX 手动设置框的信息。
此外,在这种情况下,这些pdf
软件包似乎没有帮助。至少我在手册中找不到有关修剪的任何信息……
答案1
问题是\c_space_token
不会扩展为空格,我\space
在这里使用了 。 它是\let
一个空格,所以它是一个不可扩展的隐式字符,如果你取消注释第一行,\pdfcompresslevel
这样 pdf 流就是可读的,你会看到 被\c_space_token
逐字写入了 pdf 流中的裁切框坐标之间。 相反,\space
是一个扩展为空格字符的宏。
%\pdfcompresslevel0
\documentclass{article}
\usepackage{xparse}
\ExplSyntaxOn\makeatletter %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%% bleed value (keyval class option in real document)
\dim_new:N \g_@@_bleed_dim
\dim_set:Nn \g_@@_bleed_dim { 3mm }
%% set page size (and other stuff in the real document)
\usepackage { geometry }
\geometry { papersize = { 185mm , 245mm } }
%% set crop size
\usepackage [ center ] { crop }
\CROP@size {
\dim_eval:n { \paperwidth + 2 \g_@@_bleed_dim }
} {
\dim_eval:n { \paperheight + 2 \g_@@_bleed_dim }
}
%% new variant
\cs_generate_variant:Nn \dim_to_decimal_in_bp:n { N }
% values for the rim box
\tl_new:N \g_@@_trim_box_quadruple_tl
\tl_set:Nx \g_@@_trim_box_quadruple_tl {
\dim_to_decimal_in_bp:N \g_@@_bleed_dim \space
\dim_to_decimal_in_bp:N \g_@@_bleed_dim \space
\dim_to_decimal_in_bp:n { \paperwidth + \g_@@_bleed_dim } \space
\dim_to_decimal_in_bp:n { \paperheight + \g_@@_bleed_dim }
}
%% special for use with XeTeX
\tl_new:N \g_@@_trim_special_tl
\tl_set:Nx \g_@@_trim_special_tl {
pdf: ~ put ~ @thispage ~
<< ~ /TrimBox \space [ \g_@@_trim_box_quadruple_tl ] ~ >>
}
%% page attribute for use with LuaTeX and PDFTeX
\tl_new:N \g_@@_trim_pageattr_tl
\tl_set:Nx \g_@@_trim_pageattr_tl {
/TrimBox \space [ \g_@@_trim_box_quadruple_tl ]
}
%% command to set the specials for xetex
\cs_new:Npn \@@_special:n #1 {
\AtBeginShipout { \immediate \special { #1 } }
\immediate \special { #1 }
}
%% command to set the page attributes for pdftex/luatex
\cs_new:Npn \@@_pdfpageattr:n #1 {
\pdfpageattr { #1 }
}
%% make a variants to make sure we get the expaned content
\cs_generate_variant:Nn \@@_special:n { V }
\cs_generate_variant:Nn \@@_pdfpageattr:n { V }
%% [A] THIS DOES NOT WORK!
%% set the trim box according to engine
\bool_if:nTF { \sys_if_engine_luatex_p: || \sys_if_engine_pdftex_p: } {
\@@_pdfpageattr:V \g_@@_trim_pageattr_tl
} {
\sys_if_engine_xetex:TF {
\usepackage{atbegshi}
\@@_special:V \g_@@_trim_special_tl
} { ERROR: UNKOWN MACHINE! }
}
%% just a macro to show some debug info
\NewDocumentCommand { \debuginfo } { } {
\par\noindent
Machine: ~ \texttt{ \c_sys_engine_str }
\par\bigskip\noindent
special: \\
\mbox { \texttt { \g_@@_trim_special_tl } }
\par\medskip\noindent
pageattribute: \\
\mbox { \texttt { \g_@@_trim_pageattr_tl } }
}
\ExplSyntaxOff\makeatother %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%% [B] THIS WORKS!
%% for pdftex and luatex
%\pdfpageattr { /TrimBox [8.50392 8.50392 532.91336 702.99211] }
%% for xetex
%\usepackage{atbegshi}
%\AtBeginShipout { \special { pdf: put @thispage << /TrimBox [8.50392 8.50392 532.91336 702.99211] >> } }
%\special { pdf: put @thispage << /TrimBox [8.50392 8.50392 532.91336 702.99211] >> }
\begin{document}
\section*{Test Document}
\debuginfo \clearpage Just another page \ldots
\end{document}