我对使用非矩形页面几何形状来实现我的翻页书创意很感兴趣(带有图像和流动文本的 fancyhdr)。
我追求的页面几何形状是,每个奇数页的文本右下角都有一个小矩形缺失(切除的矩形)。在我之前的问题中,我们找到了一种方法来更改每个页面上的文本高度,但没有正确的几何形状:
\documentclass[twoside]{article}
\usepackage[textheight=15cm]{geometry}
\usepackage{lipsum}
\usepackage[demo]{graphicx}
\usepackage{fancyhdr}
\usepackage{everyshi}
\usepackage{xifthen}
\newcounter{flipbookcount}
\setcounter{flipbookcount}{1}
\fancyfoot[RO]{\setlength{\unitlength}{1mm}
\begin{picture}(0,10)
\put(-24,-34){\includegraphics[width=5cm]{mypic\theflipbookcount.png}}
\end{picture}
\stepcounter{flipbookcount}
}
\EveryShipout{%
\ifthenelse{\isodd{\value{page}}}%
{\global\textheight=20cm}% Next page is even
{\global\textheight=15cm}% Next page is odd
}
\begin{document}
\pagestyle{fancy}
\lipsum
\lipsum
\lipsum
\lipsum
\lipsum
\end{document}
有办法实现这个功能吗?如果我的意思不清楚,我可以添加一张图片作为示例。
答案1
这只是一次非常片面的尝试。它实际上不起作用,但可以帮助某人找到更好的解决方案。
我的想法是\parshape
,根据页面上剩余的空间,为每个段落设置 。即,页面上应容纳的行数为(\pagegoal-\pagetotal)/\baselineskip
。\parshape
以全长 的行开始\hsize
,然后是一些用于剪切的缩短行,其他行设置为全长\hsize
。全长的行数为(\pagegoal-\pagetotal-\l_cutout_height_dim)/\baselineskip
,较短的行数为差值。
不幸的是,这些计算没有考虑到页面可以拉伸或收缩的事实。此外,我不确定是否应该使用\int_div_truncate:nn
或\int_div_round:nn
(即,截断结果或将其四舍五入为最接近的整数)来计算行数。
此外,\everypar
直接使用通常不是一个好主意,或许我应该使用包everyhook
。
\documentclass{article}
\usepackage{lipsum}
\usepackage{expl3,xparse}
\ExplSyntaxOn
% This code accesses \everypar, \value{page}, \hsize, \pagegoal,
% \pagetotal, \baselineskip, \parshape, \interlinepenalties from
% TeX/LaTeX2e directly, as they do not have an expl3 interface.
%
\dim_new:N \l__cutout_height_dim
\dim_new:N \l__cutout_width_dim
\dim_new:N \l__cutout_hsize_dim
\int_new:N \l__cutout_long_lines_int
\int_new:N \l__cutout_total_lines_int
\NewDocumentCommand { \cutoutbottomodd } { m m }
{ \__cutout_bottom_odd:nn {#1} {#2} }
\cs_new_protected:Npn \__cutout_bottom_odd:nn #1#2
{
\dim_set:Nn \l__cutout_height_dim {#1}
\dim_set:Nn \l__cutout_width_dim {#2}
\exp_args:Nx \everypar
{
\exp_not:V \everypar
\exp_not:N \__cutout_everypar_test:
}
}
\cs_new_protected_nopar:Npn \__cutout_everypar_test:
{ \int_if_odd:nT { \value{page} } { \__cutout_everypar: } }
\cs_new_protected:Npn \__cutout_everypar:
{
\dim_set:Nn \l__cutout_hsize_dim
{ \hsize - \l__cutout_width_dim }
\int_set:Nn \l__cutout_total_lines_int
{
\int_max:nn { \c_one }
{
\int_div_truncate:nn
{ \pagegoal - \pagetotal }
{ \baselineskip }
}
}
\int_set:Nn \l__cutout_long_lines_int
{
\int_div_truncate:nn
{ \pagegoal - \pagetotal - \l__cutout_height_dim }
{ \baselineskip }
}
\int_compare:nNnF \l__cutout_long_lines_int > \c_zero
{ \int_zero:N \l__cutout_long_lines_int }
\parshape
= \int_eval:n { \l__cutout_total_lines_int + \c_one } \exp_stop_f:
\prg_replicate:nn \l__cutout_long_lines_int
{ \c_zero_dim \hsize }
\prg_replicate:nn
{ \l__cutout_total_lines_int - \l__cutout_long_lines_int }
{ \c_zero_dim \l__cutout_hsize_dim }
\c_zero_dim \hsize
\interlinepenalties
= \int_eval:n { \l__cutout_total_lines_int + \c_one } \exp_stop_f:
\prg_replicate:nn { \l__cutout_total_lines_int - \c_one }
{ 10000 \exp_stop_f: }
-10000 \exp_stop_f:
10000 \exp_stop_f:
}
\ExplSyntaxOff
\begin{document}
\cutoutbottomodd{96pt}{120pt}
\lipsum[1-10]
\large
\lipsum[11-20]
\Large
\lipsum[21-30]
\scriptsize
\lipsum[31-50]
\footnotesize
\lipsum[51-70]
\end{document}
编辑:上面的代码已更新,只在奇数页上打洞。此外,在之前的版本中,长行有时会从下一页延伸到上一页,因此会从洞中溢出。现在我使用 eTeX 来\interlinepenalties
强制分页。
EDIT2:使用\int_eval:n
而不是早已弃用的\int_eval:w
。同时将代码更新到更新的编码约定。