总结:目前剩余的问题在文章底部
考虑以下测试代码:
% ---------------------------------------------------------------------------- %
% Files
\begin{filecontents*}{empty\jobname.cpp}
\end{filecontents*}
\begin{filecontents*}{\jobname.cpp}
0000
0000
\end{filecontents*}
\begin{filecontents*}{multi\jobname.cpp}
0000
0000
0000
0000
\end{filecontents*}
% ---------------------------------------------------------------------------- %
% Preamble
\documentclass[letterpaper, 12pt, onecolumn]{article}
% ---------------------------------------------------------------------------- %
% Packages
\usepackage[paperwidth = 160mm, paperheight = 550mm, margin = 10mm]{geometry}
\usepackage{xcolor}
\usepackage{listings}
\usepackage{multicol}
\usepackage[most]{tcolorbox}
% ---------------------------------------------------------------------------- %
% Listings options
\newtcbinputlisting{\inputcode}[4][\normalsize]{
code = {},
enhanced,
listing only,
top = 0pt,
bottom = 0pt,
left = 0pt,
right = 0pt,
arc = 0pt,
outer arc = 0pt,
boxsep = 0pt,
titlerule = 0pt,
colback = blue,
colframe = black,
boxrule = 2pt,
title = {\centering{\fontfamily{cmtt}\selectfont#2\strut}},
listing options = {
language = C++,
framesep = 0pt,
rulesep = 0pt,
aboveskip = 0pt,
belowskip = 0pt,
backgroundcolor = \color{lightgray},
basicstyle = \fontfamily{cmtt}\selectfont#1,
#3,
},
listing file={#4},
}
% ---------------------------------------------------------------------------- %
% Commands
\newcommand{\makelisting}[2]{%
\inputcode[#1]{#2}{}{\jobname.cpp}%
\inputcode[#1]{#2}{multicols = 2}{multi\jobname.cpp}%
\bigskip\bigskip%
}
% ---------------------------------------------------------------------------- %
% Document
\pagestyle{empty}
\begin{document}
\inputcode[]{empty}{}{empty\jobname.cpp}
\inputcode[]{empty}{multicols = 2}{empty\jobname.cpp}
\bigskip\bigskip
\makelisting{\tiny}{tiny}
\makelisting{\scriptsize}{scriptsize}
\makelisting{\footnotesize}{footnotesize}
\makelisting{\small}{small}
\makelisting{\normalsize}{normalsize}
\makelisting{\large}{large}
\makelisting{\Large}{Large}
\makelisting{\LARGE}{LARGE}
\makelisting{\huge}{huge}
\makelisting{\Huge}{Huge}
\end{document}
% ---------------------------------------------------------------------------- %
它在 tcolorboxes 中生成列表对:一个没有多列,另一个有多列。结果输出:
如这些图片所示,该multicols
选项最终会在列表顶部和底部添加额外的空间(图片上为蓝色)。此间距的确切测量值似乎取决于列表的字体样式(\tiny
、\small
、\large
...)以及文档的字体大小(10pt
、11pt
、 )。使用空列表(文档开头)进行实验还表明,激活12pt
该选项后会剩余蓝色间距。multicols
到目前为止,我还不能理解这个垂直间距来自哪里,以及它的确切值来自哪里。
问题:
- 这个额外的间距来自哪里(在列表的顶部和底部)?
- 它的值(顶部和底部)是如何计算的?
- 如何让这个额外的垂直间距消失?
更新 1:
经过几个小时的研究,这里有一个小发现。如果将顶部参数调整为以下内容:
\newlength{\normalsizestrutheight}
\settoheight{\normalsizestrutheight}{\strut}
\newlength{\fontstrutheight}
\newcommand{\getfontstrutheight}[1]{\settoheight{\fontstrutheight}{#1\strut}}
\newlength{\topshift}
\newcommand{\computetopshift}[1]{%
\getfontstrutheight{#1}%
\setlength{\topshift}{%
\minof{-\normalsizestrutheight + \fontstrutheight}{0pt}%
}%
}
然后对于所有小于 的字体\normalsize
,剩余的顶部空间是恒定的。仍然不是零,但至少是常数。但是,这个常数的值仍然取决于文档的默认字体大小(10pt
、11pt
、12pt
、8pt
(带有extarticle
)、17pt
(带有extarticle
)...),我仍然无法找到公式。
这是我更新的测试文件:
% ---------------------------------------------------------------------------- %
% Files
\begin{filecontents*}{empty\jobname.cpp}
\end{filecontents*}
\begin{filecontents*}{\jobname.cpp}
0000
\end{filecontents*}
\begin{filecontents*}{multi\jobname.cpp}
0000
0000
0000
0000
\end{filecontents*}
% ---------------------------------------------------------------------------- %
% Preamble
\documentclass[letterpaper, 12pt, onecolumn]{article}
% ---------------------------------------------------------------------------- %
% Packages
\usepackage[paperwidth = 160mm, paperheight = 500mm, margin = 10mm]{geometry}
\usepackage{calc}
\usepackage{xcolor}
\usepackage{listings}
\usepackage{multicol}
\usepackage{printlen}
\usepackage[most]{tcolorbox}
% ---------------------------------------------------------------------------- %
% Measurement computation
\newlength{\normalsizestrutheight}
\settoheight{\normalsizestrutheight}{\strut}
\newlength{\fontstrutheight}
\newcommand{\getfontstrutheight}[1]{\settoheight{\fontstrutheight}{#1\strut}}
\newlength{\topshift}
\newcommand{\computetopshift}[1]{%
\getfontstrutheight{#1}%
\setlength{\topshift}{%
\minof{-\normalsizestrutheight + \fontstrutheight}{0pt}%
}%
}
% ---------------------------------------------------------------------------- %
% Listings options
\newtcbinputlisting{\inputcode}[5][\normalsize]{
code = {\computetopshift{\fontfamily{cmtt}\selectfont#1}},
enhanced,
listing only,
top = 0pt,
bottom = 0pt,
left = 0pt,
right = 0pt,
arc = 0pt,
outer arc = 0pt,
boxsep = 0pt,
titlerule = 0pt,
colback = red,
colframe = black,
boxrule = 2pt,
title = {\centering{\fontfamily{cmtt}\selectfont#2\strut}},
listing options = {
language = C++,
framesep = 0pt,
rulesep = 0pt,
aboveskip = 0pt,
belowskip = 0pt,
backgroundcolor = \color{white},
basicstyle = \fontfamily{cmtt}\selectfont#1,
#3,
},
#4,
listing file={#5},
}
% ---------------------------------------------------------------------------- %
% Commands
\newcommand{\makeempty}{%
\inputcode[]{empty}{}{}{empty\jobname.cpp}%
\inputcode[]{empty}{multicols = 2}{}{empty\jobname.cpp}%
\bigskip\bigskip%
}
\newcommand{\makelisting}[3]{%
\inputcode[#1]{#2}{}{}{\jobname.cpp}%
\inputcode[#1]{#2}{multicols = 2}{top = \topshift, #3,}{multi\jobname.cpp}%
\bigskip\bigskip%
}
% ---------------------------------------------------------------------------- %
% Document
\pagestyle{empty}
\begin{document}
\makeempty{}
\makelisting{\tiny}{tiny}{}
\makelisting{\scriptsize}{scriptsize}{}
\makelisting{\footnotesize}{footnotesize}{}
\makelisting{\small}{small}{}
\makelisting{\normalsize}{normalsize}{}
\makelisting{\large}{large}{}
\makelisting{\Large}{Large}{}
\makelisting{\LARGE}{LARGE}{}
\makelisting{\huge}{huge}{}
\makelisting{\Huge}{Huge}{}
\end{document}
% ---------------------------------------------------------------------------- %
输出:
但是,如何以通用的方式让剩余的顶部空间消失,以适用于每个默认文档字体大小,以及底部空间,仍然是个谜。
更新2:
\documentclass[Npt]{extarticle}
我尝试计算刚刚描述的常数的值,即给定文档字体大小时 tcolorbox 和列表顶部之间的剩余空间N=8, 9, 10, 11, 12, 14, 17, 20
。我使用了以下代码:
\newlength{\normalsizestrutheight}
\settoheight{\normalsizestrutheight}{\strut}
\newlength{\fontstrutheight}
\newcommand{\getfontstrutheight}[1]{\settoheight{\fontstrutheight}{#1\strut}}
\newlength{\topconstant}
\setlength{\topconstant}{% something here %}
\newlength{\topshift}
\newcommand{\computetopshift}[1]{%
\getfontstrutheight{#1}%
\setlength{\topshift}{%
\minof{-\normalsizestrutheight + \fontstrutheight - \topconstant}{0pt}%
}%
}
如果您明白的话,我想知道给定N
的 值是多少topconstant
才能使顶部的额外间距消失。以下是我收集的近似值:
value of N -> value of topconstant
8pt -> 2.350pt
9pt -> 1.335pt
10pt -> 1.600pt
11pt -> 1.480pt
12pt -> 1.850pt
14pt -> 2.100pt
17pt -> 1.600pt
20pt -> 2.500pt
如果有人知道这些值从何而来以及如何自动计算它们,那就太好了。剩下的另一个问题是如何处理额外的底部间距。
更新 3:
我觉得我发现了一些东西。使用以下代码:
\newlength{\mainfontsize}
\makeatletter
\setlength{\mainfontsize}{\@ptsize}
\makeatother
\newlength{\normalsizestrutheight}
\settoheight{\normalsizestrutheight}{\strut}
\newlength{\fontstrutheight}
\newcommand{\getfontstrutheight}[1]{\settoheight{\fontstrutheight}{#1\strut}}
\newlength{\topshift}
\newcommand{\computetopshift}[1]{%
\getfontstrutheight{#1}%
\setlength{\topshift}{%
\minof{-\mainfontsize + \fontstrutheight}{0pt}%
}%
}
额外的顶部间距消失... 除了\documentclass[8pt]{extarticle}
。对于该特定情况,\mainfontsize
需要设置为9pt
。更令人惊讶的是,它适用于 ,extarticle
但不适用于article
。
- 知道为什么
8pt
在 的字体大小上有这个细微差别吗extarticle
? - 为什么它对 有效
extarticle
,而对 无效article
? - 但是,如何消除底部间距?
更新 4:剩余问题
后Ulrike Fischer 的回答,底部间距的问题仍然悬而未决。通过测试,我还发现额外的底部间距取决于列表中的行数是偶数还是奇数。
答案1
如果将\topskip
和\mathdepth
本地设置为 0pt 和(例如使用before upper*
),它似乎可以工作,但空的情况除外。
\begin{filecontents*}{empty\jobname.cpp}
\end{filecontents*}
\begin{filecontents*}{\jobname.cpp}
0000
0000
\end{filecontents*}
\begin{filecontents*}{multi\jobname.cpp}
0000
0000
0000
0000
\end{filecontents*}
% ---------------------------------------------------------------------------- %
% Preamble
\documentclass[letterpaper, 12pt, onecolumn]{article}
% ---------------------------------------------------------------------------- %
% Packages
\usepackage[paperwidth = 160mm, paperheight = 550mm, margin = 10mm]{geometry}
\usepackage{xcolor}
\usepackage{listings}
\usepackage{multicol}
\usepackage[most]{tcolorbox}
% ---------------------------------------------------------------------------- %
% Listings options
\newtcbinputlisting{\inputcode}[4][\normalsize]{
code = {},
before upper*={\topskip0pt \maxdepth=0pt}, %<---------------
enhanced,
listing only,
top = 0pt,
bottom = 0pt,
left = 0pt,
right = 0pt,
arc = 0pt,
outer arc = 0pt,
boxsep = 0pt,
titlerule = 0pt,
colback = blue,
colframe = black,
boxrule = 2pt,
title = {\centering{\fontfamily{cmtt}\selectfont#2\strut}},
listing options = {
language = C++,
framesep = 0pt,
rulesep = 0pt,
aboveskip = 0pt,
belowskip = 0pt,
backgroundcolor = \color{lightgray},
basicstyle = \fontfamily{cmtt}\selectfont#1,
#3,
},
listing file={#4},
}
% ---------------------------------------------------------------------------- %
% Commands
\newcommand{\makelisting}[2]{%
\inputcode[#1]{#2}{}{\jobname.cpp}%
\inputcode[#1]{#2}{multicols = 2}{multi\jobname.cpp}%
\bigskip\bigskip%
}
% ---------------------------------------------------------------------------- %
% Document
\pagestyle{empty}
\begin{document}
\inputcode[]{empty}{}{empty\jobname.cpp}
\inputcode[]{empty}{multicols = 2}{empty\jobname.cpp}
\bigskip\bigskip
\makelisting{\tiny}{tiny}
\makelisting{\scriptsize}{scriptsize}
\makelisting{\footnotesize}{footnotesize}
\makelisting{\small}{small}
\makelisting{\normalsize}{normalsize}
\makelisting{\large}{large}
\makelisting{\Large}{Large}
\makelisting{\LARGE}{LARGE}
\makelisting{\huge}{huge}
\makelisting{\Huge}{Huge}
\end{document}
答案2
底部间距问题在此处理回答。底线:\hrule height0pt
使用钩子在每行后添加\lst@AddToHook{EOL}
。这解决了@Ulrike Fischer 的剩余问题回答。
\begin{filecontents*}{empty\jobname.cpp}
\end{filecontents*}
\begin{filecontents*}{normal\jobname.cpp}
0000
0000
\end{filecontents*}
\begin{filecontents*}{multiOne\jobname.cpp}
0000
\end{filecontents*}
\begin{filecontents*}{multiEven\jobname.cpp}
0000
0000
\end{filecontents*}
\begin{filecontents*}{multiOdd\jobname.cpp}
0000
0000
0000
\end{filecontents*}
\documentclass[letterpaper, 12pt, onecolumn]{article}
\usepackage[paperwidth = 160mm, paperheight = 550mm, margin = 10mm]{geometry}
\usepackage{xcolor}
\usepackage{listings}
\usepackage{multicol}
\usepackage[most]{tcolorbox}
\makeatletter
\newtcbinputlisting{\inputcodeTemp}[4][\normalsize]{
before upper* = {\topskip0pt\lst@AddToHook{EOL}{\hrule height0pt}},% set topskip to 0pt and add hrule after each input line
enhanced,
listing only,
top = 0pt,
bottom = 0pt,
left = 0pt,
right = 0pt,
arc = 0pt,
outer arc = 0pt,
boxsep = 0pt,
titlerule = 0pt,
colback = blue,
colframe = black,
boxrule = 2pt,
title = {\centering{\fontfamily{cmtt}\selectfont#2\strut}},
listing options = {
language = C++,
framesep = 0pt,
rulesep = 0pt,
aboveskip = 0pt,
belowskip = 0pt,
backgroundcolor = \color{lightgray},
basicstyle = \fontfamily{cmtt}\selectfont#1,
#3,
},
listing file = {#4},
}
\makeatother
\makeatletter
\newcommand{\inputcode}[4][\normalsize]{%
\inputcodeTemp[#1]{#2}{#3}{#4}
\gdef\lsthk@EOL{}% clear the hook
}
\makeatother
\makeatletter
\newcommand{\makelisting}[2]{%
\inputcode[#1]{#2}{}{normal\jobname.cpp}%
\inputcode[#1]{#2}{multicols = 2}{multiOne\jobname.cpp}%
\inputcode[#1]{#2}{multicols = 2}{multiEven\jobname.cpp}%
\inputcode[#1]{#2}{multicols = 2}{multiOdd\jobname.cpp}%
\vspace{2\baselineskip}
}
\makeatother
\pagestyle{empty}
\begin{document}
\inputcode[]{empty}{}{empty\jobname.cpp}
\inputcode[]{empty}{multicols = 2}{empty\jobname.cpp}
\vspace{2\baselineskip}
\makelisting{\tiny}{tiny}
\makelisting{\scriptsize}{scriptsize}
\makelisting{\footnotesize}{footnotesize}
\makelisting{\small}{small}
\makelisting{\normalsize}{normalsize}
\makelisting{\large}{large}
\makelisting{\Large}{Large}
\makelisting{\LARGE}{LARGE}
\makelisting{\huge}{huge}
\makelisting{\Huge}{Huge}
\end{document}