自从修复了由于我的代码错误而导致的原始问题以来,这个问题已经被编辑。
我尝试使用wrapfig
将文本环绕在右边距的框内,但该包的行为不可预测,它与我的文档的交互对我来说毫无意义。(例如,将一些文本封闭在组中会{}
极大地影响最终的布局。)
现在,我正在寻找一个简单且可预测的解决方案,将段落环绕在一个与右边距齐平的框周围,并与段落的开头在顶部对齐。
我创建了一个框,并将其保存为名称\sbox
下的\mybox
。我编写了一些代码,以使用该框的宽度在右边距保留可用空间\parshape
。
我想知道将框插入保留空间(使用\usebox{\mybox}
)的“标准”或最简单的方法是什么,并将其与段落顶部对齐。我认为与段落框顶部对齐或与第一行的基线对齐都可以令人满意。以下是我所做的:
\documentclass{article}
\usepackage{lipsum}
\begin{document}
\newsavebox{\mybox}
\sbox{\mybox}{%
\raisebox{-\height}{\fbox{\parbox{0.5\textwidth}{Floating\\\\\\frame}}}%
}
\newlength{\myboxwidth}
\setlength{\myboxwidth}{\wd\mybox}
\newlength{\parshapelinelen}
\setlength{\parshapelinelen}{\textwidth}
\addtolength{\parshapelinelen}{-\myboxwidth}
\addtolength{\parshapelinelen}{-\columnsep}
\hbox to \hsize{\hfill\smash{\usebox{\mybox}}}
\vspace*{-\baselineskip}
\parshape=5
0pt \parshapelinelen
0pt \parshapelinelen
0pt \parshapelinelen
0pt \parshapelinelen
0pt \textwidth
\lipsum[1]
\end{document}
我的代码怎样才能改进或简化?
事实上,还存在一个问题:我不想使用\vspace*
负参数,因为它会导致前面的材料之后出现错误的间距。
一个更普遍的问题:如果我在段落第 n 行到第 n+k 行的右边距为一个框保留一个空白区域,如何将框放在那里?
答案1
简单的解决方案是将段落环绕在与右(或左)边距齐平的框内,并在顶部与段落开头对齐。无需其他软件包。
\InsertBox
为了自动化该过程,定义了具有 4 个参数的命令。
\InsertBox[<l or r (default} >]{<box content>}{<box width>}{<text to be shaped>}
- (可选)在文本区域中放置框的位置:
r
或l
(r
,right, 是默认值); - 盒子的内容(它不是一个浮点数!)
- 所需的盒子宽度;
- 要成形的段落。
其余一切都由他们决定。
使用宏生成用于格式化形状的行\newparshape
从中获取的宏生成的parshape 的精简版本
更新在 Peter Wilson 发表评论之后。
现在\parindent
可以取任意值,因此段落的开头很清晰。
到目前为止,它在分页符时还不能正常运行。
\documentclass{article}
\usepackage{kantlipsum}% dummy text
\usepackage{graphicx}% insert figures
%***************************************************************************************************
\newlength{\AboveSkipbox}
\setlength{\AboveSkipbox}{0.7\baselineskip} % above space <<<<
\newlength{\Sidesepbox}
\setlength{\Sidesepbox}{1.5em} % side space <<<
\newlength{\BoxHeight}
\newlength{\ParHeight}
\newlength{\FirstIndent}
\newlength{\FigureBoxWidth}
\newlength{\FigIndent}
\newsavebox{\mybox}
\newsavebox{\tmpbox}
%% From https://tex.stackexchange.com/questions/127504/more-condensed-version-of-parshape
\makeatletter
\let\SavedIndent\parindent
\let\@afterindentfalse\@afterindenttrue
\@afterindenttrue
\def\newparshape{\parshape\@npshape0{}}
\def\@npshape#1#2#3{\ifx\\#3\expandafter\@@@npshape\else\expandafter\@@npshape\fi
{#1}{#2}{#3}}
\def\@@npshape#1#2#3#4#5{%
\ifnum#3>\z@\expandafter\@firstoftwo\else\expandafter\@secondoftwo\fi
{\expandafter\@@npshape\expandafter{\the\numexpr#1+1\relax}{#2 #4 #5}{\numexpr#3-1\relax}{#4}{#5}}%
{\@npshape{#1}{#2}}}
\def\@@@npshape#1#2#3{#1 #2}
\def\SetFirstIndent{\if@afterindent\FirstIndent\SavedIndent\else\FirstIndent\z@\fi}
\makeatother
\newcommand{\nlines}[1]{\the\numexpr#1/\baselineskip +1 \relax}
\newcommand{\TypesetBox}[1]{\makebox[\linewidth][#1]{\raisebox{\dimexpr-\ht\mybox-\AboveSkipbox\relax}[0pt][0pt]{\usebox{\mybox}}}}
\newcommand{\TypesetTextShortLong}[1]{%
\hspace*{\parindent}
\ifdim\dimexpr\ht\tmpbox+\dp\tmpbox<\dimexpr\ht\mybox+\dp\mybox+2\baselineskip\relax%short
\hspace{-\parindent}\usebox{\tmpbox}\vspace{\dimexpr\ht\mybox+\dp\mybox+\AboveSkipbox-\ht\tmpbox-\dp\tmpbox\relax}
\else%long
#1\fi
}
\newcommand{\MakeFigureSpace}[1]{%
\ifx#1l% left
\setlength{\FigIndent}{\FigureBoxWidth}
\else% right
\setlength{\FigIndent}{0pt}
\fi
}
\newcommand{\InsertBox}[4][r]{%
\SetFirstIndent%
\setlength{\FigureBoxWidth}{\dimexpr#3+\Sidesepbox\relax}
\sbox{\tmpbox}{\parbox[t]{\dimexpr\linewidth-\FigureBoxWidth\relax}{\hspace{\FirstIndent}#4}}
\sbox{\mybox}{\fbox{\parbox{#3}{#2}}}%
\MakeFigureSpace{#1}% Figure Indent = \parindent or Fig Box width
\vspace{-\baselineskip}
\hspace{\dimexpr-\FigIndent-\parindent\relax}\TypesetBox{#1}
\newparshape% shape paragraph text
{\nlines{\dimexpr\ht\mybox+\dp\mybox+\baselineskip\relax}}{\FigIndent}{\dimexpr\linewidth-\FigureBoxWidth\relax}%
{1}{0pt}{\linewidth}\\
\TypesetTextShortLong{#4}
}
%***************************************************************************************************
\begin{document}
\InsertBox{It is not a floating \\ \\ \\ \\ frame}{0.5\textwidth}{\kant[2]}
\kant[9]
\InsertBox{\bfseries \large As I have shown elsewhere, Aristotle tells
us that the objects in space and time, in the full sense of these
terms, would be falsified.}{0.4\textwidth}{\kant[4]}
\newpage
\section*{Right side}
\noindent \kant[9]
\InsertBox{\centering\includegraphics[scale=0.35]{example-image}}{0.35\textwidth}{\kant[9]}
\section*{Left side}
\InsertBox[l]{\centering\includegraphics[scale=0.4]{example-image}}{0.4\textwidth}{\kant[9]}
\newpage
\section*{Right side, short paragraph}
\noindent \kant[9]
\InsertBox{\centering\includegraphics[scale=0.4]{example-image}}{0.4\textwidth}{As any dedicated reader can clearly see, the Ideal of
practical reason is a representation of, as far as I know, the things
in themselves; as I have shown elsewhere, the phenomena should only be
used as a canon for our understanding. }
\kant[9]
\section*{Left side, short paragraph}
\InsertBox[l]{\centering\includegraphics[scale=0.4]{example-image}}{0.4\textwidth}{As any dedicated reader can clearly see, the Ideal of
practical reason is a representation of, as far as I know, the things
in themselves; as I have shown elsewhere, the phenomena should only be
used as a canon for our understanding.}
\kant[9]
\end{document}