% % ***************** THE SPBMARK PACKAGE ***************** % % Copyright (C) 2021 by Qu Yi % % This work may be distributed and/or modified under the % conditions of the CC-BY 4.0 License. % The latest version of this license is in % https://creativecommons.org/licenses/by/4.0/legalcode \NeedsTeXFormat{LaTeX2e}[2018/12/31] \RequirePackage{xparse,l3keys2e} \ProvidesExplPackage{spbmark}{2021/12/16}{1.2B} {Customize superscripts and subscripts} \cs_generate_variant:Nn \dim_max:nn { VV } \cs_generate_variant:Nn \dim_compare:nNnTF { V } \cs_generate_variant:Nn \msg_warning:nnn { nnV } \cs_generate_variant:Nn \str_case:nn { x } \cs_generate_variant:Nn \tl_if_novalue:nF { V } \cs_new_protected:Npn \spb_define:n { \keys_define:nn { ctex/style } } \cs_new_protected:Npn \spbset { \keys_set:nn { ctex/style } } \keys_define:nn { spbmark/option } { text .bool_set:N = \l_spb_newsupb_text_bool, text .default:n = true, math .bool_set:N = \l_spb_newsupb_math_bool, math .default:n = true, foot .bool_set:N = \l_spb_newsupb_foot_bool, foot .default:n = true, both .meta:n = { text,math }, both .value_forbidden:n = true, all .meta:n = { text,math,foot }, all .value_forbidden:n = true, ctex .code:n = { }, newsupb .code:n = { } } \ProcessKeysOptions{spbmark/option} \tl_new:N \l__spb_super_cmd_ii_tl \tl_new:N \l__spb_sub_cmd_ii_tl \tl_new:N \g__spb_hshift_init_tl \tl_new:N \g__spb_vshift_init_tl \tl_new:N \g__spb_cmd_init_tl \cs_new_protected:Npn \spb_local_case_init:nnnn #1#2#3#4 { \str_case:xn { \tl_use:c { g__spb_#1_init_tl } } { { super } {#2} { sub } {#3} { supersub } {#4} } } \spb_define:n { spvshift .dim_set:N = \l__spb_super_vshift_dim, spvshift .initial:n = 0pt, sphshift .dim_set:N = \l__spb_super_hshift_dim, sphshift .initial:n = 0pt, sbvshift .dim_set:N = \l__spb_sub_vshift_dim, sbvshift .initial:n = 0pt, sbhshift .dim_set:N = \l__spb_sub_hshift_dim, sbhshift .initial:n = 0pt, spbhshift .dim_set:N = \l__spb_supersub_hshift_dim, spbhshift .initial:n = 0pt, vshift .code:n = { \spb_local_case_init:nnnn { vshift } { \dim_set:Nn \l__spb_super_vshift_dim {#1} } { \dim_set:Nn \l__spb_sub_vshift_dim {#1} } { \dim_set:Nn \l__spb_supersub_vsep_dim {#1} } }, hshift .code:n = { \spb_local_case_init:nnnn { hshift } { \dim_set:Nn \l__spb_super_hshift_dim {#1} } { \dim_set:Nn \l__spb_sub_hshift_dim {#1} } { \dim_set:Nn \l__spb_supersub_hshift_dim {#1} } }, nohshift .meta:n = { sphshift = 0pt,sbhshift = 0pt }, novshift .meta:n = { spvshift = 0pt,sbvshift = 0pt }, spcmd .tl_set:N = \l__spb_super_cmd_i_tl, sbcmd .tl_set:N = \l__spb_sub_cmd_i_tl, spbcmd .code:n = \spb_both_cmd_assign:n {#1}, cmd .code:n = { \spb_local_case_init:nnnn { cmd } { \tl_set:Nn \l__spb_super_cmd_i_tl {#1} } { \tl_set:Nn \l__spb_sub_cmd_i_tl {#1} } { \spb_both_cmd_assign:n {#1} } }, vsep .dim_set:N = \l__spb_supersub_vsep_dim, vsep .initial:n = 0.3ex, halign .tl_set:N = \l__spb_supersub_align_tl, halign .initial:n = l, mode .tl_set:N = \l__spb_mode_value_tl, mode .initial:n = match } \tl_set:Nn \l__spb_boxa_wd_tl { \box_wd:N \l_tmpa_box } \tl_set:Nn \l__spb_boxb_wd_tl { \box_wd:N \l_tmpb_box } \tl_set:Nn \l__spb_box_max_wd_tl { \dim_max:VV \l__spb_boxa_wd_tl \l__spb_boxb_wd_tl } \providecommand{\hbox_overlap_center:n}[1] { \hbox_to_zero:n { \hss #1\hss } } \cs_new:Npn \spb_boxa_move_up:n #1 { \box_move_up:nn {#1} { \box_use:N \l_tmpa_box } } \cs_new:Npn \spb_boxa_move_down:n #1 { \box_move_down:nn {#1} { \box_use:N \l_tmpa_box } } \cs_new:Npn \spb_boxb_move_down:n #1 { \box_move_down:nn {#1} { \box_use:N \l_tmpb_box } } \cs_new:Npn \spb_boxa_vshift:nn #1 { \str_case:nn {#1} { { super } { \spb_boxa_move_up:n } { sub } { \spb_boxa_move_down:n } } } \cs_generate_variant:Nn \spb_boxa_move_up:n { V } \cs_generate_variant:Nn \spb_boxb_move_down:n { V } \cs_new:Npn \spb_hbox_overlap_vshift:n #1 { \use:c { hbox_overlap_#1:n } { \spb_boxa_move_up:V \l__spb_supersub_vsep_dim } \use:c { hbox_overlap_#1:n } { \spb_boxb_move_down:V \l__spb_supersub_vsep_dim } } \cs_set_eq:NN \spb@textsuperscript@save \textsuperscript \cs_set_eq:NN \spb@textsubscript@save \textsubscript \cs_set_eq:NN \spb@math@super@save \sp \cs_set_eq:NN \spb@math@sub@save \sb \cs_new:Npn \spb_math_print_store_i:nn #1#2 { \hbox_set:Nn \l_tmpa_box { \ensuremath { \use:c { spb@math@#1@save } { \tl_use:c { l__spb_#1_cmd_i_tl }{#2} } } } } \cs_new:Npn \spb_text_print_store_i:nn #1#2 { \hbox_set:Nn \l_tmpa_box { \use:c { spb@text#1script@save } { \tl_use:c { l__spb_#1_cmd_i_tl }{#2} } } } \cs_new:Npn \spb_math_print_store_ii:nn #1#2 { \hbox_set:Nn \l_tmpa_box { \ensuremath{\spb@math@super@save{\l__spb_super_cmd_ii_tl{#1}}} } \hbox_set:Nn \l_tmpb_box { \ensuremath{\spb@math@sub@save{\l__spb_sub_cmd_ii_tl{#2}}} } } \cs_new:Npn \spb_text_print_store_ii:nn #1#2 { \hbox_set:Nn \l_tmpa_box { \spb@textsuperscript@save{\l__spb_super_cmd_ii_tl{#1}} } \hbox_set:Nn \l_tmpb_box { \spb@textsubscript@save{\l__spb_sub_cmd_ii_tl{#2}} } } \cs_new_protected:Npn \spb_box_ht_dp_assign:nn #1#2 { \tl_if_empty:nF {#1} { \box_set_ht:Nn \l_tmpb_box {#1} } \tl_if_novalue:nF {#2} { \box_set_dp:Nn \l_tmpb_box {#2} } } \NewDocumentCommand{\spb_both_cmd_assign:n} {>{\SplitArgument{1}{,}}m} {\spb_supersub_both_cmd:nn #1} \cs_new_protected:Npn \spb_supersub_both_cmd:nn #1#2 { \tl_set:Nn \l__spb_super_cmd_ii_tl {#1} \tl_if_novalue:nTF {#2} { \tl_clear:N \l__spb_sub_cmd_ii_tl } { \tl_set:Nn \l__spb_sub_cmd_ii_tl {#2} } } \cs_new_protected:Npn \spb_mode_switch:nnn #1#2#3 { \str_case:Vn \l__spb_mode_value_tl { { math } {#1} { text } {#2} { match } {#3} } } \cs_new_protected:Npn \spb_global_value_init:n #1 { \tl_gset:Nn \g__spb_hshift_init_tl {#1} \tl_gset:Nn \g__spb_vshift_init_tl {#1} \tl_gset:Nn \g__spb_cmd_init_tl {#1} } \cs_new_protected:Npn \spb_both_newcmd_map:n #1 { \exp_args:Nc \NewDocumentCommand {#1} {O{}>{\SplitArgument{1}{,}}O{}mO{}} { \group_begin: \spb_global_value_init:n {#1} \keys_set:nn { ctex/style } {##1,##4} \spb_mode_switch:nnn { \spb_math_print_store_i:nn {#1} {##3} } { \spb_text_print_store_i:nn {#1} {##3} } { \mode_if_math:TF { \spb_math_print_store_i:nn {#1} {##3} } { \spb_text_print_store_i:nn {#1} {##3} } } \spb_content_hbox_set:n {#1} \spb_box_ht_dp_assign:nn ##2 \box_use:N \l_tmpa_box \group_end: } } \cs_new_protected:Npn \spb_content_hbox_set:n #1 { \hbox_set:Nn \l_tmpa_box { \dim_compare:nNnTF { \dim_use:c { l__spb_#1_hshift_dim } } < { 0pt } { \hbox_overlap_left:n { \hbox_to_wd:nn { \l__spb_boxa_wd_tl - \dim_use:c { l__spb_#1_hshift_dim } } { \spb_boxa_vshift:nn {#1} { \dim_use:c { l__spb_#1_vshift_dim } }\hss } } } { \hbox_to_wd:nn { \l__spb_boxa_wd_tl + \dim_use:c { l__spb_#1_hshift_dim } } { \hss\spb_boxa_vshift:nn {#1} { \dim_use:c { l__spb_#1_vshift_dim } } } } } } \clist_map_inline:nn { super,sub } { \spb_both_newcmd_map:n {#1} } \cs_new:Npn \spb_supersub_hshift_if_negative:TF #1#2 { \dim_compare:VNnTF \l__spb_supersub_hshift_dim < { 0pt } {#1} {#2} } \NewDocumentCommand{\supersub}{O{}mmO{}} { \group_begin: \spb_global_value_init:n { supersub } \keys_set:nn { ctex/style } {#1,#4} \spb_mode_switch:nnn { \spb_math_print_store_ii:nn {#2} {#3} } { \spb_text_print_store_ii:nnnn {#2} {#3} } { \mode_if_math:TF { \spb_math_print_store_ii:nn {#2} {#3} } { \spb_text_print_store_ii:nn {#2} {#3} } } \str_case:VnF \l__spb_supersub_align_tl { { l } { \use_i:nnn } { c } { \use_ii:nnn } { r } { \use_iii:nnn } } { \msg_warning:nn { spbmark } { unsupported-align } \use_i:nnn } { \spb_supersub_hshift_if_negative:TF { \hbox_overlap_left:n { \spb_hbox_overlap_vshift:n { right } \skip_horizontal:n { -\l__spb_supersub_hshift_dim } } } { \hbox:n { \skip_horizontal:n { \l__spb_supersub_hshift_dim } \spb_hbox_overlap_vshift:n { right } \skip_horizontal:n { \l__spb_box_max_wd_tl } } } } { \spb_supersub_hshift_if_negative:TF { \hbox_overlap_left:n { \spb_hbox_overlap_vshift:n { center } \skip_horizontal:n { \l__spb_box_max_wd_tl/2 - \l__spb_supersub_hshift_dim } } } { \hbox:n { \skip_horizontal:n { \l__spb_box_max_wd_tl/2 + \l__spb_supersub_hshift_dim } \spb_hbox_overlap_vshift:n { center } \skip_horizontal:n { \l__spb_box_max_wd_tl/2 } } } } { \spb_supersub_hshift_if_negative:TF { \hbox_overlap_left:n { \spb_hbox_overlap_vshift:n { left } \skip_horizontal:n { -\l__spb_supersub_hshift_dim } } } { \hbox:n { \skip_horizontal:n { \l__spb_box_max_wd_tl + \l__spb_supersub_hshift_dim } \spb_hbox_overlap_vshift:n { left } } } } \group_end: } \msg_new:nnn { spbmark } { unsupported-align } { Alignment~only~supports~l,~c,~and~r. \\ The~l~parameter~will~be~used~by~default. } \bool_if:NT \l_spb_newsupb_text_bool { \cs_set_eq:NN \textsuperscript \super \cs_set_eq:NN \textsubscript \sub } \bool_if:NT \l_spb_newsupb_math_bool { \cs_set_eq:NN \sp \super \cs_set_eq:NN \sb \sub } \bool_if:NT \l_spb_newsupb_foot_bool { \cs_set:Npn \@makefnmark { \hbox:n { \fnmarkfont{\super{\@thefnmark}} } } } \cs_set_eq:NN \spb \supersub \tl_if_exist:NTF \ftntm@font { \tl_set_eq:NN \fnmarkfont \ftntm@font } { \tl_set_eq:NN \fnmarkfont \normalfont } \endinput % % End of file `spbmark.sty'.