ブック クラスの ToC (章用) でタイトル行のテキストにプレフィックスを付けて折り返すにはどうすればよいでしょうか?

ブック クラスの ToC (章用) でタイトル行のテキストにプレフィックスを付けて折り返すにはどうすればよいでしょうか?

私は、書籍クラスの ToC の章番号のプレフィックスとして「Chapter」というテキストを含め、章のタイトルを ToC リストの左端に折り返す方法を探しています。私はこれを共通リソースに組み込んでいますが、現在は 2 つの部分から構成されています。1 つはパッケージのみを含むクラス ファイル、もう 1 つはプリアンブルに \input されている設定 .tex ファイルです。設定ファイル内で 2 つの異なるアプローチを試しました。以下の最初のアプローチでは、必要なパッチが正しくキャプチャされません。

\documentclass{book}

\usepackage{xpatch}
\usepackage{hyperref}

\makeatletter
\xpatchcmd{\@chapter}
    {\addcontentsline{toc}{chapter}{\numberline {#1}}}
    {\addcontentsline{toc}{chapter}{\numberline {Chapter~\thechapter{}.~#1}}}
    {\typeout{Success}}
    {\typeout{Failed!}}
\makeatother

\begin{document}

\tableofcontents

\chapter{This is First}

Some day this will work.

\chapter{This is Second}

Perhaps soon!

\end{document}

この 2 番目のアプローチでは、章の単語が目次に配置されますが、長い第 2 章のタイトルのテキストは目次行で要求されているように折り返されません。

\documentclass{book}

\usepackage{tocloft}

\begin{document}

\newlength{\tocchapwidth}
\settowidth{\tocchapwidth}{\chaptername\ }
\addtolength{\cftchapnumwidth}{\tocchapwidth}
\renewcommand{\cftchappresnum}{\chaptername\ }
\renewcommand{\cftchapaftersnum}{.}
\renewcommand{\cftchapaftersnumb}{~}
\renewcommand{\cftchapdotsep}{\cftdotsep}

\tableofcontents

\chapter{This is First}

Some day this will work.

\chapter{This is Second, a Rather Long and Windy Road Leading to a Door Going to Nowhere Fast}

Perhaps soon!

\end{document}

これは、論文/学位論文文書の書式設定要件を満たすための試みです。現在、大まかな回避策があります。つまり、\chapter{Chapter 2.~This is the Second ...} のように、プレフィックスを含む章のタイトルを入力します (そして、titlesec パッケージを使用して、ToC の章番号の出力を抑制します)。

また、2 番目の例には含めていませんが、ドキュメントには hyperref パッケージが必要です。別の投稿から、Hy@... 章コマンドにパッチを適用する必要があるかもしれないと推測しましたが、これを実行しようとしても失敗しました。

私は LaTeX3 に十分精通しているわけではありませんが、このような変更を喜んで取り入れます。最後に、提供されるオプションが何であれ、Overleaf で問題なく機能することを期待します。Overleaf では、このパッケージを使用する大勢の人が作業を行う可能性が高いからです。

答え1

最初のアプローチにはいくつか問題があります。

まず、 の元の定義にも次のbook.clsものがありません。

\addcontentsline{toc}{chapter}{\numberline {#1}}

の定義では\@chapter、しかし:

\addcontentsline{toc}{chapter}{\protect\numberline{\thechapter}#1}

したがって、\protectへの正しい引数が欠落しており\numberline、 の最初の引数は\@chapter中括弧なしで使用されています。

hyperref2つ目の問題は、変更の定義をロードした後です\@chapter。そのため、パッチは前に読み込み中hyperref

ところで: 元の定義を確認するには、\show\@chapterbeforeを追加するだけです。これにより、-fileに\xpatchcmdパッチを適用する前の現在の定義が出力されます。\@chapterlog

3 番目の問題は、次の置き換えです。

\addcontentsline{toc}{chapter}{\protect\numberline {Chapter~\thechapter{}.~#1}}

数値引数だけでなくChapter~<number>.タイトルも入力します。したがって、少なくとも次のようになります。

\addcontentsline{toc}{chapter}{\numberline {Chapter~\thechapter{}.}#1}

しかし、この定義では、数値用に予約されるスペースを増やすために の変更も必要になります\l@chapter。代わりに、数値スペースを予約せずに、次のように使用することもできます。

\addcontentsline{toc}{chapter}{Chapter~\thechapter{}.~#1}

したがって、次のようになります。

\documentclass{book}

\usepackage{xpatch}

\makeatletter
\xpatchcmd{\@chapter}
  {\addcontentsline{toc}{chapter}{\protect\numberline{\thechapter}#1}}
  {\addcontentsline{toc}{chapter}{Chapter~\thechapter{}.~#1}}
  {\typeout{Success}}
  {\typeout{Failed!}}
\makeatother

\usepackage{hyperref}

\begin{document}

\tableofcontents

\chapter{This is First}

Some day this will work.

\chapter{This is Second}

Perhaps soon!

\end{document}

得られるもの:

第1章。これは…

Chapter <number>.を引数として使用する別の方法は\numberline、次のようになります。

\documentclass{book}

\usepackage{xpatch}

\makeatletter
\xpatchcmd{\@chapter}
  {\addcontentsline{toc}{chapter}{\protect\numberline{\thechapter}#1}}
  {\addcontentsline{toc}{chapter}{\protect\numberline{Chapter~\thechapter{}.}#1}}
  {\typeout{\string\@chapter\space patch success}}
  {\typeout{\string\@chapter\space patch failed!}}
\xpatchcmd{\l@chapter}
  {\setlength\@tempdima{1.5em}}
  {\setlength\@tempdima{6em}}% increase reserved number width
  {\typeout{\string\l@chapter\space patch success}}
  {\typeout{\string\l@chapter\space patch failed!}}
\makeatother

\usepackage{hyperref}

\begin{document}

\tableofcontents

\chapter{This is First}

Some day this will work.

\chapter{This is Second}

Perhaps soon!

\end{document}

1行のエントリの結果は最初の提案と似ています。違いを確認するには、1行以上のエントリを試してください。例:

\chapter{This is Second Chapter with very long Titel Needing more than one
  Line in the Table of Contents}

したがって、私の意見では、この 2 番目のアプローチが、あなたが望むものであると思います。


2 番目のアプローチの問題点は、 を増やすときに、数字の後のドット.とスペースを考慮していないことです。設定の修正方法の 1 つを以下に示します。~\cftchapnumwidth

\documentclass{book}

\usepackage{tocloft}

\begin{document}

\newlength{\tocchapwidth}
\renewcommand{\cftchappresnum}{\chaptername\ }
\settowidth{\tocchapwidth}{\cftchappresnum}
\renewcommand{\cftchapaftersnum}{.~}
\newlength{\tocchapafternumwidth}
\settowidth{\tocchapafternumwidth}{\cftchapaftersnum}
\addtolength{\cftchapnumwidth}{\tocchapwidth}
\addtolength{\cftchapnumwidth}{\tocchapafternumwidth}
\renewcommand{\cftchapdotsep}{\cftdotsep}

\tableofcontents

\chapter{This is First}

Some day this will work.

\chapter{This is Second, a Rather Long and Windy Road Leading to a Door Going to Nowhere Fast}

Perhaps soon!

\end{document}

トクロフトを使用する

しかし、この提案をよく見ると、まだ正しくありません。なぜなら、章のエントリに使用されているフォントではなく、現在のドキュメント フォントでテキストを測定しているからです。したがって、前のコードは正しいように見えますが、正しくはありません。正しいコードにするには、テキストの幅を測定するときに を考慮する必要があります。(プレフィックスとポストフィックス\cftchapfontのない数値の幅がすでに十分である場合は、スペースによっても幅を増やす必要はありません)。したがって、より良いコードは次のようになります。Chapter.

\documentclass{book}

\usepackage{tocloft}

\newlength{\tocchapwidth}
\newlength{\tocchapafternumwidth}
\renewcommand{\cftchappresnum}{\chaptername\ }
\renewcommand{\cftchapaftersnum}{.}
\renewcommand{\cftchapdotsep}{\cftdotsep}
\AtBeginDocument{% final font setup is done in \begin{document} so we delay all text measuring
  \settowidth{\tocchapwidth}{\cftchapfont\cftchappresnum}%
  \settowidth{\tocchapafternumwidth}{\cftchapfont\cftchapaftersnum}%
  \addtolength{\cftchapnumwidth}{\tocchapwidth}%
  \addtolength{\cftchapnumwidth}{\tocchapafternumwidth}%
}

\begin{document}
\tableofcontents

\chapter{This is First}

Some day this will work.

\chapter{This is Second, a Rather Long and Windy Road Leading to a Door Going to Nowhere Fast}

Perhaps soon!

\end{document}

付録の問題

注: どちらの例も付録のある文書には適していません。この場合、Chapter付録の正しい用語ではないためです。

付録付きの文書に適した推奨提案を作成するのはtocloft簡単です。ハードコードされてChapterいる部分を置き換え\@chapappて幅を広げるだけです。

\documentclass{book}

\usepackage{xpatch}

\makeatletter
\xpatchcmd{\@chapter}
  {\addcontentsline{toc}{chapter}{\protect\numberline{\thechapter}#1}}
  {\addcontentsline{toc}{chapter}{\protect\numberline{\@chapapp~\thechapter{}.}#1}}
  {\typeout{\string\@chapter\space patch success}}
  {\typeout{\string\@chapter\space patch failed!}}
\xpatchcmd{\l@chapter}
  {\setlength\@tempdima{1.5em}}
  {\setlength\@tempdima{7em}}% increase reserved number width
  {\typeout{\string\l@chapter\space patch success}}
  {\typeout{\string\l@chapter\space patch failed!}}
\makeatother

\usepackage{hyperref}

\begin{document}

\tableofcontents

\chapter{This is First}

Some day this will work.

\chapter{This is Second}

Perhaps soon!

\appendix
\chapter{This is a Rather Long and Windy Road Leading to a Door Going
  to Nowhere Fast}

\end{document}

解決策としては、tocloft次のようなものを使用できます。

\documentclass{book}

\usepackage{tocloft}

\newlength{\tocchapwidth}
\newlength{\tocappwidth}
\newlength{\tocchapafternumwidth}
\renewcommand{\cftchappresnum}{\chaptername\ }
\renewcommand{\cftchapaftersnum}{.}
\renewcommand{\cftchapdotsep}{\cftdotsep}
\AtBeginDocument{%
  \settowidth{\tocchapwidth}{\cftchapfont\chaptername}%
  \settowidth{\tocappwidth}{\cftchapfont\appendixname}%
  \ifdim\tocappwidth>\tocchapwidth
    \addtolength{\cftchapnumwidth}{\tocappwidth}%
  \else
    \addtolength{\cftchapnumwidth}{\tocchapwidth}%
  \fi
  \settowidth{\tocchapafternumwidth}{\cftchapfont\cftchapaftersnum}%
  \addtolength{\cftchapnumwidth}{\tocchapafternumwidth}%
}
\AddToHook{cmd/appendix/after}{%
  \addtocontents{toc}{%
    \protect\renewcommand{\protect\cftchappresnum}{\protect\appendixname{} }%
  }%
}
\begin{document}
\tableofcontents

\chapter{This is First}

Some day this will work.

\chapter{This is Second, a Rather Long and Windy Road Leading to a Door Going to Nowhere Fast}

Perhaps soon!

\appendix
\chapter{A Rather Long Appendix Heading and Windy Road Leading to a Door Going to Nowhere Fast}


\end{document}

関連情報