我的问题
我想创建某种深度定制的内容表(简称 ToC)。我已经有一些做这类事情的经验,但这里所需的复杂程度远远超出了我的能力。
我们的想法是创建如下图所示的内容:
更多细节
本目录将成为我正在编写的课程的一部分(并愿意在完成后立即根据开放许可发布)。这些文档将使用以下方式编译:LuaLaTeX. 我有一些了解蒂克兹和标题目录并想用它们来创造这个设计,但我真的不知道从哪里开始。这背后的想法是真正的随机性(因此,每次编译时目录都会改变!)
需要以下功能:
- 页面左侧应为白色
- 页面的右侧和侧面应为彩色(黑色、深灰色或整个文档使用的主色)(例如,使用 tikz
remember picture
和选项)overlay
- 酒吧应该有随机的长度(使用 lua
math.random
?) - 布局应该适应负值和正值
- 目录应该只显示章节和部分条目(例如
\setcounter{tocdepth}{0}
,我的观点是只需要章节和部分的设计) - 对于每个章节条目,应显示章节编号、章节标题和章节页码
重要的是全局概念。细节不会改变,而且可能会随着时间的推移而改变。例如,我不确定章节号会出现在现在的位置,我仍然需要弄清楚如何显示超出一行可用空间的章节名称,等等。
答案1
使用另一种语言(如 Python 或 Pearl)解析第一次运行 LaTeX 时生成的目录文件。使用该语言添加所需的功能,然后让其调用 LaTeX 生成完整的文档。在您的编辑器中(例如在 Kile 中),设置一个自定义编译脚本,该脚本将首先运行 LaTeX 以生成基本目录数据,然后调用解析语言脚本并生成您喜欢的目录,最后再次使用 LaTeX 进行编译以生成最终的 pdf。根据要求,这是一个“全局想法”答案,而不是针对任何特定类型的喜欢的目录的特定解决方案。
答案2
最后,经过一番研究和努力,我终于编写了一个版本:
\documentclass{report}
\usepackage{tikz}
\RequirePackage{interfaces-base}
\LoadInterface{pgfkeys}
\usetikzlibrary{calc}
\usepackage{xparse}
\usepackage{calc}
\usepackage{ifthen}
\usepackage{titletoc}
\usepackage{ragged2e}
\usepackage{xcolor}
\definecolor{mainColor}{RGB}{211, 47, 47}
\usepackage{geometry}
% Comment this block if you don't have the Fira Sans font installed!
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
\usepackage{fontspec}
\setmainfont{Fira Sans Light}[
BoldFont=Fira Sans Medium,
ItalicFont=Fira Sans Light Italic,
BoldItalicFont=Fira Sans Medium Italic
]
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
\DeclareDocumentCommand{\myTableOfContent}{}{%
\begingroup
% remove hyphenation in titles
\hyphenpenalty10000\exhyphenpenalty10000\righthyphenmin62\lefthyphenmin62
% Allow to draw on the table of content page, other wise blank pages are added between the ToC and the big vertical line
\let\clearpage\relax
% Drawing the big vertical line
\begin{tikzpicture}[remember picture, overlay, inner sep=0mm]
\fill[fill=mainColor] (current page.north) rectangle (current page.south east);
\end{tikzpicture}
% Only show chapter (and part) in the toc
\setcounter{tocdepth}{0}
% Change ToC title
\renewcommand{\contentsname}{Table of Content}
% Print the ToC
\tableofcontents
\endgroup
}
% This length contains temporarily the width of the current chapter's bar
\newlength{\chapterBarTempLength}
% This length stores the height of a chapter entry for proper spacing between them
\newlength{\chapterEntryHeight}
\newsavebox{\chapterEntryBox}
% Configuration Options
\pgfkeys{
/customized toc/space between entries/.store as dimen,
/customized toc/space between entries = 3mm,
}
\pgfkeys{
/customized toc/bar/height/.store as dimen,
/customized toc/bar/height = 1.2\baselineskip,
}
\pgfkeys{
/customized toc/bar/xoffset/.store as dimen,
/customized toc/bar/xoffset = 6mm,
}
\pgfkeys{
/customized toc/bar/style/.style = {rounded corners=1pt,},
}
\pgfkeys{
/customized toc/bar/left style/.style = {},
}
\pgfkeys{
/customized toc/bar/right style/.style = {},
}
\pgfkeys{
/customized toc/text/xoffset/.store as dimen,
/customized toc/text/xoffset = \pgfkeysvalueof{/customized toc/bar/xoffset},
}
\pgfkeys{
/customized toc/text/yoffset/.store as dimen,
/customized toc/text/yoffset=7mm,
}
\pgfkeys{
/customized toc/text/format/.store in=\customizedTocChapterTextFont,
/customized toc/text/format = \fontsize{1.7\baselineskip}{2\baselineskip}\selectfont,
}
\pgfkeys{
/customized toc/text/format/.store in=\customizedTocChapterTextRightFont,
/customized toc/text/format = \color{white},
}
\pgfkeys{
/customized toc/text/format/.store in=\customizedTocChapterTextLeftFont,
/customized toc/text/format = ,
}
\pgfkeys{
/customized toc/text/color/.store as color,
/customized toc/text/color = mainColor,
}
\pgfkeys{
/customized toc/text/height/.store as dimen,
}
\pgfkeys{
/customized toc/page number/width/.store as dimen,
/customized toc/page number/width = 4mm,
}
\pgfkeys{
/customized toc/page number/style/.style = {
font=\bfseries,
},
}
\pgfkeys{
/customized toc/page number/left style/.style={},
}
\pgfkeys{
/customized toc/page number/right style/.style={},
}
\pgfkeys{
/customized toc/chapter number/style/.style={
font=\fontsize{4\baselineskip}{4\baselineskip}\selectfont\itshape\bfseries\color{mainColor}
},
}
% Saveboxes don't take in account the fontsize, to compensate, some more calculations are needed
\newlength{\normalsizeXHeight}\setlength{\normalsizeXHeight}{\heightof{\normalsize x}}
\newlength{\chapterTocEntryXHeight}\setlength{\chapterTocEntryXHeight}{\heightof{\customizedTocChapterTextFont x}}
\newlength{\scaledChapterEntryHeight}
% Arguments: chapter title, coefficient (should be 1 or -1)
\DeclareDocumentCommand{\chapterEntryGraphicalElementPrint}{m m}{%
\ifthenelse{#2>0}{
\DeclareDocumentCommand{\tempChapterEntryAnchor}{}{east}
\DeclareDocumentCommand{\tempChapterEntryTikzAlign}{}{left}
\DeclareDocumentCommand{\tempChapterEntryParboxAlign}{}{\FlushRight}
\DeclareDocumentCommand{\tempChapterEntrySideFont}{}{\customizedTocChapterTextLeftFont}
\pgfkeys{/customized toc/bar/temp style/.style={/customized toc/bar/style, /customized toc/bar/right style}}
\pgfkeys{/customized toc/page number/temp style/.style={/customized toc/page number/style, /customized toc/page number/right style}}
}{
\DeclareDocumentCommand{\tempChapterEntryAnchor}{}{west}
\DeclareDocumentCommand{\tempChapterEntryTikzAlign}{}{right}
\DeclareDocumentCommand{\tempChapterEntryParboxAlign}{}{\FlushLeft}
\DeclareDocumentCommand{\tempChapterEntrySideFont}{}{\customizedTocChapterTextRightFont}
\pgfkeys{/customized toc/bar/temp style/.style={/customized toc/bar/style, /customized toc/bar/left style}}
\pgf
keys{/customized toc/page number/temp style/.style={/customized toc/page number/style, /customized toc/page number/left style}}
}
% Bar
% Coordinates
\coordinate[xshift=#2\pgfkeysvalueof{/customized toc/bar/xoffset}, yshift=.5*\pgfkeysvalueof{/customized toc/bar/height}] (chapterBarBegin) at (currentCenter);
\coordinate[xshift=\chapterBarTempLength, yshift=-\pgfkeysvalueof{/customized toc/bar/height}] (chapterBarEnd) at (chapterBarBegin);
% Drawing the bar
\fill[/customized toc/bar/temp style] (chapterBarBegin) rectangle (chapterBarEnd);
% Page Number
\coordinate[yshift=.5*\pgfkeysvalueof{/customized toc/bar/height}] (pageNumberAnchor) at (chapterBarEnd);
\node [anchor=\tempChapterEntryAnchor, text=white, text width=\pgfkeysvalueof{/customized toc/page number/width}, align=\tempChapterEntryTikzAlign, /customized toc/page number/temp style] at (pageNumberAnchor) {\thecontentspage};
%Text
\coordinate[xshift=#2*-\pgfkeysvalueof{/customized toc/text/xoffset}] (chapterTextAnchor) at (currentCenter);
\node[yshift=\pgfkeysvalueof{/customized toc/text/yoffset}, font=\customizedTocChapterTextFont\tempChapterEntrySideFont, anchor=mid \tempChapterEntryAnchor, text=\pgfkeysvalueof{/customized toc/text/color}] (chapterText) at (chapterTextAnchor) {\mbox{}\parbox[t]{.5\textwidth-\pgfkeysvalueof{/customized toc/text/xoffset}}{\tempChapterEntryParboxAlign#1}};
% Chapter Number
\node[xshift=-1mm, anchor=center, /customized toc/chapter number/style] at (currentCenter) {\thecontentslabel};
}
% Command that format each chapter entry in the ToC
\DeclareDocumentCommand{\formatChapterEntry}{m}{%
% Random bar length (between (-1, 1) )
\setlength{\chapterBarTempLength}{\directlua{tex.print(tostring(math.random()*2-1))}\textwidth/2}
\begin{tikzpicture}[remember picture, overlay, inner sep=0mm]
% Calculate the current entry's center
\path let
\p1 = (current page.center)
in
coordinate (currentCenter) at (\x1, 0);
% Draw the graphical elements
\ifthenelse{\lengthtest{\chapterBarTempLength>0pt}}{%
% Bar has positive value
% Bar must have the minimal size needed to display the page number
\ifthenelse{\lengthtest{\chapterBarTempLength<\pgfkeysvalueof{/customized toc/page number/width}}}{\setlength{\chapterBarTempLength}{\pgfkeysvalueof{/customized toc/page number/width}+2mm}}{}
\chapterEntryGraphicalElementPrint{#1}{1}
}{%
% Bar has negative value
% Bar must have the minimal size needed to display the page number
\ifthenelse{\lengthtest{-1\chapterBarTempLength<\pgfkeysvalueof{/customized toc/page number/width}}}{\setlength{\chapterBarTempLength}{-\pgfkeysvalueof{/customized toc/page number/width}-2mm}}{}
\chapterEntryGraphicalElementPrint{#1}{-1}
}%
\end{tikzpicture}
% Calculating the height of the chapter's entry
\savebox{\chapterEntryBox}{\parbox{.5\textwidth-\pgfkeysvalueof{/customized toc/text/xoffset}}{\customizedTocChapterTextFont#1}}%
\setlength{\chapterEntryHeight}{\ht\chapterEntryBox}%
\setlength{\scaledChapterEntryHeight}{\chapterEntryHeight*\ratio{\chapterTocEntryXHeight}{\normalsizeXHeight}}%
\vspace*{\scaledChapterEntryHeight}%
\vspace*{\pgfkeysvalueof{/customized toc/space between entries}}%
}
% Redefine the styling of the chapter entries in the ToC
\titlecontents{chapter}%
[0pt] % left
{} % Above code
{\formatChapterEntry} % numbered entry format (the last command can take as argument the chapter's text)
{} % number-less entry format
{} % filler code
[] % Below code
\begin{document}
\myTableOfContent
\chapter{This is chapter one}
\section{This is a section}
\section{This is a section}
\chapter{This is chapter two with a very long title}
\section{This is a section}
\section{This is a section}
\chapter{This is chapter three}
\section{This is a section}
\section{This is a section}
\chapter{This is chapter four}
\section{This is a section}
\section{This is a section}
\end{document}
其结果为: