章节:自动从标题派生短标题

章节:自动从标题派生短标题

我有一份文档,其中章节标题很长,跨越多行(可能是考试题目)。我想将它们限制在目录中的一行内。

我刚刚发现,通过提供一个简短的标题,例如,可以很容易地手动实现这\subsection[Short Title]{Title}一点。但是,我想使这一过程自动化。我非常确定,重新定义\subsection等操作很容易,可以自动设置相应的简短标题,只是我自己还不够熟练,无法想出这个办法。

例子:

\documentclass{article}
\begin{document}
\tableofcontents

\section{What I have}

\subsection{This is an insanely long subsection title that is supposed to span multiple lines, which it does because it's insanely long}
\subsubsection{This is a similarly long subsubsection title that should also span more than one line, which it does as it's very long}

\section{What I want}

\subsection[This is an insanely long subsection title that is supposed to span\ldots]{This is an insanely long subsection title that is supposed to span multiple lines, which it does because it's insanely long}
\subsubsection[This is a similarly long subsubsection title that should\ldots]{This is a similarly long subsubsection title that should also span more than one line, which it does as it's very long}

\end{document}

理想情况下,目录中的标题会自动按单词截断,以便它们刚好适合一行,但具有固定宽度甚至固定字符数的解决方案也可以。

奖励要求:我还为标题着色以指示相应部分的状态,也就是说,如果有一个解决方案也能适用于包装的标题\textcolor{...}{...}(或允许通过可选参数等设置颜色),那就太好了。

答案1

此解决方案使用虚拟保护令牌\splithere从其余部分标题中获取 ToC 材料:

\documentclass{article}

\makeatletter
\def\DefSplitSection#1#2{%
  \def#1{\split@startsection#2}%
}
\def\split@startsection#1#2{%
  \split@section@aux#1#2\splithere\@nil
}
\def\split@section@aux#1#2\splithere#3\@nil{%
  \if\relax\detokenize{#3}\relax
    \expandafter\@firstoftwo
  \else
    \expandafter\@secondoftwo
  \fi
    {#1{#2}}%
    {#1[#2]{#2#3}}%
}
\let\splithere\@empty
\makeatother

\DefSplitSection\splitsection\section
\DefSplitSection\splitsubsection\subsection
\DefSplitSection\splitsubsubsection\subsubsection

\begin{document}

\tableofcontents

\section{What I have}

\splitsubsection{This is an insanely long subsection title that is supposed to span \splithere multiple lines, which it does because it's insanely long}
\splitsubsubsection{This is a similarly long subsubsection title that should \splithere also span more than one line, which it does as it's very long}

\section{What I want}

\subsection[This is an insanely long subsection title that is supposed to span\ldots]{This is an insanely long subsection title that is supposed to span multiple lines, which it does because it's insanely long}
\subsubsection[This is a similarly long subsubsection title that should\ldots]{This is a similarly long subsubsection title that should also span more than one line, which it does as it's very long}

\end{document}

如果使用 no,\splithere则行为与标准分段命令相同。请注意,此变体不适用于可选项*(这毫无意义,因为此变体不会写入 ToC),也不适用于可选[...]参数(同样毫无意义,因为它已经在内部定义了可选参数)。


编辑:在可选参数中支持颜色:

\documentclass{article}
\usepackage{xcolor}

\makeatletter
\def\DefSplitSection#1#2{%
  \def#1{\split@startsection#2}%
}
\def\split@startsection#1{%
  \let\split@color@cmd\@empty
  \@ifnextchar[%]
    {\split@color@startsection#1}%
    {\split@actually@startsection#1}%
}
\def\split@color@startsection#1[#2]{%
  \def\split@color@cmd{\color{#2}}%
  \split@actually@startsection#1%
}
\def\split@actually@startsection#1#2{%
  \split@section@aux#1#2\splithere\@nil
}
\def\split@section@aux#1#2\splithere#3\@nil{%
  \if\relax\detokenize{#3}\relax
    \expandafter\@firstoftwo
  \else
    \expandafter\@secondoftwo
  \fi
    {#1{\split@color@cmd#2}}%
    {#1[\split@color@cmd#2]{\split@color@cmd#2#3}}%
}
\let\splithere\@empty
\makeatother

\DefSplitSection\splitsection\section
\DefSplitSection\splitsubsection\subsection
\DefSplitSection\splitsubsubsection\subsubsection

\begin{document}

\tableofcontents

\section{What I have}

\splitsubsection[blue]{This is an insanely long subsection title that is supposed to span \splithere multiple lines, which it does because it's insanely long}
\splitsubsubsection{This is a similarly long subsubsection title that should \splithere also span more than one line, which it does as it's very long}

\section{What I want}

\subsection[This is an insanely long subsection title that is supposed to span\ldots]{This is an insanely long subsection title that is supposed to span multiple lines, which it does because it's insanely long}
\subsubsection[This is a similarly long subsubsection title that should\ldots]{This is a similarly long subsubsection title that should also span more than one line, which it does as it's very long}

\end{document}

相关内容