我的目标:
\begin{equation}[singular=<sing_flag>,plural=<plur_flag>]\label{eq:1}
a < b
\end{equation}
\cref{eq:1}
收益<sing_flag> (1)
率任何输入对于singular
和plural
(我想避免手动\crefname
为每种方程类型指定)。
基本思想:当singular
和/或plural
传递时,创建新的计数器(在等式内)作为cleveref
和传递singular
/plural
到的锚\crefname
。
问题:
- 仅设置
\crefname
不起作用,出于某种原因,我必须设置\crefformat
等,这很麻烦并且不能很好地通过 Babel 实现自动化 - Even
\crefformat
不太管用。它只是使用singular
和的默认设置plural
。
梅威瑟:
\documentclass[]{article}
%% Packages
\usepackage{xkeyval}
\usepackage{xparse}
\usepackage{ifthen}
\usepackage{aliascnt}
\usepackage{cleveref}
\makeatletter
%% New Counter for counting new types of equations
\newcounter{misitex@formulatypes}
%% Set up for options
\define@cmdkey[misitex]{equation}{singular}{}
\define@cmdkey[misitex]{equation}{plural}{}
\setkeys[misitex]{equation}{singular=none,plural=none} % initialize
%% Save old equation env
\let\oldequation\equation
\let\endoldequation\endequation
%% Set Crefformat
\newcommand{\misitex@setcrefformat}[3]{
SetCrefFormat gets: \noexpand{#2} \noexpand{#3}
%% Shouldn't this suffice?
\crefname{#1}{#2}{#3}
\Crefname{#1}{#2}{#3}
%% Why do I need this?
\crefformat{#1}{##2#2~\upshape{(##1)}##3}
\crefrangeformat{#1}{
##3#3~\upshape{(##1)}##4 to~##5\upshape{(##2)}##6
}
\crefmultiformat{#1}{##2#3~\upshape{(##1)}##3}%
{ and~##2\upshape{(##1)}##3}%
{, ##2\upshape{(##1)})}%
{ and~##2\upshape{(##1)}##3}
}
%% Set options only if passed
\NewDocumentCommand{\misitex@equation@parse}{m m}{
\IfValueTF{#1}{\setkeys[misitex]{equation}{#1}}{}
\IfValueTF{#2}{\setkeys[misitex]{equation}{#2}}{}
}
%% Create new type of equation
\newcommand{\misitex@eqaution@setnew}[2]{
% Add new equation counter
\stepcounter{misitex@formulatypes}
\newaliascnt{misitex@formulatype@\themisitex@formulatypes}{equation}
% Set cref format
\misitex@setcrefformat{misitex@formulatype@\themisitex@formulatypes}{#1}{#2}
% Refstep for cref
\refstepcounter{misitex@formulatype@\themisitex@formulatypes}
% Set Equation Numbering
\def\eqNumber{\eqno{\hbox{\upshape{
(\csname themisitex@formulatype@\themisitex@formulatypes \endcsname)
}}}\@ignoretrue}
}
%% Renew Equation env
%% If singular/plural is passed: cerate new counter and apply cref names
%% Else just use old equation env
\RenewDocumentEnvironment{equation}{>{\SplitArgument{1}{,}}o}{
% Parse Arguments
\IfValueT{#1}{\misitex@equation@parse #1}%
\ifthenelse{\equal{\cmdmisitex@equation@singular}{none}}%
{%
\ifthenelse{\equal{\cmdmisitex@equation@plural}{none}}%
{%
\oldequation%
}{%
\misitex@eqaution@setnew%
{\cref@equation@name}{\cmdmisitex@equation@plural}%
$$
}%
}{%
\ifthenelse{\equal{\cmdmisitex@equation@plural}{none}}%
{%
\misitex@eqaution@setnew%
{\cmdmisitex@equation@singular}{\cref@equation@name@plural}%
$$%
}{%
\misitex@eqaution@setnew%
{\cmdmisitex@equation@singular}
{\cmdmisitex@equation@plural}%
$$%
}%
}%
}{
\ifthenelse{\equal{\cmdmisitex@equation@singular}{none}}%
{%
\ifthenelse{\equal{\cmdmisitex@equation@plural}{none}}%
{
\endoldequation
}%
{\eqNumber $$}%
}{
\eqNumber $$
}
}
\makeatother
\begin{document}
\begin{equation}[singular=Ineq.,plural=Ineqs.]\label{test}
a = b
\end{equation}
\cref{test}
\begin{equation}\label{test2}
a = b
\end{equation}
\cref{test,test2}
\end{document}
输出:
因此,虽然看起来singular
和plural
已正确传递\crefformat
,\cref
但使用默认的none
。
虽然我知道这是一个相当具体的问题,但我还是很高兴得到任何建议:)
答案1
问题似乎是,它没有定义全局命令。一种解决方法是在编译之前使用读取文件\crefname
的功能。通过将指令写入该文件,即可实现所需的解决方案。cleveref
cleveref.cfg
\crefname
梅威瑟:
请注意,命令处理已被改变,但这并不是问题的实际重点。
\documentclass{scrartcl}
\usepackage{hyperref}
\usepackage{mathtools}
\usepackage{aliascnt}
\usepackage{cleveref}
\usepackage{xparse}
\makeatletter
\newcounter{misitex@formulatypes}
\let\oldequation\equation
\let\endoldequation\endequation
%% Open file
\newwrite\cleverefcfg
\immediate\openout\cleverefcfg=cleveref.cfg
%% Some shortcuts to write special characters to file
\begingroup\lccode`?=`# \lowercase{\endgroup
\newcommand{\hashsymb}{?}
}
\begingroup\lccode`?=`{ \lowercase{\endgroup
\newcommand{\bracksymbo}{?}
}
\begingroup\lccode`?=`} \lowercase{\endgroup
\newcommand{\bracksymbc}{?}
}
\begingroup\lccode`?=`\% \lowercase{\endgroup
\newcommand{\commentsymb}{?}
}
%% write cleveref directives to file
\newcommand{\creflabelformat@tofile}[1]{
\if@cref@nameinlink
\protected@write\cleverefcfg{}{
\string\creflabelformat{#1}\bracksymbo\hashsymb\commentsymb%
}
\protected@write\cleverefcfg{}{
2\string\textup\bracksymbo(\hashsymb\commentsymb
}
\protected@write\cleverefcfg{}{
1)\bracksymbc\hashsymb\commentsymb
}
\protected@write\cleverefcfg{}{
3\bracksymbc\commentsymb
}
\else
\protected@write\cleverefcfg{}{
\string\creflabelformat{#1}\bracksymbo\string\textup\bracksymbo(\hashsymb\commentsymb%
}
\protected@write\cleverefcfg{}{
2\hashsymb\commentsymb
}
\protected@write\cleverefcfg{}{
1\hashsymb\commentsymb
}
\protected@write\cleverefcfg{}{
3)\bracksymbc\bracksymbc\commentsymb
}
\fi
}
%% Renew equation env
%% Input may be [<cstm number>], [<sing>][<plur>], or [<cstm number>][<sing>][<plur>]
\RenewDocumentEnvironment{equation}{o o o}{
\IfNoValueTF{#3}{
\IfNoValueTF{#2}{
\oldequation
\IfValueT{#1}{\tag{#1}}
}{
\IfValueT{#1}{
\stepcounter{misitex@formulatypes}
\newaliascnt{misitex@formulatype@\themisitex@formulatypes}{equation}
%% Write \crefname instruction to config file
\protected@write\cleverefcfg{}{
\string\crefname{misitex@formulatype@\themisitex@formulatypes}{#1}{#2}
\string\Crefname{misitex@formulatype@\themisitex@formulatypes}{#1}{#2}
}
\creflabelformat@tofile{misitex@formulatype@\themisitex@formulatypes}
}
\oldequation
\IfValueT{#1}{
\addtocounter{equation}{-1}
\refstepcounter{misitex@formulatype@\themisitex@formulatypes}
}
}
}{
\IfValueT{#2}{
\stepcounter{misitex@formulatypes}
\newaliascnt{misitex@formulatype@\themisitex@formulatypes}{equation}
%% Write \crefname instruction to config file
\protected@write\cleverefcfg{}{
\string\crefname{misitex@formulatype@\themisitex@formulatypes}{#2}{#3}
\string\Crefname{misitex@formulatype@\themisitex@formulatypes}{#2}{#3}
}
\creflabelformat@tofile{misitex@formulatype@\themisitex@formulatypes}
}
\oldequation
\IfNoValueTF{#1}{}{
\IfValueT{#2}{
\expandafter\def\csname themisitex@formulatype@\themisitex@formulatypes\endcsname{#1}
\addtocounter{equation}{-1}
}
\renewcommand{\theequation}{#1}
}
\IfValueT{#2}{
\addtocounter{equation}{-1}
\refstepcounter{misitex@formulatype@\themisitex@formulatypes}
}
}
}{
\endoldequation
}
\makeatother
\begin{document}
\begin{equation}[a]\label{test}
a = b
\end{equation}
\begin{equation}[Ineq][Ineqs]\label{test2}
a = b
\end{equation}
\begin{equation}[c]\label{test3}
a = b
\end{equation}
\begin{equation}[Formula][Formulae]\label{test4}
a = b
\end{equation}
\begin{equation}[Formula][Formulae]\label{test45}
a = b
\end{equation}
\begin{equation}\label{test5}
a = b
\end{equation}
\cref{test,test2,test3,test4,test5,test45}
\end{document}
笔记
如图所示,方程(2)
和(3)
没有分组为Formulae (2) and (3)
。然而,这是一个普遍的问题,可以在更简单的设置中重现。一种解决方法是\crefformat
除了明确设置之外,还明确设置\crefname
。