%% 
%% This is file `phy-xmat.sty',
%% the `xmat' module of `physics2' package.
%% 
%% ******************************************************
%% * This work may be distributed and/or modified under *
%% * the conditions of the LaTeX Project Public License *
%% *                                                    *
%% *     http://www.latex-project.org/lppl.txt          *
%% *                                                    *
%% * either version 1.3c of this license or any later   *
%% * version.                                           *
%% ******************************************************
%% 
%% This work has the LPPL maintenance status `maintained'.
%% 
%% The Current Maintainer of this work is Zhang Tingxuan.
%% 
\ProvidesExplFile{phy-xmat.sty}{2023/01/25}{}
  {`xmat' module of `physics2.sty'}
\phy@requiremodule { explsetup }
\RequirePackage { amsmath }
\phy@define@key { xmat } { showtop }
  { \int_gset:Nn \l__phy_xmat_showtop_int { #1 } }
\phy@define@key { xmat } { showleft }
  { \int_gset:Nn \l__phy_xmat_showleft_int { #1 } }
% New variables
\bool_new:N \l__phy_xmat_extra_vdots_bool
\bool_new:N \l__phy_xmat_extra_cdots_bool
\int_new:N \l__phy_xmat_showtop_int
\int_new:N \l__phy_xmat_showleft_int
\tl_new:N \l__phy_xmat_tl
\int_gset:Nn \l__phy_xmat_showtop_int { \value { MaxMatrixCols } - 2 }
\int_gset:Nn \l__phy_xmat_showleft_int { \value { MaxMatrixCols } - 2 }
\cs_new:Npn \__phy_xmat_entry_format:nnn #1#2#3
  {
    #1 \c_math_subscript_token { #2 #3 }
  }
\phy@processkeyopt { xmat }
\DeclareDocumentCommand \xmat { O{} m m m }
 { \__phy_xmat_type:nnnnn { } { #1 } { #2 } { #3 } { #4 } }
\DeclareDocumentCommand \pxmat { O{} m m m }
 { \__phy_xmat_type:nnnnn { p } { #1 } { #2 } { #3 } { #4 } }
\DeclareDocumentCommand \bxmat { O{} m m m }
 { \__phy_xmat_type:nnnnn { b } { #1 } { #2 } { #3 } { #4 } }
\DeclareDocumentCommand \Bxmat { O{} m m m }
 { \__phy_xmat_type:nnnnn { B } { #1 } { #2 } { #3 } { #4 } }
\DeclareDocumentCommand \vxmat { O{} m m m }
 { \__phy_xmat_type:nnnnn { v } { #1 } { #2 } { #3 } { #4 } }
\DeclareDocumentCommand \Vxmat { O{} m m m }
 { \__phy_xmat_type:nnnnn { V } { #1 } { #2 } { #3 } { #4 } }

\keys_define:nn { phy/xmat }
  {
    format  .cs_set:Np = \__phy_xmat_entry_format:nnn #1#2#3 ,
    showtop .int_set:N = \l__phy_xmat_showtop_int ,
    showleft.int_set:N = \l__phy_xmat_showleft_int ,
  }
% Use regex to judge if the total row/column number contains digits **only**.
\prg_new_conditional:Npnn \__phy_if_digits_only:n #1 { TF }
  {
    \regex_match:nnTF { \A [[:digit:]]* \Z } { #1 }
      { \prg_return_true: } { \prg_return_false: }
  }
% #1: p,b,B; #2: options; #2: common entry; #3: total rows; #4: total cols.
\cs_new:Npn \__phy_xmat_type:nnnnn #1#2#3#4#5
  {
    \group_begin:
    \tl_gclear:N \l__phy_xmat_tl
    \keys_set:nn { phy/xmat } { #2 } % 
    \__phy_if_digits_only:nTF { #4 }
      {
        \int_compare:nNnTF { #4 } < { \l__phy_xmat_showtop_int + 1 }
          {
            \int_set:Nn \l__phy_xmat_showtop_int { #4 }
            \bool_set_false:N \l__phy_xmat_extra_vdots_bool
          }
          {
            \bool_set_true:N \l__phy_xmat_extra_vdots_bool
          }
      }
      {
        \bool_set_true:N \l__phy_xmat_extra_vdots_bool
      }
    \__phy_if_digits_only:nTF { #5 }
      {
        \int_compare:nNnTF { #5 } < { \l__phy_xmat_showleft_int + 1 }
          {
            \int_set:Nn \l__phy_xmat_showleft_int { #5 }
            \bool_set_false:N \l__phy_xmat_extra_cdots_bool
          }
          {
            \bool_set_true:N \l__phy_xmat_extra_cdots_bool
          }
      }
      {
        \bool_set_true:N \l__phy_xmat_extra_cdots_bool
      }
    \int_step_inline:nn { \l__phy_xmat_showtop_int }
      {
        \tl_put_right:Nn \l__phy_xmat_tl
          { \__phy_xmat_entry_format:nnn { #3 } { ##1 } { 1 } }
        \int_step_inline:nnn { 2 } { \l__phy_xmat_showleft_int }
          {
            \tl_put_right:Nn \l__phy_xmat_tl
              { & \__phy_xmat_entry_format:nnn { #3 } { ##1 } { ####1 } }
          }
        \bool_if:NT \l__phy_xmat_extra_cdots_bool
          {
            \tl_put_right:Nn \l__phy_xmat_tl
              { & \cdots & \__phy_xmat_entry_format:nnn { #3 } { ##1 } { #5 } }
          }
        \tl_put_right:Nn \l__phy_xmat_tl { \\ }
      }
    \bool_if:NT \l__phy_xmat_extra_vdots_bool
      {
        \tl_put_right:Nn \l__phy_xmat_tl { \vdots }
        \prg_replicate:nn { \l__phy_xmat_showleft_int - 1 }
          {
            \tl_put_right:Nn \l__phy_xmat_tl { & \vdots }
          }
        % Add \ddots if vdots_bool and cdots_bool be true simultaneously.
        \bool_if:NT \l__phy_xmat_extra_cdots_bool
          {
            \tl_put_right:Nn \l__phy_xmat_tl { & \ddots & \vdots }
          } % else relax
        \tl_put_right:Nn \l__phy_xmat_tl { \\ }
        % The last row.
        \tl_put_right:Nn \l__phy_xmat_tl
          { \__phy_xmat_entry_format:nnn { #3 } { #4 } { 1 } }
        \int_step_inline:nnn { 2 } { \l__phy_xmat_showleft_int }
          {
            \tl_put_right:Nn \l__phy_xmat_tl
              { & \__phy_xmat_entry_format:nnn { #3 } { #4 } { ##1 } }
          }
        \bool_if:NT \l__phy_xmat_extra_cdots_bool
          {
            \tl_put_right:Nn \l__phy_xmat_tl
              { & \cdots & \__phy_xmat_entry_format:nnn { #3 } { #4 } { #5 } }
          }
      } % else relax
    \begin { #1 matrix }
      \tl_use:N \l__phy_xmat_tl
    \end { #1 matrix }
    \group_end:
  }
\endinput
%% End of file `phy-xmat.sty'.
