使用 FPeval 嵌套宏

使用 FPeval 嵌套宏

我正在尝试创建一个易于使用的模板,其中的一部分如下所示:

在此处输入图片描述

我用来执行此操作的原始代码如下:

\begin{tabularx}{\linewidth}{|X|X|X|X|X|}
\hline
\rowcolor{tableGray}
Phase & Intitulé & Prix unitaire (€ HT) & Nombre de Jours-Etude Homme & Prix (€ HT) \\
\hline
1 & Nom de la phase 1 & 380.00 & 3 & 1140.00 \\
\hline
2 & Nom de la phase 2 & 380.00 & 1 & 380.00 \\
\hline
3 & Nom de la phase 3 & 380.00 & 4 & 1520.00 \\
\hline
TOTAL des prestations (€ HT) &  & 380.00 & 8 & 3040.00 \\
\hline
\end{tabularx}

\bigskip

我正在尝试定义自定义命令,以便自动计算并使其超级易于使用。第一列将使用自动递增的计数器,最后一列将是第三列和第四列的乘积。

例如,我希望将此模板提供给的人能够这样做:

\tableauBudgetA{380}{
\ligneBudgetA{Nom de la phase 1}{3}
\ligneBudgetA{Nom de la phase 2}{1}
\ligneBudgetA{Nom de la phase 3}{4}
}

以下是我目前所做的工作:

\usepackage{fp}

[...]

