排版段落時,我想確保最後一行不會太短也不太長了。為此,我正在尋找產生以下任一結果的設定:
- 一個完全合理、完美的長方形段落;
- 最後一行填入超過 20% 且少於 80% 的合理段落。
換句話說,任何段落的最後一行不應填充少於 20% 或超過 80% 的內容——它們應該變得完全合理。可以透過手動添加(僅)這些段落來實現效果\parfillskip 0pt
,但這正是我想要自動化的。
本文檔展示了兩個好例子和兩個壞例子:
\documentclass[a4paper]{article}
\usepackage[utf8]{inputenc}
% Page setup
\usepackage[a4paper,margin=3cm]{geometry}
% Typography
\usepackage{newtxtext,newtxmath}
\usepackage{microtype}
\parindent 0pt
\parskip\baselineskip
\begin{document}
\textbf{I'm looking for settings
that produce either a)~a~perfect rectangle
or b)~a paragraph whose last line
is filled more than 20\% and less than 80\%.}
\section*{Good examples}
\textbf{My perfect paragraph is a~rectangle:}
{
\parfillskip 0pt
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Sed rhoncus lorem eget ultricies bibendum. Duis luctus felis arcu, sit amet dapibus orci imperdiet id. Duis ullamcorper tortor eget leo fringilla, a lacinia nisl pulvinar. Etiam id facilisis augue. Sed convallis tempus ex, sed accumsan justo pulvinar vitae. Sed id sapien leo. Aliquam posuere ex lacus, ut posuere metus ullamcorper eu. Duis a imperdiet nibh. Donec tincidunt hendrerit nulla, et convallis metus imperdiet nec. Pellentesque massa enim, pharetra in pulvinar a, efficitur nec lorem. Cras mattis ex lorem, et euismod ligula rhoncus. Aenean ultricies quis velit non faucibus.
}
\textbf{However, this is not always achievable (and that's fine):}
{
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Sed rhoncus lorem eget ultricies bibendum. Duis luctus felis arcu, sit amet dapibus orci imperdiet id. Duis ullamcorper tortor eget leo fringilla, a lacinia nisl pulvinar. Etiam id facilisis augue. Sed convallis tempus ex, sed accumsan justo pulvinar vitae. Sed id sapien leo. Aliquam posuere ex lacus, ut posuere metus ullamcorper eu. Duis a imperdiet nibh. Donec tincidunt hendrerit nulla, et convallis metus imperdiet nec. Pellentesque massa enim, pharetra in pulvinar a, efficitur nec lorem. Cras mattis ex lorem, et euismod ligula rhoncus.
}
\section*{Bad examples}
\textbf{This last line is too short:}
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Sed rhoncus lorem eget ultricies bibendum. Duis luctus felis arcu, sit amet dapibus orci imperdiet id. Duis ullamcorper tortor eget leo fringilla, a lacinia nisl pulvinar. Etiam id facilisis augue. Sed convallis tempus ex, sed accumsan justo pulvinar vitae. Sed id sapien leo. Aliquam posuere ex lacus, ut posuere metus ullamcorper eu. Duis a imperdiet nibh. Donec tincidunt hendrerit nulla, et convallis metus imperdiet nec. Pellentesque massa enim, pharetra in pulvinar a, efficitur nec lorem.
\textbf{The above can be fixed with}
\verb!\parfillskip 0pt plus 0.80\textwidth!
\textbf{but that doesn't help for the case below.}
\textbf{This last line should have been justified (note the small gap at the end):}
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Sed rhoncus lorem eget ultricies bibendum. Duis luctus felis arcu, sit amet dapibus orci imperdiet id. Duis ullamcorper tortor eget leo fringilla, a lacinia nisl pulvinar. Etiam id facilisis augue. Sed convallis tempus ex, sed accumsan justo pulvinar vitae. Sed id sapien leo. Aliquam posuere ex lacus, ut posuere metus ullamcorper eu. Duis a imperdiet nibh. Donec tincidunt hendrerit nulla, et convallis metus imperdiet nec. Pellentesque massa enim, pharetra in pulvinar a, efficitur nec lorem. Cras mattis ex lorem, et euismod ligula rhoncus. Aenean ultricies quis velit non ut faucibus.
\textbf{The above can be fixed with}
\verb!\parfillskip 0pt!
\textbf{but that doesn't help for the case below.}
\end{document}
解決方案應包括僅對序言進行調整。任何段落的開頭或結尾都不應要求特殊命令。我希望,就像在幾個相關案例中一樣,可以透過 中的特殊膠水來解決\parfillskip
,但我不確定這是否可能。
相關問題,我嘗試過其解決方案,但沒有產生預期的輸出:
- 避免最後一行幾乎填滿解決長的最後幾行,但不是短的那些。
- 段落最後一行的最小長度解決短的最後幾行,但不是長的那些。
- 有沒有一個工具可以把段落變成長方形?太強烈地喜歡矩形,即使最後一行只填滿了一半,結果導致字間距過大。
答案1
這種方法是半-自動,因為仍然必須將段落括在\fixit
巨集中。
修訂方法
在這裡,我沒有像下面的原始方法那樣逐字剖析段落,而是測量\hbox
包含段落材料的長度,並根據長度決定是否使用尾隨\hspace{}\mbox
和/或\parfillskip0pt
.
如果需要調整,則該巨集提供一個可選參數。它代表將被壓縮掉的最大分數行溢出,目前設定為.05
(5%)。如果您認為會被壓縮的線擴展為全新的寬間距線,您就會知道它需要調整。將預設值設為.0
可以消除任何問題,但代價是一些本來可以壓縮以消除尾隨寡婦的行被擴展,以便寡婦佔據後續行的 20%。
\documentclass{article}
\usepackage[margin=1.5in,top=0cm,bottom=0cm]{geometry}
\newcommand\fixit[2][.05]{%
\setbox0=\hbox{\hspace{\parindent}#2}\fixithelp{#1}{#2}}
\newcommand\fixithelp[2]{%
\wd0=\dimexpr\wd0-\linewidth\relax%
\ifdim\wd0>0pt\relax%
\fixithelp{#1}{#2}%
\else%
\wd0=\dimexpr\wd0+\linewidth\relax
\ifdim\wd0>.9\linewidth\relax%
{\parfillskip0pt\relax#2\par}%
\else%
\ifdim\wd0>.8\linewidth\relax%
{\parfillskip0pt\relax#2\hspace{.2\linewidth}\par}%
\else%
\ifdim\wd0<#1\linewidth\relax%
{\parfillskip0pt\relax#2\par}%
\else%
\ifdim\wd0<.2\linewidth\relax%
{\parfillskip0pt\relax#2\hspace{.8\linewidth}\mbox{}\par}%
\else%
#2%
\fi
\fi
\fi
\fi
\fi%
}
\sloppy
\parskip1ex
\begin{document}
\noindent\rule{.2\linewidth}{2pt}\hfill\rule{.2\linewidth}{2pt}
\fixit{%
yakity yack, paragraphs, I want to \textit{ensure their last line} is neither
overly short nor overly long. To that end, I'm looking for settings that
produce either:}
\fixit{%
yack, yakity yack, paragraphs, I want to \textit{ensure their last line} is neither
overly short nor overly long. To that end, I'm looking for settings that
produce either:}
\fixit{%
yakity yack, yakity yack, paragraphs, I want to \textit{ensure their last line} is neither
overly short nor overly long. To that end, I'm looking for settings that
produce either:}
\fixit{%
yack, yakity yack, yakity yack, paragraphs, I want to \textit{ensure their last line} is neither
overly short nor overly long. To that end, I'm looking for settings that
produce either:}
\fixit{%
yackity yack, yakity yack, yakity yack, paragraphs, I want to \textit{ensure their last line} is neither
overly short nor overly long. To that end, I'm looking for settings that
produce either:}
\fixit{%
yack, yackity yack, yakity yack, yakity yack, paragraphs, I want to \textit{ensure their last line} is neither
overly short nor overly long. To that end, I'm looking for settings that
produce either:}
\fixit{%
yackity yack, yackity yack, yakity yack, yakity yack, paragraphs, I want to \textit{ensure their last line} is neither
overly short nor overly long. To that end, I'm looking for settings that
produce either:}
\fixit{%
yack, yackity yack, yackity yack, yakity yack, yakity yack, paragraphs, I want to \textit{ensure their last line} is neither
overly short nor overly long. To that end, I'm looking for settings that
produce either:}
\fixit{%
yackity yack, yackity yack, yackity yack, yakity yack, yakity yack, paragraphs, I want to \textit{ensure their last line} is neither
overly short nor overly long. To that end, I'm looking for settings that
produce either:}
\fixit{%
yack, yackity yack, yackity yack, yackity yack, yakity yack, yakity yack, paragraphs, I want to \textit{ensure their last line} is neither
overly short nor overly long. To that end, I'm looking for settings that
produce either:}
\fixit{%
yackity yack, yackity yack, yackity yack, yackity yack, yakity yack, yakity yack, paragraphs, I want to \textit{ensure their last line} is neither
overly short nor overly long. To that end, I'm looking for settings that
produce either:}
\fixit{%
yack, yackity yack, yackity yack, yackity yack, yackity yack, yakity yack, yakity yack, paragraphs, I want to \textit{ensure their last line} is neither
overly short nor overly long. To that end, I'm looking for settings that
produce either:}
\fixit{%
yackity yack, yackity yack, yackity yack, yackity yack, yackity yack, yakity yack, yakity yack, paragraphs, I want to \textit{ensure their last line} is neither
overly short nor overly long. To that end, I'm looking for settings that
produce either:}
\fixit{%
yack, yackity yack, yackity yack, yackity yack, yackity yack, yackity yack, yakity yack, yakity yack, paragraphs, I want to \textit{ensure their last line} is neither
overly short nor overly long. To that end, I'm looking for settings that
produce either:}
\fixit{%
yackity yack, yackity yack, yackity yack, yackity yack, yackity yack, yackity yack, yakity yack, yakity yack, paragraphs, I want to \textit{ensure their last line} is neither
overly short nor overly long. To that end, I'm looking for settings that
produce either:}
\fixit{%
yack, yackity yack, yackity yack, yackity yack, yackity yack, yackity yack, yackity yack, yakity yack, yakity yack, paragraphs, I want to \textit{ensure their last line} is neither
overly short nor overly long. To that end, I'm looking for settings that
produce either:}
\fixit{%
yackity yack, yackity yack, yackity yack, yackity yack, yackity yack, yackity yack, yackity yack, yakity yack, yakity yack, paragraphs, I want to \textit{ensure their last line} is neither
overly short nor overly long. To that end, I'm looking for settings that
produce either:}
\end{document}
邊距=1.5英寸
邊距 = 1.7 英寸
邊距 = 1.9 英寸
原始方法
但宏的作用是逐字反省段落,直到最後 4 個字。然後,它確定需要超過多少個最後的單詞,並將它們與 a 一起.2\linewidth
捆綁在一起。如果最後 3 個單字不超過,則使用 中的全部 4 個單字。\mbox
\hspace{.2\linewidth}
.2\linewidth
\mbox
對於OP的要求,\sloppy
幾乎肯定會被要求,因為我們正在談論一下子改變文字長度.4\linewidth
(這幾乎總是一件不受歡迎的事情)。所以我添加了它。
會破壞該方法的一件事是,如果先前打開的組在段落的最後 4 個單字內結束。例如,當\textit
在段落末尾附近關閉長句時,這將適用。
另一件需要注意的事情是,一個完美的矩形段落將絕不使用這種方法創建,因為\hspace
在段落末尾添加了。
\documentclass{article}
\newcommand\fixit[1]{\fixithelp#1 \cr\relax}
\def\fixithelp#1 #2 #3 #4 #5\relax{\ifx \cr#5\finishup#1 #2 #3 #4\relax%
\else#1 \fixithelp#2 #3 #4 #5\relax\fi}
\def\finishup#1 #2 #3 #4\relax{ %
\setbox0=\hbox{#4}%
\ifdim\wd0>.2\linewidth\relax #1 #2 #3 \mbox{#4\hspace{.2\linewidth}}\else%
\setbox0=\hbox{#3 #4}%
\ifdim\wd0>.2\linewidth\relax #1 #2 \mbox{#3 #4\hspace{.2\linewidth}}\else%
\setbox0=\hbox{#2 #3 #4}%
\ifdim\wd0>.2\linewidth\relax #1 \mbox{#2 #3 #4\hspace{.2\linewidth}}\else%
\mbox{#1 #2 #3 #4\hspace{.2\linewidth}}%
\fi%
\fi%
\fi%
}
\sloppy
\parskip1em
\begin{document}
\fixit{typesetting
paragraphs, I want to \textit{ensure their last line} is neither
overly short nor overly long. To that end, I'm looking for settings that
produce either:}
\fixit{%
paragraphs, I want to \textit{ensure their last line} is neither
overly short nor overly long. To that end, I'm looking for settings that
produce either:}
\fixit{%
paragraphs, I want to \textit{ensure their last line} is neither
overly short nor overly long. To that end, I'm looking for settings that
produce overlylongwords:}
\fixit{%
I want to \textit{ensure their last line} is neither
overly short nor overly long. To that end, I'm looking for settings that
produce overlylongwords:}
\fixit{%
typesetting paragraphs, I want to \textit{ensure their last line} is neither
overly short nor overly long. To that end, I'm looking for settings that
produce I I I I:}
\fixit{%
typesetting I want to \textit{ensure their last line} is neither
overly short nor overly long. To that end, I'm looking for settings that
produce I I I I:}
\end{document}