%%%==============================================================================
% WinEdt pragmas
% !Mode:: "TeX:EN"
% Default Compile engines:
% !TEX program = pdflatex
% !PDFTeXify ext =  --enable-etex  --restrict-write18
% !PDFLaTeX ext  =  --enable-etex  --restrict-write18
% !BIB program = biber
%%%==============================================================================
%% Copyright 2026-present by Alceu Frigeri
%%
%% This work may be distributed and/or modified under the conditions of
%%
%% * The [LaTeX Project Public License](http://www.latex-project.org/lppl.txt),
%%   version 1.3c (or later), and/or
%% * The [GNU Affero General Public License](https://www.gnu.org/licenses/agpl-3.0.html),
%%   version 3 (or later)
%%
%% This work has the LPPL maintenance status *maintained*.
%%
%% The Current Maintainer of this work is Alceu Frigeri
%%
%% This is version {1.0} {2026/02/18}
%%
%% The list of files that compose this work can be found in the README.md file at
%% https://ctan.org/pkg/tokgroupmark
%%
%%%==============================================================================
\documentclass[10pt]{article}
\RequirePackage[verbose,a4paper,marginparwidth=27.5mm,top=2.5cm,bottom=1.5cm,hmargin={40mm,20mm},marginparsep=2.5mm,columnsep=10mm,asymmetric]{geometry}
\usepackage[T1]{fontenc}
\usepackage[utf8]{inputenc}
\usepackage{lmodern}
\usepackage[infograb,silence]{codedescribe}
\RequirePackage[inline]{enumitem}
\SetEnumitemKey{miditemsep}{parsep=0ex,itemsep=0.4ex}

\usepackage{tokgroupmark}

%% if needed
\RequirePackage[backend=biber]{biblatex}
\addbibresource{tokgroupmark.bib}

\newcodekey{groupmark}
  {
    letter = {_},
    texcs = [3]{groupmark_new },
    emph  = [3]{myMarkA, myMarkA_aftergroup,myMarkA_groupmark,myMarkB, myMarkB_aftergroup,myMarkB_groupmark},
    keywd = [2]{l__mytest_tmpa_bool,l__mytest_tmpb_bool,l__mytest_tmpc_bool,mytest_show_bools},
    codeprefix = {},
    resultprefix = {},
  }
\RequirePackage[hidelinks,hypertexnames=false]{hyperref}

\begin{document}
\tstitle{
  author={Alceu Frigeri\footnote{\tsverb{https://github.com/alceu-frigeri/tokgroupmark}}},
  date={\tsdate},
  title={The tokgroupmark Package\break Version \PkgInfo{tokgroupmark}{version}}
  }
  

\begin{typesetabstract}
 This package aims at solving the problem of how to preserve some tokens beyond a variable number of nested groups.
\end{typesetabstract}

\tableofcontents

\tsOn

\section{Introduction}

When it's necessary to preserve the value of some tokens beyond a local group, in simple cases, it's enough to use !:[code,or]{\group_insert_after:N,\aftergroup}.

But, sometimes you don't have (or can't use) this information, see \cite{exchange}, for instance. For those cases, this package deploys one of the strategies presented and compared in \cite{xstacks}, based on  !:{\aftergroup}.

\section{Custom Group Mark Commands}

\begin{codedescribe}{\groupmark_new:n}
  \begin{codesyntax}
    !!?{\groupmark_new:n}{mark-prefix}
  \end{codesyntax}
This will globally create two commands (below), named after !:[marg]{mark-prefix}, to ``mark'' and ``restore'' a token up to that ``mark''.
\begin{tsremark}
  Internally, an unique integer will be created to track the group mark.
\end{tsremark}  
\begin{tsremark}
  An error will be raised if !:[marg]{mark-prefix} is already used.
\end{tsremark}  
\end{codedescribe}

\begin{codedescribe}{\<mark-prefix>_groupmark:,\<mark-prefix>_aftergroup:N}
\begin{codesyntax}%
!!?{\<mark-prefix>_groupmark:}{}
!!?{\<mark-prefix>_aftergroup:N}{token}
\end{codesyntax}
The !:{\<mark-prefix>_groupmark:} will save, local assignment, the current group level, so that, when using  !:{\<mark-prefix>_aftergroup:N} the token will be restored once the same group level is reached once again  (similar to !:{\aftergroup}, but going beyond a single group).

\begin{tsremark}
  It is possible to have multiple, nested marks, associated with the same set, see example of use.
\end{tsremark}
\begin{tsremark}
  If !:{\<mark-prefix>_aftergroup:N} is called at the same level (or above) of !:{\<mark-prefix>_groupmark:}, it will behave as a simple !:{\group_insert_after:N}
\end{tsremark}


\end{codedescribe}


\section{Examples of Use}
In the following examples, two sets of mark commands will be used, !:[marg]{myMarkA,myMarkB}. 

\begin{codestore}[grpmark]
\ExplSyntaxOn
  % Just a set of booleans for testing
  \bool_new:N \l__mytest_tmpa_bool
  \bool_new:N \l__mytest_tmpb_bool
  \bool_new:N \l__mytest_tmpc_bool
  \cs_new:Npn \mytest_show_bools:n #1
    { \underline{#1:}\par
      \bool_if:NTF \l__mytest_tmpa_bool {{\color{red}a~true}}{a~false}  ~-~ 
      \bool_if:NTF \l__mytest_tmpb_bool {{\color{red}b~true}}{b~false}  ~-~
      \bool_if:NTF \l__mytest_tmpc_bool {{\color{red}c~true}}{c~false}  \par
    }
    
  \groupmark_new:n {myMarkA}
  \groupmark_new:n {myMarkB}
\ExplSyntaxOff
\end{codestore}

\tscode*[groupmark]{grpmark}
\tsexec{grpmark}

\subsection{Trivial Case, Single Mark}
Note that, despite the group level at which the booleans were saved, they are all restored at the same group level, \emph{T3} in the example below.
\begin{codestore}[grpmark]
\ExplSyntaxOn
\group_begin:
  \myMarkA_groupmark:   
  {{  \myMarkA_aftergroup:N \bool_set_true:N
      \myMarkA_aftergroup:N \l__mytest_tmpa_bool
    {
      \myMarkB_groupmark:  %dummy, not used...
     {{ \myMarkA_aftergroup:N \bool_set_true:N
        \myMarkA_aftergroup:N \l__mytest_tmpb_bool
        \mytest_show_bools:n {T1}   
     }}
      \mytest_show_bools:n {T2}   
    }
  }}
  \mytest_show_bools:n {T3}
\group_end:
\ExplSyntaxOff
\end{codestore}

\tsdemo[groupmark]{grpmark}[2]

\subsection{Multiple Marks, Single  Command Set}
Note that !:{\myMarkA_groupmark:} is called twice in the example below, effectively defining two, nested, restoring points.
\begin{codestore}[grpmark]
\ExplSyntaxOn
\group_begin:
  \myMarkA_groupmark:   
  {{  \myMarkA_aftergroup:N \bool_set_true:N
      \myMarkA_aftergroup:N \l__mytest_tmpa_bool
    {
      \myMarkA_groupmark:  %second call !
     {{ \myMarkA_aftergroup:N \bool_set_true:N
        \myMarkA_aftergroup:N \l__mytest_tmpb_bool
        \mytest_show_bools:n {T1}   
     }}
      \mytest_show_bools:n {T2}   
    }
  }}
  \mytest_show_bools:n {T3}
\group_end:
\ExplSyntaxOff
\end{codestore}

\tsdemo[groupmark]{grpmark}[3]

\newpage
\subsection{Multiple Command Sets}
This variant is less prone to errors than the previous one, when setting various, nested, restoring points.
\begin{codestore}[grpmark]
\ExplSyntaxOn
\group_begin:
  \myMarkA_groupmark:   
  {{  \myMarkA_aftergroup:N \bool_set_true:N
      \myMarkA_aftergroup:N \l__mytest_tmpa_bool
    {
      \myMarkB_groupmark:  
     {{ \myMarkB_aftergroup:N \bool_set_true:N
        \myMarkB_aftergroup:N \l__mytest_tmpb_bool
        \mytest_show_bools:n {T1}   
     }}
      \mytest_show_bools:n {T2}   
    }
  }}
  \mytest_show_bools:n {T3}
\group_end:
\ExplSyntaxOff
\end{codestore}

\tsdemo[groupmark]{grpmark}[4]


%% if needed
\printbibliography

\end{document} 