\newcommand{\tableauBudgetA}[2]{
\FPeval{prixUnitaireJEH}{round(#1,2)}
\FPeval{totalJEH}{0}
\FPeval{cntPhase}{0}
\FPeval{totalJEHprix}{round(0,2)}
\begin{tabularx}{\linewidth}{|X|X|X|X|X|}
\hline
\rowcolor{tableGray}
Phase & Intitulé & Prix unitaire (€ HT) & Nombre de Jours-Etude Homme & Prix (€ HT) \\
\hline
#2
TOTAL des prestations (€ HT) &  & \prixUnitaireJEH & \totalJEH & \totalJEHprix \\
\hline
\end{tabularx}
\bigskip
}

\newcommand{\ligneBudgetA}[2]{
\FPeval{cntPhase}{clip(cntPhase+1)}
\FPeval{totalJEH}{clip(totalJEH+#2)}
\FPeval{prixPhase}{round(#2 * prixUnitaireJEH,2)}
\FPeval{totalJEHprix}{round(totalJEHprix+prixPhase,2)}
\cntPhase & #1 & \prixUnitaireJEH & #2 & \prixPhase \\\hline
}

然而,这并不按预期运行:

在此处输入图片描述

我已经搜索了几个小时,我怀疑这与变量范围有关,但我无法弄清楚。

有什么想法吗?谢谢。

附言:这是我第一次使用这个论坛,所以如果我忘记了有用的信息,请告诉我。

编辑:正如 Rmano 所建议的,这是我的代码的可编译版本。

\documentclass[paper=a4, fontsize=11pt]{scrartcl}
\usepackage[T1]{fontenc}
\usepackage[dvipsnames,table]{xcolor}
\usepackage[french]{babel}
\usepackage{tabularx}
\usepackage{fourier}
\usepackage{fp}

\definecolor{tableGray}{RGB}{220, 180, 180}

\newcommand{\tableauBudgetA}[2]{
\FPeval{prixUnitaireJEH}{round(#1,2)}
\FPeval{totalJEH}{0}
\FPeval{cntPhase}{0}
\FPeval{totalJEHprix}{round(0,2)}
\begin{tabularx}{\linewidth}{|X|X|X|X|X|}
\hline
\rowcolor{tableGray}
Phase & Intitulé & Prix unitaire (€ HT) & Nombre de Jours-Etude Homme & Prix (€ HT) \\
\hline
#2
TOTAL des prestations (€ HT) &  & \prixUnitaireJEH & \totalJEH & \totalJEHprix \\
\hline
\end{tabularx}
\bigskip
}

\newcommand{\ligneBudgetA}[2]{ %Nom de la phase ; Nombre de JEH
\FPeval{cntPhase}{clip(cntPhase+1)}
\FPeval{totalJEH}{clip(totalJEH+#2)}
\FPeval{prixPhase}{round(#2 * prixUnitaireJEH,2)}
\FPeval{totalJEHprix}{round(totalJEHprix+prixPhase,2)}

\cntPhase & #1 & \prixUnitaireJEH & #2 & \prixPhase \\\hline
}

\begin{document}

\tableauBudgetA{380}{
\ligneBudgetA{Nom de la phase 1}{3}
\ligneBudgetA{Nom de la phase 2}{1}
\ligneBudgetA{Nom de la phase 3}{4}
}

\end{document}

答案1

您的尝试存在一些问题。

第一个问题:您在表格单元格中进行计算,因此单元格结束后结果会被遗忘。可以通过“全局化”包含总计的变量来解决此问题。

第二个问题:您需要在将行传递给表扫描器之前扩展变量。

第三个问题:tabularx处理材料三次。因此,您得到的总数是预期值的三倍。

一个解决方案是避免tabularx手动计算宽度。使用最近的 TeX 发行版,\expanded可以避免全局化所有变量。

\documentclass[paper=a4, fontsize=11pt]{scrartcl}
\usepackage[T1]{fontenc}
\usepackage[dvipsnames,table]{xcolor}
\usepackage[french]{babel}
\usepackage{fourier}
\usepackage[nomessages]{fp}

\definecolor{tableGray}{RGB}{220, 180, 180}

\newcolumntype{L}{%
  >{\raggedright\arraybackslash}p{\dimexpr(\textwidth-10\tabcolsep-6\arrayrulewidth)/5\relax}}

\newcommand{\tableauBudgetA}[2]{%
  \FPeval{prixUnitaireJEH}{round(#1,2)}%
  \FPeval{totalJEH}{0}%
  \FPeval{cntPhase}{0}%
  \FPeval{totalJEHprix}{round(0,2)}%
  \par\noindent\begin{tabular}{|L|L|L|L|L|}
  \hline
  \rowcolor{tableGray}
  Phase & Intitulé & Prix unitaire (€~HT) & Nombre de Jours-Etude Homme & Prix (€~HT) \\
  \hline
  #2
  TOTAL des prestations (€~HT) &  & \prixUnitaireJEH & \totalJEH & \totalJEHprix \\
  \hline
  \end{tabular}%
  \bigskip
}
\newcommand{\ligneBudgetA}[2]{% Nom de la phase ; Nombre de JEH
  \FPeval{cntPhase}{clip(cntPhase+1)}%
  \FPeval{totalJEH}{clip(totalJEH+#2)}%
  \global\let\totalJEH\totalJEH
  \FPeval{prixPhase}{round(#2 * prixUnitaireJEH,2)}%
  \FPeval{totalJEHprix}{round(totalJEHprix+prixPhase,2)}%
  \global\let\totalJEHprix\totalJEHprix
  \expanded{\cntPhase & #1 & \prixUnitaireJEH & #2 & \prixPhase} \\\hline
}

\begin{document}

\tableauBudgetA{380}{%
\ligneBudgetA{Nom de la phase 1}{3}%
\ligneBudgetA{Nom de la phase 2}{1}%
\ligneBudgetA{Nom de la phase 3}{4}%
}

\end{document}

在此处输入图片描述

另一种方法是建立表,将各个部分存储在令牌寄存器中,然后立即传送。

\documentclass[paper=a4, fontsize=11pt]{scrartcl}
\usepackage[T1]{fontenc}
\usepackage[dvipsnames,table]{xcolor}
\usepackage[french]{babel}
\usepackage{tabularx}
\usepackage{fourier}
\usepackage[nomessages]{fp}

\definecolor{tableGray}{RGB}{220, 180, 180}

\newcolumntype{L}{>{\raggedright\arraybackslash}X}
\newtoks\tabletoks

\newcommand{\tableauBudgetA}[2]{%
  \FPeval{prixUnitaireJEH}{round(#1,2)}%
  \FPeval{totalJEH}{0}%
  \FPeval{cntPhase}{0}%
  \FPeval{totalJEHprix}{round(0,2)}%
  % start the table
  \tabletoks={%
    \par\noindent\begin{tabularx}{\textwidth}{|L|L|L|L|L|}
    \hline
    \rowcolor{tableGray}
    Phase & Intitulé & Prix unitaire (€~HT) & Nombre de Jours-Etude Homme & Prix (€~HT) \\
    \hline
  }%
  % process the rows
  #2%
  % deliver the contents and end the table
  \the\tabletoks
  TOTAL des prestations (€~HT) &  & \prixUnitaireJEH & \totalJEH & \totalJEHprix \\
  \hline
  \end{tabularx}%
  \bigskip
}
\newcommand{\ligneBudgetA}[2]{% Nom de la phase ; Nombre de JEH
  \FPeval{cntPhase}{clip(cntPhase+1)}%
  \FPeval{totalJEH}{clip(totalJEH+#2)}%
  \FPeval{prixPhase}{round(#2 * prixUnitaireJEH,2)}%
  \FPeval{totalJEHprix}{round(totalJEHprix+prixPhase,2)}%
  \tabletoks=\expandafter{%
    \the\expandafter\tabletoks\expanded{%
      \cntPhase & \unexpanded{#1} & \prixUnitaireJEH & #2 & \prixPhase
    } \\\hline
  }%
}

\begin{document}

\tableauBudgetA{380}{%
\ligneBudgetA{Nom de la phase 1}{3}%
\ligneBudgetA{Nom de la phase 2}{1}%
\ligneBudgetA{Nom de la phase 3}{4}%
}

\end{document}

相关内容