summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--Master/texmf-dist/doc/latex/chinesechess/chinesechess.pdfbin4072654 -> 4096186 bytes
-rw-r--r--Master/texmf-dist/doc/latex/chinesechess/chinesechess.tex137
-rw-r--r--Master/texmf-dist/tex/latex/chinesechess/chinesechess.sty539
3 files changed, 445 insertions, 231 deletions
diff --git a/Master/texmf-dist/doc/latex/chinesechess/chinesechess.pdf b/Master/texmf-dist/doc/latex/chinesechess/chinesechess.pdf
index 22951bd3dbd..a965c4fe305 100644
--- a/Master/texmf-dist/doc/latex/chinesechess/chinesechess.pdf
+++ b/Master/texmf-dist/doc/latex/chinesechess/chinesechess.pdf
Binary files differ
diff --git a/Master/texmf-dist/doc/latex/chinesechess/chinesechess.tex b/Master/texmf-dist/doc/latex/chinesechess/chinesechess.tex
index 9220174cc84..60404db6235 100644
--- a/Master/texmf-dist/doc/latex/chinesechess/chinesechess.tex
+++ b/Master/texmf-dist/doc/latex/chinesechess/chinesechess.tex
@@ -123,7 +123,7 @@
{ \__codedoc_cmd:no {#1} { #2 } }
\ExplSyntaxOff
-\def\vers{\texttt{v1.0.0} }
+\def\vers{\texttt{v1.1.0} }
\begin{document}
\title{
@@ -150,15 +150,14 @@
\section{引言}
-\pkg{chinesechess}是一个基于\pkg{l3draw}用\pkg{Expl3}开发的
-中国象棋排版宏包。它提供了\tn{cchessboard} 全棋盘、
-\tn{cchessbord*}空白棋盘和\tn{cchessman}棋谱排版命令。同时,
+\pkg{chinesechess}是一个基于\pkg{l3draw}绘图宏包,用\pkg{Expl3}%
+开发的中国象棋排版宏包。它提供了\tn{cchessboard}(全棋盘)、%
+\tn{cchessbord*}(空棋盘)和\tn{cchessman}(棋谱)排版命令。同时,
该宏包还提供了用于打谱的排版环境\env{setcchessman},在该环境
-中,可以通过环境专用命令\tn{init}初始化棋谱状态,\tn{set}在
-指定位置布置棋子,\tn{del}删除指定位置的棋子,\tn{mov}实现
-棋子的移动,从而实现打谱操作,并在环境结束后以最终状态排版棋谱。
-另外,也可以通过星号环境\env{setcchessman*}实现棋谱的文本描述
-输出。
+中,可以通过环境专用命令\tn{init}(初始化棋谱状态),\tn{set}(在
+指定位置布置棋子),\tn{del}(删除指定位置的棋子),\tn{mov}(实现
+棋子的移动),从而实现打谱操作,并在环境结束后以最终状态排版棋谱。
+另外,也可以通过星号环境\env{setcchessman*}实现棋谱文本输出。
棋子、棋盘、背景等外观可以通过命令、环境选项或\tn{cchessset}%
命令进行设置。
@@ -226,8 +225,8 @@
编码 & 红棋 & 编码 & 黑棋\\\hline
K & 帥 & k & 將 \\
A & 仕 & a & 士 \\
- E & 相 & e & 象 \\
- H & 马 & h & 馬 \\
+ B(E) & 相 & b(e) & 象 \\
+ N(H) & 马 & n(h) & 馬 \\
R & 车 & r & 車 \\
C & 炮 & c & 炮 \\
P & 兵 & p & 卒 \\\hline
@@ -274,7 +273,9 @@
指定位置的棋子,\tn{mov}实现棋子的移动,从而实现打谱操作。
在环境结束后以最终打谱状态排版棋谱。
- 星号环境\env{setcchessman*}会同时排版棋谱的文本描述(如:车一进二等)。
+ 星号环境\env{setcchessman*}用于记录排版棋谱的文本描述(如:车一进二等)。
+ 可在在\env{setcchessman*}环境中用label选项进行标记,然后用\tn{printman}%
+ 输出该棋谱。
在\oarg{外观选项}中可以通过key-value的方式设置棋子、棋盘的颜色、
字体、字号、线宽等外观。
@@ -302,27 +303,6 @@
\end{setcchessman}
\end{SideBySideExample}
-\begin{SideBySideExample}[frame=single,numbers=left,
- xrightmargin=.45\linewidth,gobble=2]
- \centering
- % 为便排版,进行缩放
- \cchessset{resize=real,
- width=.30\linewidth}
- \begin{setcchessman*}
- % 残局初始化
- \init{ {{4,0}{K}}, {{2,2}{p}},
- {{1,7}{C}}, {{4,9}{k}} }
- % 添加棋子
- \set{e,d}{P} \set{8,g}{h}
- % 删除棋子
- \del{4,3}
- % 移动棋子
- \mov{C}{b,h}{b,b} \mov{p}{2,2}{3,2}
- \mov{K}{4,0}{4,1} \mov{h}{8,6}{6,7}
- \mov{K}{4,1}{3,1} \mov{h}{6,7}{5,5}
- \end{setcchessman*}
-\end{SideBySideExample}
-
\subsection{打谱专用命令}
\subsubsection{\tn{init}棋谱初始化命令}
@@ -386,6 +366,52 @@
\textbf{\textsf{注意: }}该命令只能用于\env{setcchessman}环境中。
+\subsection{\tn{printman}输出打谱结果命令}
+
+\begin{function}{\printman}
+ \begin{syntax}
+ \cs{printman} \marg{\env{setcchessman*}环境的label标签}
+ \end{syntax}
+\end{function}
+
+ 输出由label标签指定的\env{setcchessman*}打谱环境生成的棋谱。
+
+\subsection{\tn{getpiece}输出棋子命令}
+
+\begin{function}{\getpiece}
+ \begin{syntax}
+ \cs{getpiece} \oarg{棋子字号} \marg{棋子编码}
+ \end{syntax}
+\end{function}
+
+ 按\oarg{棋子字号}指定的字号将用\marg{棋子编码}指定的棋子在当前位置输出。
+
+ \marg{棋子编码}中的编码详见表表\ref{tab-piececode}。
+
+\begin{SideBySideExample}[frame=single,numbers=left,
+ xrightmargin=.28\linewidth,gobble=2]
+ \centering
+ \getpiece{K}\getpiece{A}\getpiece{B}\getpiece{R}%
+ \getpiece{N}\getpiece{C}\getpiece{P}
+
+ \getpiece{k}\getpiece{a}\getpiece{b}\getpiece{r}%
+ \getpiece{n}\getpiece{c}\getpiece{p}
+\end{SideBySideExample}
+
+\subsection{\tn{piecechar}棋子字符设置命令}
+
+\begin{function}{\piecechar}
+ \begin{syntax}
+ \cs{piecechar} \marg{棋子编码} \marg{棋子字符}
+ \end{syntax}
+\end{function}
+
+ 用于将\marg{棋子编码}指定的棋子字符设置为指定的\marg{棋子字符}。
+
+ \marg{棋子编码}中的编码详见表表\ref{tab-piececode}。
+
+ \textbf{\textsf{说明: }}该功能也可以通过|piecechar|外观选项实现。
+
\subsection{\tn{resetpiece}棋子字符复位命令}
\begin{function}{\resetpiece}
@@ -624,14 +650,14 @@
piecechar={E}{\faChessBishop},
piecechar={H}{\faChessKnight},
piecechar={R}{\faChessRook},
- piecechar={C}{\faBomb},
+ piecechar={C}{\faMeteor},
piecechar={P}{\faChessPawn},
piecechar={k}{\faChessQueen},
piecechar={a}{\faShield*},
piecechar={e}{\faChessBishop},
piecechar={h}{\faChessKnight},
piecechar={r}{\faChessRook},
- piecechar={c}{\faBomb},
+ piecechar={c}{\faMeteor},
piecechar={p}{\faChessPawn},
boardlinecolor=red]
\end{SideBySideExample}
@@ -862,6 +888,47 @@
redupper=red,blkupper=black]
\end{SideBySideExample}
+\bigskip
+
+\subsection{打谱}
+
+\subsubsection{label标签}
+
+\begin{option}{ opt = label, desc = {= \meta{棋谱标签}}, init=init-none }
+ 设置\env{setcchessman*}打谱环境交叉引用标签。
+\end{option}
+
+\subsubsection{每行棋谱步数}
+
+\begin{option}{ opt = mansperline, desc = {= \meta{每行棋谱步数}}, init=2 }
+ 设置\tn{printman}输出棋谱时,每行输出棋谱的步数。
+\end{option}
+
+\begin{SideBySideExample}[frame=single,numbers=left,
+ xrightmargin=.45\linewidth,gobble=2]
+ \centering
+ \printman{test}
+
+ \bigskip
+
+ % 为便排版,进行缩放
+ \cchessset{resize=real,
+ width=0.90\linewidth}
+ \begin{setcchessman*}[label=test]
+ % 残局初始化
+ \init{ {{4,0}{K}}, {{2,2}{p}},
+ {{1,7}{C}}, {{4,9}{k}} }
+ % 添加棋子
+ \set{e,d}{P} \set{8,g}{h}
+ % 删除棋子
+ \del{4,3}
+ % 移动棋子
+ \mov{C}{b,h}{b,b} \mov{p}{2,2}{3,2}
+ \mov{K}{4,0}{4,1} \mov{h}{8,6}{6,7}
+ \mov{K}{4,1}{3,1} \mov{h}{6,7}{5,5}
+ \end{setcchessman*}
+\end{SideBySideExample}
+
% \bigskip
% \title{
diff --git a/Master/texmf-dist/tex/latex/chinesechess/chinesechess.sty b/Master/texmf-dist/tex/latex/chinesechess/chinesechess.sty
index 6ddb58b8368..2a2db971ede 100644
--- a/Master/texmf-dist/tex/latex/chinesechess/chinesechess.sty
+++ b/Master/texmf-dist/tex/latex/chinesechess/chinesechess.sty
@@ -19,21 +19,18 @@
%%
\NeedsTeXFormat{LaTeX2e}[2020/10/01]
\RequirePackage{expl3}
-\ProvidesExplPackage{chinesechess}{2022-04-29}{v1.0.0}
+\ProvidesExplPackage{chinesechess}{2022-05-06}{v1.1.0}
{Typeset Chinese chess with l3draw}
\RequirePackage { l3keys2e, l3draw, xparse }
-% 保证TeXLive的向下兼容
+% 测量盒子总高度(保证TeXLive的向下兼容)
\cs_if_free:NT \box_ht_plus_dp:N
{
\cs_new_protected:Npn \box_ht_plus_dp:N #1
{ \tex_dimexpr:D \box_ht:N #1 + \box_dp:N #1 \scan_stop: }
}
-% 可以使用>{\SplitArgument{1}{~}}分割参数,如:
-% \NewDocumentCommand{\cchessboard}{ s >{\SplitArgument{1}{,}}O{10mm,10mm} }
-%
% 棋盘排版命令用户接口
% #1 星号命令,是否输出棋子
% #2 棋盘类型、棋子类型等外观选项
@@ -56,10 +53,10 @@
% 棋谱排版命令用户接口
% #1 棋盘类型、棋子类型等外观选项
% #2 棋子位置列表
-% 棋子字母汉字对照表(取xq.sty中的定义)
-% K=帅,A=仕,E=相,R=车,C=砲,H=马,P=兵, k=将,a=士,e=象,r=車,c=炮,h=馬,p=卒
-% 水平定位: a(0),b(1),c(2),d(3),e(4),f(5),g(6),h(7),i(8)
-% 垂直定位: a(0),b(1),c(2),d(3),e(4),f(5),g(6),h(7),i(8),j(9)
+% 红棋:K=帅,A=仕,E/B=相,R=车,C=砲,N/H=马,P=兵,
+% 黑棋:k=将,a=士,e/b=象,r=車,c=炮,n/h=馬,p=卒
+% 横向定位: a(0),b(1),c(2),d(3),e(4),f(5),g(6),h(7),i(8)
+% 纵向定位: a(0),b(1),c(2),d(3),e(4),f(5),g(6),h(7),i(8),j(9)
\NewDocumentCommand{\cchessman}{ O{} m }
{
\group_begin:
@@ -75,29 +72,43 @@
% 定义棋子字符常量
\clist_map_inline:nn
{
- { K } {\__cchess_symbol:n {"5E25} }, % 帥
- { A } {\__cchess_symbol:n {"4ED5} }, % 仕
- { E } {\__cchess_symbol:n {"76F8} }, % 相
- { H } {\__cchess_symbol:n {"9A6C} }, % 马
- { R } {\__cchess_symbol:n {"8F66} }, % 车
- { C } {\__cchess_symbol:n {"7832} }, % 砲
- { P } {\__cchess_symbol:n {"5175} }, % 兵
- { k } {\__cchess_symbol:n {"5C07} }, % 將
- { a } {\__cchess_symbol:n {"58EB} }, % 士
- { e } {\__cchess_symbol:n {"8C61} }, % 象
- { h } {\__cchess_symbol:n {"99AC} }, % 馬
- { r } {\__cchess_symbol:n {"8ECA} }, % 車
- { c } {\__cchess_symbol:n {"70AE} }, % 炮
- { p } {\__cchess_symbol:n {"5352} }, % 卒
+ { K } { 帥 }, % 帥\__cchess_symbol:n {"5E25}
+ { A } { 仕 }, % 仕\__cchess_symbol:n {"4ED5}
+ { E } { 相 }, % 相\__cchess_symbol:n {"76F8}
+ { B } { 相 }, % 相\__cchess_symbol:n {"76F8}
+ { H } { 马 }, % 马\__cchess_symbol:n {"9A6C}
+ { N } { 马 }, % 马\__cchess_symbol:n {"9A6C}
+ { R } { 车 }, % 车\__cchess_symbol:n {"8F66}
+ { C } { 砲 }, % 砲\__cchess_symbol:n {"7832}
+ { P } { 兵 }, % 兵\__cchess_symbol:n {"5175}
+ { k } { 將 }, % 將\__cchess_symbol:n {"5C07}
+ { a } { 士 }, % 士\__cchess_symbol:n {"58EB}
+ { e } { 象 }, % 象\__cchess_symbol:n {"8C61}
+ { b } { 象 }, % 象\__cchess_symbol:n {"8C61}
+ { h } { 馬 }, % 馬\__cchess_symbol:n {"99AC}
+ { n } { 馬 }, % 馬\__cchess_symbol:n {"99AC}
+ { r } { 車 }, % 車\__cchess_symbol:n {"8ECA}
+ { c } { 炮 }, % 炮\__cchess_symbol:n {"70AE}
+ { p } { 卒 }, % 卒\__cchess_symbol:n {"5352}
}
{ \__cchess_piece_char_setup:nn ##1 }
}
+
+% 棋子字符设置命令
+% #1 棋子编号及字符
+% K=帅,A=仕,B/E=相,R=车,C=砲,N/H=马,P=兵
+% k=将,a=士,b/e=象,r=車,c=炮,n/h=馬,p=卒
+\NewDocumentCommand{\piecechar}{ m m }
+ {
+ \__cchess_piece_char_setup:nn { #1 } { #2 }
+ }
+
% 打谱环境初始化(仅用于setcchessman环境中)
% #1 棋子位置列表
-% 棋子字母汉字对照表(取xq.sty中的定义)
-% K=帅,A=仕,E=相,R=车,C=砲,H=马,P=兵, k=将,a=士,e=象,r=車,c=炮,h=馬,p=卒
-% 水平定位: a(0),b(1),c(2),d(3),e(4),f(5),g(6),h(7),i(8)
-% 垂直定位: a(0),b(1),c(2),d(3),e(4),f(5),g(6),h(7),i(8),j(9)
+% 红棋:K=帅,A=仕,E/B=相,R=车,C=砲,N/H=马,P=兵,
+% 黑棋:k=将,a=士,e/b=象,r=車,c=炮,n/h=馬,p=卒
+% 横向定位: a(0),b(1),c(2),d(3),e(4),f(5),g(6),h(7),i(8)
+% 纵向定位: a(0),b(1),c(2),d(3),e(4),f(5),g(6),h(7),i(8),j(9)
\NewDocumentCommand{\init}{ m }
{
% 临时clist
@@ -110,20 +121,20 @@
% 打谱环境中的棋子布置命令(仅用于setcchessman环境中)
% #1 棋子位置
-% #2 棋子名称(单个英文字母)
-% 棋子字母汉字对照表(取xq.sty中的定义)
-% K=帅,A=仕,E=相,R=车,C=砲,H=马,P=兵, k=将,a=士,e=象,r=車,c=炮,h=馬,p=卒
-% 水平定位: a(0),b(1),c(2),d(3),e(4),f(5),g(6),h(7),i(8)
-% 垂直定位: a(0),b(1),c(2),d(3),e(4),f(5),g(6),h(7),i(8),j(9)
+% #2 棋子位置列表
+% 红棋:K=帅,A=仕,E/B=相,R=车,C=砲,N/H=马,P=兵,
+% 黑棋:k=将,a=士,e/b=象,r=車,c=炮,n/h=馬,p=卒
+% 横向定位: a(0),b(1),c(2),d(3),e(4),f(5),g(6),h(7),i(8)
+% 纵向定位: a(0),b(1),c(2),d(3),e(4),f(5),g(6),h(7),i(8),j(9)
\NewDocumentCommand{\set}{ m m }
{
\__cchess_piece_replace_handle:nn { #1 } { #2 }
}
% 删除打谱环境中的棋子(仅用于setcchessman环境中)
-% #1 棋子位置
-% 水平定位: a(0),b(1),c(2),d(3),e(4),f(5),g(6),h(7),i(8)
-% 垂直定位: a(0),b(1),c(2),d(3),e(4),f(5),g(6),h(7),i(8),j(9)
+% #1 棋子位置列表
+% 横向定位: a(0),b(1),c(2),d(3),e(4),f(5),g(6),h(7),i(8)
+% 纵向定位: a(0),b(1),c(2),d(3),e(4),f(5),g(6),h(7),i(8),j(9)
\NewDocumentCommand{\del}{ m }
{
\__cchess_piece_remove_handle:n { #1 }
@@ -133,9 +144,10 @@
% #1 棋子名称(单个英文字母)
% #2 棋子当前位置
% #3 棋子目的位置
-% K=帅,A=仕,E=相,R=车,C=砲,H=马,P=兵, k=将,a=士,e=象,r=車,c=炮,h=馬,p=卒
-% 水平定位: a(0),b(1),c(2),d(3),e(4),f(5),g(6),h(7),i(8)
-% 垂直定位: a(0),b(1),c(2),d(3),e(4),f(5),g(6),h(7),i(8),j(9)
+% 红棋:K=帅,A=仕,E/B=相,R=车,C=砲,N/H=马,P=兵,
+% 黑棋:k=将,a=士,e/b=象,r=車,c=炮,n/h=馬,p=卒
+% 横向定位: a(0),b(1),c(2),d(3),e(4),f(5),g(6),h(7),i(8)
+% 纵向定位: a(0),b(1),c(2),d(3),e(4),f(5),g(6),h(7),i(8),j(9)
\NewDocumentCommand{\mov}{ m m m }
{
\__cchess_piece_move_handle:nnn { #1 } { #2 } { #3 }
@@ -167,13 +179,37 @@
\group_end:
}
+% 打谱棋谱输出用户接口
+% #1 每行输出步数
+% #2 棋谱交叉引用label
+% 参考雾月的回复:https://ask.latexstudio.net/ask/question/7430.html
+\NewDocumentCommand{\printman}{ O{} >{\TrimSpaces} m } % 去掉两侧空格
+ {
+ \group_begin:
+ \keys_set:nn { cchess } { #1 }
+ \__cchess_setman_print:n { #2 }
+ \group_end:
+ }
+
+% 棋子输出用户接口
+% #1 棋子字体字号
+% #2 棋子编码
+% 红棋:K=帅,A=仕,E/B=相,R=车,C=砲,N/H=马,P=兵,
+% 黑棋:k=将,a=士,e/b=象,r=車,c=炮,n/h=馬,p=卒
+\NewDocumentCommand{\getpiece}{ O{\normalsize} m }
+ {
+ \group_begin:
+ \__cchess_getpiece_handle:nn {#1} { #2 }
+ \group_end:
+ }
-% ==========棋子字符定义=====================
+% ==========棋子字符常量定义=====================
% 读取符号
\cs_new:Npn \__cchess_symbol:n #1
{
- \tex_char:D #1
- \scan_stop:
+ #1
+ % \tex_char:D #1
+ % \scan_stop:
}
% 棋子符号定义
@@ -233,30 +269,39 @@
% 出于对国际象棋棋手意识习惯的兼容性设计
% 相 B ,也可兼容使用 E,
% 马N, 也可兼容使用 H 代替
+% 在此,为兼容性考虑使用B/E同时表示相,使用H/N同时表示马
+% 在使用时,可以任意选择习惯的名称
+
% 判断红黑棋子英文单字母名称的正则表达式
\regex_new:N \l__capital_regex
-\regex_set:Nn \l__capital_regex { [KAERCHP] }
-% 判断棋子英文单字母名称的正则表达式
-\clist_const:Nn \c__cchess_pieces_name_clist { K,A,E,R,C,H,P,k,a,e,r,c,h,p }
+\regex_set:Nn \l__capital_regex { [KAEBRCHNP] }
+
+% 棋子英文单字母名称列表
+\clist_const:Nn \c__cchess_pieces_name_clist { K,A,E,B,R,C,H,N,P,k,a,e,b,r,c,h,n,p }
\msg_new:nnn { cchess } { piecename-exists } { The~ piece~ name~ `#1~ not~ exists. }
% 定义棋子字符常量
+% 注意相和马分别用两个符号以适配不同习惯
\clist_map_inline:nn
{
- { K } { "5E25 }, % 帥
- { A } { "4ED5 }, % 仕
- { E } { "76F8 }, % 相
- { H } { "9A6C }, % 马
- { R } { "8F66 }, % 车
- { C } { "7832 }, % 砲
- { P } { "5175 }, % 兵
- { k } { "5C07 }, % 將
- { a } { "58EB }, % 士
- { e } { "8C61 }, % 象
- { h } { "99AC }, % 馬
- { r } { "8ECA }, % 車
- { c } { "70AE }, % 炮
- { p } { "5352 }, % 卒
+ { K } { 帥 }, % 帥"5E25
+ { A } { 仕 }, % 仕"4ED5
+ { E } { 相 }, % 相"76F8
+ { B } { 相 }, % 相"76F8
+ { H } { 马 }, % 马"9A6C
+ { N } { 马 }, % 马"9A6C
+ { R } { 车 }, % 车"8F66
+ { C } { 砲 }, % 砲"7832
+ { P } { 兵 }, % 兵"5175
+ { k } { 將 }, % 將"5C07
+ { a } { 士 }, % 士"58EB
+ { e } { 象 }, % 象"8C61
+ { b } { 象 }, % 象"8C61
+ { h } { 馬 }, % 馬"99AC
+ { n } { 馬 }, % 馬"99AC
+ { r } { 車 }, % 車"8ECA
+ { c } { 炮 }, % 炮"70AE
+ { p } { 卒 }, % 卒"5352
}
{ \__cchess_piece_define:nn #1 }
@@ -268,8 +313,8 @@
{ #1 } { \use:c { c__cchess_ #1 _tl } }
}
-% 在棋子编码列表中添加n表示空(null)棋子
-\clist_push:Nn \c__cchess_pieces_name_clist { n }
+% 在棋子编码列表中添加z表示空棋子
+\clist_push:Nn \c__cchess_pieces_name_clist { z }
% 定义棋子盒子容器
\clist_map_inline:Nn \c__cchess_pieces_name_clist
@@ -277,7 +322,7 @@
\coffin_new:c { l__cchess_piece_ #1 _coffin }
}
% 将空棋子盒子容器置空
-\hcoffin_gset:Nn \l__cchess_piece_n_coffin { \phantom{空} }
+\hcoffin_gset:Nn \l__cchess_piece_z_coffin { \phantom{a} }
% 棋盘盒子容器
\coffin_new:N \l__cchess_board_coffin
@@ -311,11 +356,11 @@
5 = f, 6 = g, 7 = h, 8 = i, 9 = j
}
-% 判断是水平方向位置合法性的正则表达式
+% 判断是横向位置合法性的列表
\clist_const:Nn \c__cchess_pos_x_index_clist
{ a,b,c,d,e,f,g,h,i,0,1,2,3,4,5,6,7,8 }
\msg_new:nnn { cchess } { posx-exists } { The~ x~ index~ `#1~ not~ exists. }
-% 判断是垂直方向位置合法性的正则表达式
+% 判断是纵向位置合法性的列表
\clist_const:Nn \c__cchess_pos_y_index_clist
{ a,b,c,d,e,f,g,h,i,j,0,1,2,3,4,5,6,7,8,9 }
\msg_new:nnn { cchess } { posy-exists } { The~ y~ index~ `#1~ not~ exists. }
@@ -331,20 +376,20 @@
{
\coffin_new:c { l__cchess_board_piece_ #1 _ ##1 _coffin }
\hcoffin_gset:cn { l__cchess_board_piece_ #1 _ ##1 _coffin }
- { \phantom{空} }
+ { \phantom{a} }
}
}
-\coffin_new:N \l__cchess_board_piece_n_coffin
-\hcoffin_gset:Nn \l__cchess_board_piece_n_coffin { \phantom{空} }
+\coffin_new:N \l__cchess_board_piece_z_coffin
+\hcoffin_gset:Nn \l__cchess_board_piece_z_coffin { \phantom{a} }
-% 红方棋盘坐标字母与竖线标位对应关系
+% 红方棋盘坐标字母与红棋竖线标位对应关系
\prop_const_from_keyval:Nn \c__cchess_board_red_x_idx_prop
{
a = 九, b = 八, c = 七 , d = 六, e = 五,
f = 四, g = 三, h = 二, i = 一
}
-% 黑方棋盘坐标字母与竖线标位对应关系
+% 黑方棋盘坐标字母与黑棋竖线标位对应关系
\prop_const_from_keyval:Nn \c__cchess_board_black_x_idx_prop
{
a = 1, b = 2, c = 3 , d = 4, e = 5,
@@ -358,7 +403,7 @@
5 = 五, 6 = 六, 7 = 七, 8 = 八, 9 = 九
}
-% 棋谱文字说明列表(如车一进二等)
+% 棋谱记录列表(如车一进二等)
\clist_new:N \l__cchess_manual_clist
% 棋子外框盒子容器
@@ -393,16 +438,21 @@
% 棋子缩放比例
\tl_new:N \l__cchess_piece_scale_tl
% 待处理棋子字符
-\tl_new:N \l__cchess_pieces_tl
+\tl_new:N \l__cchess_pieces_tl
% 棋子字符格式
-\tl_new:N \l__cchess_piece_char_format_tl
+\tl_new:N \l__cchess_piece_char_format_tl
% 棋盘背景图片名称
-\tl_new:N \l__cchess_board_background_tl
+\tl_new:N \l__cchess_board_background_tl
% 棋子字符字形类型(实线、虚线等)
-\int_new:N \l__cchess_charstroke_type_int
+\int_new:N \l__cchess_charstroke_type_int
+
+% 打谱环境棋谱标签
+\tl_new:N \l__cchess_setman_label_tl
+% 打谱结果每行棋谱步数
+\int_new:N \l__cchess_mans_per_line_int
% 打谱环境用计数器
-% \int_new:N \c@cchessman
+\newcounter{setman}
% 增加两个临时int变量
\int_new:N \l_tmpc_int
@@ -415,7 +465,8 @@
% 棋子盒子由l3draw实现,
-% 棋子外围盒子及缩放设计思路来自zitie宏包(\url{https://www.ctan.org/pkg/zitie})。
+% 棋子外围盒子及缩放设计思路来自zitie宏包
+% (\url{https://www.ctan.org/pkg/zitie})。
% =============颜色处理函数=============
% 填充色辅助函数
@@ -448,11 +499,11 @@
\coffin_ht:N #1 + \coffin_dp:N #1
}
-% 计算基字符外框大小(外接正方形边长和外接圆半径)
+% 计算外框大小(外接正方形边长和外接圆半径)
\cs_new:Npn \__cchess_calc_piece_box_size:
{
- % 设置基字符格式的基字符盒子
- \hbox_set:Nn \l_tmpa_box { 将 }
+ % 设置计算基础盒子
+ \hbox_set:Nn \l_tmpa_box { xx }
% 盒子宽度
\dim_set:Nn \l_tmpa_dim
@@ -491,31 +542,16 @@
% =============构造棋子函数=============
% 字符盒子构造类型函数名称生成函数
-% 名称中6个参数分别表示:
-% #1 左下角x坐标
-% #2 左下角y坐标
-% #3 右上角x坐标
-% #4 右上角y坐标
-% #5 x方向缩放比例(扩展保留参数)
-% #6 y方向缩放比例(扩展保留参数)
+% #1 缩放比例
\cs_new_nopar:Npn \__cchess_piece_box_type:n #1
{
__cchess_piece_box_construct_type_ #1 :n
}
% 字符盒子构造类型函数名称命令生成函数
-% 名称命令中6个参数分别表示:
-% #1 左下角x坐标
-% #2 左下角y坐标
-% #3 右上角x坐标
-% #4 右上角y坐标
-% #5 x方向缩放比例(扩展保留参数)
-% #6 y方向缩放比例(扩展保留参数)
+% #1 缩放比例
\cs_new_nopar:Npn \__cchess_piece_box_type_c:n #1
{
- \use:c
- {
- __cchess_piece_box_construct_type_ #1 :n
- }
+ \use:c { __cchess_piece_box_construct_type_ #1 :n }
}
% 字符盒子构造类型函数内部生成器函数
@@ -647,25 +683,21 @@
% =============构造棋盘函数=============
% 棋盘部件构造函数函数名称生成函数
% 名称中2个参数分别表示:
-% #1 x方向缩放比例(暂未使用保留参数)
-% #2 y方向缩放比例(暂未使用保留参数)
+% #1 x方向缩放比例(暂未使用, 保留参数)
+% #2 y方向缩放比例(暂未使用, 保留参数)
\cs_new_nopar:Npn \__cchess_board_type:n #1
{
__cchess_board_construct_type_ #1 :nn
}
-% 字符盒子构造类型函数名称命令生成函数
% 名称命令中2个参数分别表示:
-% #1 x方向缩放比例(暂未使用保留参数)
-% #2 y方向缩放比例(暂未使用保留参数)
+% #1 x方向缩放比例(暂未使用, 保留参数)
+% #2 y方向缩放比例(暂未使用, 保留参数)
\cs_new_nopar:Npn \__cchess_board_type_c:n #1
{
- \use:c
- {
- __cchess_board_construct_type_ #1 :nn
- }
+ \use:c { __cchess_board_construct_type_ #1 :nn }
}
-% 字符盒子构造类型函数生成器内部函数
+% 棋盘类型函数生成器内部函数
% #1 类型名称
\cs_new:Npn \__cchess_new_board_private_construct:nn #1
{
@@ -675,7 +707,7 @@
\cs_generate_variant:Nn \__cchess_new_board_private_construct:nn { V }
\cs_generate_variant:Nn \__cchess_new_board_private_construct:nn { x }
-% 字符盒子构造类型函数生成器函数
+% 棋盘类型函数生成器函数
% #1 类型名称
\cs_new:Npn \__cchess_new_board_construct:nn #1
{
@@ -687,10 +719,10 @@
\cs_generate_variant:Nn \__cchess_new_board_construct:nn { V }
\cs_generate_variant:Nn \__cchess_new_board_construct:nn { x }
-% 无棋盘
+% 空棋盘
\__cchess_new_board_construct:nn { none } { }
-% 半部棋盘
+% 仅格子线半部棋盘
\__cchess_new_board_private_construct:nn { __semiboard }
{
\draw_scope_begin:
@@ -787,7 +819,7 @@
\draw_scope_end:
}
-% 兵、炮标志
+% 兵、炮标志(半棋盘)
\__cchess_new_board_private_construct:nn { __semipos }
{
\hcoffin_set:Nn \l_tmpa_coffin
@@ -867,7 +899,7 @@
\draw_scope_end:
}
-% 象位线
+% 象位虚线
\__cchess_new_board_private_construct:nn { __elephantcross }
{
\draw_scope_begin:
@@ -910,8 +942,8 @@
\color_select:n { cchessboardlinecolor }
- \hcoffin_set:Nn \l_char_tmpa_coffin { 河 }
- \hcoffin_set:Nn \l_char_tmpb_coffin { 楚 }
+ \hcoffin_set:Nn \l_char_tmpa_coffin { 楚 }
+ \hcoffin_set:Nn \l_char_tmpb_coffin { 河 }
\hcoffin_set:Nn \l_char_tmpc_coffin { 漢 }
\hcoffin_set:Nn \l_char_tmpd_coffin { 界 }
@@ -924,7 +956,7 @@
\coffin_rotate:cn { l_char_tmp ##1 _coffin } { 90 }
}
- % 测量盒子容器总高度(用内切圆则不需要)
+ % 测量盒子容器总高度
\dim_set:Nn \l_tmpa_dim
{ \__cchess_coffin_ht_plus_dp:N \l_char_tmpa_coffin }
@@ -933,7 +965,8 @@
\fp_to_dim:n { \fp_eval:n { \gridsize * 0.45 } }
}
- \clist_map_inline:Nn \l_tmpa_clist
+ % 缩放盒子容器
+ \clist_map_inline:nn { a, b, c, d }
{
\coffin_scale:cnn { l_char_tmp ##1 _coffin }
{
@@ -945,17 +978,26 @@
% 排版文字
\draw_scope_begin:
- \int_set:Nn \l_tmpa_int { 1 }
- \clist_map_inline:Nn \l_tmpa_clist
- {
- \draw_path_scope_begin:
- \draw_transform_shift:n
- { \gridsize * \l_tmpa_int, \gridsize * 4.5 }
- \draw_coffin_use:cnn { l_char_tmp ##1 _coffin } { hc } { vc }
- \draw_path_scope_end:
- \int_incr:N \l_tmpa_int
- \int_incr:N \l_tmpa_int
- }
+ \draw_path_scope_begin:
+ \draw_transform_shift:n { \gridsize * 2, \gridsize * 4.5 }
+ \draw_transform_shift:n { -\gridsize / 2, 0pt }
+ \draw_coffin_use:cnn { l_char_tmpb_coffin } { hc } { vc }
+ \draw_path_scope_end:
+ \draw_path_scope_begin:
+ \draw_transform_shift:n { \gridsize * 2, \gridsize * 4.5 }
+ \draw_transform_shift:n { \gridsize / 2, 0pt }
+ \draw_coffin_use:cnn { l_char_tmpa_coffin } { hc } { vc }
+ \draw_path_scope_end:
+ \draw_path_scope_begin:
+ \draw_transform_shift:n { \gridsize * 6, \gridsize * 4.5 }
+ \draw_transform_shift:n { -\gridsize / 2, 0pt }
+ \draw_coffin_use:cnn { l_char_tmpc_coffin } { hc } { vc }
+ \draw_path_scope_end:
+ \draw_path_scope_begin:
+ \draw_transform_shift:n { \gridsize * 6, \gridsize * 4.5 }
+ \draw_transform_shift:n { \gridsize / 2, 0pt }
+ \draw_coffin_use:cnn { l_char_tmpd_coffin } { hc } { vc }
+ \draw_path_scope_end:
\draw_scope_end:
}
@@ -1255,13 +1297,18 @@
% =============棋子文字设置函数=============
% 设置棋子的文字
% 红棋编码用大写字母,默认:
-% K=帅,A=仕,E=相,R=车,C=砲,H=马,P=兵
+% K=帅,A=仕,E/B=相,R=车,C=砲,H/N=马,P=兵
% 黑棋编码用小字字母,默认:
-% k=将,a=士,e=象,r=車,c=炮,h=馬,p=卒
+% k=将,a=士,e/b=象,r=車,c=炮,h/n=馬,p=卒
% #1 棋子编码
% #2 棋子字符
\cs_new_nopar:Npn \__cchess_piece_char_setup:nn #1#2
{
+ \clist_if_in:NnF \c__cchess_pieces_name_clist { #1 }
+ {
+ \msg_error:nnx { cchess } { piecename-exists } { #1 }
+ }
+
\prop_gput:Nnn \c__cchess_board_pieces_alph_name_prop
{ #1 } { #2 }
}
@@ -1310,21 +1357,10 @@
boardlinecolor .initial:n = black ,
boardlinecolor* .code:n = { \__cchess_color_select:nnn { cchessboardlinecolor } #1 } ,
- % 设置棋子字符
- piecechar .code:n = { \__cchess_piece_char_setup:nn #1 },
- piecechar .initial:n = {K}{\c__cchess_K_tl} ,
-
- % 字符格式
- piecefont .code:n = { \tl_set:Nn \l__cchess_piece_char_format_tl {#1}
- \__cchess_calc_piece_box_size:
- },
+ % 棋盘背景图片
+ boardbg .tl_set:N = \l__cchess_board_background_tl ,
+ boardbg .initial:n = {} ,
- % 边框类型
- piecetype .code:n = { \exp_args:NNx \clist_if_in:NnTF
- \g__cchess_piece_box_list_clist {#1}
- { \tl_set:Nx \l__cchess_piece_box_type_tl {#1} }
- { \msg_error:nnx { cchess } { box-exists } {#1} }
- },
% 缩放方式
resize .code:n = { \exp_args:NNx \clist_if_in:NnTF
\g__cchess_resize_method_clist {#1}
@@ -1340,6 +1376,22 @@
width .dim_set:N = \l__cchess_manual_width_dim ,
height .dim_set:N = \l__cchess_manual_height_dim ,
+ % 设置棋子字符
+ piecechar .code:n = { \__cchess_piece_char_setup:nn #1 },
+ piecechar .initial:n = {K}{\c__cchess_K_tl} ,
+
+ % 字符格式
+ piecefont .code:n = { \tl_set:Nn \l__cchess_piece_char_format_tl {#1}
+ \__cchess_calc_piece_box_size:
+ },
+
+ % 边框类型
+ piecetype .code:n = { \exp_args:NNx \clist_if_in:NnTF
+ \g__cchess_piece_box_list_clist {#1}
+ { \tl_set:Nx \l__cchess_piece_box_type_tl {#1} }
+ { \msg_error:nnx { cchess } { box-exists } {#1} }
+ },
+
% 字符边框线宽
boxlinewd .dim_set:N = \l__cchess_box_linewidth_dim ,
boxlinewd .initial:n = 0.4pt ,
@@ -1434,9 +1486,13 @@
{ \int_set_eq:NN \l__cchess_charstroke_type_int \l_keys_choice_int },
charstroke .initial:n = bold,
- % 棋盘背景图片
- boardbg .tl_set:N = \l__cchess_board_background_tl ,
- boardbg .initial:n = {} ,
+ % 打谱环境交叉引用标签
+ label .tl_gset:N = \l__cchess_setman_label_tl ,
+ label .initial:n = {} ,
+
+ % 每行棋谱步数
+ mansperline .tl_gset:N = \l__cchess_mans_per_line_int ,
+ mansperline .initial:n = 2 ,
unknown .code:n = { \msg_error:nn { cchess } { unknown-option } }
}
@@ -1448,7 +1504,7 @@
piecefont = \kaishu,
piecetype = ooo,
boardtype = x+tn,
- resize = none,
+ resize = none,
}
% 选项设置用户接口
@@ -1491,7 +1547,7 @@
% 缩放棋子盒子容器
\coffin_resize:Nnn \l__cchess_piece_coffin { \piecesize }{ \piecesize }
- % 复制结果以备后续使用
+ % 保存结果
\coffin_gset_eq:cN
{ l__cchess_piece_ ##1 _coffin } \l__cchess_piece_coffin
}
@@ -1531,17 +1587,17 @@
}
% =============创建棋子占位coffins=============
- % 缩放空白棋子(n---null)
-\cs_new:Nn \__cchess_board_piece_n_resize:
+ % 缩放空白棋子
+\cs_new:Nn \__cchess_board_piece_z_resize:
{
- \coffin_resize:Nnn \l__cchess_piece_n_coffin { \piecesize } { \piecesize }
+ \coffin_resize:Nnn \l__cchess_piece_z_coffin { \piecesize } { \piecesize }
}
-% 执行缩放
-\__cchess_board_piece_n_resize:
+% 缩放空白棋子
+\__cchess_board_piece_z_resize:
% 将棋子盒子容器布置到棋盘指定位置(用于棋谱和棋盘排版)
% #1 棋子参数
-% 棋子参数的形式为{0,0}{k},{0,1}{K},注意需要包含大括号,
+% 棋子参数的形式为{{0,0}{k},{0,1}{K}},注意需要包含大括号,
% 不同棋子之间用英文逗号分隔
\cs_new:Npn \__cchess_board_piece_pos_construct:n #1
{
@@ -1550,7 +1606,7 @@
\draw_begin:
% 在四个角布置空白棋子实现占位(用于撑满棋子画布)
\clist_set:Nn \l_tmpa_clist
- { {0, 0}{n}, {8, 0}{n}, {0, 9}{n}, {8, 9}{n}}
+ { {0, 0}{z}, {8, 0}{z}, {0, 9}{z}, {8, 9}{z}}
\clist_map_inline:Nn \l_tmpa_clist
{
\__cchess_piece_set_handle:nn ##1
@@ -1575,7 +1631,7 @@
% 如果文件名不为空则载入图片,否则创建一个空盒子容器
\tl_if_empty:NTF \l__cchess_board_background_tl
{
- \phantom{将}
+ \phantom{a}
}{
\includegraphics{\l__cchess_board_background_tl}
}
@@ -1670,6 +1726,43 @@
}
}
+% 在正文中排版棋子
+\cs_new:Npn \__cchess_getpiece_handle:nn #1#2
+ {
+ % 构建红黑各7个棋子
+ \__cchess_pieces_construct:
+
+ % 设置指定格式的基字符盒子
+ \hbox_set:Nn \l_tmpa_box { #1 将 }
+
+ % 盒子高度
+ \dim_set:Nn \l_tmpa_dim
+ {
+ \box_ht_plus_dp:N \l_tmpa_box
+ }
+
+ % 棋子高度
+ \dim_set:Nn \l_tmpb_dim
+ {
+ \__cchess_coffin_ht_plus_dp:N \l__cchess_piece_K_coffin
+ }
+
+ % 缩放棋子
+ \coffin_scale:cnn { l__cchess_piece_ #2 _coffin }
+ {
+ \dim_ratio:nn { \l_tmpa_dim } { \l_tmpb_dim }
+ }{
+ \dim_ratio:nn { \l_tmpa_dim } { \l_tmpb_dim }
+ }
+
+ % 盒子深度
+ \dim_set:Nn \l_tmpb_dim { \box_dp:N \l_tmpa_box }
+
+ % 输出盒子(下沉深度距离)
+ \coffin_typeset:cnnnn { l__cchess_piece_ #2 _coffin }
+ { l } { b } { 0pt } { -\l_tmpb_dim }
+ }
+
% =============排版棋谱=============
% 棋谱排版
\cs_new:Npn \__cchess_manual_output:n #1
@@ -1820,12 +1913,14 @@
}
\cs_generate_variant:Nn \__cchess_piece_set:nnn {VV}
+% ======================================================
% ===采用棋子替换方式创建棋子画布coffin(用于打谱排版)===
-% 缩放棋子盒子容器
+% ======================================================
+% 缩放占棋子盒子容器
\cs_new:Nn \__cchess_board_pieces_resize:
{
% 空白棋子
- \coffin_resize:Nnn \l__cchess_board_piece_n_coffin
+ \coffin_resize:Nnn \l__cchess_board_piece_z_coffin
{ \piecesize } { \piecesize }
% 其它棋子,按行(a-i)列(a-j)编号命名。
@@ -1912,8 +2007,8 @@
}
% 棋子占位替换函数
-% #1 x方向数字型坐标值(a-i)
-% #2 y方向数字型坐标值(a-j)
+% #1 横向字符型坐标值(a-i)
+% #2 纵向字符型坐标值(a-j)
% #3 棋子名称(单英文字母)
\cs_new:Npn \__cchess_piece_replace:nnn #1#2#3
{
@@ -1958,14 +2053,14 @@
}
% 棋子删除函数
-% #1 x方向数字型坐标值(a-i)
-% #2 y方向数字型坐标值(a-j)
+% #1 横向字符型坐标值(a-i)
+% #2 纵方向字符型坐标值(a-j)
% #3 棋子名称(单英文字母)
\cs_new:Npn \__cchess_piece_remove:nn #1#2
{
\coffin_gset_eq:cN
{ l__cchess_board_piece_ #1 _ #2 _coffin }
- \l__cchess_board_piece_n_coffin
+ \l__cchess_board_piece_z_coffin
}
\cs_generate_variant:Nn \__cchess_piece_remove:nn {VV}
@@ -2028,10 +2123,10 @@
}
% 棋子移动函数
-% #1 原位置x方向数字型坐标值(a-i)
-% #2 原位置y方向数字型坐标值(a-j)
-% #3 新位置x方向数字型坐标值(a-i)
-% #4 新位置y方向数字型坐标值(a-j)
+% #1 原位置横向字符型坐标值(a-i)
+% #2 原位置纵向字符型坐标值(a-j)
+% #3 新位置横向字符型坐标值(a-i)
+% #4 新位置纵向字符型坐标值(a-j)
% #5 棋子名称(单英文字母)
\cs_new:Npn \__cchess_piece_move:nnnnn #1#2#3#4#5
{
@@ -2050,14 +2145,14 @@
% 生成打谱棋谱记录
% TODO:暂未实现纵向同类棋子前后判断
-% #1 原位置x方向数字型坐标值(a-i)
-% #2 原位置y方向数字型坐标值(a-j)
-% #3 新位置x方向数字型坐标值(a-i)
-% #4 新位置y方向数字型坐标值(a-j)
+% #1 原位置横向字符型坐标值(a-i)
+% #2 原位置纵向字符型坐标值(a-j)
+% #3 新位置横向字符型坐标值(a-i)
+% #4 新位置纵向字符型坐标值(a-j)
% #5 棋子名称(单英文字母)
\cs_new:Npn \__cchess_piece_manual_str_construct:nnnnn #1#2#3#4#5
{
- % 将字母坐标数据转换为整数坐标
+ % 将字符坐标数据转换为整数坐标
\prop_get:NnN \c__cchess_board_pos_alph_num_prop { #1 } \l_tmpa_tl
\prop_get:NnN \c__cchess_board_pos_alph_num_prop { #2 } \l_tmpb_tl
\prop_get:NnN \c__cchess_board_pos_alph_num_prop { #3 } \l_tmpc_tl
@@ -2226,6 +2321,11 @@
\tl_use:N \l_tmpa_tl
}
+% 定义\label命令的变体函数
+%\label { #1 }
+\cs_set_eq:NN \__cchess_setman_label:n \label
+\cs_generate_variant:Nn \__cchess_setman_label:n { x }
+
% 打谱环境后处理函数
\cs_new:Nn \__cchess_setcchessman_post_setup:
{
@@ -2257,36 +2357,27 @@
% 星号环境需要输出打谱记录
\bool_if:NT \l__cchess_with_setman_bool
{
- % 测量打谱记录盒子水平尺寸
- \hcoffin_set:Nn \l_tmpa_coffin { 车九平八\quad 车九平八}
- \dim_set:Nn \l_tmpa_dim { \coffin_wd:N \l_tmpa_coffin }
+ % 递增计数器
+ \refstepcounter{setman}
+ % 设置label标签
+ \__cchess_setman_label:x { \l__cchess_setman_label_tl }
- % 构建打谱记录垂直盒子容器
- \vcoffin_set:Nnn \l_tmpa_coffin { \l_tmpa_dim }
+ % 构造临时文件
+ \iow_open:Nn \g_tmpa_iow
{
- % 遍历打谱记录列表,输出打谱记录
- \bool_until_do:nn { \clist_if_empty_p:N \l__cchess_manual_clist }
- {
- % 取消首行缩进
- \noindent
- \clist_pop:NN \l__cchess_manual_clist \l_tmpa_tl
+ \c_sys_jobname_str\l__cchess_setman_label_tl\thesetman .man
+ }
- \clist_if_empty:NTF \l__cchess_manual_clist
- {
- \l_tmpa_tl
- }{
- \clist_pop:NN \l__cchess_manual_clist \l_tmpb_tl
- \l_tmpa_tl
- \quad
- \l_tmpb_tl
- \par
- }
- }
+ % 遍历打谱记录列表,输出打谱记录到临时文件
+ \bool_until_do:nn { \clist_if_empty_p:N \l__cchess_manual_clist }
+ {
+ \clist_pop:NN \l__cchess_manual_clist \l_tmpa_tl
+ \tl_set:Nx \l_tmpb_tl {\l_tmpa_tl}
+ \iow_now:Nx \g_tmpa_iow { \l_tmpb_tl }
}
- % 拼装打谱记录盒子容器到结果容器
- \coffin_join:NnnNnnnn \l__cchess_manual_coffin
- { l } { t } \l_tmpa_coffin { r } { t } { -10pt } { -\piecesize }
+ % 关闭文件
+ \iow_close:N \g_tmpa_iow
}
% 输出结果盒子容器
@@ -2294,4 +2385,60 @@
{ l }{ b } { 0pt } { 0pt }
}
+% 参考雾月的回复:https://ask.latexstudio.net/ask/question/7430.html
+% LaTeX3 并未定义 \use_i:nnnnn
+\cs_set:Npn \use_i:nnnnn #1#2#3#4#5 {#1}
+
+% 打谱棋谱排版描述处理
+\cs_new:Npn \__cchess_setman_print:n #1
+ {
+ % 根据棋谱label构建文件名
+ \cs_if_exist:cTF { r@#1 }
+ {
+ % 这一步是得到 ref,它保存在 \r@#1 中。
+ % \r@#1 有两项,当使用 hyperref 时,
+ % \r@#1 有 5 项,这里使用 \empty 统一解决
+ \tl_set:Nx \l_tmpa_tl
+ {
+ \c_sys_jobname_str
+ #1 \exp_args:NNc \exp_after:wN \use_i:nnnnn { r@ #1 }
+ \c_empty_tl \c_empty_tl \c_empty_tl .man
+ }
+
+ % 打开文件读取数据并输出结果
+ \ior_open:NnTF \g_tmpb_ior { \l_tmpa_tl }
+ {
+ % 循环计数
+ \int_set:Nn \l_tmpa_int { 1 }
+ % 循环读取一行棋谱
+ \ior_str_map_variable:NNn \g_tmpb_ior \l_tmpb_str
+ {
+ % 转换为token
+ \tl_set_rescan:Nno \l_tmpb_tl
+ {
+ \char_set_catcode_letter:N \_
+ \char_set_catcode_letter:N :
+ }{ \l_tmpb_str }
+
+ % 输出结果
+ \tl_use:N \l_tmpb_tl
+
+ % 根据每行步数确定输出\quad或是\par
+ \int_set:Nn \l_tmpb_int
+ {
+ \int_mod:nn { \l_tmpa_int } { \l__cchess_mans_per_line_int }
+ }
+ \int_compare:nNnTF { \l_tmpb_int } = { 0 }
+ { \par } { \quad }
+
+ \int_incr:N \l_tmpa_int
+ }
+ }
+ { \msg_error:nnx { cchess } { file-not-found } { \l_tmpa_tl } }
+
+ % 关闭文件
+ \iow_close:N \g_tmpa_ior
+ }{ \G@refundefinedtrue }% 引用未定义
+ }
+
\endinput