我正在尝试构建一个宏来生成整个变更日志表动态地(专业文档模板 - 原型)。我找到了几个有用的答案来实现它,但我被困在另一个宏重置中。
警告:我已详细说明了一切,以便我所采取的路径清晰明了,而不是发布不起作用的代码并期待答案......
我的目标 :
有一个宏可以在文档中动态构建更改日志表:
在序言中声明版本:
\newrow{A}{H. Potter,R. Weasley}{First release for Snape} \newrow{B}{H. Granger}{Fixed tons of typos}
=> 在单独的表格行上以逗号分隔的作者和/或修改列表。
在核心中构建表(宏
\modifications
是这个问题的重点):\setlength\extrarowheight{4.5pt} \begin{tabularx}{\textwidth}{|c|c|X|} \hline \multicolumn{3}{|c|}{\textbf{LOG OF CHANGES}}\\[2.25pt] \hline Version & \centering{Author} & {Modification} \\[2.25pt] \hline \modifications % <-- TABLE BUILD HERE DEPENDING ON HOW MANY ROWS THEY ARE... \end{tabularx}
目前,此表是使用此代码实现的。除了\specialcell
允许换行之外,没有什么特别的。
% Command to brake line in a cell.
\newcommand{\specialcell}[2][c]{
\begin{tabular}{@{}#1@{}}#2\end{tabular}
}
% Construction of the tabular
\setlength\extrarowheight{4.5pt}
\begin{tabularx}{\textwidth}{|c|c|X|}
\hline
\multicolumn{3}{|c|}{\textbf{LOG OF CHANGES}}\\[2.25pt]
\hline
Version & \centering{Author} & {Modification} \\[2.25pt] \hline
A & \specialcell{H. Potter\\R. Weasley} & \specialcell[l]{First release for Snape\\Additions to Fred's old version} \\ \hline
B & \specialcell{H. Granger} & Fixed tons of typos ! \\ \hline
\end{tabularx}
问题 0:当输入以逗号分隔的作者和/或修改列表时,换行。这个问题已经通过以下方法解决:这个答案。
问题1:我事先不知道他们会创建多少个版本!
我发现这个答案根据\addtotable{}
传递的命令数量“动态”构建一个表。似乎是正确的方法!我尝试将其与我的情况结合起来,并且成功了。
代码如下:
\documentclass{article}
\RequirePackage{tabularx}
\usepackage[top=3cm,bottom=4.5cm,left=2.5cm,right=2.5cm]{geometry}
\makeatletter
% Command to brake line in a cell.
\newcommand{\specialcell}[2][c]{
\begin{tabular}{@{}#1@{}}#2\end{tabular}
}
\newcommand\modifications{} % macro containing whole code to build all the lines of the table
\newcommand\authorsList{} % macro containing the code for the authors list
\newcommand\modifList{} % macro containing the code for the modifications list
\newcommand{\newrow}[3]{
% Version cell of the table
\g@addto@macro\modifications{#1 &}
% build \specialcell{Element1\\Element2} and put it the second cell
\g@addto@macro\authorsList{\@gobble}
\@for\tmp:=#2\do{%
\expandafter\g@addto@macro\expandafter\authorsList
\expandafter{\expandafter\\\tmp}
}%
\g@addto@macro\modifications{\specialcell{\authorsList}&}
% build \specialcell{Element1\\Element2} and put it the third cell
\g@addto@macro\modifList{\@gobble}
\@for\tmp:=#3\do{%
\expandafter\g@addto@macro\expandafter\modifList
\expandafter{\expandafter\\\tmp}
}%
\g@addto@macro\modifications{\specialcell[l]{\modifList}}
% end table
\g@addto@macro\modifications{\\\hline}
}
\makeatother
% Version definitions
\newrow{A}{H. Potter,R. Weasley}{First release for Snape, Additions to Fred's old version}
%\newrow{B}{H. Granger}{Fixed tons of typos}
\begin{document}
\setlength\extrarowheight{4.5pt}
\begin{tabularx}{\textwidth}{|c|c|X|}
\hline
\multicolumn{3}{|c|}{\textbf{LOG OF CHANGES}}\\[2.25pt]
\hline
Version & \centering{Author} & {Modification} \\[2.25pt] \hline
\modifications % <-- build of the table
\end{tabularx}
\end{document}
它在表格中只有 1 行时工作得很好。然后我遇到了另一个问题,当我添加
主要问题
宏modifList
和authorsList
未重置,然后一切都乱了套。我厌倦了在开始时强制它们重置和\let\authorsList\@empty
,\let\modifList\@empty
但它只保留最后一个值。
在某些时候,输入的值\specialcell
不是当前的值,而是从头开始的所有值......
这是当前输出:
和代码:
\documentclass{article}
\usepackage{tabularx}
\usepackage[top=3cm,bottom=4.5cm,left=2.5cm,right=2.5cm]{geometry}
\makeatletter
% Command to brake line in a cell.
\newcommand{\specialcell}[2][c]{
\begin{tabular}{@{}#1@{}}#2\end{tabular}
}
\newcommand\modifications{} % macro containing whole code to build all the lines of the table
\newcommand\authorsList{} % macro containing the code for the authors list
\newcommand\modifList{} % macro containing the code for the modifications list
\newcommand{\newrow}[3]{
% Version cell of the table
\g@addto@macro\modifications{#1 &}
% build \specialcell{Element1\\Element2} and put it the second cell
\g@addto@macro\authorsList{\@gobble}
\@for\tmp:=#2\do{%
\expandafter\g@addto@macro\expandafter\authorsList
\expandafter{\expandafter\\\tmp}
}%
\g@addto@macro\modifications{\specialcell{\authorsList}&}
% build \specialcell{Element1\\Element2} and put it the third cell
\g@addto@macro\modifList{\@gobble}
\@for\tmp:=#3\do{%
\expandafter\g@addto@macro\expandafter\modifList
\expandafter{\expandafter\\\tmp}
}%
\g@addto@macro\modifications{\specialcell[l]{\modifList}}
% end table
\g@addto@macro\modifications{\\\hline}
}
\makeatother
% Version definitions
\newrow{A}{H. Potter,R. Weasley}{First release for Snape, Additions to Fred's old version}
\newrow{B}{H. Granger}{Fixed tons of typos}
\begin{document}
\setlength\extrarowheight{4.5pt}
\begin{tabularx}{\textwidth}{|c|c|X|}
\hline
\multicolumn{3}{|c|}{\textbf{LOG OF CHANGES}}\\[2.25pt]
\hline
Version & \centering{Author} & {Modification} \\[2.25pt] \hline
\modifications % <-- build of the table
\end{tabularx}
\end{document}
关于如何使其适用于多个版本,有什么想法吗?
答案1
问题是,当你将 和 添加到 时,必须将其展开\authorsList
。否则将使用它们的最后含义。添加很多s 就可以达到这个目的:\modifList
\modifications
\expandafter
\documentclass{article}
\usepackage{tabularx}
\usepackage[top=3cm,bottom=4.5cm,left=2.5cm,right=2.5cm]{geometry}
\makeatletter
% Command to brake line in a cell.
\newcommand{\specialcell}[2][c]{
\begin{tabular}{@{}#1@{}}#2\end{tabular}
}
\newcommand\modifications{} % macro containing whole code to build all the lines of the table
\newcommand\authorsList{} % macro containing the code for the authors list
\newcommand\modifList{} % macro containing the code for the modifications list
\newcommand{\newrow}[3]{
% Version cell of the table
\g@addto@macro\modifications{#1 &}
% build \specialcell{Element1\\Element2} and put it the second cell
\gdef\authorsList{\@gobble}
\@for\tmp:=#2\do{%
\expandafter\g@addto@macro\expandafter\authorsList
\expandafter{\expandafter\\\tmp}
}%
% added \expandafter's here
\expandafter\g@addto@macro\expandafter\modifications
\expandafter{\expandafter\specialcell\expandafter{\authorsList}&}
% build \specialcell{Element1\\Element2} and put it the third cell
\gdef\modifList{\@gobble}
\@for\tmp:=#3\do{%
\expandafter\g@addto@macro\expandafter\modifList
\expandafter{\expandafter\\\tmp}
}%
% added \expandafter's here
\expandafter\g@addto@macro\expandafter\modifications
\expandafter{\expandafter\specialcell
\expandafter[\expandafter l\expandafter]\expandafter{\modifList}}
% end table
\g@addto@macro\modifications{\\\hline}
}
\makeatother
% Version definitions
\newrow{A}{H. Potter,R. Weasley}{First release for Snape, Additions to Fred's old version}
\newrow{B}{H. Granger}{Fixed tons of typos}
\begin{document}
\setlength\extrarowheight{4.5pt}
\begin{tabularx}{\textwidth}{|c|c|X|}
\hline
\multicolumn{3}{|c|}{\textbf{LOG OF CHANGES}}\\[2.25pt]
\hline
Version & \centering{Author} & {Modification} \\[2.25pt] \hline
\modifications % <-- build of the table
\end{tabularx}
\end{document}
答案2
这是一个扩展问题:您必须添加\AuthorsList
和的扩展\modifList
。
您还应该注意代码中的空格:定义主体中的新行将计为输出中的空格,除非它被屏蔽%
。
我提出了一种expl3
基于代码的代码,除了可以缓解扩展问题之外,还可以避免担心不受保护的行尾。
\\
您可能会喜欢将逗号分隔列表转换为分隔列表的更简单的代码\specialcell
。
\documentclass{article}
\usepackage{tabularx}
\usepackage[top=3cm,bottom=4.5cm,left=2.5cm,right=2.5cm]{geometry}
\usepackage{xparse}
\ExplSyntaxOn
\NewDocumentCommand{\printchanges}{}
{
\group_begin:
\par\noindent
\setlength{\extrarowheight}{2.5pt}
\begin{tabularx}{\textwidth}{|c|c|X|}
\hline
\multicolumn{3}{|c|}{\textbf{LOG~OF~CHANGES}}\\[2.5pt]
\hline
Version & Author & Modification \\[2.5pt]
\hline
\tl_use:N \g_eisenheim_modifications_tl
\end{tabularx}
\group_end:
}
\NewDocumentCommand{\newrow}{mmm}
{
\eisenheim_newrow:nnn { #1 } { #2 } { #3 }
}
\NewDocumentCommand{\specialcell}{O{c}m}
{
\eisenheim_specialcell:nn { #1 } { #2 }
}
\tl_new:N \g_eisenheim_modifications_tl
\seq_new:N \l__eisenheim_specialcell_seq
\cs_new_protected:Nn \eisenheim_newrow:nnn
{
% add the tag
\tl_put_right:Nn \g_eisenheim_modifications_tl { #1 & }
% add the authors
% first split the text at commas
\seq_set_from_clist:Nn \l__eisenheim_specialcell_seq { #2 }
% then add the items separated by \\
\tl_put_right:Nx \g_eisenheim_modifications_tl
{
\specialcell { \seq_use:Nn \l__eisenheim_specialcell_seq { \\ } } &
}
% add the description
\tl_put_right:Nn \g_eisenheim_modifications_tl { #3 \\[2.5pt] \hline }
}
\cs_new_protected:Nn \eisenheim_specialcell:nn
{
\begin{tabular}{@{}#1@{}}#2\end{tabular}
}
\ExplSyntaxOff
% Version definitions
\newrow{A}{H. Potter,R. Weasley}{First release for Snape, Additions to Fred's old version}
\newrow{B}{H. Granger}{Fixed tons of typos}
\begin{document}
\printchanges
\end{document}