From 3879f5443ec624b0f958ce876d5b31234e093755 Mon Sep 17 00:00:00 2001 From: Karl Berry Date: Tue, 13 Jul 2021 20:03:54 +0000 Subject: macrolist (13jul21) git-svn-id: svn://tug.org/texlive/trunk@59919 c570f23f-e606-0410-a88d-b1316a301751 --- .../texmf-dist/tex/latex/macrolist/macrolist.sty | 178 +++++++++++++++++++++ 1 file changed, 178 insertions(+) create mode 100644 Master/texmf-dist/tex/latex/macrolist/macrolist.sty (limited to 'Master/texmf-dist/tex/latex/macrolist') diff --git a/Master/texmf-dist/tex/latex/macrolist/macrolist.sty b/Master/texmf-dist/tex/latex/macrolist/macrolist.sty new file mode 100644 index 00000000000..13f791ddd2c --- /dev/null +++ b/Master/texmf-dist/tex/latex/macrolist/macrolist.sty @@ -0,0 +1,178 @@ +%% +%% This is file `macrolist.sty', +%% generated with the docstrip utility. +%% +%% The original source files were: +%% +%% macrolist.dtx (with options: `package') +%% This work may be distributed and/or modified under +%% the conditions the LaTeX Project Public License (LPPL), +%% either version 1.3 of this license or (at your option) +%% any later version. The latest version of this license +%% can be found in +%% http://www.latex-project.org/lppl.txt +%% and version 1.3 or later is part of all distributions of LaTeX +%% version 2005/12/01 or later. + +\NeedsTeXFormat{LaTeX2e} +\ProvidesPackage{macrolist}[2021/07/09 v1.0.0 Create lists of macros and perform operations on them] + +\RequirePackage{pgffor} + +\newcommand{\newlist}[1]{ + \ifcsname c@macrolist@list@#1\endcsname + \PackageError{macrolist}{The list '#1' is already defined}{} + \else + \newcounter{macrolist@list@#1} + \setcounter{macrolist@list@#1}{0} + \fi +} +\newcommand{\listelement}[2]{% + \macrolist@inbounds{#1}{#2}% + \csname macrolist@list@#1\the\numexpr #2\relax\endcsname% +} +\newcommand{\listadd}[1]{ + \macrolist@exists{#1} + \def\macrolist@currlist{#1} + \macrolist@listadd +} +%% We write \listadd this way such that the optional argument will be positioned correctly +\newcommand{\macrolist@listadd}[2][]{ + \stepcounter{macrolist@list@\macrolist@currlist} + + \if\relax\detokenize{#1}\relax + \expandafter\def\csname macrolist@list@\macrolist@currlist\listsize{\macrolist@currlist}\endcsname{#2} + \else + \expandafter\ifnum\csname themacrolist@list@\macrolist@currlist\endcsname=#1 + \expandafter\def\csname macrolist@list@\macrolist@currlist\listsize{\macrolist@currlist}\endcsname{#2} + \else + \macrolist@inbounds{\macrolist@currlist}{#1} + \foreach \macrolist@index in {\listsize{\macrolist@currlist}, ...,\the\numexpr #1+1\relax} { + \global\expandafter\let\csname macrolist@list@\macrolist@currlist\macrolist@index\expandafter\endcsname\csname macrolist@list@\macrolist@currlist\the\numexpr\macrolist@index-1\relax\endcsname + } + \expandafter\def\csname macrolist@list@\macrolist@currlist#1\endcsname{#2} + \fi + \fi +} +\newcommand{\listremove}[2]{ + \macrolist@inbounds{#1}{#2} + + \ifnum\numexpr#2\relax=\listsize{#1} + \else + \foreach \macrolist@index in {#2, ..., \the\numexpr\listsize{#1}-1\relax} { + \global\expandafter\let\csname macrolist@list@#1\macrolist@index\expandafter\endcsname\csname macrolist@list@#1\the\numexpr\macrolist@index+1\endcsname + } + \fi + + \expandafter\let\csname macrolist@list@#1\listsize{#1}\endcsname\relax + \addtocounter{macrolist@list@#1}{-1} +} +\newcommand{\listremovelast}[1]{ + \macrolist@exists{#1} + \expandafter\let\csname macrolist@list@#1\listsize{#1}\endcsname\relax + \addtocounter{macrolist@list@#1}{-1} +} +\newcommand{\listclear}[2]{ + \macrolist@inbounds{#1}{#2} + + \foreach \macrolist@index in {1, ..., \listsize{#1}} { + \expandafter\let\csname \macrolist@list@#1\macrolist@index\endcsname\relax + } + + \setcounter{macrolist@list@#1}{0} +} +\newcommand*{\listsize}[1]{% + \macrolist@exists{#1}% + \csname themacrolist@list@#1\endcsname +} +\newcommand{\listforeach}[2] +{ + \def\macrolist@foreachstart{0} % Reset + % This is used to make optional arguments line up correctly + + \def\macrolist@start{1} + \def\macrolist@end{\listsize{#1}} + \def\macrolist@listname{#1} + \def\macrolist@element{#2} + \macrolist@listforeachi +} + +\newcommand{\macrolist@listforeachi}[1][]{ + \if\relax\detokenize{#1}\relax + \else + \def\macrolist@start{#1} + \def\macrolist@foreachstart{1} + \fi + \macrolist@listforeachii +} + +\newcommand{\macrolist@listforeachii}[1][]{ + \if\relax\detokenize{#1}\relax + \ifnum\macrolist@foreachstart=1 + \PackageError{macrolist}{You must either pass in both a starting and ending position or neither}{} + \fi + \else + \def\macrolist@end{#1} + \fi + \macrolist@listforeachaction +} + +\newcommand{\macrolist@listforeachaction}[1]{ + + \macrolist@exists{\macrolist@listname} + + \ifnum\numexpr\macrolist@start\relax>\listsize{\macrolist@listname}% + \PackageError{macrolist}{The starting index of the loop is out of the bounds of list '\macrolist@listname'}{} + \fi + + \ifnum\numexpr\macrolist@end\relax>\listsize{\macrolist@listname} + \PackageError{macrolist}{The ending index of the loop is out of the bounds of list '\macrolist@listname'}{} + \fi + + \foreach \macrolist@index in {\the\numexpr\macrolist@start\relax, ..., \the\numexpr\macrolist@end\relax} {% + \expandafter\expandafter\expandafter\let\expandafter\expandafter\macrolist@element\csname macrolist@list@\macrolist@listname\macrolist@index\endcsname + #1% + }% +} +\newcommand{\listjoin}[2]{% + \ifnum\listsize{#1}>1 + \listforeach{#1}{\macrolist@joinelement}[1][\listsize{#1}-1]{\macrolist@joinelement#2}% + \fi + \ifnum\listsize{#1}>0 + \listelement{#1}{\listsize{#1}}% + \fi +} +%% List: Some text +%% List: Some text, \macro +%% Prints out "Some text" +%% List: Element inserted into beginning, Some text, \macro +%% List: Some text, \macro +%% We're printing out \textbf{Some text}. We're printing out \textbf{\macro}. +%% Some text, \macro +\newcommand*{\macrolist@exists}[1]{% + \ifcsname c@macrolist@list@#1\endcsname + \else + \PackageError{macrolist} + {The first argument is not a defined list} + {Make sure you have defined the list before trying to operate on it.} + \fi +} +\newcommand*{\macrolist@inbounds}[2]{% + \macrolist@exists{#1}% + % + \if\relax\detokenize{#2} + \PackageError{macrolist} + {No number has been passed into the second argument of your command + }{Pass in a number to the second argument of your command.} + \fi + % + \ifnum\numexpr#2 \relax>\listsize{#1} + \PackageError{macrolist} + {Index out of bounds} + {The number you have passed in to the second argument of your command\MessageBreak + is out of the bounds of list '#1'.} + \fi +} +\endinput +%% +%% End of file `macrolist.sty'. -- cgit v1.2.3