Skip to content

Commit 3c5f7cb

Browse files
committed
feat: 使用 LaTeX Hook 机制改写封面绘制逻辑 (#308)
1 parent dc20f4a commit 3c5f7cb

2 files changed

Lines changed: 97 additions & 61 deletions

File tree

CHANGELOG.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@
99
### 新增
1010

1111
- 成果列表显示全部作者名 - [#306]
12+
- 使用 LaTeX Hook 机制改写封面绘制逻辑 - [#308]
1213

1314
### 修复
1415

@@ -734,6 +735,7 @@
734735
[#302]: https://github.com/nju-lug/NJUThesis/pull/302
735736
[#305]: https://github.com/nju-lug/NJUThesis/discussions/305
736737
[#306]: https://github.com/nju-lug/NJUThesis/issues/306
738+
[#308]: https://github.com/nju-lug/NJUThesis/issues/308
737739

738740
[CTeX-org/ctex-kit#678]: https://github.com/CTeX-org/ctex-kit/pull/678
739741
[CTeX-org/ctex-kit#700]: https://github.com/CTeX-org/ctex-kit/pull/700

source/njuthesis.dtx

Lines changed: 95 additions & 61 deletions
Original file line numberDiff line numberDiff line change
@@ -4555,6 +4555,28 @@ To produce the documentation run the original source files ending with
45554555
}
45564556
% \end{macrocode}
45574557
%
4558+
%
4559+
% \subsection{钩子机制}
4560+
% \changes{v1.5}{2026/04/24}{将封面执行逻辑拆解为三个钩子。}
4561+
%
4562+
% \begin{macro}{njuthesis/cover/begin,njuthesis/cover/body,njuthesis/cover/end}
4563+
% 封面流程钩子。由于默认配置文件会向这些钩子添加代码,
4564+
% 需要在载入配置文件前先行声明。
4565+
% 名称中的 |.| 代表本模板名 \cls{njuthesis}。
4566+
% 命名逻辑为,钩子名代表模块下的逻辑位置,而标签概括实际执行的功能。
4567+
% \begin{macrocode}
4568+
\hook_new:n { . / cover / begin }
4569+
\hook_new:n { . / cover / body }
4570+
\hook_new:n { . / cover / end }
4571+
% \end{macrocode}
4572+
%
4573+
% 设置标签的默认规则,规定主封面代码始终在承诺书前执行。
4574+
% \begin{macrocode}
4575+
\hook_gset_rule:nnnn { . / cover / body } { main } < { decl-i }
4576+
% \end{macrocode}
4577+
% \end{macro}
4578+
%
4579+
%
45584580
% \subsection{配置文件}
45594581
%
45604582
% \cls{njuthesis} 包含三套区别较大的模板配置,分别适用于\emph{本科生}、
@@ -7805,75 +7827,102 @@ To produce the documentation run the original source files ending with
78057827
% \end{macrocode}
78067828
% \end{macro}
78077829
%
7808-
% \begin{macro}{\@@_make_cover:}
78097830
% \changes{v1.3}{2023/05/24}{修复非研究生类型时调用 \opt{nl-cover} 选项的错误。}
7810-
% 调用实例生成封面。
7831+
% 在草稿模式下,封面绘制将被禁用,有助于提升编译速度。
7832+
% 通过不同选项进行分流,使得钩子内部最终不包含逻辑判断,
7833+
% 仅需调用恰当的实例生成封面。
78117834
% \begin{macrocode}
78127835
%<*(def-u|def-g|def-p)>
7813-
\cs_new_protected:Npn \@@_make_cover:
7836+
\bool_if:NF \g_@@_opt_draft_bool
78147837
{
7815-
%<def-u> \UseInstance { nju } { cover-u }
7816-
%<def-p> \UseInstance { nju } { cover-p }
7838+
%<def-u|def-p> \hook_gput_code:nnn { . / cover / body } { main }
7839+
%<def-u> { \UseInstance { nju } { cover-u } }
7840+
%<def-p> { \UseInstance { nju } { cover-p } }
78177841
% \end{macrocode}
78187842
% 如果在研究生模板中选择了 \opt{nlcover},就生成用于申请学位的国家图书馆封面,
78197843
% 反之生成普通封面。
78207844
% \begin{macrocode}
78217845
%<*def-g>
7822-
\bool_if:NTF \g_@@_opt_nlcover_bool
7823-
{ \UseInstance { nju } { cover-nl } }
7824-
{
7825-
\UseInstance { nju } { cover-g-front }
7826-
\UseInstance { nju } { cover-g-back }
7827-
\UseInstance { nju } { cover-g-en }
7828-
}
7846+
\bool_if:NTF \g_@@_opt_nlcover_bool
7847+
{
7848+
\hook_gput_code:nnn { . / cover / body } { main }
7849+
{ \UseInstance { nju } { cover-nl } }
7850+
}
7851+
{
7852+
\hook_gput_code:nnn { . / cover / body } { main }
7853+
{
7854+
\UseInstance { nju } { cover-g-front }
7855+
\UseInstance { nju } { cover-g-back }
7856+
\UseInstance { nju } { cover-g-en }
7857+
}
7858+
}
78297859
%</def-g>
7830-
}
78317860
% \end{macrocode}
7832-
% \end{macro}
78337861
%
7834-
% \begin{macro}{\@@_make_decl_i:}
78357862
% \changes{v0.13}{2021/12/15}{加入本科生的诚信承诺书。}
7863+
% \changes{v0.17}{2022/04/04}{加入研究生的学位论文出版授权书。}
78367864
% \changes{v0.19}{2022/05/22}{跟进新版本科生诚信承诺书样式。}
7837-
% 位于封面后的承诺书页面。
7838-
% 生成本科生的诚信承诺书或研究生的学位论文原创性声明。
7865+
% 根据选项设置声明页钩子。
7866+
% 位于封面后的承诺书页面,
7867+
% 用于生成本科生的诚信承诺书或研究生的学位论文原创性声明。
78397868
% \begin{macrocode}
7840-
\cs_new_protected:Npn \@@_make_decl_i:
7841-
{
7842-
\cleardoublepage
7843-
%<def-u> \UseInstance { nju } { origdecl-u }
7844-
%<def-g> \UseInstance { nju } { origdecl-g }
7845-
%<def-p> \UseInstance { nju } { authdecl-p }
7846-
\cleardoublepage
7847-
}
7869+
\bool_if:NT \g_@@_opt_decl_bool
7870+
{
7871+
\hook_gput_code:nnn { . / cover / body } { decl-i }
7872+
{
7873+
\cleardoublepage
7874+
%<def-u> \UseInstance { nju } { origdecl-u }
7875+
%<def-g> \UseInstance { nju } { origdecl-g }
7876+
%<def-p> \UseInstance { nju } { authdecl-p }
7877+
\cleardoublepage
7878+
}
78487879
% \end{macrocode}
7849-
% \end{macro}
7850-
%
7851-
% \begin{macro}{\@@_make_decl_ii:}
7852-
% \changes{v0.17}{2022/04/04}{加入研究生的学位论文出版授权书。}
78537880
% 位于封底的承诺书页面。生成研究生的学位论文出版授权书。
78547881
% \begin{macrocode}
7855-
\cs_new_protected:Npn \@@_make_decl_ii:
7856-
{
78577882
%<*def-g>
7858-
\AtEndEnvironment { document }
7859-
{
7860-
\cleardoublepage
7861-
\UseInstance { nju } { authdecl-g }
7862-
\cleardoublepage
7863-
}
7883+
\hook_gput_code:nnn { env / document / end } { decl-ii }
7884+
{
7885+
\cleardoublepage
7886+
\UseInstance { nju } { authdecl-g }
7887+
\cleardoublepage
7888+
}
78647889
%</def-g>
7890+
}
78657891
}
78667892
%</(def-u|def-g|def-p)>
78677893
% \end{macrocode}
7868-
% \end{macro}
7894+
%
7895+
% 封面前处理。封面本身不占用页码编号。
7896+
% \begin{macrocode}
7897+
%<*class>
7898+
\hook_gput_code:nnn { . / cover / begin } { presetup }
7899+
{ \pagenumbering { gobble } }
7900+
% \end{macrocode}
7901+
%
7902+
% 封面后处理。在标题页后清空标题中的换行符,
7903+
% 使用大写罗马字母页码,恢复正常字体设置。
7904+
% \begin{macrocode}
7905+
\hook_gput_code:nnn { . / cover / end } { postsetup }
7906+
{
7907+
\tl_gremove_all:Nn \g_@@_info_title_tl { \\ }
7908+
\tl_gremove_all:Nn \g_@@_info_title_en_tl { \\ }
7909+
\cleardoublepage
7910+
\exp_args:NV \pagestyle \l_@@_fmt_pagestyle_tl
7911+
\pagenumbering { Roman }
7912+
}
7913+
% \end{macrocode}
7914+
%
7915+
% 保证文档在 \opt{twoside} 模式下总是在偶数页结束。
7916+
% \begin{macrocode}
7917+
\hook_gput_next_code:nn { env / document / end } { \cleardoublepage }
7918+
% \end{macrocode}
78697919
%
78707920
%
78717921
% \subsubsection{用户接口}
78727922
%
78737923
% \begin{macro}{\@@_new_img_cmd:nn}
78747924
% 用于定义插入图片命令的辅助函数。
78757925
% \begin{macrocode}
7876-
%<*class>
78777926
\cs_new_protected:Npn \@@_new_img_cmd:nn #1#2
78787927
{
78797928
\exp_args:Nc \NewDocumentCommand { nju #1 } { o m m }
@@ -7930,32 +7979,17 @@ To produce the documentation run the original source files ending with
79307979
% \changes{v0.13}{2021/12/12}{重新绘制封面。}
79317980
% \changes{v0.13}{2021/12/15}{草稿模式下不绘制封面。}
79327981
% \changes{v1.4}{2024/03/12}{在生成封面时删除标题换行符。}
7982+
% \changes{v1.5}{2026/04/24}{使用 \LaTeX 钩子机制处理封面绘制。}
79337983
% 重定义 \tn{maketitle} 以生成封面。
7934-
% 在草稿模式下,封面绘制将被禁用,有助于提升编译速度。
7984+
% 在钩子机制下,这里只需要作为钩子的锚点,
7985+
% 具体需要执行的代码已被预先分发到钩子内。
7986+
% \cs{hook_use:n} 不能用 |.| 来简化钩子路径。
79357987
% \begin{macrocode}
79367988
\RenewDocumentCommand \maketitle { }
79377989
{
7938-
\bool_if:NF \g_@@_opt_draft_bool
7939-
{
7940-
\pagenumbering { gobble }
7941-
\@@_make_cover:
7942-
}
7943-
\tl_gremove_all:Nn \g_@@_info_title_tl { \\ }
7944-
\tl_gremove_all:Nn \g_@@_info_title_en_tl { \\ }
7945-
% \end{macrocode}
7946-
% 如果在选择了 \opt{decl-page},就生成本科生的诚信承诺书,
7947-
% 或研究生的原创性声明和出版授权书。
7948-
% \begin{macrocode}
7949-
\bool_lazy_and:nnT
7950-
{ ! \g_@@_opt_draft_bool }
7951-
{ \g_@@_opt_decl_bool }
7952-
{ \@@_make_decl_i: \@@_make_decl_ii: }
7953-
% \end{macrocode}
7954-
% 在标题页后使用大写罗马字母页码,恢复正常字体设置。
7955-
% \begin{macrocode}
7956-
\cleardoublepage
7957-
\exp_args:NV \pagestyle \l_@@_fmt_pagestyle_tl
7958-
\pagenumbering { Roman }
7990+
\hook_use:n { njuthesis / cover / begin }
7991+
\hook_use:n { njuthesis / cover / body }
7992+
\hook_use:n { njuthesis / cover / end }
79597993
}
79607994
%</class>
79617995
% \end{macrocode}

0 commit comments

Comments
 (0)