[git] main @ 78d452f 2024-07-18 V3.24.4
latexindent.pl
Version
3.24.4
Chris Hughes
*
2024-07-18
latexindent.pl is a Perl script that indents .tex (and other) files according to an indentation
scheme that the user can modify to suit their taste. Environments, including those with align-
ment delimiters (such as tabular), and commands, including those that can split braces and
brackets across lines, are usually handled correctly by the script. Options for verbatim-like envi-
ronments and commands, together with indentation after headings (such as chapter, section,
etc) are also available. The script also has the ability to modify line breaks, and to add comment
symbols and blank lines; furthermore, it permits string or regex-based substitutions. All user
options are customisable via the switches and the YAML interface.
tl;dr, a quick start guide is given in Section 1.3 on page 5.
Contents
1 Introduction 5
1.1 Thanks . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 5
1.2 License . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 5
1.3 Quick start . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 5
1.4 Required perl modules . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 11
1.5 About this documentation . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 11
1.6 A word about regular expressions . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 12
2 Demonstration: before and after 13
3 How to use the script 14
3.1 Requirements . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 14
3.1.1 Perl users . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 14
3.1.2 Windows users without perl . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 14
3.1.3 Ubuntu Linux users without perl . . . . . . . . . . . . . . . . . . . . . . . . . . . . 14
3.1.4 macOS users without perl . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 14
3.1.5 conda users . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 14
*
and contributors! See Section 11.5 on page 155. For all communication, please visit [36].
[git] main @ 78d452f 2024-07-18 V3.24.4
CONTENTS 2
3.1.6 docker users . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 14
3.2 From the command line . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 15
3.3 From arara . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 21
3.4 Summary of exit codes . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 21
4 indentconfig.yaml, local settings and the -y switch 23
4.1 indentconfig.yaml and .indentconfig.yaml . . . . . . . . . . . . . . . . . . . . . . . . . . . 23
4.2 localSettings.yaml and friends . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 24
4.3 The -y|yaml switch . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 25
4.4 Settings load order . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 25
5 defaultSettings.yaml 27
5.1 Backup and log file preferences . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 27
5.2 Verbatim code blocks . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 29
5.3 filecontents and preamble . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 32
5.4 Indentation and horizontal space . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 33
5.5 Aligning at delimiters . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 33
5.5.1 lookForAlignDelims: spacesBeforeAmpersand . . . . . . . . . . . . . . . . . . . . 38
5.5.2 lookForAlignDelims: alignFinalDoubleBackSlash . . . . . . . . . . . . . . . . . . 40
5.5.3 lookForAlignDelims: the dontMeasure feature . . . . . . . . . . . . . . . . . . . . 41
5.5.4 lookForAlignDelims: the delimiterRegEx and delimiterJustification feature . . 43
5.5.5 lookForAlignDelims: lookForChildCodeBlocks . . . . . . . . . . . . . . . . . . . . 45
5.5.6 lookForAlignDelims: alignContentAfterDoubleBackSlash . . . . . . . . . . . . . 45
5.6 Indent after items, specials and headings . . . . . . . . . . . . . . . . . . . . . . . . . . . 46
5.7 The code blocks known latexindent.pl . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 55
5.8 noAdditionalIndent and indentRules . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 55
5.8.1 Environments and their arguments . . . . . . . . . . . . . . . . . . . . . . . . . . . 57
5.8.2 Environments with items . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 64
5.8.3 Commands with arguments . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 65
5.8.4 ifelsefi code blocks . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 67
5.8.5 specialBeginEnd code blocks . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 68
5.8.6 afterHeading code blocks . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 69
5.8.7 The remaining code blocks . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 71
5.8.7.1 keyEqualsValuesBracesBrackets . . . . . . . . . . . . . . . . . . . . . . . 71
5.8.7.2 namedGroupingBracesBrackets . . . . . . . . . . . . . . . . . . . . . . . 72
5.8.7.3 UnNamedGroupingBracesBrackets . . . . . . . . . . . . . . . . . . . . . 72
5.8.7.4 filecontents . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 73
5.8.8 Summary . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 73
5.9 Commands and the strings between their arguments . . . . . . . . . . . . . . . . . . . . 73
6 The -m (modifylinebreaks) switch 79
6.1 Text Wrapping . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 81
6.1.1 Text wrap: overview . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 81
6.1.2 Text wrap: simple examples . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 82
6.1.3 Text wrap: blocksFollow examples . . . . . . . . . . . . . . . . . . . . . . . . . . 83
6.1.4 Text wrap: blocksBeginWith examples . . . . . . . . . . . . . . . . . . . . . . . 87
6.1.5 Text wrap: blocksEndBefore examples . . . . . . . . . . . . . . . . . . . . . . . 89
6.1.6 Text wrap: trailing comments and spaces . . . . . . . . . . . . . . . . . . . . . . . 90
6.1.7 Text wrap: when before/after . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 91
6.1.8 Text wrap: wrapping comments . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 93
6.1.9 Text wrap: huge, tabstop and separator . . . . . . . . . . . . . . . . . . . . . . . . 94
6.2 oneSentencePerLine: modifying line breaks for sentences . . . . . . . . . . . . . . . . . 95
6.2.1 oneSentencePerLine: overview . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 96
6.2.2 oneSentencePerLine: sentencesFollow . . . . . . . . . . . . . . . . . . . . . . . . . 98
6.2.3 oneSentencePerLine: sentencesBeginWith . . . . . . . . . . . . . . . . . . . . . . 99
6.2.4 oneSentencePerLine: sentencesEndWith . . . . . . . . . . . . . . . . . . . . . . . 100
6.2.5 oneSentencePerLine: sentencesDoNOTcontain . . . . . . . . . . . . . . . . . . . . 102
6.2.6 Features of the oneSentencePerLine routine . . . . . . . . . . . . . . . . . . . . . 103
[git] main @ 78d452f 2024-07-18 V3.24.4
CONTENTS 3
6.2.7 oneSentencePerLine: text wrapping and indenting sentences . . . . . . . . . . . 104
6.2.8 oneSentencePerLine: text wrapping and indenting sentences, when before/after107
6.2.9 oneSentencePerLine: text wrapping sentences and comments . . . . . . . . . . 108
6.3 Poly-switches . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 108
6.3.1 Poly-switches for environments . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 109
6.3.1.1 Adding line breaks: BeginStartsOnOwnLine and BodyStartsOnOwn-
Line . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 109
6.3.1.2 Adding line breaks: EndStartsOnOwnLine and EndFinishesWithLine-
Break . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 111
6.3.1.3 poly-switches 1, 2, and 3 only add line breaks when necessary . . . . 113
6.3.1.4 Removing line breaks (poly-switches set to 1) . . . . . . . . . . . . . 114
6.3.1.5 About trailing horizontal space . . . . . . . . . . . . . . . . . . . . . . . 116
6.3.1.6 poly-switch line break removal and blank lines . . . . . . . . . . . . . 116
6.3.2 Poly-switches for double backslash . . . . . . . . . . . . . . . . . . . . . . . . . . . 118
6.3.2.1 Double backslash starts on own line . . . . . . . . . . . . . . . . . . . . 118
6.3.2.2 Double backslash finishes with line break . . . . . . . . . . . . . . . . . 119
6.3.2.3 Double backslash poly-switches for specialBeginEnd . . . . . . . . . . 120
6.3.2.4 Double backslash poly-switches for optional and mandatory arguments120
6.3.2.5 Double backslash optional square brackets . . . . . . . . . . . . . . . . 121
6.3.3 Poly-switches for other code blocks . . . . . . . . . . . . . . . . . . . . . . . . . . . 122
6.3.4 Partnering BodyStartsOnOwnLine with argument-based poly-switches . . . . . 124
6.3.5 Conflicting poly-switches: sequential code blocks . . . . . . . . . . . . . . . . . . 125
6.3.6 Conflicting poly-switches: nested code blocks . . . . . . . . . . . . . . . . . . . . 126
7 The -r, -rv and -rr switches 129
7.1 Introduction to replacements . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 129
7.2 The two types of replacements . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 130
7.3 Examples of replacements . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 130
8 The –lines switch 138
9 Fine tuning 144
10 Conclusions and known limitations 153
11 References 154
11.1 perl-related links . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 154
11.2 conda-related links . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 154
11.3 VScode-related links . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 154
11.4 Other links . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 154
11.5 Contributors (in chronological order) . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 155
A Required Perl modules 157
A.1 Module installer script . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 157
A.2 Manually installing modules . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 158
A.2.1 Linux . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 158
A.2.1.1 perlbrew . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 158
A.2.1.2 Ubuntu/Debian . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 158
A.2.1.3 Ubuntu: using the texlive from apt-get . . . . . . . . . . . . . . . . . . 158
A.2.1.4 Ubuntu: users without perl . . . . . . . . . . . . . . . . . . . . . . . . . . 158
A.2.1.5 Arch-based distributions . . . . . . . . . . . . . . . . . . . . . . . . . . . 158
A.2.1.6 Alpine . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 159
A.2.2 Mac . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 159
A.2.3 Windows . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 159
A.3 The GCString switch . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 160
B Updating the path variable 161
B.1 Add to path for Linux . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 161
B.2 Add to path for Windows . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 161
[git] main @ 78d452f 2024-07-18 V3.24.4
CONTENTS 4
C Batches of files 163
C.1 location of indent.log . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 163
C.2 interaction with -w switch . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 163
C.3 interaction with -o switch . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 163
C.4 interaction with lines switch . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 163
C.5 interaction with check switches . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 164
C.6 when a file does not exist . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 164
D latexindent-yaml-schema.json 165
D.1 VSCode demonstration . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 165
E Using conda 166
E.1 Sample conda installation on Ubuntu . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 166
F Using docker 167
F.1 Sample docker installation on Ubuntu . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 167
F.2 How to format on Docker . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 167
G pre-commit 168
G.1 Sample pre-commit installation on Ubuntu . . . . . . . . . . . . . . . . . . . . . . . . . . 168
G.2 pre-commit defaults . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 168
G.3 pre-commit using CPAN . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 169
G.4 pre-commit using conda . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 169
G.5 pre-commit using docker . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 170
G.6 pre-commit example using -l, -m switches . . . . . . . . . . . . . . . . . . . . . . . . . . . 170
H indentconfig options 172
H.1 Why to change the configuration location . . . . . . . . . . . . . . . . . . . . . . . . . . . 172
H.2 How to change the configuration location . . . . . . . . . . . . . . . . . . . . . . . . . . . 173
H.2.1 Linux . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 173
H.2.2 Windows . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 173
H.2.3 Mac . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 173
I paths demonstration 174
J logFilePreferences 177
K Encoding 178
L dos2unix linebreak adjustment 179
M Differences from Version 2.2 to 3.0 180
List of listings 182
Index 189
[git] main @ 78d452f 2024-07-18 V3.24.4
SECTION 1
Introduction
1.1 Thanks
I first created latexindent.pl to help me format chapter files in a big project. After I blogged about
it on the T
E
X stack exchange [29] I received some positive feedback and follow-up feature requests.
A big thank you to Harish Kumar [2] who helped to develop and test the initial versions of the script.
The YAML-based interface of latexindent.pl was inspired by the wonderful arara tool; any simi-
larities are deliberate, and I hope that it is perceived as the compliment that it is. Thank you to Paulo
Cereda and the team for releasing this awesome tool; I initially worried that I was going to have to
make a GUI for latexindent.pl, but the release of arara has meant there is no need.
There have been several contributors to the project so far (and hopefully more in the future!); thank
you very much to the people detailed in Section 11.5 on page 155 for their valued contributions, and
thank you to those who report bugs and request features at [36].
1.2 License
latexindent.pl is free and open source, and it always will be; it is released under the GNU General
Public License v3.0.
Before you start using it on any important files, bear in mind that latexindent.pl has the option
to overwrite your .tex files. It will always make at least one backup (you can choose how many
it makes, see page 28) but you should still be careful when using it. The script has been tested on
many files, but there are some known limitations (see Section 10). You, the user, are responsible for
ensuring that you maintain backups of your files before running latexindent.pl on them. I think
it is important at this stage to restate an important part of the license here:
This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
PURPOSE. See the GNU General Public License for more details.
There is certainly no malicious intent in releasing this script, and I do hope that it works as you expect
it to; if it does not, please first of all make sure that you have the correct settings, and then feel free
to let me know at [36] with a complete minimum working example as I would like to improve the
code as much as possible.
Warning!
Before you try the script on anything important (like your thesis), test it out on the
sample files in the test-case directory [36].
If you have used any version 2.* of latexindent.pl, there are a few changes to the interface; see
appendix M on page 180 and the comments throughout this document for details.
1.3 Quick start
When latexindent.pl reads and writes files, the files are read and written in UTF-8 format by
default. That is to say, the encoding format for tex and yaml files needs to be in UTF-8 format.
If you’d like to get started with latexindent.pl then simply type
cmh:$ latexindent.pl myfile.tex
[git] main @ 78d452f 2024-07-18 V3.24.4
1.3 Quick start 6
from the command line.
We give an introduction to latexindent.pl using Listing 1; there is no explanation in this section,
which is deliberate for a quick start. The rest of the manual is more verbose.
LISTING 1: quick-start.tex
\documentclass{article}
\usepackage[
inner=2.5cm,
]{geometry}
\begin{document}
A quick start
demonstration for latexindent.pl.
\begin{myenv}
The body of environments and
other code blocks
receive indentation.
\end{myenv}
\end{document}
Running
cmh:$ latexindent.pl quick-start.tex
gives Listing 2.
LISTING 2: quick-start-default.tex
\documentclass{article}
\usepackage[
inner=2.5cm,
]{geometry}
\begin{document}
A quick start
demonstration for latexindent.pl.
\begin{myenv}
The body of environments and
other code blocks
receive indentation.
\end{myenv}
\end{document}
example 1
Running
cmh:$ latexindent.pl -l quick-start1.yaml quick-start.tex
gives Listing 3.
[git] main @ 78d452f 2024-07-18 V3.24.4
1.3 Quick start 7
LISTING 3: quick-start-mod1.tex
\documentclass{article}
\usepackage[
inner=2.5cm,
]{geometry}
\begin{document}
A␣quick␣start
demonstration␣for␣latexindent.pl.
\begin{myenv}
␣The␣body␣of␣environments␣and
␣other␣code␣blocks
␣receive␣indentation.
\end{myenv}
\end{document}
LISTING 4: quick-start1.yaml
defaultIndent: " "
See Section 5.4.
example 2
Running
cmh:$ latexindent.pl -l quick-start2.yaml quick-start.tex
gives Listing 5.
LISTING 5: quick-start-mod2.tex
\documentclass{article}
\usepackage[
inner=2.5cm,
]{geometry}
\begin{document}
A␣quick␣start
demonstration␣for␣latexindent.pl.
\begin{myenv}
␣␣␣The␣body␣of␣environments␣and
␣␣␣other␣code␣blocks
␣␣␣receive␣indentation.
\end{myenv}
\end{document}
LISTING 6: quick-start2.yaml
indentRules:
myenv: " "
See Section 5.8.
example 3
Running
cmh:$ latexindent.pl -l quick-start3.yaml quick-start.tex
gives Listing 7.
[git] main @ 78d452f 2024-07-18 V3.24.4
1.3 Quick start 8
LISTING 7: quick-start-mod3.tex
\documentclass{article}
\usepackage[
inner=2.5cm,
]{geometry}
\begin{document}
A quick start
demonstration for latexindent.pl.
\begin{myenv}
The body of environments and
other code blocks
receive indentation.
\end{myenv}
\end{document}
LISTING 8: quick-start3.yaml
noAdditionalIndent:
myenv: 1
See Section 5.8.
example 4
Running
cmh:$ latexindent.pl -m -l quick-start4.yaml quick-start.tex
gives Listing 9.
LISTING 9: quick-start-mod4.tex
\documentclass{article}
\usepackage[
inner=2.5cm,
]{geometry}
\begin{document}
A quick start
demonstration for latexindent.pl.
\begin{myenv}
The body of environments and
other code blocks
receive indentation.
\end{myenv}
\end{document}
-m
LISTING 10: quick-start4.yaml
modifyLineBreaks:
textWrapOptions:
columns: 20
Full details of text wrapping in Section 6.1.
example 5
Running
cmh:$ latexindent.pl -m -l quick-start5.yaml quick-start.tex
gives Listing 11.
[git] main @ 78d452f 2024-07-18 V3.24.4
1.3 Quick start 9
LISTING 11: quick-start-mod5.tex
\documentclass{article}
\usepackage[
inner=2.5cm,
]{geometry}
\begin{document}
A quick start
demonstration for latexindent.pl.
\begin{myenv}
The body of
environments and
other code blocks
receive
indentation.
\end{myenv}
\end{document}
-m
LISTING 12: quick-start5.yaml
modifyLineBreaks:
textWrapOptions:
columns: 20
blocksFollow:
other: ’\\begin\{myenv\}’
Full details of text wrapping in Section 6.1.
example 6
Running
cmh:$ latexindent.pl -m -l quick-start6.yaml quick-start.tex
gives Listing 13.
LISTING 13: quick-start-mod6.tex
\documentclass{article}
\usepackage[
inner=2.5cm,
]{geometry}\begin{document}
A quick start
demonstration for
latexindent.pl.\begin{myenv}
The body of environments and
other code blocks
receive indentation.
\end{myenv}
\end{document}
-m
LISTING 14: quick-start6.yaml
modifyLineBreaks:
environments:
BeginStartsOnOwnLine: -1
This is an example of a poly-switch; full details of poly-switches are covered in Section 6.3.
example 7
Running
cmh:$ latexindent.pl -m -l quick-start7.yaml quick-start.tex
gives Listing 15.
[git] main @ 78d452f 2024-07-18 V3.24.4
1.3 Quick start 10
LISTING 15: quick-start-mod7.tex
\documentclass{article}
\usepackage[
inner=2.5cm,
]{geometry}
\begin{document}
A quick start
demonstration for latexindent.pl.
\begin{myenv}
The body of environments and
other code blocks
receive
indentation.\end{myenv}\end{document}
-m
LISTING 16: quick-start7.yaml
modifyLineBreaks:
environments:
EndStartsOnOwnLine: -1
Full details of poly-switches are covered in Section 6.3.
example 8
Running
cmh:$ latexindent.pl -l quick-start8.yaml quick-start.tex
gives Listing 17; note that the preamble has been indented.
LISTING 17: quick-start-mod8.tex
\documentclass{article}
\usepackage[
inner=2.5cm,
]{geometry}
\begin{document}
A quick start
demonstration for latexindent.pl.
\begin{myenv}
The body of environments and
other code blocks
receive indentation.
\end{myenv}
\end{document}
LISTING 18: quick-start8.yaml
indentPreamble: 1
See Section 5.3.
example 9
Running
cmh:$ latexindent.pl -l quick-start9.yaml quick-start.tex
gives Listing 19.
[git] main @ 78d452f 2024-07-18 V3.24.4
1.4 Required perl modules 11
LISTING 19: quick-start-mod9.tex
\documentclass{article}
\usepackage[
inner=2.5cm,
]{geometry}
\begin{document}
A quick start
demonstration for latexindent.pl.
\begin{myenv}
The body of environments and
other code blocks
receive indentation.
\end{myenv}
\end{document}
LISTING 20: quick-start9.yaml
noAdditionalIndent:
document: 0
See Section 5.8.
1.4 Required perl modules
If you receive an error message such as that given in Listing 21, then you need to install the missing
perl modules.
LISTING 21: Possible error messages
Can’t␣locate␣File/HomeDir.pm␣in␣@INC␣(@INC␣contains:␣
/Library/Perl/5.12/darwin-thread-multi-2level␣/Library/Perl/5.12␣
/Network/Library/Perl/5.12/darwin-thread-multi-2level␣
/Network/Library/Perl/5.12␣
/Library/Perl/Updates/5.12.4/darwin-thread-multi-2level␣
/Library/Perl/Updates/5.12.4␣
/System/Library/Perl/5.12/darwin-thread-multi-2level␣/System/Library/Perl/5.12␣
/System/Library/Perl/Extras/5.12/darwin-thread-multi-2level␣
/System/Library/Perl/Extras/5.12␣.)␣at␣helloworld.pl␣line␣10.
BEGIN␣failed--compilation␣aborted␣at␣helloworld.pl␣line␣10.
latexindent.pl ships with a script to help with this process; if you run the following script, you
should be prompted to install the appropriate modules.
cmh:$ perl latexindent-module-installer.pl
You might also like to see https://stackoverflow.com/questions/19590042/error-cant-locate-file-homedir-
pm-in-inc, for example, as well as appendix A on page 157.
1.5 About this documentation
As you read through this documentation, you will see many listings; in this version of the documen-
tation, there are a total of 629. This may seem a lot, but I deem it necessary in presenting the various
different options of latexindent.pl and the associated output that they are capable of producing.
The different listings are presented using different styles:
LISTING 22: demo-tex.tex
demonstration .tex file
This type of listing is a .tex file.
LISTING 23:
fileExtensionPreference
47 fileExtensionPreference:
48 .tex: 1
49 .sty: 2
50 .cls: 3
51 .bib: 4
This type of listing is a .yaml file; when
you see line numbers given (as here) it
means that the snippet is taken directly from
defaultSettings.yaml, discussed in detail in
Section 5 on page 27.
[git] main @ 78d452f 2024-07-18 V3.24.4
1.6 A word about regular expressions 12
-m
LISTING 24: modifyLineBreaks
502 modifyLineBreaks:
503 preserveBlankLines: 1 # 0/1
504 condenseMultipleBlankLinesInto: 1 # 0/1
This type of listing is a .yaml file, but it will only
be relevant when the -m switch is active; see Sec-
tion 6 on page 79 for more details.
-r
LISTING 25: replacements
622 replacements:
623 - amalgamate: 1
624 - this: latexindent.pl
625 that: pl.latexindent
626 lookForThis: 0
627 when: before
This type of listing is a .yaml file, but it will only
be relevant when the -r switch is active; see Sec-
tion 7 on page 129 for more details.
You will occasionally see dates shown in the margin (for example, next to this paragraph!)
N: 2017-06-25
which
detail the date of the version in which the feature was implemented; the ‘N’ stands for ‘new as of the
date shown’ and ‘U’ stands for ‘updated as of the date shown’. If you see , it means that the feature
is either new (N) or updated (U) as of the release of the current version; if you see attached to
a listing, then it means that listing is new (N) or updated (U) as of the current version. If you have
not read this document before (and even if you have!), then you can ignore every occurrence of the
; they are simply there to highlight new and updated features. The new and updated features in
this documentation (V3.24.4) are on the following pages:
paths within local YAML settings (N) · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 24
nested paths demonstration (N) · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 174
1.6 A word about regular expressions
As you read this documentation, you may encounter the term regular expressions. I’ve tried to write
this documentation in such a way so as to allow you to engage with them or not, as you prefer. This
documentation is not designed to be a guide to regular expressions, and if you’d like to read about
them, I recommend [35].
[git] main @ 78d452f 2024-07-18 V3.24.4
SECTION 2
Demonstration: before and after
Let’s give a demonstration of some before and after code – after all, you probably won’t want to try
the script if you don’t much like the results. You might also like to watch the video demonstration I
made on youtube [49]
As you look at Listings 26 to 31, remember that latexindent.pl is just following its rules, and
there is nothing particular about these code snippets. All of the rules can be modified so that you
can personalise your indentation scheme.
In each of the samples given in Listings 26 to 31 the ‘before’ case is a ‘worst case scenario’ with no
effort to make indentation. The ‘after’ result would be the same, regardless of the leading white
space at the beginning of each line which is stripped by latexindent.pl (unless a verbatim-like
environment or noIndentBlock is specified – more on this in Section 5).
LISTING 26: filecontents1.tex
\begin{filecontents}{mybib.bib}
@online{strawberryperl,
title="Strawberry Perl",
url="http://strawberryperl.com/"}
@online{cmhblog,
title="A Perl script ...
url="...
}
\end{filecontents}
LISTING 27: filecontents1.tex default output
\begin{filecontents}{mybib.bib}
@online{strawberryperl,
title="Strawberry Perl",
url="http://strawberryperl.com/"}
@online{cmhblog,
title="A Perl script ...
url="...
}
\end{filecontents}
LISTING 28: tikzset.tex
\tikzset{
shrink inner sep/.code={
\pgfkeysgetvalue...
\pgfkeysgetvalue...
}
}
LISTING 29: tikzset.tex default output
\tikzset{
shrink inner sep/.code={
\pgfkeysgetvalue...
\pgfkeysgetvalue...
}
}
LISTING 30: pstricks.tex
\def\Picture#1{%
\def\stripH{#1}%
\begin{pspicture}[showgrid}
\psforeach{\row}{%
{{3,2.8,2.7,3,3.1}},%
{2.8,1,1.2,2,3},%
...
}{%
\expandafter...
}
\end{pspicture}}
LISTING 31: pstricks.tex default output
\def\Picture#1{%
\def\stripH{#1}%
\begin{pspicture}[showgrid}
\psforeach{\row}{%
{{3,2.8,2.7,3,3.1}},%
{2.8,1,1.2,2,3},%
...
}{%
\expandafter...
}
\end{pspicture}}
[git] main @ 78d452f 2024-07-18 V3.24.4
SECTION 3
How to use the script
latexindent.pl ships as part of the T
E
XLive distribution for Linux and Mac users; latexindent.exe
ships as part of the T
E
XLive for Windows users. These files are also available from github [36] should
you wish to use them without a T
E
X distribution; in this case, you may like to read appendix B on
page 161 which details how the path variable can be updated.
In what follows, we will always refer to latexindent.pl, but depending on your operating system
and preference, you might substitute latexindent.exe or simply latexindent.
There are two ways to use latexindent.pl: from the command line, and using arara; we discuss
these in Section 3.2 and Section 3.3 respectively. We will discuss how to change the settings and
behaviour of the script in Section 5 on page 27.
3.1 Requirements
3.1.1 Perl users
Perl users will need a few standard Perl modules – see appendix A on page 157 for details;
N: 2018-01-13
in partic-
ular, note that a module installer helper script is shipped with latexindent.pl.
3.1.2 Windows users without perl
latexindent.pl ships with latexindent.exe for Windows users, so that you can use the script
with or without a Perl distribution.
latexindent.exe is available from [36].
MiKTeX users on Windows may like to see [39] for details of how to use latexindent.exe without
a Perl installation.
3.1.3 Ubuntu Linux users without perl
latexindent.pl ships with latexindent-linux for Ubuntu Linux users, so that you can use the
script with or without a Perl distribution.
latexindent-linux is available from [36].
N: 2022-10-30
3.1.4 macOS users without perl
latexindent.pl ships with latexindent-macos for macOS users, so that you can use the script
with or without a Perl distribution.
latexindent-macOS is available from [36].
N: 2022-10-30
3.1.5 conda users
Users of conda should see the details given in appendix E.
3.1.6 docker users
Users of docker should see the details given in appendix F.
[git] main @ 78d452f 2024-07-18 V3.24.4
3.2 From the command line 15
3.2 From the command line
latexindent.pl has a number of different switches/flags/options, which can be combined in any
way that you like, either in short or long form as detailed below. latexindent.pl produces a .log
file, indent.log, every time it is run; the name of the log file can be customised, but we will refer
to the log file as indent.log throughout this document. There is a base of information that is
written to indent.log, but other additional information will be written depending on which of the
following options are used.
When using latexindent.pl in different ways on different systems, the range of characters sup-
ported by its switches/flags/options may vary. We discuss these in Section appendix K.
-v, –version
N: 2017-06-25
cmh:$ latexindent.pl -v
cmh:$ latexindent.pl --version
This will output only the version number to the terminal.
-vv, –vversion
N: 2022-01-08
cmh:$ latexindent.pl -vv
cmh:$ latexindent.pl --vversion
This will output verbose version details to the terminal, including the location of latexindent.pl
and defaultSettings.yaml.
-h, –help
cmh:$ latexindent.pl -h
cmh:$ latexindent.pl --help
As above this will output a welcome message to the terminal, including the version number and
available options.
cmh:$ latexindent.pl myfile.tex
This will operate on myfile.tex, but will simply output to your terminal; myfile.tex will not be
changed by latexindent.pl in any way using this command.
You can
N: 2022-03-25
instruct latexindent.pl to operate on multiple (batches) of files, for example
cmh:$ latexindent.pl myfile1.tex myfile2.tex
Full details are given in appendix C on page 163.
-w, –overwrite
cmh:$ latexindent.pl -w myfile.tex
cmh:$ latexindent.pl --overwrite myfile.tex
cmh:$ latexindent.pl myfile.tex --overwrite
This will overwrite myfile.tex, but it will make a copy of myfile.tex first. You can control the
name of the extension (default is .bak), and how many different backups are made – more on this
in Section 5, and in particular see backupExtension and onlyOneBackUp.
Note that if latexindent.pl can not create the backup, then it will exit without touching your
original file; an error message will be given asking you to check the permissions of the backup file.
[git] main @ 78d452f 2024-07-18 V3.24.4
3.2 From the command line 16
-wd, –overwriteIfDifferent
N: 2022-03-25
cmh:$ latexindent.pl -wd myfile.tex
cmh:$ latexindent.pl --overwriteIfDifferent myfile.tex
cmh:$ latexindent.pl myfile.tex --overwriteIfDifferent
This will overwrite myfile.tex but only if the indented text is different from the original. If the
indented text is not different from the original, then myfile.tex will not be overwritten.
All other details from the -w switch are relevant here. If you call latexindent.pl with both the
-wd and the -w switch, then the -w switch will be deactivated and the -wd switch takes priority.
-o=output.tex,–outputfile=output.tex
cmh:$ latexindent.pl -o=output.tex myfile.tex
cmh:$ latexindent.pl myfile.tex -o=output.tex
cmh:$ latexindent.pl --outputfile=output.tex myfile.tex
cmh:$ latexindent.pl --outputfile output.tex myfile.tex
This will indent myfile.tex and output it to output.tex, overwriting it (output.tex) if it already
exists
1
.
Note that if latexindent.pl is called with both the -w and -o switches, then -w will be ignored
and -o will take priority (this seems safer than the other way round). The same is true for the -wd
switch, and the -o switch takes priority over it.
Note that using -o as above is equivalent to using
cmh:$ latexindent.pl myfile.tex > output.tex
You can call the -o switch with the name of the output file without an extension; in
N: 2017-06-25
this case,
latexindent.pl will use the extension from the original file. For example, the following two calls
to latexindent.pl are equivalent:
cmh:$ latexindent.pl myfile.tex -o=output
cmh:$ latexindent.pl myfile.tex -o=output.tex
You can call the -o switch using a + symbol at the beginning; this will
N: 2017-06-25
concatenate the name of the in-
put file and the text given to the -o switch. For example, the following two calls to latexindent.pl
are equivalent:
cmh:$ latexindent.pl myfile.tex -o=+new
cmh:$ latexindent.pl myfile.tex -o=myfilenew.tex
You can call the -o switch using a ++ symbol at the end of the name
N: 2017-06-25
of your output file; this tells
latexindent.pl to search successively for the name of your output file concatenated with 0, 1, . . .
while the name of the output file exists. For example,
cmh:$ latexindent.pl myfile.tex -o=output++
tells latexindent.pl to output to output0.tex, but if it exists then output to output1.tex, and
so on.
Calling latexindent.pl with simply
1
Users of version 2.* should note the subtle change in syntax
[git] main @ 78d452f 2024-07-18 V3.24.4
3.2 From the command line 17
cmh:$ latexindent.pl myfile.tex -o=++
tells it to output to myfile0.tex, but if it exists then output to myfile1.tex and so on.
The + and ++ feature of the -o switch can be combined; for example, calling
cmh:$ latexindent.pl myfile.tex -o=+out++
tells latexindent.pl to output to myfileout0.tex, but if it exists, then try myfileout1.tex, and
so on.
There is no need to specify a file extension when using the ++ feature, but if you wish to, then you
should include it after the ++ symbols, for example
cmh:$ latexindent.pl myfile.tex -o=+out++.tex
See appendix M on page 180 for details of how the interface has changed from Version 2.2 to Version
3.0 for this flag.
-s, –silent
cmh:$ latexindent.pl -s myfile.tex
cmh:$ latexindent.pl myfile.tex -s
Silent mode: no output will be given to the terminal.
-t, –trace
cmh:$ latexindent.pl -t myfile.tex
cmh:$ latexindent.pl myfile.tex -t
Tracing mode: verbose output will be given to indent.log. This is useful if latexindent.pl has
made a mistake and you’re trying to find out where and why. You might also be interested in learning
about latexindent.pl’s thought process – if so, this switch is for you, although it should be noted
that, especially for large files, this does affect performance of the script.
-tt, –ttrace
cmh:$ latexindent.pl -tt myfile.tex
cmh:$ latexindent.pl myfile.tex -tt
More detailed tracing mode: this option gives more details to indent.log than the standard trace
option (note that, even more so than with -t, especially for large files, performance of the script will
be affected).
-l, –local[=myyaml.yaml,other.yaml,...]
cmh:$ latexindent.pl -l myfile.tex
cmh:$ latexindent.pl -l=myyaml.yaml myfile.tex
cmh:$ latexindent.pl -l myyaml.yaml myfile.tex
cmh:$ latexindent.pl -l first.yaml,second.yaml,third.yaml myfile.tex
cmh:$ latexindent.pl -l=first.yaml,second.yaml,third.yaml myfile.tex
cmh:$ latexindent.pl myfile.tex -l=first.yaml,second.yaml,third.yaml
latexindent.pl will always load defaultSettings.yaml (rhymes with camel) and if it is called
with the -l switch and it finds localSettings.yaml in the same directory as myfile.tex, then, if
not found, it looks for localSettings.yaml (and friends, see Section 4.2 on page 24) in the current
[git] main @ 78d452f 2024-07-18 V3.24.4
3.2 From the command line 18
working directory, then these
U: 2021-03-14
settings will be added to the indentation scheme. Information will be
given in indent.log on the success or failure of loading localSettings.yaml.
The -l flag can take an optional parameter which details the name (or names separated by com-
mas) of a YAML file(s) that resides in the same directory as myfile.tex; you can use this op-
tion if you would like to load a settings file in the current working directory that is not called
localSettings.yaml.
U: 2017-08-21
In fact, you can specify both relative and absolute paths for your YAML files;
for example
cmh:$ latexindent.pl -l=../../myyaml.yaml myfile.tex
cmh:$ latexindent.pl -l=/home/cmhughes/Desktop/myyaml.yaml myfile.tex
cmh:$ latexindent.pl -l=C:\Users\cmhughes\Desktop\myyaml.yaml myfile.tex
You will find a lot of other explicit demonstrations of how to use the -l switch throughout this
documentation,
You can call the -l switch with a ‘+’ symbol either before or after
N: 2017-06-25
another YAML file; for example:
cmh:$ latexindent.pl -l=+myyaml.yaml myfile.tex
cmh:$ latexindent.pl -l "+␣myyaml.yaml" myfile.tex
cmh:$ latexindent.pl -l=myyaml.yaml+ myfile.tex
which translate, respectively, to
cmh:$ latexindent.pl -l=localSettings.yaml,myyaml.yaml myfile.tex
cmh:$ latexindent.pl -l=localSettings.yaml,myyaml.yaml myfile.tex
cmh:$ latexindent.pl -l=myyaml.yaml,localSettings.yaml myfile.tex
Note that the following is not allowed:
cmh:$ latexindent.pl -l+myyaml.yaml myfile.tex
and
cmh:$ latexindent.pl -l + myyaml.yaml myfile.tex
will only load localSettings.yaml, and myyaml.yaml will be ignored. If you wish to use spaces
between any of the YAML settings, then you must wrap the entire list of YAML files in quotes, as
demonstrated above.
You may also choose to omit the yaml extension, such as
N: 2017-06-25
cmh:$ latexindent.pl -l=localSettings,myyaml myfile.tex
-y, –yaml=yaml settings
cmh:$ latexindent.pl myfile.tex -y="defaultIndent:␣’␣’"
cmh:$ latexindent.pl myfile.tex -y="defaultIndent:␣’␣’,maximumIndentation:’␣’"
cmh:$ latexindent.pl myfile.tex -y="indentRules:␣one:␣’\t\t\t\t’"
cmh:$ latexindent.pl myfile.tex
-y=’modifyLineBreaks:environments:EndStartsOnOwnLine:3’ -m
cmh:$ latexindent.pl myfile.tex
-y=’modifyLineBreaks:environments:one:EndStartsOnOwnLine:3’ -m
You
N: 2017-08-21
can specify YAML settings from the command line using the -y or –yaml switch; sample demon-
strations are given above. Note, in particular, that multiple settings can be specified by separating
[git] main @ 78d452f 2024-07-18 V3.24.4
3.2 From the command line 19
them via commas. There is a further option to use a ; to separate fields, which is demonstrated in
Section 4.3 on page 25.
Any settings specified via this switch will be loaded after any specified using the -l switch. This is
discussed further in Section 4.4 on page 25.
-d, –onlydefault
cmh:$ latexindent.pl -d myfile.tex
Only defaultSettings.yaml: you might like to read Section 5 before using this switch. By de-
fault, latexindent.pl will always search for indentconfig.yaml or .indentconfig.yaml in
your home directory. If you would prefer it not to do so then (instead of deleting or renaming
indentconfig.yaml or .indentconfig.yaml) you can simply call the script with the -d switch;
note that this will also tell the script to ignore localSettings.yaml even if it has been called with
the -l switch; latexindent.pl
U: 2017-08-21
will also ignore any settings specified from the -y switch.
-c, –cruft=<directory>
cmh:$ latexindent.pl -c=/path/to/directory/ myfile.tex
If you wish to have backup files and indent.log written to a directory other than the current working
directory, then you can send these ‘cruft’ files to another directory. Note the use of a trailing forward
slash.
If the cruft directory does not exist, latexindent.pl will attempt to create it.
-g, –logfile=<name of log file>
cmh:$ latexindent.pl -g=other.log myfile.tex
cmh:$ latexindent.pl -g other.log myfile.tex
cmh:$ latexindent.pl --logfile other.log myfile.tex
cmh:$ latexindent.pl myfile.tex -g other.log
By default, latexindent.pl reports information to indent.log, but if you wish to change the name
of this file, simply call the script with your chosen name after the -g switch as demonstrated above.
N: 2021-05-07
If latexindent.pl can not open the log file that you specify, then the script will operate, and no log
file will be produced; this might be helpful to users who wish to specify the following, for example
cmh:$ latexindent.pl -g /dev/null myfile.tex
-sl, –screenlog
cmh:$ latexindent.pl -sl myfile.tex
cmh:$ latexindent.pl -screenlog myfile.tex
Using this
N: 2018-01-13
option tells latexindent.pl to output the log file to the screen, as well as to your chosen
log file.
-m, –modifylinebreaks
cmh:$ latexindent.pl -m myfile.tex
cmh:$ latexindent.pl -modifylinebreaks myfile.tex
One of the most exciting developments in Version 3.0 is the ability to modify line breaks; for full
details see Section 6 on page 79
latexindent.pl can also be called on a file without the file extension, for example
[git] main @ 78d452f 2024-07-18 V3.24.4
3.2 From the command line 20
cmh:$ latexindent.pl myfile
and in which case, you can specify the order in which extensions are searched for; see Listing 35 on
page 27 for full details.
STDIN
cmh:$ cat myfile.tex | latexindent.pl
cmh:$ cat myfile.tex | latexindent.pl -
latexindent.pl will
N: 2018-01-13
allow input from STDIN, which means that you can pipe output from other
commands directly into the script. For example assuming that you have content in myfile.tex,
then the above command will output the results of operating upon myfile.tex.
If you wish to use this feature with your own local settings, via the -l switch, then you should finish
your call to latexindent.pl with a - sign:
cmh:$ cat myfile.tex | latexindent.pl -l=mysettings.yaml -
Similarly, if you
U: 2018-01-13
simply type latexindent.pl at the command line, then it will expect (STDIN) input
from the command line.
cmh:$ latexindent.pl
Once you have finished typing your input, you can press
CTRL+D on Linux
CTRL+Z followed by ENTER on Windows
to signify that your input has finished. Thanks to [9] for an update to this feature.
-r, –replacement
cmh:$ latexindent.pl -r myfile.tex
cmh:$ latexindent.pl -replacement myfile.tex
You can
N: 2019-07-13
call latexindent.pl with the -r switch to instruct it to perform replacements/substitutions
on your file; full details and examples are given in Section 7 on page 129.
-rv, –replacementrespectverb
cmh:$ latexindent.pl -rv myfile.tex
cmh:$ latexindent.pl -replacementrespectverb myfile.tex
You can
N: 2019-07-13
instruct latexindent.pl to perform replacements/substitutions by using the -rv switch,
but will respect verbatim code blocks; full details and examples are given in Section 7 on page 129.
-rr, –onlyreplacement
cmh:$ latexindent.pl -rr myfile.tex
cmh:$ latexindent.pl -onlyreplacement myfile.tex
You can
N: 2019-07-13
instruct latexindent.pl to skip all of its other indentation operations and only perform
replacements/substitutions by using the -rr switch; full details and examples are given in Section 7
on page 129.
-k, –check
[git] main @ 78d452f 2024-07-18 V3.24.4
3.3 From arara 21
cmh:$ latexindent.pl -k myfile.tex
cmh:$ latexindent.pl -check myfile.tex
You can
N: 2021-09-16
instruct latexindent.pl to check if the text after indentation matches that given in the
original file.
The exit code of latexindent.pl is 0 by default. If you use the -k switch then
if the text after indentation matches that given in the original file, then the exit code is 0;
if the text after indentation does not match that given in the original file, then the exit code is
1.
The value of the exit code may be important to those wishing to, for example, check the status of
the indentation in continuous integration tools such as GitHub Actions. Full details of the exit codes
of latexindent.pl are given in Table 1.
A simple diff will be given in indent.log.
-kv, –checkv
cmh:$ latexindent.pl -kv myfile.tex
cmh:$ latexindent.pl -checkv myfile.tex
N: 2021-09-16
The check verbose switch is exactly the same as the -k switch, except that it is verbose, and it will
output the (simple) diff to the terminal, as well as to indent.log.
-n, –lines=MIN-MAX
cmh:$ latexindent.pl -n 5-8 myfile.tex
cmh:$ latexindent.pl -lines 5-8 myfile.tex
N: 2021-09-16
The lines switch instructs latexindent.pl to operate only on specific line ranges within myfile.tex.
Complete demonstrations are given in Section 8.
–GCString
cmh:$ latexindent.pl --GCString myfile.tex
N: 2022-03-25
instructs latexindent.pl to load the Unicode::GCString module. This should only be necessary
if you find that the alignment at ampersand routine (described in Section 5.5) does not work for
your language. Further details are given in appendix A.3.
3.3 From arara
Using latexindent.pl from the command line is fine for some folks, but others may find it easier to
use from arara; you can find the arara rule for latexindent.pl and its associated documentation
at [1].
3.4 Summary of exit codes
Assuming that you call latexindent.pl on myfile.tex
cmh:$ latexindent.pl myfile.tex
then latexindent.pl can exit with the exit codes given in Table 1.
[git] main @ 78d452f 2024-07-18 V3.24.4
3.4 Summary of exit codes 22
TABLE 1: Exit codes for latexindent.pl
exit code indentation status
0 Ë success; if -k or -kv active, indented text matches original
0 é success; if -version, -vversion or -help, no indentation performed
1 Ë success, and -k or -kv active; indented text different from original
2 é failure, defaultSettings.yaml could not be read
3 é failure, myfile.tex not found
4 é failure, myfile.tex exists but cannot be read
5 é failure, -w active, and back-up file cannot be written
6 é failure, -c active, and cruft directory could not be created
[git] main @ 78d452f 2024-07-18 V3.24.4
SECTION 4
indentconfig.yaml, local settings and the -y
switch
The behaviour of latexindent.pl is controlled from the settings specified in any of the YAML files
that you tell it to load. By default, latexindent.pl will only load defaultSettings.yaml, but
there are a few ways that you can tell it to load your own settings files.
We focus our discussion on indentconfig.yaml, but there are other options which are detailed in
appendix H.
N: 2023-01-01
4.1 indentconfig.yaml and .indentconfig.yaml
latexindent.pl will always check your home directory for indentconfig.yaml and .indentconfig.yaml
(unless it is called with the -d switch), which is a plain text file you can create that contains the
absolute paths for any settings files that you wish latexindent.pl to load. There is no difference be-
tween indentconfig.yaml and .indentconfig.yaml, other than the fact that .indentconfig.yaml
is a ‘hidden’ file; thank you to [5] for providing this feature. In what follows, we will use indentconfig.yaml,
but it is understood that this could equally represent .indentconfig.yaml. If you have both files
in existence then indentconfig.yaml takes priority.
For Mac and Linux users, their home directory is /username while Windows (Vista onwards) is
C:\Users\username
2
Listing 32 shows a sample indentconfig.yaml file.
LISTING 32: indentconfig.yaml (sample)
# Paths to user settings for latexindent.pl
#
# Note that the settings will be read in the order you
# specify here- each successive settings file will overwrite
# the variables that you specify
paths:
- /home/cmhughes/Documents/yamlfiles/mysettings.yaml
- /home/cmhughes/folder/othersettings.yaml
- /some/other/folder/anynameyouwant.yaml
- C:\Users\chughes\Documents\mysettings.yaml
- C:\Users\chughes\Desktop\test spaces\more spaces.yaml
Note that the .yaml files you specify in indentconfig.yaml will be loaded in the order in which
you write them. Each file doesn’t have to have every switch from defaultSettings.yaml; in fact,
I recommend that you only keep the switches that you want to change in these settings files.
To get started with your own settings file, you might like to save a copy of defaultSettings.yaml
in another directory and call it, for example, mysettings.yaml. Once you have added the path to
indentconfig.yaml you can change the switches and add more code-block names to it as you see
fit have a look at Listing 33 for an example that uses four tabs for the default indent, adds the
tabbing environment/command to the list of environments that contains alignment delimiters; you
might also like to refer to the many YAML files detailed throughout the rest of this documentation.
2
If you’re not sure where to put indentconfig.yaml, don’t worry latexindent.pl will tell you in the log file exactly
where to put it assuming it doesn’t exist already.
[git] main @ 78d452f 2024-07-18 V3.24.4
4.2 localSettings.yaml and friends 24
LISTING 33: mysettings.yaml (example)
# Default value of indentation
defaultIndent: "\t\t\t\t"
# environments that have tab delimiters, add more
# as needed
lookForAlignDelims:
tabbing: 1
You can make sure that your settings are loaded by checking indent.log for details if you have
specified a path that latexindent.pl doesn’t recognise then you’ll get a warning, otherwise you’ll
get confirmation that latexindent.pl has read your settings file
3
.
Warning!
When editing .yaml files it is extremely important to remember how sensitive they are
to spaces. I highly recommend copying and pasting from defaultSettings.yaml
when you create your first whatevernameyoulike.yaml file.
If latexindent.pl can not read your .yaml file it will tell you so in indent.log.
As of
N: 2024-04-28
you can specify the paths field from Listing 32 within any of your latexindent.yaml and
friends settings files. This can lead to creative nesting of configuration files; a demonstration is given
in appendix I on page 174.
4.2 localSettings.yaml and friends
The -l switch tells latexindent.pl to look for localSettings.yaml and/or friends in the same
directory as myfile.tex. For
U: 2021-03-14
example, if you use the following command
cmh:$ latexindent.pl -l myfile.tex
then latexindent.pl will search for and then, assuming they exist, load each of the following files
in the following order:
1. localSettings.yaml
2. latexindent.yaml
3. .localSettings.yaml
4. .latexindent.yaml
These files will be assumed to be in the same directory as myfile.tex, or otherwise in the current
working directory. You do not need to have all of the above files, usually just one will be sufficient.
In what follows, whenever we refer to localSettings.yaml it is assumed that it can mean any of
the four named options listed above.
If you’d prefer to name your localSettings.yaml file something different, (say, mysettings.yaml
as in Listing 33) then you can call latexindent.pl using, for example,
cmh:$ latexindent.pl -l=mysettings.yaml myfile.tex
Any settings file(s) specified using the -l switch will be read after defaultSettings.yaml and,
assuming they exist, any user setting files specified in indentconfig.yaml.
Your settings file can contain any switches that you’d like to change; a sample is shown in Listing 34,
and you’ll find plenty of further examples throughout this manual.
3
Windows users may find that they have to end .yaml files with a blank line
[git] main @ 78d452f 2024-07-18 V3.24.4
4.3 The -y|yaml switch 25
LISTING 34: localSettings.yaml (example)
# verbatim environments - environments specified
# here will not be changed at all!
verbatimEnvironments:
cmhenvironment: 0
myenv: 1
You can make sure that your settings file has been loaded by checking indent.log for details; if it
can not be read then you receive a warning, otherwise you’ll get confirmation that latexindent.pl
has read your settings file.
4.3 The -y|yaml switch
You
N: 2017-08-21
may use the -y switch to load your settings; for example, if you wished to specify the settings
from Listing 34 using the -y switch, then you could use the following command:
cmh:$ latexindent.pl -y="verbatimEnvironments:cmhenvironment:0;myenv:1" myfile.tex
Note the use of ; to specify another field within verbatimEnvironments. This is shorthand, and
equivalent, to using the following command:
cmh:$ latexindent.pl
-y="verbatimEnvironments:cmhenvironment:0,verbatimEnvironments:myenv:1"
myfile.tex
You may, of course, specify settings using the -y switch as well as, for example, settings loaded using
the -l switch; for example,
cmh:$ latexindent.pl -l=mysettings.yaml
-y="verbatimEnvironments:cmhenvironment:0;myenv:1" myfile.tex
Any settings specified using the -y switch will be loaded after any specified using indentconfig.yaml
and the -l switch.
If you wish to specify any regex-based settings using the -y switch, it is important not to use quotes
surrounding the regex; for example, with reference to the ‘one sentence per line’ feature (Section 6.2
on page 95) and the listings within Listing 375 on page 98, the following settings give the option to
have sentences end with a semicolon
cmh:$ latexindent.pl -m
--yaml=’modifyLineBreaks:oneSentencePerLine:sentencesEndWith:other:\;’
Note that the paths settings (see appendix I on page 174) can not be specified using the -y switch.
4.4 Settings load order
latexindent.pl loads the settings files in the following order:
1. defaultSettings.yaml is always loaded, and can not be renamed;
2. anyUserSettings.yaml and any other arbitrarily-named files specified in indentconfig.yaml;
3. localSettings.yaml but only if found in the same directory as myfile.tex and called with
-l switch; this file can be renamed, provided that the call to latexindent.pl is adjusted
accordingly (see Section 4.2). You may specify both relative and absolute
U: 2017-08-21
paths to other YAML
files using the -l switch, separating multiple files using commas;
4. any settings
N: 2017-08-21
specified in the -y switch.
A visual representation of this is given in Figure 1.
[git] main @ 78d452f 2024-07-18 V3.24.4
4.4 Settings load order 26
latexindent.pl
defaultSettings.yaml
indentconfig.yaml
any.yaml
name.yaml
you.yamlwant.yaml
localSettings.yaml
-y switch
1
2
3
4
FIGURE 1: Schematic of the load order described in Section 4.4; solid lines represent mandatory files, dotted
lines represent optional files. indentconfig.yaml can contain as many files as you like. The files
will be loaded in order; if you specify settings for the same field in more than one file, the most recent
takes priority.
[git] main @ 78d452f 2024-07-18 V3.24.4
SECTION 5
defaultSettings.yaml
latexindent.pl loads its settings from defaultSettings.yaml. The idea is to separate the be-
haviour of the script from the internal working this is very similar to the way that we separate
content from form when writing our documents in L
A
T
E
X.
If you look in defaultSettings.yaml you’ll find the switches that govern the behaviour of latexindent.pl.
If you’re not sure where defaultSettings.yaml resides on your computer, don’t worry as indent.log
will tell you where to find it. defaultSettings.yaml is commented, but here is a description of
what each switch is designed to do. The default value is given in each case; whenever you see integer
in this section, assume that it must be greater than or equal to 0 unless otherwise stated.
For most of the settings in defaultSettings.yaml that are specified as integers, then we under-
stand 0 to represent ‘off’ and 1 to represent ‘on’. For fields that allow values other than 0 or 1, it is
hoped that the specific context and associated commentary should make it clear which values are
allowed.
fileExtensionPreference: fields
latexindent.pl can be called to act on a file without specifying the file extension. For example we
can call
cmh:$ latexindent.pl myfile
in which case the script will look for myfile with the extensions specified in fileExtensionPreference
in their numeric order. If no match is found, the script will exit. As with all of the fields, you should
change and/or add to this as necessary.
LISTING 35: fileExtensionPreference
47 fileExtensionPreference:
48 .tex: 1
49 .sty: 2
50 .cls: 3
51 .bib: 4
Calling latexindent.pl myfile with the (default) settings specified in Listing 35 means that the
script will first look for myfile.tex, then myfile.sty, myfile.cls, and finally myfile.bib in
order
4
.
5.1 Backup and log file preferences
backupExtension: extension name
If you call latexindent.pl with the -w switch (to overwrite myfile.tex) then it will create a
backup file before doing any indentation; the default extension is .bak, so, for example, myfile.bak0
would be created when calling latexindent.pl myfile.tex for the first time.
By default, every time you subsequently call latexindent.pl with the -w to act upon myfile.tex,
it will create successive back up files: myfile.bak1, myfile.bak2, etc.
4
Throughout this manual, listings shown with line numbers represent code taken directly from defaultSettings.yaml.
[git] main @ 78d452f 2024-07-18 V3.24.4
5.1 Backup and log file preferences 28
onlyOneBackUp: integer
If you don’t want a backup for every time that you call latexindent.pl (so you don’t want myfile.bak1,
myfile.bak2, etc) and you simply want myfile.bak (or whatever you chose backupExtension to
be) then change onlyOneBackUp to 1; the default value of onlyOneBackUp is 0.
maxNumberOfBackUps: integer
Some users may only want a finite number of backup files, say at most 3, in which case, they can
change this switch. The smallest value of maxNumberOfBackUps is 0 which will not prevent backup
files being made; in this case, the behaviour will be dictated entirely by onlyOneBackUp. The default
value of maxNumberOfBackUps is 0.
cycleThroughBackUps: integer
Some users may wish to cycle through backup files, by deleting the oldest backup file and keeping
only the most recent; for example, with maxNumberOfBackUps: 4, and cycleThroughBackUps
set to 1 then the copy procedure given below would be obeyed.
cmh:$ copy myfile.bak1 to myfile.bak0
cmh:$ copy myfile.bak2 to myfile.bak1
cmh:$ copy myfile.bak3 to myfile.bak2
cmh:$ copy myfile.bak4 to myfile.bak3
The default value of cycleThroughBackUps is 0.
logFilePreferences: fields
latexindent.pl writes information to indent.log, some of which can be customized by changing
logFilePreferences; see Listing 36. If you load your own user settings (see Section 4 on page 23)
then latexindent.pl will detail them in indent.log; you can choose not to have the details logged
by switching showEveryYamlRead to 0. Once all of your settings have been loaded, you can see the
amalgamated settings in the log file by switching showAmalgamatedSettings to 1, if you wish.
LISTING 36: logFilePreferences
90 logFilePreferences:
91 showEveryYamlRead: 1
92 showAmalgamatedSettings: 0
93 showDecorationStartCodeBlockTrace: 0
94 showDecorationFinishCodeBlockTrace: 0
95 endLogFileWith: ’--------------’
96 showGitHubInfoFooter: 1
97 Dumper:
98 Terse: 1
99 Indent: 1
100 Useqq: 1
101 Deparse: 1
102 Quotekeys: 0
103 Sortkeys: 1
104 Pair: " => "
When
N: 2018-01-13
either of the trace modes (see page 17) are active, you will receive detailed information in
indent.log. You can specify character strings to appear before and after the notification of a found
code block using, respectively, showDecorationStartCodeBlockTrace and showDecorationFinishCodeBlockTrace.
A demonstration is given in appendix J on page 177.
[git] main @ 78d452f 2024-07-18 V3.24.4
5.2 Verbatim code blocks 29
The log file will end with the characters given in endLogFileWith, and will report the GitHub
address of latexindent.pl to the log file if showGitHubInfoFooter is set to 1.
Note: latexindent.pl no longer uses the log4perl module to handle the creation of the logfile.
U: 2021-03-14
Some of the options
U: 2021-06-19
for Perl’s Dumper module can be specified in Listing 36; see [34] and [33] for
more information. These options will mostly be helpful for those calling latexindent.pl with the
-tt option described in Section 3.2.
5.2 Verbatim code blocks
verbatimEnvironments: fields
A field that contains a list of environments that you would like left completely alone – no indentation
will be performed on environments that you have specified in this field, see Listing 37.
LISTING 37: verbatimEnvironments
108 verbatimEnvironments:
109 verbatim: 1
110 lstlisting: 1
111 minted: 1
LISTING 38: verbatimCommands
114 verbatimCommands:
115 verb: 1
116 lstinline: 1
Note that if you put an environment in verbatimEnvironments and in other fields such as lookForAlignDelims
or noAdditionalIndent then latexindent.pl will always prioritize verbatimEnvironments.
You can, optionally, specify
N: 2021-10-30
the verbatim field using the name field which takes a regular expression
as its argument; thank you to [18] for contributing this feature.
example 10
For demonstration, then assuming that your file contains the environments latexcode, latexcode*,
pythoncode and pythoncode*, then the listings given in Listings 39 and 40 are equivalent.
LISTING 39: nameAsRegex1.yaml
verbatimEnvironments:
latexcode: 1
latexcode*: 1
pythoncode: 1
pythoncode*: 1
LISTING 40: nameAsRegex2.yaml
verbatimEnvironments:
nameAsRegex:
name: ’\w+code\*?’
lookForThis: 1
With reference to Listing 40:
the name field as specified here means any word followed by the word code, optionally fol-
lowed by *;
we have used nameAsRegex to identify this field, but you can use any description you like;
the lookForThis field is optional, and can take the values 0 (off) or 1 (on); by default, it
is assumed to be 1 (on).
verbatimCommands: fields
A field that contains a list of commands that are verbatim commands, for example \lstinline; any
commands populated in this field are protected from line breaking routines (only relevant if the -m
is active, see Section 6 on page 79).
With reference to Listing 38, by default latexindent.pl looks for \verb immediately followed by
another character, and then it takes the body as anything up to the next occurrence of the character;
this means that, for example, \verb!x+3! is treated as a verbatimCommands.
You can, optionally, specify
N: 2021-10-30
the verbatimCommands field using the name field which takes a regular
expression as its argument; thank you to [18] for contributing this feature.
[git] main @ 78d452f 2024-07-18 V3.24.4
5.2 Verbatim code blocks 30
example 11
For demonstration, then assuming that your file contains the commands verbinline, myinline
then the listings given in Listings 41 and 42 are equivalent.
LISTING 41: nameAsRegex3.yaml
verbatimCommands:
verbinline: 1
myinline: 1
LISTING 42: nameAsRegex4.yaml
verbatimCommands:
nameAsRegex:
name: ’\w+inline’
lookForThis: 1
With reference to Listing 42:
the name field as specified here means any word followed by the word inline;
we have used nameAsRegex to identify this field, but you can use any description you like;
the lookForThis field is optional, and can take the values 0 (off) or 1 (on); by default, it
is assumed to be 1 (on).
noIndentBlock: fields
If you have a block of code that you don’t want latexindent.pl to touch (even if it is not a verbatim-
like environment) then you can wrap it in an environment from noIndentBlock; you can use any
name you like for this, provided you populate it as demonstrate in Listing 43.
LISTING 43: noIndentBlock
121 noIndentBlock:
122 noindent: 1
123 cmhtest: 1
Of course, you don’t want to have to specify these as null environments in your code, so you use them
with a comment symbol, %, followed by as many spaces (possibly none) as you like; see Listing 44
for example.
LISTING 44: noIndentBlock.tex
% \begin{noindent}
some before text
this code
won’t
be touched
by
latexindent.pl!
some after text
% \end{noindent}
Important note: it is assumed that the noindent block statements specified in this way appear on
their own line.
example 12
The noIndentBlock fields can also be specified in terms of begin and end fields. We use the
code in Listing 45 to demonstrate this feature.
N: 2021-06-19
LISTING 45: noIndentBlock1.tex
some before text
this code
won’t
be touched
by
latexindent.pl!
some after text
The settings given in Listings 46 and 47 are equivalent:
[git] main @ 78d452f 2024-07-18 V3.24.4
5.2 Verbatim code blocks 31
LISTING 46: noindent1.yaml
noIndentBlock:
demo:
begin: ’some\hbefore’
body: ’.*?’
end: ’some\hafter\htext’
lookForThis: 1
LISTING 47: noindent2.yaml
noIndentBlock:
demo:
begin: ’some\hbefore’
end: ’some\hafter\htext’
LISTING 48: noindent3.yaml
noIndentBlock:
demo:
begin: ’some\hbefore’
body: ’.*?’
end: ’some\hafter\htext’
lookForThis: 0
Upon running the commands
cmh:$ latexindent.pl -l noindent1.yaml noindent1
cmh:$ latexindent.pl -l noindent2.yaml noindent1
then we receive the output given in Listing 49.
LISTING 49: noIndentBlock1.tex using Listing 46 or Listing 47
some before text
this code
won’t
be touched
by
latexindent.pl!
some after text
The begin, body and end fields for noIndentBlock are all regular expressions. If the body field is
not specified, then it takes a default value of .*? which is written explicitly in Listing 46. In this
context, we interpret .*? in words as the fewest number of characters (possibly none) until the ‘end’
field is reached.
The lookForThis field is optional, and can take the values 0 (off) or 1 (on); by default, it is assumed
to be 1 (on).
example 13
Using Listing 48 demonstrates setting lookForThis to 0 (off); running the command
cmh:$ latexindent.pl -l noindent3.yaml noindent1
gives the output in Listing 50.
LISTING 50: noIndentBlock1.tex using Listing 48
some before text
this code
won’t
be touched
by
latexindent.pl!
some after text
We will demonstrate this feature later in the documentation in Listing 582.
You can, optionally, specify
N: 2021-10-30
the noIndentBlock field using the name field which takes a regular
expression as its argument; thank you to [18] for contributing this feature.
example 14
For demonstration, then assuming that your file contains the environments testnoindent, testnoindent*
then the listings given in Listings 51 and 52 are equivalent.
[git] main @ 78d452f 2024-07-18 V3.24.4
5.3 filecontents and preamble 32
LISTING 51: nameAsRegex5.yaml
noIndentBlock:
mytest:
begin: ’\\begin\{testnoindent\*?\}’
end: ’\\end\{testnoindent\*?\}’
LISTING 52: nameAsRegex6.yaml
noIndentBlock:
nameAsRegex:
name: ’\w+noindent\*?’
lookForThis: 1
With reference to Listing 52:
the name field as specified here means any word followed by the word noindent, optionally
followed by *;
we have used nameAsRegex to identify this field, but you can use any description you like;
the lookForThis field is optional, and can take the values 0 (off) or 1 (on); by default, it
is assumed to be 1 (on).
5.3 filecontents and preamble
fileContentsEnvironments: field
Before latexindent.pl determines the difference between preamble (if any) and the main doc-
ument, it first searches for any of the environments specified in fileContentsEnvironments, see
Listing 53. The behaviour of latexindent.pl on these environments is determined by their location
(preamble or not), and the value indentPreamble, discussed next.
LISTING 53: fileContentsEnvironments
127 fileContentsEnvironments:
128 filecontents: 1
129 filecontents*: 1
indentPreamble: 0|1
The preamble of a document can sometimes contain some trickier code for latexindent.pl to op-
erate upon. By default, latexindent.pl won’t try to operate on the preamble (as indentPreamble
is set to 0, by default), but if you’d like latexindent.pl to try then change indentPreamble to 1.
lookForPreamble: fields
Not all files contain preamble; for example, sty, cls and bib files typically do not. Referenc-
ing Listing 54, if you set, for example, .tex to 0, then regardless of the setting of the value of
indentPreamble, preamble will not be assumed when operating upon .tex files.
LISTING 54: lookForPreamble
135 lookForPreamble:
136 .tex: 1
137 .sty: 0
138 .cls: 0
139 .bib: 0
140 STDIN: 1
preambleCommandsBeforeEnvironments: 0|1
Assuming that latexindent.pl is asked to operate upon the preamble of a document, when this
switch is set to 0 then environment code blocks will be sought first, and then command code blocks.
When this switch is set to 1, commands will be sought first. The example that first motivated this
switch contained the code given in Listing 55.
[git] main @ 78d452f 2024-07-18 V3.24.4
5.4 Indentation and horizontal space 33
LISTING 55: Motivating preambleCommandsBeforeEnvironments
...
pre head hook ={\ begin { m dfr amed }[ style = myframedstyle ]} ,
pos tf oo th oo k =\ end { md fra med },
...
5.4 Indentation and horizontal space
defaultIndent: horizontal space
This is the default indentation used in the absence of other details for the code block with which
we are working. The default value is \t which means a tab; we will explore customisation beyond
defaultIndent in Section 5.8 on page 55.
If you’re interested in experimenting with latexindent.pl then you can remove all indentation by
setting defaultIndent: "".
removeTrailingWhitespace: fields
Trailing white space can be removed both before and after processing the document, as detailed in
Listing 56; each of the fields can take the values 0 or 1. See Listings 470 to 472 on page 116 for
before and after results. Thanks to [3] for providing this feature.
LISTING 56: removeTrailingWhitespace
153 removeTrailingWhitespace:
154 beforeProcessing: 0
155 afterProcessing: 1
LISTING 57: removeTrailingWhitespace (alt)
removeTrailingWhitespace: 1
You can specify removeTrailingWhitespace simply as 0 or 1, if you wish; in this case,
N: 2017-06-28
latexindent.pl
will set both beforeProcessing and afterProcessing to the value you specify; see Listing 57.
5.5 Aligning at delimiters
lookForAlignDelims: fields
This contains a list of code blocks that are operated upon in a special way by latexindent.pl (see
Listing 58). In fact, the fields in lookForAlignDelims can actually take two different forms: the
basic version is shown in Listing 58 and the advanced version in Listing 61; we will discuss each in
turn.
LISTING 58: lookForAlignDelims (basic)
lookForAlignDelims:
tabular: 1
tabularx: 1
longtable: 1
array: 1
matrix: 1
...
Specifying code blocks in this field instructs latexindent.pl to try and align each column by its
alignment delimiters. It does have some limitations (discussed further in Section 10), but in many
cases it will produce results such as those in Listings 59 and 60; running the command
cmh:$ latexindent.pl tabular1.tex
[git] main @ 78d452f 2024-07-18 V3.24.4
5.5 Aligning at delimiters 34
gives the output given in Listing 60.
LISTING 59: tabular1.tex
\begin{tabular}{cccc}
1& 2 &3 &4\\
5& &6 &\\
\end{tabular}
LISTING 60: tabular1.tex default output
\begin{tabular}{cccc}
1 & 2 & 3 & 4 \\
5 & & 6 & \\
\end{tabular}
If you find that latexindent.pl does not perform satisfactorily on such environments then you
can set the relevant key to 0, for example tabular: 0; alternatively, if you just want to ignore
specific instances of the environment, you could wrap them in something from noIndentBlock (see
Listing 43 on page 30).
If, for example, you wish to remove the alignment of the \\ within a delimiter-aligned block, then
the advanced form of lookForAlignDelims shown in Listing 61 is for you.
LISTING 61: lookForAlignDelims (advanced)
158 lookForAlignDelims:
159 tabular:
160 delims: 1
161 alignDoubleBackSlash: 1
162 spacesBeforeDoubleBackSlash: 1
163 multiColumnGrouping: 0
164 alignRowsWithoutMaxDelims: 1
165 spacesBeforeAmpersand: 1
166 spacesAfterAmpersand: 1
167 justification: left
168 alignFinalDoubleBackSlash: 0
169 dontMeasure: 0
170 delimiterRegEx: (?<!\\)(&)
171 delimiterJustification: left
172 lookForChildCodeBlocks: 1
173 alignContentAfterDoubleBackSlash: 0
174 spacesAfterDoubleBackSlash: 1
175 tabularx:
176 delims: 1
177 longtable: 1
Note that you can use a mixture of the basic and advanced form: in Listing 61 tabular and tabularx
are advanced and longtable is basic. When using the advanced form, each field should receive at
least 1 sub-field, and can (but does not have to) receive any of the following fields:
delims: binary switch (0 or 1) equivalent to simply specifying, for example, tabular: 1 in
the basic version shown in Listing 58. If delims is set to 0 then the align at ampersand routine
will not be called for this code block (default: 1);
alignDoubleBackSlash: binary switch (0 or 1) to determine if \\ should be aligned (default:
1);
spacesBeforeDoubleBackSlash: optionally,
U: 2018-01-13
specifies the number (integer 0) of spaces to
be inserted before \\ (default: 1);
N: 2017-06-19
multiColumnGrouping: binary switch (0 or 1) that details if latexindent.pl should group
columns above and below a \multicolumn command (default: 0);
N: 2017-06-19
alignRowsWithoutMaxDelims: binary switch (0 or 1) that details if rows that do not contain
the maximum number of delimiters should be formatted so as to have the ampersands aligned
(default: 1);
N: 2018-01-13
spacesBeforeAmpersand: optionally specifies the number (integer 0) of spaces to be placed
before ampersands (default: 1);
N: 2018-01-13
spacesAfterAmpersand: optionally specifies the number (integer 0) of spaces to be placed
After ampersands (default: 1);
[git] main @ 78d452f 2024-07-18 V3.24.4
5.5 Aligning at delimiters 35
N: 2018-01-13
justification: optionally specifies the justification of each cell as either left or right (default:
left);
N: 2020-03-21
alignFinalDoubleBackSlash optionally specifies if the final double backslash should be used for
alignment (default: 0);
N: 2020-03-21
dontMeasure optionally specifies if user-specified cells, rows or the largest entries should not
be measured (default: 0);
N: 2020-03-21
delimiterRegEx optionally specifies the pattern matching to be used for the alignment delimiter
(default: ’(?<!\\)(&)’);
N: 2020-03-21
delimiterJustification optionally specifies the justification for the alignment delimiters (default:
left); note that this feature is only useful if you have delimiters of different lengths in the same
column, discussed in Section 5.5.4;
N: 2021-12-13
lookForChildCodeBlocks optionally instructs latexindent.pl to search for child code blocks
or not (default: 1), discussed in Section 5.5.5;
N: 2023-05-01
alignContentAfterDoubleBackSlash optionally instructs latexindent.pl to align content after
double back slash (default: 0), discussed in Section 5.5.6;
N: 2023-05-01
spacesAfterDoubleBackSlash optionally specifies the number (integer 0) of spaces to be
placed after the double back slash when alignContentAfterDoubleBackSlash is active; demon-
strated in Section 5.5.6.
example 15
We will explore most of these features using the file tabular2.tex in Listing 62 (which contains a
\multicolumn command), and the YAML files in Listings 63 to 69; we will explore alignFinalDoubleBackSlash
in Listing 90; the dontMeasure feature will be described in Section 5.5.3, and delimiterRegEx
in Section 5.5.4.
LISTING 62: tabular2.tex
\begin{tabular}{cccc}
A& B & C &D\\
AAA& BBB & CCC &DDD\\
\multicolumn{2}{c}{first heading} & \multicolumn{2}{c}{second heading}\\
one& two & three &four\\
five& &six &\\
seven & \\
\end{tabular}
LISTING 63: tabular2.yaml
lookForAlignDelims:
tabular:
multiColumnGrouping: 1
LISTING 64: tabular3.yaml
lookForAlignDelims:
tabular:
alignRowsWithoutMaxDelims: 0
LISTING 65: tabular4.yaml
lookForAlignDelims:
tabular:
spacesBeforeAmpersand: 4
LISTING 66: tabular5.yaml
lookForAlignDelims:
tabular:
spacesAfterAmpersand: 4
LISTING 67: tabular6.yaml
lookForAlignDelims:
tabular:
alignDoubleBackSlash: 0
LISTING 68: tabular7.yaml
lookForAlignDelims:
tabular:
spacesBeforeDoubleBackSlash: 0
[git] main @ 78d452f 2024-07-18 V3.24.4
5.5 Aligning at delimiters 36
LISTING 69: tabular8.yaml
lookForAlignDelims:
tabular:
justification: "right"
On running the commands
cmh:$ latexindent.pl tabular2.tex
cmh:$ latexindent.pl tabular2.tex -l tabular2.yaml
cmh:$ latexindent.pl tabular2.tex -l tabular3.yaml
cmh:$ latexindent.pl tabular2.tex -l tabular2.yaml,tabular4.yaml
cmh:$ latexindent.pl tabular2.tex -l tabular2.yaml,tabular5.yaml
cmh:$ latexindent.pl tabular2.tex -l tabular2.yaml,tabular6.yaml
cmh:$ latexindent.pl tabular2.tex -l tabular2.yaml,tabular7.yaml
cmh:$ latexindent.pl tabular2.tex -l tabular2.yaml,tabular8.yaml
we obtain the respective outputs given in Listings 70 to 77.
LISTING 70: tabular2.tex default output
\begin{tabular}{cccc}
A & B & C & D \\
AAA & BBB & CCC & DDD \\
\multicolumn{2}{c}{first heading} & \multicolumn{2}{c}{second heading} \\
one & two & three & four \\
five & & six & \\
seven & \\
\end{tabular}
LISTING 71: tabular2.tex using Listing 63
\begin{tabular}{cccc}
A & B & C & D \\
AAA & BBB & CCC & DDD \\
\multicolumn{2}{c}{first heading} & \multicolumn{2}{c}{second heading} \\
one & two & three & four \\
five & & six & \\
seven & \\
\end{tabular}
LISTING 72: tabular2.tex using Listing 64
\begin{tabular}{cccc}
A & B & C & D \\
AAA & BBB & CCC & DDD \\
\multicolumn{2}{c}{first heading} & \multicolumn{2}{c}{second heading} \\
one & two & three & four \\
five & & six & \\
seven & \\
\end{tabular}
[git] main @ 78d452f 2024-07-18 V3.24.4
5.5 Aligning at delimiters 37
LISTING 73: tabular2.tex using Listings 63 and 65
\begin{tabular}{cccc}
A & B & C & D \\
AAA & BBB & CCC & DDD \\
\multicolumn{2}{c}{first heading} & \multicolumn{2}{c}{second heading} \\
one & two & three & four \\
five & & six & \\
seven & \\
\end{tabular}
LISTING 74: tabular2.tex using Listings 63 and 66
\begin{tabular}{cccc}
A & B & C & D \\
AAA & BBB & CCC & DDD \\
\multicolumn{2}{c}{first heading} & \multicolumn{2}{c}{second heading} \\
one & two & three & four \\
five & & six & \\
seven & \\
\end{tabular}
LISTING 75: tabular2.tex using Listings 63 and 67
\begin{tabular}{cccc}
A & B & C & D \\
AAA & BBB & CCC & DDD \\
\multicolumn{2}{c}{first heading} & \multicolumn{2}{c}{second heading} \\
one & two & three & four \\
five & & six & \\
seven & \\
\end{tabular}
LISTING 76: tabular2.tex using Listings 63 and 68
\begin{tabular}{cccc}
A & B & C & D \\
AAA & BBB & CCC & DDD \\
\multicolumn{2}{c}{first heading} & \multicolumn{2}{c}{second heading}\\
one & two & three & four \\
five & & six & \\
seven & \\
\end{tabular}
LISTING 77: tabular2.tex using Listings 63 and 69
\begin{tabular}{cccc}
A & B & C & D \\
AAA & BBB & CCC & DDD \\
\multicolumn{2}{c}{first heading} & \multicolumn{2}{c}{second heading} \\
one & two & three & four \\
five & & six & \\
seven & \\
\end{tabular}
Notice in particular:
in both Listings 70 and 71 all rows have been aligned at the ampersand, even those that
do not contain the maximum number of ampersands (3 ampersands, in this case);
in Listing 70 the columns have been aligned at the ampersand;
in Listing 71 the \multicolumn command has grouped the 2 columns beneath and above it,
[git] main @ 78d452f 2024-07-18 V3.24.4
5.5 Aligning at delimiters 38
because multiColumnGrouping is set to 1 in Listing 63;
in Listing 72 rows 3 and 6 have not been aligned at the ampersand, because alignRowsWithoutMaxDelims
has been to set to 0 in Listing 64; however, the \\ have still been aligned;
in Listing 73 the columns beneath and above the \multicolumn commands have been
grouped (because multiColumnGrouping is set to 1), and there are at least 4 spaces before
each aligned ampersand because spacesBeforeAmpersand is set to 4;
in Listing 74 the columns beneath and above the \multicolumn commands have been
grouped (because multiColumnGrouping is set to 1), and there are at least 4 spaces after
each aligned ampersand because spacesAfterAmpersand is set to 4;
in Listing 75 the \\ have not been aligned, because alignDoubleBackSlash is set to 0,
otherwise the output is the same as Listing 71;
in Listing 76 the \\ have been aligned, and because spacesBeforeDoubleBackSlash is
set to 0, there are no spaces ahead of them; the output is otherwise the same as Listing 71;
in Listing 77 the cells have been right-justified; note that cells above and below the \multicol
statements have still been group correctly, because of the settings in Listing 63.
5.5.1 lookForAlignDelims: spacesBeforeAmpersand
The spacesBeforeAmpersand
U: 2021-06-19
can be specified in a few different ways. The basic form is demon-
strated in Listing 65, but we can customise the behaviour further by specifying if we would like this
value to change if it encounters a leading blank column; that is, when the first column contains only
zero-width entries. We refer to this as the advanced form.
example 16
We demonstrate this feature in relation to Listing 78; upon running the following command
cmh:$ latexindent.pl aligned1.tex -o=+-default
then we receive the default output given in Listing 79.
LISTING 78: aligned1.tex
\begin{aligned}
& a & b, \\
& c & d.
\end{aligned}
LISTING 79: aligned1-default.tex
\begin{aligned}
& a & b, \\
& c & d.
\end{aligned}
The settings in Listings 80 to 83 are all equivlanent; we have used the not-yet discussed noAdditionalIndent
field (see Section 5.8 on page 55) which will assist in the demonstration in what follows.
LISTING 80: sba1.yaml
noAdditionalIndent:
aligned: 1
lookForAlignDelims:
aligned: 1
LISTING 81: sba2.yaml
noAdditionalIndent:
aligned: 1
lookForAlignDelims:
aligned:
spacesBeforeAmpersand: 1
LISTING 82: sba3.yaml
noAdditionalIndent:
aligned: 1
lookForAlignDelims:
aligned:
spacesBeforeAmpersand:
default: 1
LISTING 83: sba4.yaml
noAdditionalIndent:
aligned: 1
lookForAlignDelims:
aligned:
spacesBeforeAmpersand:
leadingBlankColumn: 1
Upon running the following commands
[git] main @ 78d452f 2024-07-18 V3.24.4
5.5 Aligning at delimiters 39
cmh:$ latexindent.pl aligned1.tex -l sba1.yaml
cmh:$ latexindent.pl aligned1.tex -l sba2.yaml
cmh:$ latexindent.pl aligned1.tex -l sba3.yaml
cmh:$ latexindent.pl aligned1.tex -l sba4.yaml
then we receive the (same) output given in Listing 84; we note that there is one space before each
ampersand.
LISTING 84: aligned1-mod1.tex
\begin{aligned}
& a & b, \\
& c & d.
\end{aligned}
We note in particular:
Listing 80 demonstrates the basic form for lookForAlignDelims; in this case, the default
values are specified as in Listing 61 on page 34;
Listing 81 demonstrates the advanced form for lookForAlignDelims and specified spacesBeforeAmpersand.
The default value is 1;
Listing 82 demonstrates the new advanced way to specify spacesBeforeAmpersand, and
for us to set the default value that sets the number of spaces before ampersands which
are not in leading blank columns. The default value is 1.
We note that leadingBlankColumn has not been specified in Listing 82, and it will inherit
the value from default;
Listing 83 demonstrates spaces to be used before amperands for leading blank columns. We
note that default has not been specified, and it will be set to 1 by default.
example 17
We can customise the space before the ampersand in the leading blank column of Listing 84 by
using either of Listings 85 and 86, which are equivalent.
LISTING 85: sba5.yaml
noAdditionalIndent:
aligned: 1
lookForAlignDelims:
aligned:
spacesBeforeAmpersand:
leadingBlankColumn: 0
LISTING 86: sba6.yaml
noAdditionalIndent:
aligned: 1
lookForAlignDelims:
aligned:
spacesBeforeAmpersand:
leadingBlankColumn: 0
default: 1
Upon running
cmh:$ latexindent.pl aligned1.tex -l sba5.yaml
cmh:$ latexindent.pl aligned1.tex -l sba6.yaml
then we receive the (same) output given in Listing 87. We note that the space before the amper-
sand in the leading blank column has been set to 0 by Listing 86.
We can demonstrated this feature further using the settings in Listing 89 which give the output
in Listing 88.
[git] main @ 78d452f 2024-07-18 V3.24.4
5.5 Aligning at delimiters 40
LISTING 87: aligned1-mod5.tex
\begin{aligned}
& a & b, \\
& c & d.
\end{aligned}
LISTING 88: aligned1.tex using
Listing 89
\begin{aligned}
& a& b, \\
& c& d.
\end{aligned}
LISTING 89: sba7.yaml
noAdditionalIndent:
aligned: 1
lookForAlignDelims:
aligned:
spacesBeforeAmpersand:
leadingBlankColumn: 3
default: 0
5.5.2 lookForAlignDelims: alignFinalDoubleBackSlash
There may be times when a line of a code block contains more than \\, and in which case, you may
want the final double backslash to be aligned.
example 18
We explore the alignFinalDoubleBackSlash feature by using the file in Listing 90. Upon run-
ning the following commands
N: 2020-03-21
cmh:$ latexindent.pl tabular4.tex -o=+-default
cmh:$ latexindent.pl tabular4.tex -o=+-FDBS
-y="lookForAlignDelims:tabular:alignFinalDoubleBackSlash:1"
then we receive the respective outputs given in Listing 91 and Listing 92.
LISTING 90: tabular4.tex
\begin{tabular}{lc}
Name & \shortstack{Hi \\ Lo} \\
Foo & Bar \\
\end{tabular}
LISTING 91: tabular4-default.tex
\begin{tabular}{lc}
Name & \shortstack{Hi \\ Lo} \\
Foo & Bar \\
\end{tabular}
LISTING 92: tabular4-FDBS.tex
\begin{tabular}{lc}
Name & \shortstack{Hi \\ Lo} \\
Foo & Bar \\
\end{tabular}
We note that in:
Listing 91, by default, the first set of double back slashes in the first row of the tabular
environment have been used for alignment;
Listing 92, the final set of double backslashes in the first row have been used, because we
specified alignFinalDoubleBackSlash as 1.
As of Version 3.0, the alignment routine works on mandatory and optional arguments within com-
mands, and also within ‘special’ code blocks (see specialBeginEnd on page 47).
example 19
Assuming that you have a command called \matrix and that it is populated within lookForAlignDelims
(which it is, by default), and that you run the command
cmh:$ latexindent.pl matrix1.tex
then the before-and-after results shown in Listings 93 and 94 are achievable by default.
LISTING 93: matrix1.tex
\matrix [
1&2 &3\\
4&5&6]{
7&8 &9\\
10&11&12
}
LISTING 94: matrix1.tex default output
\matrix [
1 & 2 & 3 \\
4 & 5 & 6]{
7 & 8 & 9 \\
10 & 11 & 12
}
If you have blocks of code that you wish to align at the & character that are not wrapped in, for
example, \begin{tabular} . . . \end{tabular}, then you can use the mark up illustrated in Listing 95;
the default output is shown in Listing 96. Note that the %* must be next to each other, but that there
can be any number of spaces (possibly none) between the * and \begin{tabular}; note also that
[git] main @ 78d452f 2024-07-18 V3.24.4
5.5 Aligning at delimiters 41
you may use any environment name that you have specified in lookForAlignDelims.
LISTING 95: align-block.tex
%* \begin{tabular}
1 & 2 & 3 & 4 \\
5 & & 6 & \\
%* \end{tabular}
LISTING 96: align-block.tex default output
%* \begin{tabular}
1 & 2 & 3 & 4 \\
5 & & 6 & \\
%* \end{tabular}
With reference to Table 2 on page 56 and the, yet undiscussed, fields of noAdditionalIndent
and indentRules (see Section 5.8 on page 55), these comment-marked blocks are considered
environments.
5.5.3 lookForAlignDelims: the dontMeasure feature
The
N: 2020-03-21
lookForAlignDelims field can, optionally, receive the dontMeasure option which can be spec-
ified in a few different ways.
example 20
We will explore this feature in relation to the code given in Listing 97; the default output is shown
in Listing 98.
LISTING 97: tabular-DM.tex
\begin{tabular}{cccc}
aaaaaa&bbbbb&ccc&dd\\
11&2&33&4\\
5&66&7&8
\end{tabular}
LISTING 98: tabular-DM.tex default output
\begin{tabular}{cccc}
aaaaaa & bbbbb & ccc & dd \\
11 & 2 & 33 & 4 \\
5 & 66 & 7 & 8
\end{tabular}
The dontMeasure field can be specified as largest, and in which case, the largest element will
not be measured; with reference to the YAML file given in Listing 100, we can run the command
cmh:$ latexindent.pl tabular-DM.tex -l=dontMeasure1.yaml
and receive the output given in Listing 99.
LISTING 99: tabular-DM.tex using
Listing 100
\begin{tabular}{cccc}
aaaaaa & bbbbb & ccc & dd \\
11 & 2 & 33 & 4 \\
5 & 66 & 7 & 8
\end{tabular}
LISTING 100: dontMeasure1.yaml
lookForAlignDelims:
tabular:
dontMeasure: largest
We note that the largest column entries have not contributed to the measuring routine.
example 21
The dontMeasure field can also be specified in the form demonstrated in Listing 102. On running
the following commands,
cmh:$ latexindent.pl tabular-DM.tex -l=dontMeasure2.yaml
we receive the output in Listing 101.
[git] main @ 78d452f 2024-07-18 V3.24.4
5.5 Aligning at delimiters 42
LISTING 101: tabular-DM.tex using
Listing 102 or Listing 104
\begin{tabular}{cccc}
aaaaaa & bbbbb & ccc & dd \\
11 & 2 & 33 & 4 \\
5 & 66 & 7 & 8
\end{tabular}
LISTING 102: dontMeasure2.yaml
lookForAlignDelims:
tabular:
dontMeasure:
- aaaaaa
- bbbbb
- ccc
- dd
We note that in Listing 102 we have specified entries not to be measured, one entry per line.
example 22
The dontMeasure field can also be specified in the forms demonstrated in Listing 104 and List-
ing 105. Upon running the commands
cmh:$ latexindent.pl tabular-DM.tex -l=dontMeasure3.yaml
cmh:$ latexindent.pl tabular-DM.tex -l=dontMeasure4.yaml
we receive the output given in Listing 103
LISTING 103: tabular-DM.tex using
Listing 104 or Listing 104
\begin{tabular}{cccc}
aaaaaa & bbbbb & ccc & dd \\
11 & 2 & 33 & 4 \\
5 & 66 & 7 & 8
\end{tabular}
LISTING 104: dontMeasure3.yaml
lookForAlignDelims:
tabular:
dontMeasure:
-
this: aaaaaa
applyTo: cell
-
this: bbbbb
- ccc
- dd
LISTING 105: dontMeasure4.yaml
lookForAlignDelims:
tabular:
dontMeasure:
-
regex: [a-z]
applyTo: cell
We note that in:
Listing 104 we have specified entries not to be measured, each one has a string in the this
field, together with an optional specification of applyTo as cell;
Listing 105 we have specified entries not to be measured as a regular expression using the
regex field, together with an optional specification of applyTo as cell field, together with
an optional specification of applyTo as cell.
In both cases, the default value of applyTo is cell, and does not need to be specified.
example 23
We may also specify the applyTo field as row, a demonstration of which is given in Listing 107;
upon running
cmh:$ latexindent.pl tabular-DM.tex -l=dontMeasure5.yaml
we receive the output in Listing 106.
LISTING 106: tabular-DM.tex using
Listing 107
\begin{tabular}{cccc}
aaaaaa & bbbbb & ccc & dd \\
11 & 2 & 33 & 4 \\
5 & 66 & 7 & 8
\end{tabular}
LISTING 107: dontMeasure5.yaml
lookForAlignDelims:
tabular:
dontMeasure:
-
this: aaaaaa&bbbbb&ccc&dd\\
applyTo: row
[git] main @ 78d452f 2024-07-18 V3.24.4
5.5 Aligning at delimiters 43
example 24
Finally, the applyTo field can be specified as row, together with a regex expression. For example,
for the settings given in Listing 109, upon running
cmh:$ latexindent.pl tabular-DM.tex -l=dontMeasure6.yaml
we receive the output in Listing 108.
LISTING 108: tabular-DM.tex using
Listing 109
\begin{tabular}{cccc}
aaaaaa & bbbbb & ccc & dd \\
11 & 2 & 33 & 4 \\
5 & 66 & 7 & 8
\end{tabular}
LISTING 109: dontMeasure6.yaml
lookForAlignDelims:
tabular:
dontMeasure:
-
regex: [a-z]
applyTo: row
5.5.4 lookForAlignDelims: the delimiterRegEx and delimiterJustification feature
The delimiter alignment
N: 2020-03-21
will, by default, align code blocks at the ampersand character. The be-
haviour is controlled by the delimiterRegEx field within lookForAlignDelims; the default value
is ’(?<!\\)(&)’, which can be read as: an ampersand, as long as it is not immediately preceded by a
backslash.
Warning!
Important: note the ‘capturing’ parenthesis in the (&) which are necessary; if you
intend to customise this field, then be sure to include them appropriately.
example 25
We demonstrate how to customise this with respect to the code given in Listing 110; the default
output from latexindent.pl is given in Listing 111.
LISTING 110: tabbing.tex
\begin{tabbing}
aa \= bb \= cc \= dd \= ee \\
\>2\> 1 \> 7 \> 3 \\
\>3 \> 2\>8\> 3 \\
\>4 \>2 \\
\end{tabbing}
LISTING 111: tabbing.tex default output
\begin{tabbing}
aa \= bb \= cc \= dd \= ee \\
\>2\> 1 \> 7 \> 3 \\
\>3 \> 2\>8\> 3 \\
\>4 \>2 \\
\end{tabbing}
Let’s say that we wish to align the code at either the \= or \>. We employ the settings given in
Listing 113 and run the command
cmh:$ latexindent.pl tabbing.tex -l=delimiterRegEx1.yaml
to receive the output given in Listing 112.
LISTING 112: tabbing.tex using
Listing 113
\begin{tabbing}
aa \= bb \= cc \= dd \= ee \\
\> 2 \> 1 \> 7 \> 3 \\
\> 3 \> 2 \> 8 \> 3 \\
\> 4 \> 2 \\
\end{tabbing}
LISTING 113: delimiterRegEx1.yaml
lookForAlignDelims:
tabbing:
delimiterRegEx: ’(\\(?:=|>))’
We note that:
in Listing 112 the code has been aligned, as intended, at both the \= and \>;
[git] main @ 78d452f 2024-07-18 V3.24.4
5.5 Aligning at delimiters 44
in Listing 113 we have heeded the warning and captured the expression using grouping
parenthesis, specified a backslash using \\ and said that it must be followed by either = or
>.
example 26
We can explore delimiterRegEx a little further using the settings in Listing 115 and run the
command
cmh:$ latexindent.pl tabbing.tex -l=delimiterRegEx2.yaml
to receive the output given in Listing 114.
LISTING 114: tabbing.tex using
Listing 115
\begin{tabbing}
aa \= bb \= cc \= dd \= ee \\
\> 2 \> 1 \> 7 \> 3 \\
\> 3 \> 2 \> 8 \> 3 \\
\> 4 \> 2 \\
\end{tabbing}
LISTING 115: delimiterRegEx2.yaml
lookForAlignDelims:
tabbing:
delimiterRegEx: ’(\\>)’
We note that only the \> have been aligned.
example 27
Of course, the other lookForAlignDelims options can be used alongside the delimiterRegEx;
regardless of the type of delimiter being used (ampersand or anything else), the fields from
Listing 61 on page 34 remain the same; for example, using the settings in Listing 117, and running
cmh:$ latexindent.pl tabbing.tex -l=delimiterRegEx3.yaml
to receive the output given in Listing 116.
LISTING 116: tabbing.tex using
Listing 117
\begin{tabbing}
aa\=bb\=cc\=dd\=ee \\
\>2 \>1 \>7 \>3 \\
\>3 \>2 \>8 \>3 \\
\>4 \>2 \\
\end{tabbing}
LISTING 117: delimiterRegEx3.yaml
lookForAlignDelims:
tabbing:
delimiterRegEx: ’(\\(?:=|>))’
spacesBeforeAmpersand: 0
spacesAfterAmpersand: 0
example 28
It is possible that delimiters specified within delimiterRegEx can be of different lengths. Con-
sider the file in Listing 118, and associated YAML in Listing 120. Note that the Listing 120 specifies
the option for the delimiter to be either # or \>, which are different lengths. Upon running the
command
cmh:$ latexindent.pl tabbing1.tex -l=delimiterRegEx4.yaml -o=+-mod4
we receive the output in Listing 119.
LISTING 118: tabbing1.tex
\begin{tabbing}
1#22\>333\\
xxx#aaa#yyyyy\\
.##&\\
\end{tabbing}
LISTING 119: tabbing1-mod4.tex
\begin{tabbing}
1 # 22 \> 333 \\
xxx # aaa # yyyyy \\
. # # & \\
\end{tabbing}
LISTING 120:
delimiterRegEx4.yaml
lookForAlignDelims:
tabbing:
delimiterRegEx: ’(#|\\>)’
[git] main @ 78d452f 2024-07-18 V3.24.4
5.5 Aligning at delimiters 45
example 29
You can set the delimiter justification as either left (default) or right, which will only have effect
when delimiters in the same column have different lengths. Using the settings in Listing 122 and
running the command
cmh:$ latexindent.pl tabbing1.tex -l=delimiterRegEx5.yaml -o=+-mod5
gives the output in Listing 121.
LISTING 121: tabbing1-mod5.tex
\begin{tabbing}
1 # 22 \> 333 \\
xxx # aaa # yyyyy \\
. # # & \\
\end{tabbing}
LISTING 122: delimiterRegEx5.yaml
lookForAlignDelims:
tabbing:
delimiterRegEx: ’(#|\\>)’
delimiterJustification: right
Note that in Listing 121 the second set of delimiters have been right aligned – it is quite subtle!
5.5.5 lookForAlignDelims: lookForChildCodeBlocks
There
N: 2021-12-13
may be scenarios in which you would prefer to instruct latexindent.pl not to search for
child blocks; in which case setting lookForChildCodeBlocks to 0 may be a good way to proceed.
example 30
Using the settings from Listing 100 on page 41 on the file in Listing 123 and running the command
cmh:$ latexindent.pl tabular-DM-1.tex -l=dontMeasure1.yaml -o=+-mod1
gives the output in Listing 124.
LISTING 123: tabular-DM-1.tex
\begin{tabular}{cc}
1&2\only<2->{\\
3&4}
\end{tabular}
LISTING 124: tabular-DM-1-mod1.tex
\begin{tabular}{cc}
1 & 2\only<2->{ \\
3 & 4}
\end{tabular}
We can improve the output from Listing 124 by employing the settings in Listing 126
cmh:$ latexindent.pl tabular-DM-1.tex -l=dontMeasure1a.yaml -o=+-mod1a
which gives the output in Listing 126.
LISTING 125: tabular-DM-1-mod1a.tex
\begin{tabular}{cc}
1 & 2\only<2->{ \\
3 & 4}
\end{tabular}
LISTING 126: dontMeasure1a.yaml
lookForAlignDelims:
tabular:
dontMeasure: largest
lookForChildCodeBlocks: 0
5.5.6 lookForAlignDelims: alignContentAfterDoubleBackSlash
You can instruct latexindent to align
N: 2023-05-01
content after the double back slash. See also Section 6.3.2
on page 118.
example 31
We consider the file in Listing 127, and the default output given in Listing 128.
[git] main @ 78d452f 2024-07-18 V3.24.4
5.6 Indent after items, specials and headings 46
LISTING 127: tabular5.tex
\begin{tabular}{cc}
1 & 2
\\ aa & bbb
\\ ccc&ddd
\end{tabular}
LISTING 128: tabular5-default.tex
\begin{tabular}{cc}
1 & 2
\\ aa & bbb
\\ ccc&ddd
\end{tabular}
Using the settings given in Listing 130 and running
cmh:$ latexindent.pl -s tabular5.tex -l alignContentAfterDBS1 -o=+-mod1
gives the output in Listing 129.
LISTING 129: tabular5-mod1.tex
\begin{tabular}{cc}
1 & 2
\\ aa & bbb
\\ ccc & ddd
\end{tabular}
LISTING 130: alignContentAfterDBS1.yaml
lookForAlignDelims:
tabular:
alignContentAfterDoubleBackSlash: 1
example 32
When using the alignContentAfterDoubleBackSlash feature, then you can also specify how
many spaces to insert after the double backslash; the default is 1.
N: 2023-05-01
Starting from Listing 127 and using the the settings given in Listing 132
cmh:$ latexindent.pl -s tabular5.tex -l alignContentAfterDBS2 -o=+-mod2
gives the output in Listing 131.
LISTING 131: tabular5-mod2.tex
\begin{tabular}{cc}
1 & 2
\\ aa & bbb
\\ ccc & ddd
\end{tabular}
LISTING 132: alignContentAfterDBS2.yaml
lookForAlignDelims:
tabular:
alignContentAfterDoubleBackSlash: 1
spacesAfterDoubleBackSlash: 3
5.6 Indent after items, specials and headings
indentAfterItems: fields
The environment names specified in indentAfterItems tell latexindent.pl to look for \item
commands; if these switches are set to 1 then indentation will be performed so as indent the code
after each item. A demonstration is given in Listings 134 and 135
LISTING 133: indentAfterItems
242 indentAfterItems:
243 itemize: 1
244 itemize*: 1
245 enumerate: 1
246 enumerate*: 1
247 description: 1
248 description*: 1
249 list: 1
LISTING 134: items1.tex
\begin{itemize}
\item some text here
some more text here
some more text here
\item another item
some more text here
\end{itemize}
LISTING 135: items1.tex default
output
\begin{itemize}
\item some text here
some more text here
some more text here
\item another item
some more text here
\end{itemize}
[git] main @ 78d452f 2024-07-18 V3.24.4
5.6 Indent after items, specials and headings 47
itemNames: fields
If you have your own item commands (perhaps you prefer to use myitem, for example) then you
can put populate them in itemNames. For example, users of the exam document class might like to
add parts to indentAfterItems and part to itemNames to their user settings (see Section 4 on
page 23 for details of how to configure user settings, and Listing 33 on page 24
in particular .)
LISTING 136: itemNames
255 itemNames:
256 item: 1
257 myitem: 1
specialBeginEnd: fields
The fields specified
U: 2017-08-21
in specialBeginEnd are, in their default state, focused on math mode begin
and end statements, but there is no requirement for this to be the case; Listing 137 shows the default
settings of specialBeginEnd.
LISTING 137: specialBeginEnd
261 specialBeginEnd:
262 displayMath:
263 begin: (?<!\\)\\\[ # \[ but *not* \\[
264 end: \\\] # \]
265 lookForThis: 1
266 inlineMath:
267 begin: (?<!\$)(?<!\\)\$(?!\$) # $ but *not* \$ or $$
268 body: [^$]*? # anything *except* $
269 end: (?<!\\)\$(?!\$) # $ but *not* \$ or $$
270 lookForThis: 1
271 displayMathTeX:
272 begin: \$\$ # $$
273 end: \$\$ # $$
274 lookForThis: 1
275 specialBeforeCommand: 0
The field displayMath represents \[...\], inlineMath represents $...$ and displayMathTex
represents $$...$$. You can, of course, rename these in your own YAML files (see Section 4.2 on
page 24); indeed, you might like to set up your own special begin and end statements.
example 33
A demonstration of the before-and-after results are shown in Listings 138 and 139; explicitly,
running the command
cmh:$ latexindent.pl special1.tex -o=+-default
gives the output given in Listing 139.
[git] main @ 78d452f 2024-07-18 V3.24.4
5.6 Indent after items, specials and headings 48
LISTING 138: special1.tex before
The function $f$ has formula
\[
f(x)=x^2.
\]
If you like splitting dollars,
$
g(x)=f(2x)
$
LISTING 139: special1.tex default
output
The function $f$ has formula
\[
f(x)=x^2.
\]
If you like splitting dollars,
$
g(x)=f(2x)
$
For each field, lookForThis is set to 1 by default, which means that latexindent.pl will look for
this pattern; you can tell latexindent.pl not to look for the pattern, by setting lookForThis to 0.
There are
N: 2017-08-21
examples in which it is advantageous to search for specialBeginEnd fields before search-
ing for commands, and the specialBeforeCommand switch controls this behaviour.
example 34
For example, consider the file shown in Listing 140.
LISTING 140: specialLR.tex
\begin{equation}
\left[
\sqrt{
a+b
}
\right]
\end{equation}
Now consider the YAML files shown in Listings 141 and 142
LISTING 141: specialsLeftRight.yaml
specialBeginEnd:
leftRightSquare:
begin: ’\\left\[’
end: ’\\right\]’
lookForThis: 1
LISTING 142:
specialBeforeCommand.yaml
specialBeginEnd:
specialBeforeCommand: 1
Upon running the following commands
cmh:$ latexindent.pl specialLR.tex -l=specialsLeftRight.yaml
cmh:$ latexindent.pl specialLR.tex -l=specialsLeftRight.yaml,specialBeforeCommand.yaml
we receive the respective outputs in Listings 143 and 144.
LISTING 143: specialLR.tex using
Listing 141
\begin{equation}
\left[
\sqrt{
a+b
}
\right]
\end{equation}
LISTING 144: specialLR.tex using
Listings 141 and 142
\begin{equation}
\left[
\sqrt{
a+b
}
\right]
\end{equation}
Notice that in:
Listing 143 the \left has been treated as a command, with one optional argument;
Listing 144 the specialBeginEnd pattern in Listing 141 has been obeyed because List-
[git] main @ 78d452f 2024-07-18 V3.24.4
5.6 Indent after items, specials and headings 49
ing 142 specifies that the specialBeginEnd should be sought before commands.
You can, optionally, specify
N: 2018-04-27
the middle field for anything that you specify in specialBeginEnd.
example 35
For example, let’s consider the .tex file in Listing 145.
LISTING 145: special2.tex
\If
something 0
\ElsIf
something 1
\ElsIf
something 2
\ElsIf
something 3
\Else
something 4
\EndIf
Upon saving the YAML settings in Listings 147 and 149 and running the commands
cmh:$ latexindent.pl special2.tex -l=middle
cmh:$ latexindent.pl special2.tex -l=middle1
then we obtain the output given in Listings 146 and 148.
LISTING 146: special2.tex using
Listing 147
\If
something 0
\ElsIf
something 1
\ElsIf
something 2
\ElsIf
something 3
\Else
something 4
\EndIf
LISTING 147: middle.yaml
specialBeginEnd:
If:
begin: ’\\If’
middle: ’\\ElsIf’
end: ’\\EndIf’
lookForThis: 1
LISTING 148: special2.tex using
Listing 149
\If
something 0
\ElsIf
something 1
\ElsIf
something 2
\ElsIf
something 3
\Else
something 4
\EndIf
LISTING 149: middle1.yaml
specialBeginEnd:
If:
begin: ’\\If’
middle:
- ’\\ElsIf’
- ’\\Else’
end: ’\\EndIf’
lookForThis: 1
We note that:
in Listing 146 the bodies of each of the Elsif statements have been indented appropriately;
the Else statement has not been indented appropriately in Listing 146 – read on!
[git] main @ 78d452f 2024-07-18 V3.24.4
5.6 Indent after items, specials and headings 50
we have specified multiple settings for the middle field using the syntax demonstrated in
Listing 149 so that the body of the Else statement has been indented appropriately in
Listing 148.
You may need these fields in your own YAML files (see Section 4.2 on page 24), if you use popular
algorithm packages such as algorithms, algorithm2e or algpseudocode, etc.
example 36
For example, let’s consider the .tex file in Listing 150.
LISTING 150: specialAlgo.tex
\For{$n = 1, \dots, 10$}
\State body
\EndFor
\FOR{for 1}
\FOR{for 2}
\FOR{for 3}
\STATE{some statement.}
\ENDFOR
\ENDFOR
\ENDFOR
\If{$quality\ge 9$}
\State $a\gets perfect$
\ElsIf{$quality\ge 7$}
\State $a\gets good$
\Else
\While{$i\le n$}
\State $i\gets i+1$
\EndWhile
\EndIf
\ForAll{$n \in \{1, \dots, 10\}$}
\State body
\Loop
\State body
\EndLoop
\State $i\gets 1$
\Repeat
\State $i\gets i+1$
\Until{$i>n$}
\EndFor
\Function{Euclid}{$a,b$}\Comment{The g.c.d. of a and b}
\While{$r\not=0$}\Comment{We have the answer if r is 0}
\State $r\gets a\bmod b$
\EndWhile
\State \textbf{return} $b$\Comment{The gcd is b}
\EndFunction
Upon saving the YAML settings in Listing 152 and running the command
cmh:$ latexindent.pl -l=algo.yaml specialAlgo.tex
then we obtain the output given in Listing 151.
LISTING 151: specialAlgo.tex using
Listing 152
\For{$n = 1, \dots, 10$}
\State body
\EndFor
\FOR{for 1}
\FOR{for 2}
\FOR{for 3}
\STATE{some statement.}
\ENDFOR
\ENDFOR
\ENDFOR
\If{$quality\ge 9$}
\State $a\gets perfect$
\ElsIf{$quality\ge 7$}
\State $a\gets good$
\Else
\While{$i\le n$}
\State $i\gets i+1$
\EndWhile
\EndIf
\ForAll{$n \in \{1, \dots, 10\}$}
\State body
\Loop
\State body
\EndLoop
\State $i\gets 1$
\Repeat
\State $i\gets i+1$
\Until{$i>n$}
\EndFor
\Function{Euclid}{$a,b$}\Comment{The g.c.d. of a and b}
\While{$r\not=0$}\Comment{We have the answer if r is 0}
\State $r\gets a\bmod b$
\EndWhile
\State \textbf{return} $b$\Comment{The gcd is b}
\EndFunction
LISTING 152: algo.yaml
specialBeginEnd:
ForStatement:
begin: \\For\{[^}]+?\}
end: \\EndFor
FORStatement:
begin: \\FOR\{[^}]+?\}
end: \\ENDFOR
WhileStatement:
begin: \\While\{[^}]+?\}
end: \\EndWhile
WHILEStatement:
begin: \\WHILE\{[^}]+?\}
end: \\ENDWHILE
ForAllStatement:
begin: \\ForAll\{[^}]+?\}
end: \\EndFor
LoopStatement:
begin: \\Loop
end: \\EndLoop
RepeatStatement:
begin: \\Repeat
end: \\Until\{[^}]+?\}
ProcedureStatement:
begin: \\Procedure\{[^}]+?\}\{[^}]+?\}
end: \\EndProcedure
FunctionStatement:
begin: \\Function\{[^}]+?\}\{[^}]+?\}
end: \\EndFunction
IfStatement:
begin: \\If\{[^}]+?\}
middle:
- \\Else
- \\ElsIf\{[^}]+?\}
end: \\EndIf
IFStatement:
begin: \\IF\{[^}]+?\}
middle:
- \\ELSE
- \\ELSIF\{[^}]+?\}
end: \\ENDIF
specialBeforeCommand: 1
[git] main @ 78d452f 2024-07-18 V3.24.4
5.6 Indent after items, specials and headings 51
You may
N: 2018-08-13
specify fields in specialBeginEnd to be treated as verbatim code blocks by changing
lookForThis to be verbatim.
example 37
For example, beginning with the code in Listing 153 and the YAML in Listing 154, and running
cmh:$ latexindent.pl special3.tex -l=special-verb1
then the output in Listing 153 is unchanged.
LISTING 153: special3.tex and output
using Listing 154
\[
special code
blocks
can be
treated
as verbatim\]
LISTING 154: special-verb1.yaml
specialBeginEnd:
displayMath:
lookForThis: verbatim
We can combine the specialBeginEnd with the lookForAlignDelims feature.
example 38
We begin with the code in Listing 155.
LISTING 155: special-align.tex
\begin{tikzpicture}
\path (A) edge node {0,1,L}(B)
edge node {1,1,R} (C)
(B) edge [loop above]node {1,1,L}(B)
edge node {0,1,L}(C)
(C) edge node {0,1,L}(D)
edge [bend left]node {1,0,R}(E)
(D) edge[loop below] node {1,1,R}(D)
edge node {0,1,R}(A)
(E) edge[bend left] node {1,0,R} (A);
\end{tikzpicture}
Let’s assume that our goal is to align the code at the edge and node text; we employ the code
given in Listing 157 and run the command
cmh:$ latexindent.pl special-align.tex -l edge-node1.yaml -o=+-mod1
to receive the output in Listing 156.
LISTING 156: special-align.tex using Listing 157
\begin{tikzpicture}
\path (A) edge node {0,1,L}(B)
edge node {1,1,R} (C)
(B) edge [loop above] node {1,1,L}(B)
edge node {0,1,L}(C)
(C) edge node {0,1,L}(D)
edge [bend left] node {1,0,R}(E)
(D) edge [loop below] node {1,1,R}(D)
edge node {0,1,R}(A)
(E) edge [bend left] node {1,0,R} (A);
\end{tikzpicture}
LISTING 157: edge-node1.yaml
specialBeginEnd:
path:
begin: ’\\path’
end: ’;’
lookForThis: 1
specialBeforeCommand: 1
lookForAlignDelims:
path:
delimiterRegEx: ’(edge|node)’
The output in Listing 156 is not quite ideal. We can tweak the settings within Listing 157 in order
to improve the output; in particular, we employ the code in Listing 159 and run the command
[git] main @ 78d452f 2024-07-18 V3.24.4
5.6 Indent after items, specials and headings 52
cmh:$ latexindent.pl special-align.tex -l edge-node2.yaml -o=+-mod2
to receive the output in Listing 158.
LISTING 158: special-align.tex using Listing 159
\begin{tikzpicture}
\path (A) edge node {0,1,L} (B)
edge node {1,1,R} (C)
(B) edge [loop above] node {1,1,L} (B)
edge node {0,1,L} (C)
(C) edge node {0,1,L} (D)
edge [bend left] node {1,0,R} (E)
(D) edge [loop below] node {1,1,R} (D)
edge node {0,1,R} (A)
(E) edge [bend left] node {1,0,R} (A);
\end{tikzpicture}
LISTING 159: edge-node2.yaml
specialBeginEnd:
path:
begin: ’\\path’
end: ’;’
specialBeforeCommand: 1
lookForAlignDelims:
path:
delimiterRegEx:
’(edge|node\h*\{[0-9,A-Z]+\})’
The lookForThis field can be considered optional;
U: 2021-06-19
by default, it is assumed to be 1, which is demon-
strated in Listing 159.
Referencing Listing 137 on page 47 we see that
N: 2023-09-23
each of the specialBeginEnd fields can optionally
accept the body field. If the body field is omitted, then latexindent.pl uses a value that means
anything except one of the begin statements from specialBeginEnd.
In general, it is usually not necessary to specify the body field, but let’s detail an example just for
reference.
example 39
We begin with the example in Listing 160
LISTING 160: special-body.tex
$
a
+
(
b + c
-
(
d
)
)
=
e
$
and
$
f + g = h
$
Using the settings in Listing 162 and running the command
cmh:$ latexindent.pl special-body.tex -l=special-body1.yaml
gives the output in Listing 161.
[git] main @ 78d452f 2024-07-18 V3.24.4
5.6 Indent after items, specials and headings 53
LISTING 161: special-body.tex using Listing 162
$
a
+
(
b + c
-
(
d
)
)
=
e
$
and
$
f + g = h
$
LISTING 162: special-body1.yaml
defaultIndent: " "
specialBeginEnd:
specialBeforeCommand: 1
parentheses:
begin: \(
end: \)
We note that the output in Listing 161 is as we would expect, even without the body field specified.
Another option (purely for reference) that leaves the output in Listing 161 unchanged is shown
in Listing 163.
LISTING 163: special-body2.yaml
defaultIndent: " "
specialBeginEnd:
specialBeforeCommand: 1
parentheses:
begin: \(
body: [^()]*?
end: \)
The body field in Listing 163 means anything except ( or ).
indentAfterHeadings: fields
This field enables the user to specify indentation rules that take effect after heading commands such
as \part, \chapter, \section, \subsection*, or indeed any user-specified command written in this
field.
5
LISTING 164: indentAfterHeadings
285 indentAfterHeadings:
286 part:
287 indentAfterThisHeading: 0
288 level: 1
289 chapter:
290 indentAfterThisHeading: 0
291 level: 2
292 section:
293 indentAfterThisHeading: 0
294 level: 3
The default settings do not place indentation after a heading, but you can easily switch them on
by changing indentAfterThisHeading from 0 to 1. The level field tells latexindent.pl the
hierarchy of the heading structure in your document. You might, for example, like to have both
section and subsection set with level: 3 because you do not want the indentation to go too
5
There is a slight difference in interface for this field when comparing Version 2.2 to Version 3.0; see appendix M on
page 180 for details.
[git] main @ 78d452f 2024-07-18 V3.24.4
5.6 Indent after items, specials and headings 54
deep.
You can add any of your own custom heading commands to this field, specifying the level as appro-
priate. You can also specify your own indentation in indentRules (see Section 5.8 on the following
page); you will find the default indentRules contains chapter: " " which tells latexindent.pl
simply to use a space character after chapter headings (once indent is set to 1 for chapter).
example 40
For example, assuming that you have the code in Listing 166 saved into headings1.yaml, and
that you have the text from Listing 165 saved into headings1.tex.
LISTING 165: headings1.tex
\subsection{subsection title}
subsection text
subsection text
\paragraph{paragraph title}
paragraph text
paragraph text
\paragraph{paragraph title}
paragraph text
paragraph text
LISTING 166: headings1.yaml
indentAfterHeadings:
subsection:
indentAfterThisHeading: 1
level: 1
paragraph:
indentAfterThisHeading: 1
level: 2
If you run the command
cmh:$ latexindent.pl headings1.tex -l=headings1.yaml
then you should receive the output given in Listing 167.
LISTING 167: headings1.tex using
Listing 166
\subsection{subsection title}
subsection text
subsection text
\paragraph{paragraph title}
paragraph text
paragraph text
\paragraph{paragraph title}
paragraph text
paragraph text
LISTING 168: headings1.tex second
modification
\subsection{subsection title}
subsection text
subsection text
\paragraph{paragraph title}
paragraph text
paragraph text
\paragraph{paragraph title}
paragraph text
paragraph text
Now say that you modify the YAML from Listing 166 so that the paragraph level is 1; after running
cmh:$ latexindent.pl headings1.tex -l=headings1.yaml
you should receive the code given in Listing 168; notice that the paragraph and subsection are at
the same indentation level.
maximumIndentation: horizontal space
You can control the maximum indentation given to your file by
N: 2017-08-21
specifying the maximumIndentation
field as horizontal space (but not including tabs). This feature uses the Text::Tabs module [47],
and is off by default.
example 41
For example, consider the example shown in Listing 169 together with the default output shown
in Listing 170.
[git] main @ 78d452f 2024-07-18 V3.24.4
5.7 The code blocks known latexindent.pl 55
LISTING 169: mult-nested.tex
\begin{one}
one
\begin{two}
two
\begin{three}
three
\begin{four}
four
\end{four}
\end{three}
\end{two}
\end{one}
LISTING 170: mult-nested.tex
default output
\begin{one}
one
\begin{two}
two
\begin{three}
three
\begin{four}
four
\end{four}
\end{three}
\end{two}
\end{one}
example 42
Now say that, for example, you have the max-indentation1.yaml from Listing 172 and that
you run the following command:
cmh:$ latexindent.pl mult-nested.tex -l=max-indentation1
You should receive the output shown in Listing 171.
LISTING 171: mult-nested.tex using
Listing 172
\begin{one}
␣one
␣\begin{two}
␣two
␣\begin{three}
␣three
␣\begin{four}
␣four
␣\end{four}
␣\end{three}
␣\end{two}
\end{one}
LISTING 172: max-indentation1.yaml
maximumIndentation: " "
Comparing the output in Listings 170 and 171 we notice that the (default) tabs of indentation have
been replaced by a single space.
In general, when using the maximumIndentation feature, any leading tabs will be replaced by equiv-
alent spaces except, of course, those found in verbatimEnvironments (see Listing 37 on page 29)
or noIndentBlock (see Listing 43 on page 30).
5.7 The code blocks known latexindent.pl
As of Version 3.0, latexindent.pl processes documents using code blocks; each of these are shown
in Table 2.
We will refer to these code blocks in what follows.
N: 2019-07-13
Note that the fine tuning of the definition of the
code blocks detailed in Table 2 is discussed in Section 9 on page 144.
5.8 noAdditionalIndent and indentRules
latexindent.pl operates on files by looking for code blocks, as detailed in Section 5.7; for each
type of code block in Table 2 on the following page (which we will call a thing in what follows) it
searches YAML fields for information in the following order:
1. noAdditionalIndent for the name of the current thing;
2. indentRules for the name of the current thing;
[git] main @ 78d452f 2024-07-18 V3.24.4
5.8 noAdditionalIndent and indentRules 56
TABLE 2: Code blocks known to latexindent.pl
Code block characters allowed in name example
environments a-zA-Z@\*0-9_\\
\ begin { myenv }
body of myenv
\ end { myenv }
optionalArguments
inherits name from parent (e.g environment
name)
[
opt arg text
]
mandatoryArguments
inherits name from parent (e.g environment
name)
{
mand arg text
}
commands +a-zA-Z@\*0-9_\: \mycommandarguments
keyEqualsValuesBracesBrackets a-zA-Z@\*0-9_\/.\h\{\}:\#- my key/.style=arguments
namedGroupingBracesBrackets 0-9\.a-zA-Z@\*>< inarguments
UnNamedGroupingBracesBrackets No name!
{ or [ or , or \& or )
or ( or $ followed by
arguments
ifElseFi
@a-zA-Z but must begin with either
\if of \@if
\ ifnum ...
...
\ else
...
\ fi
items
User specified, see Listings 133 and 136 on
page 46 and on page 47
\ begin { e num er ate }
\ item ...
\ end { enume rate }
specialBeginEnd User specified, see Listing 137 on page 47
\[
...
\]
afterHeading User specified, see Listing 164 on page 53
\ chapter { title }
...
\ section { title }
filecontents User specified, see Listing 53 on page 32
\ begin { f il ec on te nt s }
...
\ end { fi le co nt en ts }
[git] main @ 78d452f 2024-07-18 V3.24.4
5.8 noAdditionalIndent and indentRules 57
3. noAdditionalIndentGlobal for the type of the current thing;
4. indentRulesGlobal for the type of the current thing.
Using the above list, the first piece of information to be found will be used; failing that, the value
of defaultIndent is used. If information is found in multiple fields, the first one according to
the list above will be used; for example, if information is present in both indentRules and in
noAdditionalIndentGlobal, then the information from indentRules takes priority.
We now present details for the different type of code blocks known to latexindent.pl, as detailed
in Table 2 on the previous page; for reference, there follows a list of the code blocks covered.
5.8.1 Environments and their arguments . . . . . . . . . . . . . . . . . . . . . . . . . . . 57
5.8.2 Environments with items . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 64
5.8.3 Commands with arguments . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 65
5.8.4 ifelsefi code blocks . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 67
5.8.5 specialBeginEnd code blocks . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 68
5.8.6 afterHeading code blocks . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 69
5.8.7 The remaining code blocks . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 71
5.8.7.1 keyEqualsValuesBracesBrackets . . . . . . . . . . . . . . . . . . . . . . . 71
5.8.7.2 namedGroupingBracesBrackets . . . . . . . . . . . . . . . . . . . . . . . 72
5.8.7.3 UnNamedGroupingBracesBrackets . . . . . . . . . . . . . . . . . . . . . 72
5.8.7.4 filecontents . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 73
5.8.8 Summary . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 73
5.8.1 Environments and their arguments
There are a few different YAML switches governing the indentation of environments; let’s start with
the code shown in Listing 173.
LISTING 173: myenv.tex
\begin{outer}
\begin{myenv}
body of environment
body of environment
body of environment
\end{myenv}
\end{outer}
noAdditionalIndent: fields
example 43
If we do not wish myenv to receive any additional indentation, we have a few choices available
to us, as demonstrated in Listings 174 and 175.
LISTING 174:
myenv-noAdd1.yaml
noAdditionalIndent:
myenv: 1
LISTING 175:
myenv-noAdd2.yaml
noAdditionalIndent:
myenv:
body: 1
On applying either of the following commands,
[git] main @ 78d452f 2024-07-18 V3.24.4
5.8 noAdditionalIndent and indentRules 58
cmh:$ latexindent.pl myenv.tex -l myenv-noAdd1.yaml
cmh:$ latexindent.pl myenv.tex -l myenv-noAdd2.yaml
we obtain the output given in Listing 176; note in particular that the environment myenv has not
received any additional indentation, but that the outer environment has still received indenta-
tion.
LISTING 176: myenv.tex output (using either Listing 174 or Listing 175)
\begin{outer}
\begin{myenv}
body of environment
body of environment
body of environment
\end{myenv}
\end{outer}
example 44
Upon changing the YAML files to those shown in Listings 177 and 178, and running either
cmh:$ latexindent.pl myenv.tex -l myenv-noAdd3.yaml
cmh:$ latexindent.pl myenv.tex -l myenv-noAdd4.yaml
we obtain the output given in Listing 179.
LISTING 177: myenv-noAdd3.yaml
noAdditionalIndent:
myenv: 0
LISTING 178: myenv-noAdd4.yaml
noAdditionalIndent:
myenv:
body: 0
LISTING 179: myenv.tex output (using either Listing 177 or Listing 178)
\begin{outer}
\begin{myenv}
body of environment
body of environment
body of environment
\end{myenv}
\end{outer}
example 45
Let’s now allow myenv to have some optional and mandatory arguments, as in Listing 180.
LISTING 180: myenv-args.tex
\begin{outer}
\begin{myenv}[%
optional argument text
optional argument text]%
{ mandatory argument text
mandatory argument text}
body of environment
body of environment
body of environment
\end{myenv}
\end{outer}
Upon running
[git] main @ 78d452f 2024-07-18 V3.24.4
5.8 noAdditionalIndent and indentRules 59
cmh:$ latexindent.pl -l=myenv-noAdd1.yaml myenv-args.tex
we obtain the output shown in Listing 181; note that the optional argument, mandatory argument
and body all have received no additional indent. This is because, when noAdditionalIndent
is specified in ‘scalar’ form (as in Listing 174), then all parts of the environment (body, optional
and mandatory arguments) are assumed to want no additional indent.
LISTING 181: myenv-args.tex using Listing 174
\begin{outer}
\begin{myenv}[%
optional argument text
optional argument text]%
{ mandatory argument text
mandatory argument text}
body of environment
body of environment
body of environment
\end{myenv}
\end{outer}
example 46
We may customise noAdditionalIndent for optional and mandatory arguments of the myenv
environment, as shown in, for example, Listings 182 and 183.
LISTING 182: myenv-noAdd5.yaml
noAdditionalIndent:
myenv:
body: 0
optionalArguments: 1
mandatoryArguments: 0
LISTING 183: myenv-noAdd6.yaml
noAdditionalIndent:
myenv:
body: 0
optionalArguments: 0
mandatoryArguments: 1
Upon running
cmh:$ latexindent.pl myenv.tex -l myenv-noAdd5.yaml
cmh:$ latexindent.pl myenv.tex -l myenv-noAdd6.yaml
we obtain the respective outputs given in Listings 184 and 185. Note that in Listing 184 the text
for the optional argument has not received any additional indentation, and that in Listing 185
the mandatory argument has not received any additional indentation; in both cases, the body has
not received any additional indentation.
LISTING 184: myenv-args.tex using
Listing 182
\begin{outer}
\begin{myenv}[%
optional argument text
optional argument text]%
{ mandatory argument text
mandatory argument text}
body of environment
body of environment
body of environment
\end{myenv}
\end{outer}
LISTING 185: myenv-args.tex using
Listing 183
\begin{outer}
\begin{myenv}[%
optional argument text
optional argument text]%
{ mandatory argument text
mandatory argument text}
body of environment
body of environment
body of environment
\end{myenv}
\end{outer}
indentRules: fields
[git] main @ 78d452f 2024-07-18 V3.24.4
5.8 noAdditionalIndent and indentRules 60
example 47
We may also specify indentation rules for environment code blocks using the indentRules field;
see, for example, Listings 186 and 187.
LISTING 186: myenv-rules1.yaml
indentRules:
myenv: " "
LISTING 187: myenv-rules2.yaml
indentRules:
myenv:
body: " "
On applying either of the following commands,
cmh:$ latexindent.pl myenv.tex -l myenv-rules1.yaml
cmh:$ latexindent.pl myenv.tex -l myenv-rules2.yaml
we obtain the output given in Listing 188; note in particular that the environment myenv has
received one tab (from the outer environment) plus three spaces from Listing 186 or 187.
LISTING 188: myenv.tex output (using either Listing 186 or Listing 187)
\begin{outer}
\begin{myenv}
␣␣␣body␣of␣environment
␣␣␣body␣of␣environment
␣␣␣body␣of␣environment
\end{myenv}
\end{outer}
If you specify a field in indentRules using anything other than horizontal space, it will be ignored.
example 48
Returning to the example in Listing 180 that contains optional and mandatory arguments. Upon
using Listing 186 as in
cmh:$ latexindent.pl myenv-args.tex -l=myenv-rules1.yaml
we obtain the output in Listing 189; note that the body, optional argument and mandatory argu-
ment of myenv have all received the same customised indentation.
LISTING 189: myenv-args.tex using Listing 186
\begin{outer}
\begin{myenv}[%
␣␣␣␣␣␣optional␣argument␣text
␣␣␣␣␣␣optional␣argument␣text]%
␣␣␣{␣mandatory␣argument␣text
␣␣␣␣␣␣mandatory␣argument␣text}
␣␣␣body␣of␣environment
␣␣␣body␣of␣environment
␣␣␣body␣of␣environment
\end{myenv}
\end{outer}
example 49
You can specify different indentation rules for the different features using, for example, List-
ings 190 and 191
[git] main @ 78d452f 2024-07-18 V3.24.4
5.8 noAdditionalIndent and indentRules 61
LISTING 190: myenv-rules3.yaml
indentRules:
myenv:
body: " "
optionalArguments: " "
LISTING 191: myenv-rules4.yaml
indentRules:
myenv:
body: " "
mandatoryArguments:
"\t\t"
After running
cmh:$ latexindent.pl myenv-args.tex -l myenv-rules3.yaml
cmh:$ latexindent.pl myenv-args.tex -l myenv-rules4.yaml
then we obtain the respective outputs given in Listings 192 and 193.
LISTING 192: myenv-args.tex using
Listing 190
\begin{outer}
\begin{myenv}[%
␣␣␣␣optional␣argument␣text
␣␣␣␣optional␣argument␣text]%
␣␣␣{␣mandatory␣argument␣text
␣␣␣mandatory␣argument␣text}
␣␣␣body␣of␣environment
␣␣␣body␣of␣environment
␣␣␣body␣of␣environment
\end{myenv}
\end{outer}
LISTING 193: myenv-args.tex using
Listing 191
\begin{outer}
\begin{myenv}[%
␣␣␣optional␣argument␣text
␣␣␣optional␣argument␣text]%
␣␣␣{␣mandatory␣argument␣text
␣␣␣mandatory␣argument␣text}
␣␣␣body␣of␣environment
␣␣␣body␣of␣environment
␣␣␣body␣of␣environment
\end{myenv}
\end{outer}
Note that in Listing 192, the optional argument has only received a single space of indentation,
while the mandatory argument has received the default (tab) indentation; the environment body
has received three spaces of indentation.
In Listing 193, the optional argument has received the default (tab) indentation, the manda-
tory argument has received two tabs of indentation, and the body has received three spaces of
indentation.
noAdditionalIndentGlobal: fields
Assuming that your environment name is not found within neither noAdditionalIndent nor indentRules,
the next place that latexindent.pl will look is noAdditionalIndentGlobal, and in particular for
the environments key (see Listing 194).
LISTING 194: noAdditionalIndentGlobal
343 noAdditionalIndentGlobal:
344 environments: 0 # 0/1
example 50
Let’s say that you change the value of environments to 1 in Listing 194, and that you run
cmh:$ latexindent.pl myenv-args.tex -l env-noAdditionalGlobal.yaml
cmh:$ latexindent.pl myenv-args.tex -l myenv-rules1.yaml,env-noAdditionalGlobal.yaml
The respective output from these two commands are in Listings 195 and 196; in Listing 195
notice that both environments receive no additional indentation but that the arguments of myenv
still do receive indentation. In Listing 196 notice that the outer environment does not receive
additional indentation, but because of the settings from myenv-rules1.yaml (in Listing 186 on
the preceding page), the myenv environment still does receive indentation.
[git] main @ 78d452f 2024-07-18 V3.24.4
5.8 noAdditionalIndent and indentRules 62
LISTING 195: myenv-args.tex using
Listing 194
\begin{outer}
\begin{myenv}[%
optional argument text
optional argument text]%
{ mandatory argument text
mandatory argument text}
body of environment
body of environment
body of environment
\end{myenv}
\end{outer}
LISTING 196: myenv-args.tex using
Listings 186 and 194
\begin{outer}
\begin{myenv}[%
optional argument text
optional argument text]%
{ mandatory argument text
mandatory argument text}
body of environment
body of environment
body of environment
\end{myenv}
\end{outer}
example 51
In fact, noAdditionalIndentGlobal also contains keys that control the indentation of optional
and mandatory arguments; on referencing Listings 197 and 198
LISTING 197:
opt-args-no-add-glob.yaml
noAdditionalIndentGlobal:
optionalArguments: 1
LISTING 198:
mand-args-no-add-glob.yaml
noAdditionalIndentGlobal:
mandatoryArguments: 1
we may run the commands
cmh:$ latexindent.pl myenv-args.tex -local opt-args-no-add-glob.yaml
cmh:$ latexindent.pl myenv-args.tex -local mand-args-no-add-glob.yaml
which produces the respective outputs given in Listings 199 and 200. Notice that in Listing 199
the optional argument has not received any additional indentation, and in Listing 200 the manda-
tory argument has not received any additional indentation.
LISTING 199: myenv-args.tex using
Listing 197
\begin{outer}
\begin{myenv}[%
optional argument text
optional argument text]%
{ mandatory argument text
mandatory argument text}
body of environment
body of environment
body of environment
\end{myenv}
\end{outer}
LISTING 200: myenv-args.tex using
Listing 198
\begin{outer}
\begin{myenv}[%
optional argument text
optional argument text]%
{ mandatory argument text
mandatory argument text}
body of environment
body of environment
body of environment
\end{myenv}
\end{outer}
indentRulesGlobal: fields
The final check that latexindent.pl will make is to look for indentRulesGlobal as detailed in
Listing 201.
LISTING 201: indentRulesGlobal
359 indentRulesGlobal:
360 environments: 0 # 0/h-space
[git] main @ 78d452f 2024-07-18 V3.24.4
5.8 noAdditionalIndent and indentRules 63
example 52
If you change the environments field to anything involving horizontal space, say " ", and then
run the following commands
cmh:$ latexindent.pl myenv-args.tex -l env-indentRules.yaml
cmh:$ latexindent.pl myenv-args.tex -l myenv-rules1.yaml,env-indentRules.yaml
then the respective output is shown in Listings 202 and 203. Note that in Listing 202, both
the environment blocks have received a single-space indentation, whereas in Listing 203 the
outer environment has received single-space indentation (specified by indentRulesGlobal),
but myenv has received " ", as specified by the particular indentRules for myenv Listing 186
on page 60.
LISTING 202: myenv-args.tex using
Listing 201
\begin{outer}
␣\begin{myenv}[%
␣␣␣␣␣optional␣argument␣text
␣␣␣␣␣optional␣argument␣text]%
␣␣{␣mandatory␣argument␣text
␣␣␣␣␣mandatory␣argument␣text}
␣␣body␣of␣environment
␣␣body␣of␣environment
␣␣body␣of␣environment
␣\end{myenv}
\end{outer}
LISTING 203: myenv-args.tex using
Listings 186 and 201
\begin{outer}
␣\begin{myenv}[%
␣␣␣␣␣␣␣optional␣argument␣text
␣␣␣␣␣␣␣optional␣argument␣text]%
␣␣␣␣{␣mandatory␣argument␣text
␣␣␣␣␣␣␣mandatory␣argument␣text}
␣␣␣␣body␣of␣environment
␣␣␣␣body␣of␣environment
␣␣␣␣body␣of␣environment
␣\end{myenv}
\end{outer}
example 53
You can specify indentRulesGlobal for both optional and mandatory arguments, as detailed in
Listings 204 and 205
LISTING 204:
opt-args-indent-rules-glob.yaml
indentRulesGlobal:
optionalArguments: "\t\t"
LISTING 205:
mand-args-indent-rules-glob.yaml
indentRulesGlobal:
mandatoryArguments: "\t\t"
Upon running the following commands
cmh:$ latexindent.pl myenv-args.tex -local opt-args-indent-rules-glob.yaml
cmh:$ latexindent.pl myenv-args.tex -local mand-args-indent-rules-glob.yaml
we obtain the respective outputs in Listings 206 and 207. Note that the optional argument in
Listing 206 has received two tabs worth of indentation, while the mandatory argument has done
so in Listing 207.
LISTING 206: myenv-args.tex using
Listing 204
\begin{outer}
\begin{myenv}[%
optional argument text
optional argument text]%
{ mandatory argument text
mandatory argument text}
body of environment
body of environment
body of environment
\end{myenv}
\end{outer}
LISTING 207: myenv-args.tex using
Listing 205
\begin{outer}
\begin{myenv}[%
optional argument text
optional argument text]%
{ mandatory argument text
mandatory argument text}
body of environment
body of environment
body of environment
\end{myenv}
\end{outer}
[git] main @ 78d452f 2024-07-18 V3.24.4
5.8 noAdditionalIndent and indentRules 64
5.8.2 Environments with items
With reference to Listings 133 and 136 on page 46 and on page 47, some commands may contain
item commands; for the purposes of this discussion, we will use the code from Listing 134 on
page 46.
Assuming that you’ve populated itemNames with the name of your item, you can put the item name
into noAdditionalIndent as in Listing 208, although a more efficient approach may be to change
the relevant field in itemNames to 0.
example 54
Similarly, you can customise the indentation that your item receives using indentRules, as in
Listing 209
LISTING 208: item-noAdd1.yaml
noAdditionalIndent:
item: 1
# itemNames:
# item: 0
LISTING 209: item-rules1.yaml
indentRules:
item: " "
Upon running the following commands
cmh:$ latexindent.pl items1.tex -local item-noAdd1.yaml
cmh:$ latexindent.pl items1.tex -local item-rules1.yaml
the respective outputs are given in Listings 210 and 211; note that in Listing 210 that the text
after each item has not received any additional indentation, and in Listing 211, the text after
each item has received a single space of indentation, specified by Listing 209.
LISTING 210: items1.tex using
Listing 208
\begin{itemize}
\item some text here
some more text here
some more text here
\item another item
some more text here
\end{itemize}
LISTING 211: items1.tex using
Listing 209
\begin{itemize}
\item␣some␣text␣here
␣some␣more␣text␣here
␣some␣more␣text␣here
\item␣another␣item
␣some␣more␣text␣here
\end{itemize}
example 55
Alternatively, you might like to populate noAdditionalIndentGlobal or indentRulesGlobal
using the items key, as demonstrated in Listings 212 and 213. Note that there is a need to
‘reset/remove’ the item field from indentRules in both cases (see the hierarchy description
given on page 55) as the item command is a member of indentRules by default.
LISTING 212:
items-noAdditionalGlobal.yaml
indentRules:
item: 0
noAdditionalIndentGlobal:
items: 1
LISTING 213:
items-indentRulesGlobal.yaml
indentRules:
item: 0
indentRulesGlobal:
items: " "
Upon running the following commands,
cmh:$ latexindent.pl items1.tex -local items-noAdditionalGlobal.yaml
cmh:$ latexindent.pl items1.tex -local items-indentRulesGlobal.yaml
the respective outputs from Listings 210 and 211 are obtained; note, however, that all such item
commands without their own individual noAdditionalIndent or indentRules settings would
behave as in these listings.
[git] main @ 78d452f 2024-07-18 V3.24.4
5.8 noAdditionalIndent and indentRules 65
5.8.3 Commands with arguments
example 56
Let’s begin with the simple example in Listing 214; when latexindent.pl operates on this file,
the default output is shown in Listing 215.
a
LISTING 214: mycommand.tex
\mycommand
{
mand arg text
mand arg text}
[
opt arg text
opt arg text
]
LISTING 215: mycommand.tex default
output
\mycommand
{
mand arg text
mand arg text}
[
opt arg text
opt arg text
]
As in the environment-based case (see Listings 174 and 175 on page 57) we may specify noAdditionalIndent
either in ‘scalar’ form, or in ‘field’ form, as shown in Listings 216 and 217
LISTING 216: mycommand-noAdd1.yaml
noAdditionalIndent:
mycommand: 1
LISTING 217: mycommand-noAdd2.yaml
noAdditionalIndent:
mycommand:
body: 1
After running the following commands,
cmh:$ latexindent.pl mycommand.tex -l mycommand-noAdd1.yaml
cmh:$ latexindent.pl mycommand.tex -l mycommand-noAdd2.yaml
we receive the respective output given in Listings 218 and 219
LISTING 218: mycommand.tex using
Listing 216
\mycommand
{
mand arg text
mand arg text}
[
opt arg text
opt arg text
]
LISTING 219: mycommand.tex using
Listing 217
\mycommand
{
mand arg text
mand arg text}
[
opt arg text
opt arg text
]
Note that in Listing 218 that the ‘body’, optional argument and mandatory argument have all
received no additional indentation, while in Listing 219, only the ‘body’ has not received any
additional indentation. We define the ‘body’ of a command as any lines following the command
name that include its optional or mandatory arguments.
a
The command code blocks have quite a few subtleties, described in Section 5.9 on page 73.
example 57
We may further customise noAdditionalIndent for mycommand as we did in Listings 182 and 183
on page 59; explicit examples are given in Listings 220 and 221.
[git] main @ 78d452f 2024-07-18 V3.24.4
5.8 noAdditionalIndent and indentRules 66
LISTING 220: mycommand-noAdd3.yaml
noAdditionalIndent:
mycommand:
body: 0
optionalArguments: 1
mandatoryArguments: 0
LISTING 221: mycommand-noAdd4.yaml
noAdditionalIndent:
mycommand:
body: 0
optionalArguments: 0
mandatoryArguments: 1
After running the following commands,
cmh:$ latexindent.pl mycommand.tex -l mycommand-noAdd3.yaml
cmh:$ latexindent.pl mycommand.tex -l mycommand-noAdd4.yaml
we receive the respective output given in Listings 222 and 223.
LISTING 222: mycommand.tex using
Listing 220
\mycommand
{
mand arg text
mand arg text}
[
opt arg text
opt arg text
]
LISTING 223: mycommand.tex using
Listing 221
\mycommand
{
mand arg text
mand arg text}
[
opt arg text
opt arg text
]
example 58
Attentive readers will note that the body of mycommand in both Listings 222 and 223 has received
no additional indent, even though body is explicitly set to 0 in both Listings 220 and 221. This is
because, by default, noAdditionalIndentGlobal for commands is set to 1 by default; this can
be easily fixed as in Listings 224 and 225.
LISTING 224: mycommand-noAdd5.yaml
noAdditionalIndent:
mycommand:
body: 0
optionalArguments: 1
mandatoryArguments: 0
noAdditionalIndentGlobal:
commands: 0
LISTING 225: mycommand-noAdd6.yaml
noAdditionalIndent:
mycommand:
body: 0
optionalArguments: 0
mandatoryArguments: 1
noAdditionalIndentGlobal:
commands: 0
After running the following commands,
cmh:$ latexindent.pl mycommand.tex -l mycommand-noAdd5.yaml
cmh:$ latexindent.pl mycommand.tex -l mycommand-noAdd6.yaml
we receive the respective output given in Listings 226 and 227.
LISTING 226: mycommand.tex using
Listing 224
\mycommand
{
mand arg text
mand arg text}
[
opt arg text
opt arg text
]
LISTING 227: mycommand.tex using
Listing 225
\mycommand
{
mand arg text
mand arg text}
[
opt arg text
opt arg text
]
[git] main @ 78d452f 2024-07-18 V3.24.4
5.8 noAdditionalIndent and indentRules 67
Both indentRules and indentRulesGlobal can be adjusted as they were for environment code
blocks, as in Listings 190 and 191 on page 61 and Listings 201, 204 and 205 on pages 6263.
5.8.4 ifelsefi code blocks
example 59
Let’s use the simple example shown in Listing 228; when latexindent.pl operates on this file,
the output as in Listing 229; note that the body of each of the \if statements have been indented,
and that the \else statement has been accounted for correctly.
LISTING 228: ifelsefi1.tex
\ifodd\radius
\ifnum\radius<14
\pgfmathparse{100-(\radius)*4};
\else
\pgfmathparse{200-(\radius)*3};
\fi\fi
LISTING 229: ifelsefi1.tex default
output
\ifodd\radius
\ifnum\radius<14
\pgfmathparse{100-(\radius)*4};
\else
\pgfmathparse{200-(\radius)*3};
\fi\fi
It is recommended to specify noAdditionalIndent and indentRules in the ‘scalar’ form only
for these type of code blocks, although the ‘field’ form would work, assuming that body was
specified. Examples are shown in Listings 230 and 231.
LISTING 230: ifnum-noAdd.yaml
noAdditionalIndent:
ifnum: 1
LISTING 231: ifnum-indent-rules.yaml
indentRules:
ifnum: " "
After running the following commands,
cmh:$ latexindent.pl ifelsefi1.tex -local ifnum-noAdd.yaml
cmh:$ latexindent.pl ifelsefi1.tex -l ifnum-indent-rules.yaml
we receive the respective output given in Listings 232 and 233; note that in Listing 232, the
ifnum code block has not received any additional indentation, while in Listing 233, the ifnum
code block has received one tab and two spaces of indentation.
LISTING 232: ifelsefi1.tex using
Listing 230
\ifodd\radius
\ifnum\radius<14
\pgfmathparse{100-(\radius)*4};
\else
\pgfmathparse{200-(\radius)*3};
\fi\fi
LISTING 233: ifelsefi1.tex using
Listing 231
\ifodd\radius
\ifnum\radius<14
␣␣\pgfmathparse{100-(\radius)*4};
\else
␣␣\pgfmathparse{200-(\radius)*3};
\fi\fi
example 60
We may specify noAdditionalIndentGlobal and indentRulesGlobal as in Listings 234 and 235.
LISTING 234:
ifelsefi-noAdd-glob.yaml
noAdditionalIndentGlobal:
ifElseFi: 1
LISTING 235:
ifelsefi-indent-rules-global.yaml
indentRulesGlobal:
ifElseFi: " "
Upon running the following commands
[git] main @ 78d452f 2024-07-18 V3.24.4
5.8 noAdditionalIndent and indentRules 68
cmh:$ latexindent.pl ifelsefi1.tex -local ifelsefi-noAdd-glob.yaml
cmh:$ latexindent.pl ifelsefi1.tex -l ifelsefi-indent-rules-global.yaml
we receive the outputs in Listings 236 and 237; notice that in Listing 236 neither of the ifelsefi
code blocks have received indentation, while in Listing 237 both code blocks have received a
single space of indentation.
LISTING 236: ifelsefi1.tex using
Listing 234
\ifodd\radius
\ifnum\radius<14
\pgfmathparse{100-(\radius)*4};
\else
\pgfmathparse{200-(\radius)*3};
\fi\fi
LISTING 237: ifelsefi1.tex using
Listing 235
\ifodd\radius
␣\ifnum\radius<14
␣␣\pgfmathparse{100-(\radius)*4};
␣\else
␣␣\pgfmathparse{200-(\radius)*3};
␣\fi\fi
example 61
We can further explore the treatment of ifElseFi code blocks in Listing 238, and the associ-
ated default output given in Listing 239; note, in particular,
U: 2018-04-27
that the bodies of each of the ‘or
statements’ have been indented.
LISTING 238: ifelsefi2.tex
\ifcase#1
zero%
\or
one%
\or
two%
\or
three%
\else
default
\fi
LISTING 239: ifelsefi2.tex default
output
\ifcase#1
zero%
\or
one%
\or
two%
\or
three%
\else
default
\fi
5.8.5 specialBeginEnd code blocks
Let’s use the example from Listing 138 on page 48 which has default output shown in Listing 139
on page 48.
example 62
It is recommended to specify noAdditionalIndent and indentRules in the ‘scalar’ form for
these type of code blocks, although the ‘field’ form would work, assuming that body was specified.
Examples are shown in Listings 240 and 241.
LISTING 240: displayMath-noAdd.yaml
noAdditionalIndent:
displayMath: 1
LISTING 241:
displayMath-indent-rules.yaml
indentRules:
displayMath: "\t\t\t"
After running the following commands,
cmh:$ latexindent.pl special1.tex -local displayMath-noAdd.yaml
cmh:$ latexindent.pl special1.tex -l displayMath-indent-rules.yaml
we receive the respective output given in Listings 242 and 243; note that in Listing 242, the
displayMath code block has not received any additional indentation, while in Listing 243, the
displayMath code block has received three tabs worth of indentation.
[git] main @ 78d452f 2024-07-18 V3.24.4
5.8 noAdditionalIndent and indentRules 69
LISTING 242: special1.tex using
Listing 240
The function $f$ has formula
\[
f(x)=x^2.
\]
If you like splitting dollars,
$
g(x)=f(2x)
$
LISTING 243: special1.tex using
Listing 241
The function $f$ has formula
\[
f(x)=x^2.
\]
If you like splitting dollars,
$
g(x)=f(2x)
$
example 63
We may specify noAdditionalIndentGlobal and indentRulesGlobal as in Listings 244 and 245.
LISTING 244: special-noAdd-glob.yaml
noAdditionalIndentGlobal:
specialBeginEnd: 1
LISTING 245:
special-indent-rules-global.yaml
indentRulesGlobal:
specialBeginEnd: " "
Upon running the following commands
cmh:$ latexindent.pl special1.tex -local special-noAdd-glob.yaml
cmh:$ latexindent.pl special1.tex -l special-indent-rules-global.yaml
we receive the outputs in Listings 246 and 247; notice that in Listing 246 neither of the special
code blocks have received indentation, while in Listing 247 both code blocks have received a
single space of indentation.
LISTING 246: special1.tex using
Listing 244
The function $f$ has formula
\[
f(x)=x^2.
\]
If you like splitting dollars,
$
g(x)=f(2x)
$
LISTING 247: special1.tex using
Listing 245
The␣function␣$f$␣has␣formula
\[
␣f(x)=x^2.
\]
If␣you␣like␣splitting␣dollars,
$
␣g(x)=f(2x)
$
5.8.6 afterHeading code blocks
Let’s use the example Listing 248 for demonstration throughout this Section. As discussed on page 54,
by default latexindent.pl will not add indentation after headings.
LISTING 248: headings2.tex
\paragraph{paragraph
title}
paragraph text
paragraph text
example 64
On using the YAML file in Listing 250 by running the command
cmh:$ latexindent.pl headings2.tex -l headings3.yaml
we obtain the output in Listing 249. Note that the argument of paragraph has received (default)
indentation, and that the body after the heading statement has received (default) indentation.
[git] main @ 78d452f 2024-07-18 V3.24.4
5.8 noAdditionalIndent and indentRules 70
LISTING 249: headings2.tex using
Listing 250
\paragraph{paragraph
title}
paragraph text
paragraph text
LISTING 250: headings3.yaml
indentAfterHeadings:
paragraph:
indentAfterThisHeading: 1
level: 1
If we specify noAdditionalIndent as in Listing 252 and run the command
cmh:$ latexindent.pl headings2.tex -l headings4.yaml
then we receive the output in Listing 251. Note that the arguments and the body after the heading
of paragraph has received no additional indentation, because we have specified noAdditionalIndent
in scalar form.
LISTING 251: headings2.tex using
Listing 252
\paragraph{paragraph
title}
paragraph text
paragraph text
LISTING 252: headings4.yaml
indentAfterHeadings:
paragraph:
indentAfterThisHeading: 1
level: 1
noAdditionalIndent:
paragraph: 1
example 65
Similarly, if we specify indentRules as in Listing 254 and run analogous commands to those
above, we receive the output in Listing 253; note that the body, mandatory argument and content
after the heading of paragraph have all received three tabs worth of indentation.
LISTING 253: headings2.tex using Listing 254
\paragraph{paragraph
title}
paragraph text
paragraph text
LISTING 254: headings5.yaml
indentAfterHeadings:
paragraph:
indentAfterThisHeading: 1
level: 1
indentRules:
paragraph: "\t\t\t"
example 66
We may, instead, specify noAdditionalIndent in ‘field’ form, as in Listing 256 which gives the
output in Listing 255.
LISTING 255: headings2.tex using
Listing 256
\paragraph{paragraph
title}
paragraph text
paragraph text
LISTING 256: headings6.yaml
indentAfterHeadings:
paragraph:
indentAfterThisHeading: 1
level: 1
noAdditionalIndent:
paragraph:
body: 0
mandatoryArguments: 0
afterHeading: 1
example 67
Analogously, we may specify indentRules as in Listing 258 which gives the output in Listing 257;
note that mandatory argument text has only received a single space of indentation, while the body
after the heading has received three tabs worth of indentation.
[git] main @ 78d452f 2024-07-18 V3.24.4
5.8 noAdditionalIndent and indentRules 71
LISTING 257: headings2.tex using
Listing 258
\paragraph{paragraph
title}
paragraph text
paragraph text
LISTING 258: headings7.yaml
indentAfterHeadings:
paragraph:
indentAfterThisHeading: 1
level: 1
indentRules:
paragraph:
mandatoryArguments: " "
afterHeading: "\t\t\t"
example 68
Finally, let’s consider noAdditionalIndentGlobal and indentRulesGlobal shown in Listings 260
and 262 respectively, with respective output in Listings 259 and 261. Note that in Listing 260
the mandatory argument of paragraph has received a (default) tab’s worth of indentation, while
the body after the heading has received no additional indentation. Similarly, in Listing 261, the
argument has received both a (default) tab plus two spaces of indentation (from the global rule
specified in Listing 262), and the remaining body after paragraph has received just two spaces
of indentation.
LISTING 259: headings2.tex using
Listing 260
\paragraph{paragraph
title}
paragraph text
paragraph text
LISTING 260: headings8.yaml
indentAfterHeadings:
paragraph:
indentAfterThisHeading: 1
level: 1
noAdditionalIndentGlobal:
afterHeading: 1
LISTING 261: headings2.tex using
Listing 262
\paragraph{paragraph
␣␣title}
␣␣paragraph␣text
␣␣paragraph␣text
LISTING 262: headings9.yaml
indentAfterHeadings:
paragraph:
indentAfterThisHeading: 1
level: 1
indentRulesGlobal:
afterHeading: " "
5.8.7 The remaining code blocks
Referencing the different types of code blocks in Table 2 on page 56, we have a few code blocks
yet to cover; these are very similar to the commands code block type covered comprehensively in
Section 5.8.3 on page 65, but a small discussion defining these remaining code blocks is necessary.
5.8.7.1 keyEqualsValuesBracesBrackets
latexindent.pl defines this type of code block by the following criteria:
it must immediately follow either { OR [ OR , with comments and blank lines allowed.
then it has a name made up of the characters detailed in Table 2 on page 56;
then an = symbol;
then at least one set of curly braces or square brackets (comments and line breaks allowed
throughout).
See the keyEqualsValuesBracesBrackets: follow and keyEqualsValuesBracesBrackets:
name fields of the fine tuning section in Listing 566 on page 144
N: 2019-07-13
example 69
An example is shown in Listing 263, with the default output given in Listing 264.
[git] main @ 78d452f 2024-07-18 V3.24.4
5.8 noAdditionalIndent and indentRules 72
LISTING 263: pgfkeys1.tex
\pgfkeys{/tikz/.cd,
start coordinate/.initial={0,
\vertfactor},
}
LISTING 264: pgfkeys1.tex default
output
\pgfkeys{/tikz/.cd,
start coordinate/.initial={0,
\vertfactor},
}
In Listing 264, note that the maximum indentation is three tabs, and these come from:
the \pgfkeys command’s mandatory argument;
the start coordinate/.initial key’s mandatory argument;
the start coordinate/.initial key’s body, which is defined as any lines following the
name of the key that include its arguments. This is the part controlled by the body field for
noAdditionalIndent and friends from page 55.
5.8.7.2 namedGroupingBracesBrackets
This type of code block is mostly motivated by tikz-based code; we define this code block as follows:
it must immediately follow either horizontal space OR one or more line breaks OR { OR [ OR $
OR ) OR (
the name may contain the characters detailed in Table 2 on page 56;
then at least one set of curly braces or square brackets (comments and line breaks allowed
throughout).
See the NamedGroupingBracesBrackets: follow and NamedGroupingBracesBrackets: name
fields of the fine tuning section in Listing 566 on page 144
N: 2019-07-13
example 70
A simple example is given in Listing 265, with default output in Listing 266.
LISTING 265: child1.tex
\coordinate
child[grow=down]{
edge from parent [antiparticle]
node [above=3pt] {$C$}
}
LISTING 266: child1.tex default output
\coordinate
child[grow=down]{
edge from parent [antiparticle]
node [above=3pt] {$C$}
}
In particular, latexindent.pl considers child, parent and node all to be namedGroupingBracesBrackets
a
.
Referencing Listing 266, note that the maximum indentation is two tabs, and these come from:
the child’s mandatory argument;
the child’s body, which is defined as any lines following the name of the namedGroupingBracesBrackets
that include its arguments. This is the part controlled by the body field for noAdditionalIndent
and friends from page 55.
a
You may like to verify this by using the -tt option and checking indent.log!
5.8.7.3 UnNamedGroupingBracesBrackets
occur in a variety of situations; specifically, we define this type of code block as satisfying the follow-
ing criteria:
it must immediately follow either { OR [ OR , OR & OR ) OR ( OR $;
then at least one set of curly braces or square brackets (comments and line breaks allowed
throughout).
See the UnNamedGroupingBracesBrackets: follow field of the fine tuning section in Listing 566
on page 144
N: 2019-07-13
[git] main @ 78d452f 2024-07-18 V3.24.4
5.9 Commands and the strings between their arguments 73
example 71
An example is shown in Listing 267 with default output give in Listing 268.
LISTING 267: psforeach1.tex
\psforeach{\row}{%
{
{3,2.8,2.7,3,3.1}},%
{2.8,1,1.2,2,3},%
}
LISTING 268: psforeach1.tex default
output
\psforeach{\row}{%
{
{3,2.8,2.7,3,3.1}},%
{2.8,1,1.2,2,3},%
}
Referencing Listing 268, there are three sets of unnamed braces. Note also that the maximum
value of indentation is three tabs, and these come from:
the \psforeach command’s mandatory argument;
the first un-named braces mandatory argument;
the first un-named braces body, which we define as any lines following the first open-
ing { or [ that defined the code block. This is the part controlled by the body field for
noAdditionalIndent and friends from page 55.
Users wishing to customise the mandatory and/or optional arguments on a per-name basis for the
UnNamedGroupingBracesBrackets should use always-un-named.
5.8.7.4 filecontents
code blocks behave just as environments, except that neither arguments nor items are sought.
5.8.8 Summary
Having considered all of the different types of code blocks, the functions of the fields given in List-
ings 269 and 270 should now make sense.
LISTING 269: noAdditionalIndentGlobal
343 noAdditionalIndentGlobal:
344 environments: 0 # 0/1
345 commands: 1 # 0/1
346 optionalArguments: 0 # 0/1
347 mandatoryArguments: 0 # 0/1
348 ifElseFi: 0 # 0/1
349 items: 0 # 0/1
350 keyEqualsValuesBracesBrackets: 0 # 0/1
351 namedGroupingBracesBrackets: 0 # 0/1
352 UnNamedGroupingBracesBrackets: 0 # 0/1
353 specialBeginEnd: 0 # 0/1
354 afterHeading: 0 # 0/1
355 filecontents: 0 # 0/1
LISTING 270: indentRulesGlobal
359 indentRulesGlobal:
360 environments: 0 #
0/h-space
361 commands: 0 #
0/h-space
362 optionalArguments: 0 #
0/h-space
363 mandatoryArguments: 0 #
0/h-space
364 ifElseFi: 0 #
0/h-space
365 items: 0 #
0/h-space
366 keyEqualsValuesBracesBrackets: 0 #
0/h-space
367 namedGroupingBracesBrackets: 0 #
0/h-space
368 UnNamedGroupingBracesBrackets: 0 #
0/h-space
369 specialBeginEnd: 0 #
0/h-space
370 afterHeading: 0 #
0/h-space
371 filecontents: 0 #
0/h-space
5.9 Commands and the strings between their arguments
The command code blocks will always look for optional (square bracketed) and mandatory (curly
braced) arguments which can contain comments, line breaks and ‘beamer’ commands <.*?> between
[git] main @ 78d452f 2024-07-18 V3.24.4
5.9 Commands and the strings between their arguments 74
them. There are switches that can allow them to contain other strings, which we discuss next.
commandCodeBlocks: fields
The commandCodeBlocks field
U: 2018-04-27
contains a few switches detailed in Listing 271.
LISTING 271: commandCodeBlocks
374 commandCodeBlocks:
375 roundParenthesesAllowed: 1
376 stringsAllowedBetweenArguments:
377 - amalgamate: 1
378 - node
379 - at
380 - to
381 - decoration
382 - \+\+
383 - \-\-
384 - \#\#\d
385 commandNameSpecial:
386 - amalgamate: 1
387 - ’@ifnextchar\[’
388
389 # change dos line breaks into unix
roundParenthesesAllowed: 0|1
example 72
The need for this field was mostly motivated by commands found in code used to generate images
in PSTricks and tikz; for example, let’s consider the code given in Listing 272.
LISTING 272: pstricks1.tex
\defFunction[algebraic]{torus}(u,v)
{(2+cos(u))*cos(v+\Pi)}
{(2+cos(u))*sin(v+\Pi)}
{sin(u)}
LISTING 273: pstricks1 default output
\defFunction[algebraic]{torus}(u,v)
{(2+cos(u))*cos(v+\Pi)}
{(2+cos(u))*sin(v+\Pi)}
{sin(u)}
Notice that the \defFunction command has an optional argument, followed by a mandatory
argument, followed by a round-parenthesis argument, (u, v).
By default, because roundParenthesesAllowed is set to 1 in Listing 271, then latexindent.pl
will allow round parenthesis between optional and mandatory arguments. In the case of the code
in Listing 272, latexindent.pl finds all the arguments of defFunction, both before and after
(u,v).
The default output from running latexindent.pl on Listing 272 actually leaves it unchanged
(see Listing 273); note in particular, this is because of noAdditionalIndentGlobal as discussed
on page 66.
Upon using the YAML settings in Listing 275, and running the command
cmh:$ latexindent.pl pstricks1.tex -l noRoundParentheses.yaml
we obtain the output given in Listing 274.
[git] main @ 78d452f 2024-07-18 V3.24.4
5.9 Commands and the strings between their arguments 75
LISTING 274: pstricks1.tex using
Listing 275
\defFunction[algebraic]{torus}(u,v)
{(2+cos(u))*cos(v+\Pi)}
{(2+cos(u))*sin(v+\Pi)}
{sin(u)}
LISTING 275:
noRoundParentheses.yaml
commandCodeBlocks:
roundParenthesesAllowed: 0
Notice the difference between Listing 273 and Listing 274; in particular, in Listing 274, because
round parentheses are not allowed, latexindent.pl finds that the \defFunction command fin-
ishes at the first opening round parenthesis. As such, the remaining braced, mandatory, argu-
ments are found to be UnNamedGroupingBracesBrackets (see Table 2 on page 56) which, by
default, assume indentation for their body, and hence the tabbed indentation in Listing 274.
example 73
Let’s explore this using the YAML given in Listing 277 and run the command
cmh:$ latexindent.pl pstricks1.tex -l defFunction.yaml
then the output is as in Listing 276.
LISTING 276: pstricks1.tex using
Listing 277
\defFunction[algebraic]{torus}(u,v)
␣{(2+cos(u))*cos(v+\Pi)}
␣{(2+cos(u))*sin(v+\Pi)}
␣{sin(u)}
LISTING 277: defFunction.yaml
indentRules:
defFunction:
body: " "
Notice in Listing 276 that the body of the defFunction command i.e, the subsequent lines contain-
ing arguments after the command name, have received the single space of indentation specified
by Listing 277.
stringsAllowedBetweenArguments: fields
example 74
tikz users may well specify code such as that given in Listing 278; processing this code using
latexindent.pl gives the default output in Listing 279.
LISTING 278: tikz-node1.tex
\draw[thin]
(c) to[in=110,out=-90]
++(0,-0.5cm)
node[below,align=left,scale=0.5]
LISTING 279: tikz-node1 default output
\draw[thin]
(c) to[in=110,out=-90]
++(0,-0.5cm)
node[below,align=left,scale=0.5]
With reference to Listing 271 on the previous page, we see that the strings
to, node, ++
are all allowed to appear between arguments; importantly, you are encouraged to add further
names to this field as necessary. This means that when latexindent.pl processes Listing 278,
it consumes:
the optional argument [thin]
the round-bracketed argument (c) because roundParenthesesAllowed is 1 by default
the string to (specified in stringsAllowedBetweenArguments)
the optional argument [in=110,out=-90]
the string ++ (specified in stringsAllowedBetweenArguments)
[git] main @ 78d452f 2024-07-18 V3.24.4
5.9 Commands and the strings between their arguments 76
the round-bracketed argument (0,-0.5cm) because roundParenthesesAllowed is 1 by
default
the string node (specified in stringsAllowedBetweenArguments)
the optional argument [below,align=left,scale=0.5]
example 75
We can explore this further, for example using Listing 281 and running the command
cmh:$ latexindent.pl tikz-node1.tex -l draw.yaml
we receive the output given in Listing 280.
LISTING 280: tikz-node1.tex using
Listing 281
\draw[thin]
␣␣(c)␣to[in=110,out=-90]
␣␣++(0,-0.5cm)
␣␣node[below,align=left,scale=0.5]
LISTING 281: draw.yaml
indentRules:
draw:
body: " "
Notice that each line after the \draw command (its ‘body’) in Listing 280 has been given the
appropriate two-spaces worth of indentation specified in Listing 281.
Let’s compare this with the output from using the YAML settings in Listing 283, and running the
command
cmh:$ latexindent.pl tikz-node1.tex -l no-strings.yaml
given in Listing 282.
LISTING 282: tikz-node1.tex using
Listing 283
\draw[thin]
(c) to[in=110,out=-90]
++(0,-0.5cm)
node[below,align=left,scale=0.5]
LISTING 283: no-strings.yaml
commandCodeBlocks:
stringsAllowedBetweenArguments:
0
In this case, latexindent.pl sees that:
the \draw command finishes after the (c), as stringsAllowedBetweenArguments has
been set to 0 so there are no strings allowed between arguments;
it finds a namedGroupingBracesBrackets called to (see Table 2 on page 56) with argu-
ment [in=110,out=-90]
it finds another namedGroupingBracesBrackets but this time called node with argument
[below,align=left,scale=0.5]
Referencing Listing 271 on page 74,
U: 2018-04-27
, we see that the first field in the stringsAllowedBetweenArguments
is amalgamate and is set to 1 by default. This is for users who wish to specify their settings in mul-
tiple YAML files. For example, by using the settings in either Listing 284 orListing 285 is equivalent
to using the settings in Listing 286.
[git] main @ 78d452f 2024-07-18 V3.24.4
5.9 Commands and the strings between their arguments 77
LISTING 284: amalgamate-demo.yaml
commandCodeBlocks:
stringsAllowedBetweenArguments:
- ’more’
- ’strings’
- ’here’
LISTING 285:
amalgamate-demo1.yaml
commandCodeBlocks:
stringsAllowedBetweenArguments:
-
amalgamate: 1
- ’more’
- ’strings’
- ’here’
LISTING 286:
amalgamate-demo2.yaml
commandCodeBlocks:
stringsAllowedBetweenArguments:
-
amalgamate: 1
- ’node’
- ’at’
- ’to’
- ’decoration’
- ’\+\+’
- ’\-\-’
- ’more’
- ’strings’
- ’here’
We specify amalgamate to be set to 0 and in which case any settings loaded prior to those specified,
including the default, will be overwritten. For example, using the settings in Listing 287 means that
only the strings specified in that field will be used.
LISTING 287: amalgamate-demo3.yaml
commandCodeBlocks:
stringsAllowedBetweenArguments:
-
amalgamate: 0
- ’further’
- ’settings’
It is important to note that the amalgamate field, if used, must be in the first field, and specified
using the syntax given in Listings 285 to 287.
example 76
We may explore this feature further with the code in Listing 288, whose default output is given
in Listing 289.
LISTING 288: for-each.tex
\foreach \x/\y in {0/1,1/2}{
body of foreach
}
LISTING 289: for-each default
output
\foreach \x/\y in {0/1,1/2}{
body of foreach
}
Let’s compare this with the output from using the YAML settings in Listing 291, and running the
command
cmh:$ latexindent.pl for-each.tex -l foreach.yaml
given in Listing 290.
LISTING 290: for-each.tex using
Listing 291
\foreach \x/\y in {0/1,1/2}{
body of foreach
}
LISTING 291: foreach.yaml
commandCodeBlocks:
stringsAllowedBetweenArguments:
-
amalgamate: 0
- ’\\x\/\\y’
- ’in’
You might like to compare the output given in Listing 289 and Listing 290. Note,in particular, in
[git] main @ 78d452f 2024-07-18 V3.24.4
5.9 Commands and the strings between their arguments 78
Listing 289 that the foreach command has not included any of the subsequent strings, and that
the braces have been treated as a namedGroupingBracesBrackets. In Listing 290 the foreach
command has been allowed to have \x/\y and in between arguments because of the settings
given in Listing 291.
commandNameSpecial: fields
There are some special command names
U: 2018-04-27
that do not fit within the names recognised by latexindent.pl,
the first one of which is \@ifnextchar[. From the perspective of latexindent.pl, the whole of the
text \@ifnextchar[ is a command, because it is immediately followed by sets of mandatory argu-
ments. However, without the commandNameSpecial field, latexindent.pl would not be able to
label it as such, because the [ is, necessarily, not matched by a closing ].
example 77
For example, consider the sample file in Listing 292, which has default output in Listing 293.
LISTING 292: ifnextchar.tex
\parbox{
\@ifnextchar[{arg 1}{arg 2}
}
LISTING 293: ifnextchar.tex
default output
\parbox{
\@ifnextchar[{arg 1}{arg 2}
}
Notice that in Listing 293 the parbox command has been able to indent its body, because latexindent.pl
has successfully found the command \@ifnextchar first; the pattern-matching of latexindent.pl
starts from the inner most <thing> and works outwards, discussed in more detail on page 127.
For demonstration, we can compare this output with that given in Listing 294 in which the settings
from Listing 295 have dictated that no special command names, including the \@ifnextchar[
command, should not be searched for specially; as such, the parbox command has been unable
to indent its body successfully, because the \@ifnextchar[ command has not been found.
LISTING 294: ifnextchar.tex using
Listing 295
\parbox{
\@ifnextchar[{arg 1}{arg 2}
}
LISTING 295: no-ifnextchar.yaml
commandCodeBlocks:
commandNameSpecial: 0
The amalgamate field can be used for commandNameSpecial, just as for stringsAllowedBetweenArguments.
The same condition holds as stated previously, which we state again here:
Warning!
It is important to note that the amalgamate field, if used, in either commandNameSpecial
or stringsAllowedBetweenArguments must be in the first field, and specified using
the syntax given in Listings 285 to 287.
[git] main @ 78d452f 2024-07-18 V3.24.4
SECTION 6
The -m (modifylinebreaks) switch
All features described in this section will only be relevant if the -m switch is used.
6.1 Text Wrapping . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 81
6.1.1 Text wrap: overview . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 81
6.1.2 Text wrap: simple examples . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 82
6.1.3 Text wrap: blocksFollow examples . . . . . . . . . . . . . . . . . . . . . . . . . . 83
6.1.4 Text wrap: blocksBeginWith examples . . . . . . . . . . . . . . . . . . . . . . . 87
6.1.5 Text wrap: blocksEndBefore examples . . . . . . . . . . . . . . . . . . . . . . . 89
6.1.6 Text wrap: trailing comments and spaces . . . . . . . . . . . . . . . . . . . . . . . 90
6.1.7 Text wrap: when before/after . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 91
6.1.8 Text wrap: wrapping comments . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 93
6.1.9 Text wrap: huge, tabstop and separator . . . . . . . . . . . . . . . . . . . . . . . . 94
6.2 oneSentencePerLine: modifying line breaks for sentences . . . . . . . . . . . . . . . . . 95
6.2.1 oneSentencePerLine: overview . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 96
6.2.2 oneSentencePerLine: sentencesFollow . . . . . . . . . . . . . . . . . . . . . . . . . 98
6.2.3 oneSentencePerLine: sentencesBeginWith . . . . . . . . . . . . . . . . . . . . . . 99
6.2.4 oneSentencePerLine: sentencesEndWith . . . . . . . . . . . . . . . . . . . . . . . 100
6.2.5 oneSentencePerLine: sentencesDoNOTcontain . . . . . . . . . . . . . . . . . . . . 102
6.2.6 Features of the oneSentencePerLine routine . . . . . . . . . . . . . . . . . . . . . 103
6.2.7 oneSentencePerLine: text wrapping and indenting sentences . . . . . . . . . . . 104
6.2.8 oneSentencePerLine: text wrapping and indenting sentences, when before/after107
6.2.9 oneSentencePerLine: text wrapping sentences and comments . . . . . . . . . . 108
6.3 Poly-switches . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 108
6.3.1 Poly-switches for environments . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 109
6.3.1.1 Adding line breaks: BeginStartsOnOwnLine and BodyStartsOnOwn-
Line . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 109
6.3.1.2 Adding line breaks: EndStartsOnOwnLine and EndFinishesWithLine-
Break . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 111
6.3.1.3 poly-switches 1, 2, and 3 only add line breaks when necessary . . . . 113
6.3.1.4 Removing line breaks (poly-switches set to 1) . . . . . . . . . . . . . 114
6.3.1.5 About trailing horizontal space . . . . . . . . . . . . . . . . . . . . . . . 116
6.3.1.6 poly-switch line break removal and blank lines . . . . . . . . . . . . . 116
6.3.2 Poly-switches for double backslash . . . . . . . . . . . . . . . . . . . . . . . . . . . 118
6.3.2.1 Double backslash starts on own line . . . . . . . . . . . . . . . . . . . . 118
[git] main @ 78d452f 2024-07-18 V3.24.4
80
6.3.2.2 Double backslash finishes with line break . . . . . . . . . . . . . . . . . 119
6.3.2.3 Double backslash poly-switches for specialBeginEnd . . . . . . . . . . 120
6.3.2.4 Double backslash poly-switches for optional and mandatory arguments120
6.3.2.5 Double backslash optional square brackets . . . . . . . . . . . . . . . . 121
6.3.3 Poly-switches for other code blocks . . . . . . . . . . . . . . . . . . . . . . . . . . . 122
6.3.4 Partnering BodyStartsOnOwnLine with argument-based poly-switches . . . . . 124
6.3.5 Conflicting poly-switches: sequential code blocks . . . . . . . . . . . . . . . . . . 125
6.3.6 Conflicting poly-switches: nested code blocks . . . . . . . . . . . . . . . . . . . . 126
modifylinebreaks: fields
As of Version 3.0, latexindent.pl has the -m switch, which permits latexindent.pl to modify
line breaks, according to the specifications in the modifyLineBreaks field. The settings in this field
will only be considered if the -m switch has been used. A snippet of the default settings of this field is
shown in Listing 296.
-m
LISTING 296: modifyLineBreaks
502 modifyLineBreaks:
503 preserveBlankLines: 1 # 0/1
504 condenseMultipleBlankLinesInto: 1 # 0/1
Having read the previous paragraph, it should sound reasonable that, if you call latexindent.pl
using the -m switch, then you give it permission to modify line breaks in your file, but let’s be clear:
Warning!
If you call latexindent.pl with the -m switch, then you are giving it permission
to modify line breaks. By default, the only thing that will happen is that multiple
blank lines will be condensed into one blank line; many other settings are possible,
discussed next.
preserveBlankLines: 0|1
This field is directly related to poly-switches, discussed in Section 6.3. By default, it is set to 1, which
means that blank lines will be protected from removal; however, regardless of this setting, multiple
blank lines can be condensed if condenseMultipleBlankLinesInto is greater than 0, discussed
next.
condenseMultipleBlankLinesInto: positive integer
Assuming that this switch takes an integer value greater than 0, latexindent.pl will condense
multiple blank lines into the number of blank lines illustrated by this switch.
example 78
As an example, Listing 297 shows a sample file with blank lines; upon running
cmh:$ latexindent.pl myfile.tex -m -o=+-mod1
the output is shown in Listing 298; note that the multiple blank lines have been condensed into
one blank line, and note also that we have used the -m switch!
[git] main @ 78d452f 2024-07-18 V3.24.4
6.1 Text Wrapping 81
LISTING 297: mlb1.tex
before blank line
after blank line
after blank line
LISTING 298: mlb1-mod1.tex
before blank line
after blank line
after blank line
6.1 Text Wrapping
N: 2022-03-13
The text wrapping routine has been over-hauled as of V3.16; I hope that the interface is simpler, and
most importantly, the results are better.
The complete settings for this feature are given in Listing 299.
-m
LISTING 299: textWrapOptions
532 textWrapOptions:
533 columns: 0
534 multipleSpacesToSingle: 1
535 removeBlockLineBreaks: 1
536 when: before # before/after
537 comments:
538 wrap: 0 # 0/1
539 inheritLeadingSpace: 0 # 0/1
540 blocksFollow:
541 headings: 1 # 0/1
542 commentOnPreviousLine: 1 # 0/1
543 par: 1 # 0/1
544 blankLine: 1 # 0/1
545 verbatim: 1 # 0/1
546 filecontents: 1 # 0/1
547 other: \\\]|\\item(?:\h|\[) # regex
548 blocksBeginWith:
549 A-Z: 1 # 0/1
550 a-z: 1 # 0/1
551 0-9: 0 # 0/1
552 other: 0 # regex
553 blocksEndBefore:
554 commentOnOwnLine: 1 # 0/1
555 verbatim: 1 # 0/1
556 filecontents: 1 # 0/1
557 other: \\begin\{|\\\[|\\end\{ # regex
558 huge: overflow # forbid mid-word line breaks
559 separator: ""
6.1.1 Text wrap: overview
An overview of how the text wrapping feature works:
1. the default value of columns is 0, which means that text wrapping will not happen by default;
2. it happens after verbatim blocks have been found;
3. it happens after the oneSentencePerLine routine (see Section 6.2);
4. it can happen before or after
N: 2023-01-01
all of the other code blocks are found and does not operate on
a per-code-block basis; when using before this means that, including indentation, you may
receive a column width wider than that which you specify in columns, and in which case you
probably wish to explore after in Section 6.1.7;
5. code blocks to be text wrapped will:
[git] main @ 78d452f 2024-07-18 V3.24.4
6.1 Text Wrapping 82
(a) follow the fields specified in blocksFollow
(b) begin with the fields specified in blocksBeginWith
(c) end before the fields specified in blocksEndBefore
6. setting columns to a value > 0 will text wrap blocks by first removing line breaks, and then
wrapping according to the specified value of columns;
7. setting columns to 1 will only remove line breaks within the text wrap block;
8. by default, the text wrapping routine will remove line breaks within text blocks because removeBlockLineBreaks
is set to 1; switch it to 0 if you wish to change this;
9. about trailing comments within text wrap blocks:
(a) trailing comments that do not have leading space instruct the text wrap routine to connect
the lines without space (see Listing 337);
(b) multiple trailing comments will be connected at the end of the text wrap block (see List-
ing 341);
(c) the number of spaces between the end of the text wrap block and the (possibly combined)
trailing comments is determined by the spaces (if any) at the end of the text wrap block
(see Listing 343);
10. trailing comments can receive text wrapping
N: 2023-01-01
; examples are shown in Section 6.1.8 and Sec-
tion 6.2.9.
We demonstrate this feature using a series of examples.
6.1.2 Text wrap: simple examples
example 79
Let’s use the sample text given in Listing 300.
LISTING 300: textwrap1.tex
Here is a line of text that will be wrapped by latexindent.pl.
Here is a line of text that will be wrapped by latexindent.pl.
We will change the value of columns in Listing 302 and then run the command
cmh:$ latexindent.pl -m -l textwrap1.yaml textwrap1.tex
then we receive the output given in Listing 301.
LISTING 301: textwrap1-mod1.tex
Here is a line of
text that will be
wrapped by
latexindent.pl.
Here is a line of
text that will be
wrapped by
latexindent.pl.
-m
LISTING 302: textwrap1.yaml
modifyLineBreaks:
textWrapOptions:
columns: 20
example 80
If we set columns to 1 then latexindent.pl remove line breaks within the text wrap block,
and will not perform text wrapping. We can use this to undo text wrapping.
Starting from the file in Listing 301 and using the settings in Listing 303
[git] main @ 78d452f 2024-07-18 V3.24.4
6.1 Text Wrapping 83
-m
LISTING 303: textwrap1A.yaml
modifyLineBreaks:
textWrapOptions:
columns: -1
and running
cmh:$ latexindent.pl -m -l textwrap1A.yaml textwrap1-mod1.tex
gives the output in Listing 304.
LISTING 304: textwrap1-mod1A.tex
Here is a line of text that will be wrapped by latexindent.pl.
Here is a line of text that will be wrapped by latexindent.pl.
example 81
By default, the text wrapping routine will convert multiple spaces into single spaces. You can
change this behaviour by flicking the switch multipleSpacesToSingle which we have done in
Listing 306
Using the settings in Listing 306 and running
cmh:$ latexindent.pl -m -l textwrap1B.yaml textwrap1-mod1.tex
gives the output in Listing 305.
LISTING 305: textwrap1-mod1B.tex
Here␣␣is␣a␣line␣of
text␣that␣will␣be
wrapped␣by
latexindent.pl.
Here␣is␣␣a␣line␣of
text␣that␣will␣be
wrapped␣by
latexindent.pl.
-m
LISTING 306: textwrap1B.yaml
modifyLineBreaks:
textWrapOptions:
columns: 20
multipleSpacesToSingle: 0
We note that in Listing 305 the multiple spaces have not been condensed into single spaces.
6.1.3 Text wrap: blocksFollow examples
We examine the blocksFollow field of Listing 299.
example 82
Let’s use the sample text given in Listing 307.
LISTING 307: tw-headings1.tex
\section{my heading}\label{mylabel1}
text to
be
wrapped from the first section
\subsection{subheading}
text to
be
wrapped from the first section
We note that Listing 307 contains the heading commands section and subsection. Upon run-
ning the command
[git] main @ 78d452f 2024-07-18 V3.24.4
6.1 Text Wrapping 84
cmh:$ latexindent.pl -m -l textwrap1.yaml tw-headings1.tex
then we receive the output given in Listing 308.
LISTING 308: tw-headings1-mod1.tex
\section{my heading}\label{mylabel1}
text to be wrapped
from the first
section
\subsection{subheading}
text to be wrapped
from the first
section
We reference Listing 299 on page 81 and also Listing 164 on page 53:
in Listing 299 the headings field is set to 1, which instructs latexindent.pl to read the
fields from Listing 164 on page 53, regardless of the value of indentAfterThisHeading or level;
the default is to assume that the heading command can, optionally, be followed by a label
command.
If you find scenarios in which the default value of headings does not work, then you can explore
the other field.
We can turn off headings as in Listing 310 and then run
cmh:$ latexindent.pl -m -l textwrap1.yaml,bf-no-headings.yaml tw-headings1.tex
gives the output in Listing 309, in which text wrapping has been instructed not to happen follow-
ing headings.
LISTING 309: tw-headings1-mod2.tex
\section{my heading}\label{mylabel1}
text to
be
wrapped from the first section
\subsection{subheading}
text to
be
wrapped from the first section
-m
LISTING 310: bf-no-headings.yaml
modifyLineBreaks:
textWrapOptions:
blocksFollow:
headings: 0
example 83
Let’s use the sample text given in Listing 311.
LISTING 311: tw-comments1.tex
% trailing comment
text to
be
wrapped following first comment
% another comment
text to
be
wrapped following second comment
We note that Listing 311 contains trailing comments. Upon running the command
cmh:$ latexindent.pl -m -l textwrap1.yaml tw-comments1.tex
[git] main @ 78d452f 2024-07-18 V3.24.4
6.1 Text Wrapping 85
then we receive the output given in Listing 312.
LISTING 312: tw-comments1-mod1.tex
% trailing comment
text to be wrapped
following first
comment
% another comment
text to be wrapped
following second
comment
With reference to Listing 299 on page 81 the commentOnPreviousLine field is set to 1, which
instructs latexindent.pl to find text wrap blocks after a comment on its own line.
We can turn off comments as in Listing 314 and then run
cmh:$ latexindent.pl -m -l textwrap1.yaml,bf-no-comments.yaml tw-comments1.tex
gives the output in Listing 313, in which text wrapping has been instructed not to happen follow-
ing comments on their own line.
LISTING 313: tw-comments1-mod2.tex
% trailing comment
text to
be
wrapped following first comment
% another comment
text to
be
wrapped following second comment
-m
LISTING 314: bf-no-comments.yaml
modifyLineBreaks:
textWrapOptions:
blocksFollow:
commentOnPreviousLine: 0
Referencing Listing 299 on page 81 the blocksFollow fields par, blankline, verbatim and filecontents
fields operate in analogous ways to those demonstrated in the above.
The other field of the blocksFollow can either be 0 (turned off) or set as a regular expression.
The default value is set to \\\]|\\item(?:\h|\[) which can be translated to backslash followed by a
square bracket or backslash item followed by horizontal space or a square bracket, or in other words,
end of display math or an item command.
example 84
Let’s use the sample text given in Listing 315.
LISTING 315: tw-disp-math1.tex
text to
be
wrapped before display math
\[ y = x\]
text to
be
wrapped after display math
We note that Listing 315 contains display math. Upon running the command
cmh:$ latexindent.pl -m -l textwrap1.yaml tw-disp-math1.tex
then we receive the output given in Listing 316.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.1 Text Wrapping 86
LISTING 316: tw-disp-math1-mod1.tex
text to be wrapped
before display math
\[ y = x\]
text to be wrapped
after display math
With reference to Listing 299 on page 81 the other field is set to \\\], which instructs latexindent.pl
to find text wrap blocks after the end of display math.
We can turn off this switch as in Listing 318 and then run
cmh:$ latexindent.pl -m -l textwrap1.yaml,bf-no-disp-math.yaml tw-disp-math1.tex
gives the output in Listing 317, in which text wrapping has been instructed not to happen follow-
ing display math.
LISTING 317:
tw-disp-math1-mod2.tex
text to be wrapped
before display math
\[ y = x\]
text to
be
wrapped after display math
-m
LISTING 318:
bf-no-disp-math.yaml
modifyLineBreaks:
textWrapOptions:
blocksFollow:
other: 0
Naturally, you should feel encouraged to customise this as you see fit.
The blocksFollow field deliberately does not default to allowing text wrapping to occur after begin
environment statements. You are encouraged to customize the other field to accommodate the
environments that you would like to text wrap individually, as in the next example.
example 85
Let’s use the sample text given in Listing 319.
LISTING 319: tw-bf-myenv1.tex
text to
be
wrapped before myenv environment
\begin{myenv}
text to
be
wrapped within myenv environment
\end{myenv}
text to
be
wrapped after myenv environment
We note that Listing 319 contains myenv environment. Upon running the command
cmh:$ latexindent.pl -m -l textwrap1.yaml tw-bf-myenv1.tex
then we receive the output given in Listing 320.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.1 Text Wrapping 87
LISTING 320: tw-bf-myenv1-mod1.tex
text to be wrapped
before myenv
environment
\begin{myenv}
text to
be
wrapped within myenv environment
\end{myenv}
text to
be
wrapped after myenv environment
We note that we have not received much text wrapping. We can turn do better by employing
Listing 322 and then run
cmh:$ latexindent.pl -m -l textwrap1.yaml,tw-bf-myenv.yaml tw-bf-myenv1.tex
which gives the output in Listing 321, in which text wrapping has been implemented across the
file.
LISTING 321:
tw-bf-myenv1-mod2.tex
text to be wrapped
before myenv
environment
\begin{myenv}
text to be wrapped
within myenv
environment
\end{myenv}
text to be wrapped
after myenv
environment
-m
LISTING 322: tw-bf-myenv.yaml
modifyLineBreaks:
textWrapOptions:
blocksFollow:
other: |-
(?x)
\\\]
|
\\item(?:\h|\[)
|
\\begin\{myenv\} # <--- new bit
| # <--- new bit
\\end\{myenv\} # <--- new bit
6.1.4 Text wrap: blocksBeginWith examples
We examine the blocksBeginWith field of Listing 299 with a series of examples.
example 86
By default, text wrap blocks can begin with the characters a-z and A-Z.
If we start with the file given in Listing 323
LISTING 323: tw-0-9.tex
123 text to
be
wrapped before display math
\[ y = x\]
456 text to
be
wrapped after display math
and run the command
cmh:$ latexindent.pl -m -l textwrap1.yaml tw-0-9.tex
then we receive the output given in Listing 324 in which text wrapping has not occurred.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.1 Text Wrapping 88
LISTING 324: tw-0-9-mod1.tex
123 text to
be
wrapped before display math
\[ y = x\]
456 text to
be
wrapped after display math
We can allow paragraphs to begin with 0-9 characters by using the settings in Listing 326 and
running
cmh:$ latexindent.pl -m -l textwrap1.yaml,bb-0-9-yaml tw-0-9.tex
gives the output in Listing 325, in which text wrapping has happened.
LISTING 325: tw-0-9-mod2.tex
123 text to be
wrapped before
display math
\[ y = x\]
456 text to be
wrapped after
display math
-m
LISTING 326: bb-0-9.yaml.yaml
modifyLineBreaks:
textWrapOptions:
blocksBeginWith:
0-9: 1
example 87
Let’s now use the file given in Listing 327
LISTING 327: tw-bb-announce1.tex
% trailing comment
\announce{announce text}
and text
to be
wrapped before
goes here
and run the command
cmh:$ latexindent.pl -m -l textwrap1.yaml tw-bb-announce1.tex
then we receive the output given in Listing 328 in which text wrapping has not occurred.
LISTING 328: tw-bb-announce1-mod1.tex
% trailing comment
\announce{announce text}
and text
to be
wrapped before
goes here
We can allow \announce to be at the beginning of paragraphs by using the settings in Listing 330
and running
cmh:$ latexindent.pl -m -l textwrap1.yaml,tw-bb-announce.yaml tw-bb-announce1.tex
gives the output in Listing 329, in which text wrapping has happened.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.1 Text Wrapping 89
LISTING 329:
tw-bb-announce1-mod2.tex
% trailing comment
\announce{announce
text} and text to
be wrapped before
goes here
-m
LISTING 330: tw-bb-announce.yaml
modifyLineBreaks:
textWrapOptions:
blocksBeginWith:
other: ’\\announce’
6.1.5 Text wrap: blocksEndBefore examples
We examine the blocksEndBefore field of Listing 299 with a series of examples.
example 88
Let’s use the sample text given in Listing 331.
LISTING 331: tw-be-equation.tex
before
equation
text
\begin{align}
1 & 2 \\
3 & 4
\end{align}
after
equation
text
We note that Listing 331 contains an environment. Upon running the command
cmh:$ latexindent.pl -m -l textwrap1A.yaml tw-be-equation.tex
then we receive the output given in Listing 332.
LISTING 332: tw-be-equation-mod1.tex
before equation text
\begin{align}
1 & 2 \\
3 & 4
\end{align}
after
equation
text
With reference to Listing 299 on page 81 the other field is set to \\begin\{|\\\[|\\end\{, which
instructs latexindent.pl to stop text wrap blocks before begin statements, display math, and
end statements.
We can turn off this switch as in Listing 333 and then run
cmh:$ latexindent.pl -m -l textwrap1A.yaml,tw-be-equation.yaml tw-be-equation.tex
gives the output in Listing 334, in which text wrapping has been instructed not to stop at these
statements.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.1 Text Wrapping 90
-m
LISTING 333: tw-be-equation.yaml
modifyLineBreaks:
textWrapOptions:
blocksEndBefore:
other: 0
LISTING 334: tw-be-equation-mod2.tex
before equation text \begin{align} 1 & 2 \\ 3 & 4 \end{align} after equation text
Naturally, you should feel encouraged to customise this as you see fit.
6.1.6 Text wrap: trailing comments and spaces
We explore the behaviour of the text wrap routine in relation to trailing comments using the following
examples.
example 89
The file in Listing 335 contains a trailing comment which does have a space infront of it.
Running the command
cmh:$ latexindent.pl -m tw-tc1.tex -l textwrap1A.yaml -o=+-mod1
gives the output given in Listing 336.
LISTING 335: tw-tc1.tex
foo␣%
bar
LISTING 336: tw-tc1-mod1.tex
foo bar%
example 90
The file in Listing 337 contains a trailing comment which does not have a space infront of it.
Running the command
cmh:$ latexindent.pl -m tw-tc2.tex -l textwrap1A.yaml -o=+-mod1
gives the output in Listing 338.
LISTING 337: tw-tc2.tex
foo%
bar
LISTING 338: tw-tc2-mod1.tex
foobar%
We note that, because there is not a space before the trailing comment, that the lines have been
joined without a space.
example 91
The file in Listing 339 contains multiple trailing comments.
Running the command
cmh:$ latexindent.pl -m tw-tc3.tex -l textwrap1A.yaml -o=+-mod1
gives the output in Listing 340.
LISTING 339: tw-tc3.tex
foo %1
bar%2
three
LISTING 340: tw-tc3-mod1.tex
foo barthree%1%2
[git] main @ 78d452f 2024-07-18 V3.24.4
6.1 Text Wrapping 91
example 92
The file in Listing 341 contains multiple trailing comments.
Running the command
cmh:$ latexindent.pl -m tw-tc4.tex -l textwrap1A.yaml -o=+-mod1
gives the output in Listing 342.
LISTING 341: tw-tc4.tex
foo %1
bar%2
three%3
LISTING 342: tw-tc4-mod1.tex
foo barthree%1%2%3
example 93
The file in Listing 343 contains multiple trailing comments.
Running the command
cmh:$ latexindent.pl -m tw-tc5.tex -l textwrap1A.yaml -o=+-mod1
gives the output in Listing 344.
LISTING 343: tw-tc5.tex
foo%1
bar%2
three␣%3
LISTING 344: tw-tc5-mod1.tex
foobarthree␣%1%2%3
The space at the end of the text block has been preserved.
example 94
The file in Listing 345 contains multiple trailing comments.
Running the command
cmh:$ latexindent.pl -m tw-tc6.tex -l textwrap1A.yaml -o=+-mod1
gives the output in Listing 346.
LISTING 345: tw-tc6.tex
foo%1
bar
LISTING 346: tw-tc6-mod1.tex
foobar␣%1
The space at the end of the text block has been preserved.
6.1.7 Text wrap: when before/after
The text wrapping routine operates, by default, before the
N: 2023-01-01
code blocks have been found, but this
can be changed to after:
before means it is likely that the columns of wrapped text may exceed the value specified in
columns;
after means it columns of wrapped text should not exceed the value specified in columns.
We demonstrate this in the following examples. See also Section 6.2.8.
example 95
Let’s begin with the file in Listing 347.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.1 Text Wrapping 92
LISTING 347: textwrap8.tex
This paragraph
has line breaks throughout its paragraph;
we would like to combine
the textwrapping
and paragraph removal routine.
\begin{myenv}
This paragraph
has line breaks throughout its paragraph;
we would like to combine
the textwrapping
and paragraph removal routine.
\end{myenv}
Using the settings given in Listing 349 and running the command
cmh:$ latexindent.pl textwrap8.tex -o=+-mod1.tex -l=tw-before1.yaml -m
gives the output given in Listing 348.
LISTING 348: textwrap8-mod1.tex
This paragraph has line breaks
throughout its paragraph; we would
like to combine the textwrapping
and paragraph removal routine.
\begin{myenv}
This paragraph has line breaks
throughout its paragraph; we would
like to combine the textwrapping
and paragraph removal routine.
\end{myenv}
----|----|----|----|----|----|----|----|
5 10 15 20 25 30 35 40
-m
LISTING 349: tw-before1.yaml
defaultIndent: ’
modifyLineBreaks:
textWrapOptions:
columns: 35
when: before # <!-------
blocksFollow:
other: \\begin\{myenv\}
We note that, in Listing 348, that the wrapped text has exceeded the specified value of columns
(35) given in Listing 349. We can affect this by changing when; we explore this next.
example 96
We continue working with Listing 347.
Using the settings given in Listing 351 and running the command
cmh:$ latexindent.pl textwrap8.tex -o=+-mod2.tex -l=tw-after1.yaml -m
gives the output given in Listing 350.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.1 Text Wrapping 93
LISTING 350: textwrap8-mod2.tex
This paragraph has line breaks
throughout its paragraph; we would
like to combine the textwrapping
and paragraph removal routine.
\begin{myenv}
This paragraph has line breaks
throughout its paragraph; we
would like to combine the
textwrapping and paragraph
removal routine.
\end{myenv}
----|----|----|----|----|----|----|----|
5 10 15 20 25 30 35 40
-m
LISTING 351: tw-after1.yaml
defaultIndent: ’
modifyLineBreaks:
textWrapOptions:
columns: 35
when: after # <!-------
blocksFollow:
other: \\begin\{myenv\}
We note that, in Listing 350, that the wrapped text has obeyed the specified value of columns
(35) given in Listing 351.
6.1.8 Text wrap: wrapping comments
You can instruct latexindent.pl to apply text wrapping to comments
N: 2023-01-01
; we demonstrate this with
examples, see also Section 6.2.9.
example 97
We use the file in Listing 352 which contains a trailing comment block.
LISTING 352: textwrap9.tex
My first sentence
% first comment
% second
%third comment
% fourth
Using the settings given in Listing 354 and running the command
cmh:$ latexindent.pl textwrap9.tex -o=+-mod1.tex -l=wrap-comments1.yaml -m
gives the output given in Listing 353.
LISTING 353: textwrap9-mod1.tex
My first sentence
% first comment second third
% comment fourth
----|----|----|----|----|----|----|----|
5 10 15 20 25 30 35 40
-m
LISTING 354: wrap-comments1.yaml
modifyLineBreaks:
textWrapOptions:
columns: 35
comments:
wrap: 1 #<!-------
We note that, in Listing 353, that the comments have been combined and wrapped because of the
annotated line specified in Listing 354.
example 98
We use the file in Listing 355 which contains a trailing comment block.
LISTING 355: textwrap10.tex
My first sentence
% first comment
% second
%third comment
% fourth
Using the settings given in Listing 357 and running the command
[git] main @ 78d452f 2024-07-18 V3.24.4
6.1 Text Wrapping 94
cmh:$ latexindent.pl textwrap10.tex -o=+-mod1.tex -l=wrap-comments1.yaml -m
gives the output given in Listing 356.
LISTING 356: textwrap10-mod1.tex
My first sentence
% first comment second third
% comment fourth
----|----|----|----|----|----|----|----|
5 10 15 20 25 30 35 40
-m
LISTING 357: wrap-comments1.yaml
modifyLineBreaks:
textWrapOptions:
columns: 35
comments:
wrap: 1 #<!-------
We note that, in Listing 356, that the comments have been combined and wrapped because of the
annotated line specified in Listing 357, and that the space from the leading comment has not
been inherited; we will explore this further in the next example.
example 99
We continue to use the file in Listing 355.
Using the settings given in Listing 359 and running the command
cmh:$ latexindent.pl textwrap10.tex -o=+-mod2.tex -l=wrap-comments2.yaml -m
gives the output given in Listing 358.
LISTING 358: textwrap10-mod2.tex
My first sentence
% first comment second third
% comment fourth
----|----|----|----|----|----|----|----|
5 10 15 20 25 30 35 40
-m
LISTING 359: wrap-comments2.yaml
modifyLineBreaks:
textWrapOptions:
columns: 35
comments:
wrap: 1 #<!-------
inheritLeadingSpace: 1 #<!-------
We note that, in Listing 358, that the comments have been combined and wrapped and that the
leading space has been inherited because of the annotated lines specified in Listing 359.
6.1.9 Text wrap: huge, tabstop and separator
The
U: 2021-07-23
default value of huge is overflow, which means that words will not be broken by the text
wrapping routine, implemented by the Text::Wrap [48]. There are options to change the huge
option for the Text::Wrap module to either wrap or die. Before modifying the value of huge,
please bear in mind the following warning:
Warning!
Changing the value of huge to anything other than overflow will slow down
latexindent.pl significantly when the -m switch is active.
Furthermore, changing huge means that you may have some words or commands(!)
split across lines in your .tex file, which may affect your output. I do not
recommend changing this field.
example 100
For example, using the settings in Listings 361 and 363 and running the commands
cmh:$ latexindent.pl -m textwrap4.tex -o=+-mod2A -l textwrap2A.yaml
cmh:$ latexindent.pl -m textwrap4.tex -o=+-mod2B -l textwrap2B.yaml
gives the respective output in Listings 360 and 362.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.2 oneSentencePerLine: modifying line breaks for sentences 95
LISTING 360: textwrap4-mod2A.tex
He
re
is
a
li
ne
of
te
xt
.
-m
LISTING 361: textwrap2A.yaml
modifyLineBreaks:
textWrapOptions:
columns: 3
huge: wrap
LISTING 362: textwrap4-mod2B.tex
Here
is
a
line
of
text.
-m
LISTING 363: textwrap2B.yaml
modifyLineBreaks:
textWrapOptions:
columns: 3
You can also specify the tabstop field
N: 2020-11-06
as an integer value, which is passed to the text wrap module;
see [48] for details.
example 101
Starting with the code in Listing 364 with settings in Listing 365, and running the command
cmh:$ latexindent.pl -m textwrap-ts.tex -o=+-mod1 -l tabstop.yaml
gives the code given in Listing 366.
LISTING 364: textwrap-ts.tex
x y
-m
LISTING 365: tabstop.yaml
modifyLineBreaks:
textWrapOptions:
columns: 80
tabstop: 9
multipleSpacesToSingle: 0
LISTING 366:
textwrap-ts-mod1.tex
x y
You can specify separator, break and unexpand options in your settings in analogous ways to those
demonstrated in Listings 363 and 365, and they will be passed to the Text::Wrap module. I have
not found a useful reason to do this; see [48] for more details.
6.2 oneSentencePerLine: modifying line breaks for sentences
You can instruct latexindent.pl to format
N: 2018-01-13
your file so that it puts one sentence per line. Thank you
to [7] for helping to shape and test this feature. The behaviour of this part of the script is controlled
by the switches detailed in Listing 367, all of which we discuss next.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.2 oneSentencePerLine: modifying line breaks for sentences 96
-m
LISTING 367: oneSentencePerLine
505 oneSentencePerLine:
506 manipulateSentences: 0 # 0/1
507 removeSentenceLineBreaks: 1 # 0/1
508 multipleSpacesToSingle: 1 # 0/1
509 textWrapSentences: 0 # 1 disables main textWrap
510 sentenceIndent: ""
511 sentencesFollow:
512 par: 1 # 0/1
513 blankLine: 1 # 0/1
514 fullStop: 1 # 0/1
515 exclamationMark: 1 # 0/1
516 questionMark: 1 # 0/1
517 rightBrace: 1 # 0/1
518 commentOnPreviousLine: 1 # 0/1
519 other: 0 # regex
520 sentencesBeginWith:
521 A-Z: 1 # 0/1
522 a-z: 0 # 0/1
523 other: 0 # regex
524 sentencesEndWith:
525 basicFullStop: 0 # 0/1
526 betterFullStop: 1 # 0/1
527 exclamationMark: 1 # 0/1
528 questionMark: 1 # 0/1
529 other: 0 # regex
530 sentencesDoNOTcontain:
531 other: \\begin # regex
6.2.1 oneSentencePerLine: overview
An overview of how the oneSentencePerLine routine feature works:
1. the default value of manipulateSentences is 0, which means that oneSentencePerLine will
not happen by default;
2. it happens after verbatim blocks have been found;
3. it happens before the text wrapping routine (see Section 6.1);
4. it happens before the main code blocks have been found;
5. sentences to be found:
(a) follow the fields specified in sentencesFollow
(b) begin with the fields specified in sentencesBeginWith
(c) end with the fields specified in sentencesEndWith
6. by default, the oneSentencePerLine routine will remove line breaks within sentences because
removeBlockLineBreaks is set to 1; switch it to 0 if you wish to change this;
7. sentences can be text wrapped according to textWrapSentences, and will be done either
before or after the main indentation routine (see Section 6.2.8);
8. about trailing comments within text wrap blocks:
(a) multiple trailing comments will be connected at the end of the sentence;
(b) the number of spaces between the end of the sentence and the (possibly combined) trail-
ing comments is determined by the spaces (if any) at the end of the sentence.
We demonstrate this feature using a series of examples.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.2 oneSentencePerLine: modifying line breaks for sentences 97
manipulateSentences: 0|1
This is a binary switch that details if latexindent.pl should perform the sentence manipulation
routine; it is off (set to 0) by default, and you will need to turn it on (by setting it to 1) if you want
the script to modify line breaks surrounding and within sentences.
removeSentenceLineBreaks: 0|1
When operating upon sentences latexindent.pl will, by default, remove internal line breaks as
removeSentenceLineBreaks is set to 1. Setting this switch to 0 instructs latexindent.pl not to
do so.
example 102
For example, consider multiple-sentences.tex shown in Listing 368.
LISTING 368: multiple-sentences.tex
This is the first
sentence. This is the; second, sentence. This is the
third sentence.
This is the fourth
sentence! This is the fifth sentence? This is the
sixth sentence.
If we use the YAML files in Listings 370 and 372, and run the commands
cmh:$ latexindent.pl multiple-sentences -m -l=manipulate-sentences.yaml
cmh:$ latexindent.pl multiple-sentences -m -l=keep-sen-line-breaks.yaml
then we obtain the respective output given in Listings 369 and 371.
LISTING 369: multiple-sentences.tex
using Listing 370
This is the first sentence.
This is the; second, sentence.
This is the third sentence.
This is the fourth sentence!
This is the fifth sentence?
This is the sixth sentence.
-m
LISTING 370:
manipulate-sentences.yaml
modifyLineBreaks:
oneSentencePerLine:
manipulateSentences: 1
LISTING 371: multiple-sentences.tex
using Listing 372
This is the first
sentence.
This is the; second, sentence.
This is the
third sentence.
This is the fourth
sentence!
This is the fifth sentence?
This is the
sixth sentence.
-m
LISTING 372:
keep-sen-line-breaks.yaml
modifyLineBreaks:
oneSentencePerLine:
manipulateSentences: 1
removeSentenceLineBreaks: 0
Notice, in particular, that the ‘internal’ sentence line breaks in Listing 368 have been removed in
Listing 369, but have not been removed in Listing 371.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.2 oneSentencePerLine: modifying line breaks for sentences 98
multipleSpacesToSingle: 0|1
U: 2022-03-25
By default, the one-sentence-per-line routine will convert multiple spaces into single spaces. You can
change this behaviour by changing the switch multipleSpacesToSingle to a value of 0.
The remainder of the settings displayed in Listing 367 on page 96 instruct latexindent.pl on how
to define a sentence. From the perspective of latexindent.pl a sentence must:
follow a certain character or set of characters (see Listing 373); by default, this is either \par,
a blank line, a full stop/period (.), exclamation mark (!), question mark (?) right brace (}) or
a comment on the previous line;
begin with a character type (see Listing 374); by default, this is only capital letters;
end with a character (see Listing 375); by default, these are full stop/period (.), exclamation
mark (!) and question mark (?).
In each case, you can specify the other field to include any pattern that you would like; you can
specify anything in this field using the language of regular expressions.
-m
LISTING 373: sentencesFollow
511 sentencesFollow:
512 par: 1 # 0/1
513 blankLine: 1 # 0/1
514 fullStop: 1 # 0/1
515 exclamationMark: 1 # 0/1
516 questionMark: 1 # 0/1
517 rightBrace: 1 # 0/1
518 commentOnPreviousLine: 1 # 0/1
519 other: 0 # regex
-m
LISTING 374: sentencesBeginWith
520 sentencesBeginWith:
521 A-Z: 1 # 0/1
522 a-z: 0 # 0/1
523 other: 0 # regex
-m
LISTING 375: sentencesEndWith
524 sentencesEndWith:
525 basicFullStop: 0 # 0/1
526 betterFullStop: 1 # 0/1
527 exclamationMark: 1 # 0/1
528 questionMark: 1 # 0/1
529 other: 0 # regex
6.2.2 oneSentencePerLine: sentencesFollow
Let’s explore a few of the switches in sentencesFollow.
example 103
We start with Listing 368 on the preceding page, and use the YAML settings given in Listing 377.
Using the command
cmh:$ latexindent.pl multiple-sentences -m -l=sentences-follow1.yaml
we obtain the output given in Listing 376.
LISTING 376: multiple-sentences.tex
using Listing 377
This is the first sentence.
This is the; second, sentence.
This is the third sentence.
This is the fourth
sentence!
This is the fifth sentence?
This is the sixth sentence.
-m
LISTING 377: sentences-follow1.yaml
modifyLineBreaks:
oneSentencePerLine:
manipulateSentences: 1
sentencesFollow:
blankLine: 0
[git] main @ 78d452f 2024-07-18 V3.24.4
6.2 oneSentencePerLine: modifying line breaks for sentences 99
Notice that, because blankLine is set to 0, latexindent.pl will not seek sentences following
a blank line, and so the fourth sentence has not been accounted for.
example 104
We can explore the other field in Listing 373 with the .tex file detailed in Listing 378.
LISTING 378: multiple-sentences1.tex
(Some sentences stand alone in brackets.) This is the first
sentence. This is the; second, sentence. This is the
third sentence.
Upon running the following commands
cmh:$ latexindent.pl multiple-sentences1 -m -l=manipulate-sentences.yaml
cmh:$ latexindent.pl multiple-sentences1 -m -l=manipulate-sentences.yaml,sentences-follow2.yaml
then we obtain the respective output given in Listings 379 and 380.
LISTING 379: multiple-sentences1.tex using Listing 370 on page 97
(Some sentences stand alone in brackets.) This is the first
sentence.
This is the; second, sentence.
This is the third sentence.
LISTING 380: multiple-sentences1.tex using
Listing 381
(Some sentences stand alone in brackets.)
This is the first sentence.
This is the; second, sentence.
This is the third sentence.
-m
LISTING 381:
sentences-follow2.yaml
modifyLineBreaks:
oneSentencePerLine:
manipulateSentences: 1
sentencesFollow:
other: "\)"
Notice that in Listing 379 the first sentence after the ) has not been accounted for, but that
following the inclusion of Listing 381, the output given in Listing 380 demonstrates that the
sentence has been accounted for correctly.
6.2.3 oneSentencePerLine: sentencesBeginWith
By default, latexindent.pl will only assume that sentences begin with the upper case letters A-Z;
you can instruct the script to define sentences to begin with lower case letters (see Listing 374), and
we can use the other field to define sentences to begin with other characters.
example 105
We use the file in Listing 382.
LISTING 382: multiple-sentences2.tex
This is the first
sentence.
$a$ can
represent a
number. 7 is
at the beginning of this sentence.
Upon running the following commands
cmh:$ latexindent.pl multiple-sentences2 -m -l=manipulate-sentences.yaml
cmh:$ latexindent.pl multiple-sentences2 -m -l=manipulate-sentences.yaml,sentences-begin1.yaml
[git] main @ 78d452f 2024-07-18 V3.24.4
6.2 oneSentencePerLine: modifying line breaks for sentences 100
then we obtain the respective output given in Listings 383 and 384.
LISTING 383: multiple-sentences2.tex using Listing 370 on page 97
This is the first sentence.
$a$ can
represent a
number. 7 is
at the beginning of this sentence.
LISTING 384: multiple-sentences2.tex using
Listing 385
This is the first sentence.
$a$ can represent a number.
7 is at the beginning of this sentence.
-m
LISTING 385:
sentences-begin1.yaml
modifyLineBreaks:
oneSentencePerLine:
manipulateSentences: 1
sentencesBeginWith:
other: "\$|[0-9]"
Notice that in Listing 383, the first sentence has been accounted for but that the subsequent
sentences have not. In Listing 384, all of the sentences have been accounted for, because the
other field in Listing 385 has defined sentences to begin with either $ or any numeric digit, 0 to
9.
6.2.4 oneSentencePerLine: sentencesEndWith
example 106
Let’s return to Listing 368 on page 97; we have already seen the default way in which latexindent.pl
will operate on the sentences in this file in Listing 369 on page 97. We can populate the other
field with any character that we wish; for example, using the YAML specified in Listing 387 and
the command
cmh:$ latexindent.pl multiple-sentences -m -l=sentences-end1.yaml
cmh:$ latexindent.pl multiple-sentences -m -l=sentences-end2.yaml
then we obtain the output in Listing 386.
LISTING 386: multiple-sentences.tex
using Listing 387
This is the first sentence.
This is the;
second, sentence.
This is the third sentence.
This is the fourth sentence!
This is the fifth sentence?
This is the sixth sentence.
-m
LISTING 387: sentences-end1.yaml
modifyLineBreaks:
oneSentencePerLine:
manipulateSentences: 1
sentencesEndWith:
other: "\:|\;|\,"
[git] main @ 78d452f 2024-07-18 V3.24.4
6.2 oneSentencePerLine: modifying line breaks for sentences 101
LISTING 388: multiple-sentences.tex
using Listing 389
This is the first sentence.
This is the;
second,
sentence.
This is the third sentence.
This is the fourth sentence!
This is the fifth sentence?
This is the sixth sentence.
-m
LISTING 389: sentences-end2.yaml
modifyLineBreaks:
oneSentencePerLine:
manipulateSentences: 1
sentencesEndWith:
other: "\:|\;|\,"
sentencesBeginWith:
a-z: 1
There is a subtle difference between the output in Listings 386 and 388; in particular, in List-
ing 386 the word sentence has not been defined as a sentence, because we have not instructed
latexindent.pl to begin sentences with lower case letters. We have changed this by using the
settings in Listing 389, and the associated output in Listing 388 reflects this.
Referencing Listing 375 on page 98, you’ll notice that there is a field called basicFullStop, which
is set to 0, and that the betterFullStop is set to 1 by default.
example 107
Let’s consider the file shown in Listing 390.
LISTING 390: url.tex
This sentence, \url{tex.stackexchange.com/} finishes here. Second sentence.
Upon running the following commands
cmh:$ latexindent.pl url -m -l=manipulate-sentences.yaml
we obtain the output given in Listing 391.
LISTING 391: url.tex using Listing 370 on page 97
This sentence, \url{tex.stackexchange.com/} finishes here.
Second sentence.
Notice that the full stop within the url has been interpreted correctly. This is because, within the
betterFullStop, full stops at the end of sentences have the following properties:
they are ignored within e.g. and i.e.;
they can not be immediately followed by a lower case or upper case letter;
they can not be immediately followed by a hyphen, comma, or number.
If you find that the betterFullStop does not work for your purposes, then you can switch it off
by setting it to 0, and you can experiment with the other field.
N: 2019-07-13
You can also seek to customise the
betterFullStop routine by using the fine tuning, detailed in Listing 566 on page 144.
The basicFullStop routine should probably be avoided in most situations, as it does not accommo-
date the specifications above.
example 108
For example, using the following command
cmh:$ latexindent.pl url -m -l=alt-full-stop1.yaml
and the YAML in Listing 393 gives the output in Listing 392.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.2 oneSentencePerLine: modifying line breaks for sentences 102
LISTING 392: url.tex using Listing 393
This sentence, \url{tex.
stackexchange.com/} finishes here.Second sentence.
-m
LISTING 393: alt-full-stop1.yaml
modifyLineBreaks:
oneSentencePerLine:
manipulateSentences: 1
sentencesEndWith:
basicFullStop: 1
betterFullStop: 0
Notice that the full stop within the URL has not been accommodated correctly because of the
non-default settings in Listing 393.
6.2.5 oneSentencePerLine: sentencesDoNOTcontain
You can specify patterns that sentences do not contain using the field
N: 2023-09-09
in Listing 394.
-m
LISTING 394: sentencesDoNOTcontain
530 sentencesDoNOTcontain:
531 other: \\begin # regex
If sentences run across environments then, by default, they will not be considered a sentence by
latexindent.pl.
U: 2023-09-09
example 109
For example, if we use the .tex file in Listing 395
LISTING 395: multiple-sentences4.tex
This sentence
\begin{itemize}
\item continues
\end{itemize}
across itemize
and finishes here.
and run the command
cmh:$ latexindent.pl multiple-sentences4 -m -l=manipulate-sentences.yaml
then the output is unchanged, because the default value of sentencesDoNOTcontain says, sen-
tences do NOT contain
This means that, by default, latexindent.pl does not consider the file in Listing 395 to have a
sentence. \\begin
example 110
We can customise the sentencesDoNOTcontain field with anything that we do not want sen-
tences to contain.
We begin with the file in Listing 396.
LISTING 396: sentence-dnc1.tex
This should not be a sentence \cmh{?} and should not change.
But this
one should.
Upon running the following commands
cmh:$ latexindent.pl sentence-dnc1.tex -m -l=dnc1.yaml
then we obtain the output given in Listing 397.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.2 oneSentencePerLine: modifying line breaks for sentences 103
LISTING 397: sentence-dnc1-mod1.tex
This should not be a sentence \cmh{?} and should not change.
But this one should.
-m
LISTING 398: dnc1.yaml
modifyLineBreaks:
oneSentencePerLine:
manipulateSentences: 1
sentencesDoNOTcontain:
other: |-
(?x)
\\begin
|
\\cmh
The settings in Listing 398 say that sentences do not contain \begin and that they do not contain
\cmh
example 111
We can implement case insensitivity for the sentencesDoNOTcontain field.
We begin with the file in Listing 399.
LISTING 399: sentence-dnc2.tex
This should not be a sentence \cmh{?} and should not change.
This should not be a sentence \CMH{?} and should not change.
But this
one should.
Upon running the following commands
cmh:$ latexindent.pl sentence-dnc2.tex -m -l=dnc2.yaml
then we obtain the output given in Listing 400.
LISTING 400: sentence-dnc2-mod2.tex
This should not be a sentence \cmh{?} and should not change.
This should not be a sentence \CMH{?} and should not change.
But this one should.
-m
LISTING 401: dnc2.yaml
modifyLineBreaks:
oneSentencePerLine:
manipulateSentences: 1
sentencesDoNOTcontain:
other: |-
(?xi) #<!----
\\begin
|
\\cmh
The settings in Listing 401 say that sentences do not contain \begin and that they do not contain
case insensitive versions of \cmh
example 112
We can turn off sentenceDoNOTcontain by setting it to 0 as in Listing 402.
-m
LISTING 402: dnc-off.yaml
modifyLineBreaks:
oneSentencePerLine:
manipulateSentences: 1
sentencesDoNOTcontain: 0
The settings in Listing 402 mean that sentences can contain any character.
6.2.6 Features of the oneSentencePerLine routine
The sentence manipulation routine takes place after verbatim environments, preamble and trailing
comments have been accounted for; this means that any characters within these types of code blocks
will not be part of the sentence manipulation routine.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.2 oneSentencePerLine: modifying line breaks for sentences 104
example 113
For example, if we begin with the .tex file in Listing 403, and run the command
cmh:$ latexindent.pl multiple-sentences3 -m -l=manipulate-sentences.yaml
then we obtain the output in Listing 404.
LISTING 403: multiple-sentences3.tex
The first sentence continues after the verbatim
\begin{verbatim}
there are sentences within this. These
will not be operated
upon by latexindent.pl.
\end{verbatim}
and finishes here. Second sentence % a commented full stop.
contains trailing comments,
which are ignored.
LISTING 404: multiple-sentences3.tex using Listing 370 on page 97
The first sentence continues after the verbatim \begin{verbatim}
there are sentences within this. These
will not be operated
upon by latexindent.pl.
\end{verbatim} and finishes here.
Second sentence contains trailing comments, which are ignored.
% a commented full stop.
6.2.7 oneSentencePerLine: text wrapping and indenting sentences
The oneSentencePerLine
N: 2018-08-13
can be instructed to perform text wrapping and indentation upon sen-
tences.
example 114
Let’s use the code in Listing 405.
LISTING 405: multiple-sentences5.tex
A distincao entre conteudo \emph{real} e conteudo \emph{intencional} esta
relacionada, ainda, a distincao entre o conceito husserliano de
\emph{experiencia} e o uso popular desse termo. No sentido comum,
o \term{experimentado} e um complexo de eventos exteriores,
e o \term{experimentar} consiste em percepcoes (alem de julgamentos e outros
atos) nas quais tais eventos aparecem como objetos, e objetos frequentemente
to the end.
Referencing Listing 407, and running the following command
cmh:$ latexindent.pl multiple-sentences5 -m -l=sentence-wrap1.yaml
we receive the output given in Listing 406.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.2 oneSentencePerLine: modifying line breaks for sentences 105
LISTING 406: multiple-sentences5.tex using Listing 407
A distincao entre conteudo \emph{real} e conteudo
\emph{intencional} esta relacionada, ainda, a
distincao entre o conceito husserliano de
\emph{experiencia} e o uso popular desse termo.
No sentido comum, o \term{experimentado} e um
complexo de eventos exteriores, e o
\term{experimentar} consiste em percepcoes (alem
de julgamentos e outros atos) nas quais tais
eventos aparecem como objetos, e objetos
frequentemente to the end.
-m
LISTING 407: sentence-wrap1.yaml
modifyLineBreaks:
oneSentencePerLine:
manipulateSentences: 1
removeSentenceLineBreaks: 1
textWrapSentences: 1
sentenceIndent: " "
textWrapOptions:
columns: 50
If you specify textWrapSentences as 1, but do not specify a value for columns then the text wrap-
ping will not operate on sentences, and you will see a warning in indent.log.
example 115
The indentation of sentences requires that sentences are stored as code blocks. This means that
you may need to tweak Listing 375 on page 98. Let’s explore this in relation to Listing 408.
LISTING 408: multiple-sentences6.tex
Consider the following:
\begin{itemize}
\item firstly.
\item secondly.
\end{itemize}
By default, latexindent.pl will find the full-stop within the first item, which means that, upon
running the following commands
cmh:$ latexindent.pl multiple-sentences6 -m -l=sentence-wrap1.yaml
cmh:$ latexindent.pl multiple-sentences6 -m -l=sentence-wrap1.yaml
-y="modifyLineBreaks:oneSentencePerLine:sentenceIndent:’’"
we receive the respective output in Listing 409 and Listing 410.
LISTING 409: multiple-sentences6-mod1.tex using Listing 407
Consider the following:
\begin{itemize}
\item firstly.
\item secondly.
\end{itemize}
LISTING 410: multiple-sentences6-mod2.tex using Listing 407 and no sentence
indentation
Consider the following:
\begin{itemize}
\item firstly.
\item secondly.
\end{itemize}
We note that Listing 409 the itemize code block has not been indented appropriately. This is
because the oneSentencePerLine has been instructed to store sentences (because Listing 407);
each sentence is then searched for code blocks.
example 116
We can tweak the settings in Listing 375 on page 98 to ensure that full stops are not followed by
item commands, and that the end of sentences contains \end{itemize} as in Listing 411. This
setting is actually an appended version of the betterFullStop from the fineTuning, detailed
in Listing 566 on page 144.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.2 oneSentencePerLine: modifying line breaks for sentences 106
-m
LISTING 411: itemize.yaml
modifyLineBreaks:
textWrapOptions:
columns: 45
oneSentencePerLine:
sentencesEndWith:
betterFullStop: 0
other: |-
(?x)
(?: # new
(?:\R|\h)*\\item # new
) # new
|
(?:
\.\)
(?!\h*[a-z])
)
|
(?:
(?<!
(?:
(?:[eE]\.[gG])
|
(?:[iI]\.[eE])
|
(?:etc)
)
)
)
\.
(?:\h*\R*(?:\\end\{itemize\})?) # new
(?!
(?:
[a-zA-Z0-9-~,]
|
\),
|
\)\.
)
)
Upon running
cmh:$ latexindent.pl multiple-sentences6 -m -l=sentence-wrap1.yaml,itemize.yaml
we receive the output in Listing 412.
LISTING 412: multiple-sentences6-mod3.tex using Listing 407 and Listing 411
Consider the following:
\begin{itemize}
\item firstly.
\item secondly.
\end{itemize}
Notice that the sentence has received indentation, and that the itemize code block has been
found and indented correctly.
Text
U: 2022-04-04
wrapping when using the oneSentencePerLine routine determines if it will remove line breaks
while text wrapping, from the value of removeSentenceLineBreaks.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.2 oneSentencePerLine: modifying line breaks for sentences 107
6.2.8 oneSentencePerLine: text wrapping and indenting sentences, when before/after
The text wrapping routine operates, by default, before the
N: 2023-01-01
code blocks have been found, but this
can be changed to after:
before means it is likely that the columns of wrapped text may exceed the value specified in
columns;
after means it columns of wrapped text should not exceed the value specified in columns.
We demonstrate this in the following examples. See also Section 6.1.7.
example 117
Let’s begin with the file in Listing 413.
LISTING 413: multiple-sentences8.tex
This paragraph
has line breaks throughout its paragraph;
we would like to combine
the textwrapping
and paragraph removal routine.
\begin{myenv}
This paragraph
has line breaks throughout its paragraph;
we would like to combine
the textwrapping
and paragraph removal routine.
\end{myenv}
Using the settings given in Listing 415 and running the command
cmh:$ latexindent.pl multiple-sentences8 -o=+-mod1.tex -l=sentence-wrap2 -m
gives the output given in Listing 414.
LISTING 414:
multiple-sentences8-mod1.tex
This paragraph has line breaks
throughout its paragraph; we would
like to combine the textwrapping
and paragraph removal routine.
\begin{myenv}
This paragraph has line breaks
throughout its paragraph; we would
like to combine the textwrapping
and paragraph removal routine.
\end{myenv}
----|----|----|----|----|----|----|----|
5 10 15 20 25 30 35 40
-m
LISTING 415: sentence-wrap2.yaml
defaultIndent: ’
modifyLineBreaks:
oneSentencePerLine:
manipulateSentences: 1
textWrapSentences: 1
textWrapOptions:
columns: 35
when: before # <!-------
We note that, in Listing 414, that the wrapped text has exceeded the specified value of columns
(35) given in Listing 415. We can affect this by changing when; we explore this next.
example 118
We continue working with Listing 413.
Using the settings given in Listing 417 and running the command
cmh:$ latexindent.pl multiple-sentences8.tex -o=+-mod2.tex -l=sentence-wrap3 -m
gives the output given in Listing 416.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.3 Poly-switches 108
LISTING 416:
multiple-sentences8-mod2.tex
This paragraph has line breaks
throughout its paragraph; we would
like to combine the textwrapping
and paragraph removal routine.
\begin{myenv}
This paragraph has line breaks
throughout its paragraph; we
would like to combine the
textwrapping and paragraph
removal routine.
\end{myenv}
----|----|----|----|----|----|----|----|
5 10 15 20 25 30 35 40
-m
LISTING 417: sentence-wrap3.yaml
defaultIndent: ’
modifyLineBreaks:
oneSentencePerLine:
manipulateSentences: 1
textWrapSentences: 1
textWrapOptions:
columns: 35
when: after # <!-------
We note that, in Listing 416, that the wrapped text has obeyed the specified value of columns
(35) given in Listing 417.
6.2.9 oneSentencePerLine: text wrapping sentences and comments
We demonstrate the one sentence per line routine with respect to text wrapping comments. See also
Section 6.1.8.
example 119
Let’s begin with the file in Listing 418.
LISTING 418: multiple-sentences9.tex
This paragraph% first comment
has line breaks throughout its paragraph;% second comment
we would like to combine% third comment
the textwrapping% fourth comment
and paragraph removal routine. % fifth comment
Using the settings given in Listing 420 and running the command
cmh:$ latexindent.pl multiple-sentences9 -o=+-mod1.tex -l=sentence-wrap4 -m
gives the output given in Listing 419.
LISTING 419:
multiple-sentences9-mod1.tex
This paragraph has line breaks
throughout its paragraph; we would
like to combine the textwrapping
and paragraph removal routine.
% first comment second comment
% third comment fourth comment
% fifth comment
----|----|----|----|----|----|----|----|
5 10 15 20 25 30 35 40
-m
LISTING 420: sentence-wrap4.yaml
defaultIndent: ’
modifyLineBreaks:
oneSentencePerLine:
manipulateSentences: 1
textWrapSentences: 1
textWrapOptions:
columns: 35
comments:
wrap: 1 #<!-------
We note that, in Listing 419, that the sentences have been wrapped, and so too have the comments
because of the annotated line in Listing 420.
6.3 Poly-switches
Every other field in the modifyLineBreaks field uses poly-switches, and can take one of the follow-
ing
U: 2017-08-21
integer values:
[git] main @ 78d452f 2024-07-18 V3.24.4
6.3 Poly-switches 109
1 remove mode: line breaks before or after the <part of thing> can be removed (assuming that
preserveBlankLines is set to 0);
0 off mode: line breaks will not be modified for the <part of thing> under consideration;
1 add mode: a line break will be added before or after the <part of thing> under consideration,
assuming that there is not already a line break before or after the <part of thing>;
2 comment then add mode: a comment symbol will be added, followed by a line break before or
after the <part of thing> under consideration, assuming that there is not already a comment
and line break before or after the <part of thing>;
3 add then blank line mode
N: 2017-08-21
: a line break will be added before or after the <part of thing> under
consideration, assuming that there is not already a line break before or after the <part of
thing>, followed by a blank line;
4 add blank line mode
N: 2019-07-13
; a blank line will be added before or after the <part of thing> under consid-
eration, even if the <part of thing> is already on its own line.
In the above, <part of thing> refers to either the begin statement, body or end statement of the code
blocks detailed in Table 2 on page 56. All poly-switches are off by default; latexindent.pl searches
first of all for per-name settings, and then followed by global per-thing settings.
6.3.1 Poly-switches for environments
We start by viewing a snippet of defaultSettings.yaml in Listing 421; note that it contains global
settings (immediately after the environments field) and that per-name settings are also allowed
in the case of Listing 421, settings for equation* have been specified for demonstration. Note that
all poly-switches are off (set to 0) by default.
-m
LISTING 421: environments
561 environments:
562 BeginStartsOnOwnLine: 0 # -1,0,1,2,3,4
563 BodyStartsOnOwnLine: 0 # -1,0,1,2,3,4
564 EndStartsOnOwnLine: 0 # -1,0,1,2,3,4
565 EndFinishesWithLineBreak: 0 # -1,0,1,2,3,4
566 # equation*:
567 # BeginStartsOnOwnLine: 0 # -1,0,1,2,3,4
568 # BodyStartsOnOwnLine: 0 # -1,0,1,2,3,4
569 # EndStartsOnOwnLine: 0 # -1,0,1,2,3,4
570 # EndFinishesWithLineBreak: 0 # -1,0,1,2,3,4
Let’s begin with the simple example given in Listing 422; note that we have annotated key parts of
the file using , , and , these will be related to fields specified in Listing 421.
LISTING 422: env-mlb1.tex
before words \begin{myenv}body of myenv\end{myenv} after words
6.3.1.1 Adding line breaks: BeginStartsOnOwnLine and BodyStartsOnOwnLine
example 120
Let’s explore BeginStartsOnOwnLine and BodyStartsOnOwnLine in Listings 423 and 424, and
in particular, let’s allow each of them in turn to take a value of 1.
-m
LISTING 423: env-mlb1.yaml
modifyLineBreaks:
environments:
BeginStartsOnOwnLine: 1
-m
LISTING 424: env-mlb2.yaml
modifyLineBreaks:
environments:
BodyStartsOnOwnLine: 1
[git] main @ 78d452f 2024-07-18 V3.24.4
6.3 Poly-switches 110
After running the following commands,
cmh:$ latexindent.pl -m env-mlb.tex -l env-mlb1.yaml
cmh:$ latexindent.pl -m env-mlb.tex -l env-mlb2.yaml
the output is as in Listings 425 and 426 respectively.
LISTING 425: env-mlb.tex using Listing 423
before words
\begin{myenv}body of myenv\end{myenv} after words
LISTING 426: env-mlb.tex using Listing 424
before words \begin{myenv}
body of myenv\end{myenv} after words
There are a couple of points to note:
in Listing 425 a line break has been added at the point denoted by in Listing 422; no
other line breaks have been changed;
in Listing 426 a line break has been added at the point denoted by in Listing 422; fur-
thermore, note that the body of myenv has received the appropriate (default) indentation.
example 121
Let’s now change each of the 1 values in Listings 423 and 424 so that they are 2 and save them
into env-mlb3.yaml and env-mlb4.yaml respectively (see Listings 427 and 428).
-m
LISTING 427: env-mlb3.yaml
modifyLineBreaks:
environments:
BeginStartsOnOwnLine: 2
-m
LISTING 428: env-mlb4.yaml
modifyLineBreaks:
environments:
BodyStartsOnOwnLine: 2
Upon running the commands
cmh:$ latexindent.pl -m env-mlb.tex -l env-mlb3.yaml
cmh:$ latexindent.pl -m env-mlb.tex -l env-mlb4.yaml
we obtain Listings 429 and 430.
LISTING 429: env-mlb.tex using Listing 427
before words%
\begin{myenv}body of myenv\end{myenv} after words
LISTING 430: env-mlb.tex using Listing 428
before words \begin{myenv}%
body of myenv\end{myenv} after words
Note that line breaks have been added as in Listings 425 and 426, but this time a comment symbol
has been added before adding the line break; in both cases, trailing horizontal space has been
stripped before doing so.
example 122
Let’s now change each of the 1 values in Listings 423 and 424 so that they are 3 and save them
into env-mlb5.yaml and env-mlb6.yaml respectively (see Listings 431 and 432).
N: 2017-08-21
-m
LISTING 431: env-mlb5.yaml
modifyLineBreaks:
environments:
BeginStartsOnOwnLine: 3
-m
LISTING 432: env-mlb6.yaml
modifyLineBreaks:
environments:
BodyStartsOnOwnLine: 3
Upon running the commands
cmh:$ latexindent.pl -m env-mlb.tex -l env-mlb5.yaml
cmh:$ latexindent.pl -m env-mlb.tex -l env-mlb6.yaml
we obtain Listings 433 and 434.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.3 Poly-switches 111
LISTING 433: env-mlb.tex using Listing 431
before words
\begin{myenv}body of myenv\end{myenv} after words
LISTING 434: env-mlb.tex using Listing 432
before words \begin{myenv}
body of myenv\end{myenv} after words
Note that line breaks have been added as in Listings 425 and 426, but this time a blank line has
been added after adding the line break.
example 123
Let’s now change each of the 1 values in Listings 431 and 432 so that they are 4 and save them
into env-beg4.yaml and env-body4.yaml respectively (see Listings 435 and 436).
N: 2019-07-13
-m
LISTING 435: env-beg4.yaml
modifyLineBreaks:
environments:
BeginStartsOnOwnLine: 4
-m
LISTING 436: env-body4.yaml
modifyLineBreaks:
environments:
BodyStartsOnOwnLine: 4
We will demonstrate this poly-switch value using the code in Listing 437.
LISTING 437: env-mlb1.tex
before words
\begin{myenv}
body of myenv
\end{myenv}
after words
Upon running the commands
cmh:$ latexindent.pl -m env-mlb1.tex -l env-beg4.yaml
cmh:$ latexindent.pl -m env-mlb.1tex -l env-body4.yaml
then we receive the respective outputs in Listings 438 and 439.
LISTING 438: env-mlb1.tex using
Listing 435
before words
\begin{myenv}
body of myenv
\end{myenv}
after words
LISTING 439: env-mlb1.tex using
Listing 436
before words
\begin{myenv}
body of myenv
\end{myenv}
after words
We note in particular that, by design, for this value of the poly-switches:
1. in Listing 438 a blank line has been inserted before the \begin statement, even though the
\begin statement was already on its own line;
2. in Listing 439 a blank line has been inserted before the beginning of the body, even though
it already began on its own line.
6.3.1.2 Adding line breaks: EndStartsOnOwnLine and EndFinishesWithLineBreak
example 124
Let’s explore EndStartsOnOwnLine and EndFinishesWithLineBreak in Listings 440 and 441,
and in particular, let’s allow each of them in turn to take a value of 1.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.3 Poly-switches 112
-m
LISTING 440: env-mlb7.yaml
modifyLineBreaks:
environments:
EndStartsOnOwnLine: 1
-m
LISTING 441: env-mlb8.yaml
modifyLineBreaks:
environments:
EndFinishesWithLineBreak: 1
After running the following commands,
cmh:$ latexindent.pl -m env-mlb.tex -l env-mlb7.yaml
cmh:$ latexindent.pl -m env-mlb.tex -l env-mlb8.yaml
the output is as in Listings 442 and 443.
LISTING 442: env-mlb.tex using
Listing 440
before words \begin{myenv}body
of myenv
\end{myenv} after words
LISTING 443: env-mlb.tex using
Listing 441
before words \begin{myenv}body
of myenv\end{myenv}
after words
There are a couple of points to note:
in Listing 442 a line break has been added at the point denoted by in Listing 422 on
page 109; no other line breaks have been changed and the \end{myenv} statement has not
received indentation (as intended);
in Listing 443 a line break has been added at the point denoted by in Listing 422 on
page 109.
example 125
Let’s now change each of the 1 values in Listings 440 and 441 so that they are 2 and save them
into env-mlb9.yaml and env-mlb10.yaml respectively (see Listings 444 and 445).
-m
LISTING 444: env-mlb9.yaml
modifyLineBreaks:
environments:
EndStartsOnOwnLine: 2
-m
LISTING 445: env-mlb10.yaml
modifyLineBreaks:
environments:
EndFinishesWithLineBreak: 2
Upon running the commands
cmh:$ latexindent.pl -m env-mlb.tex -l env-mlb9.yaml
cmh:$ latexindent.pl -m env-mlb.tex -l env-mlb10.yaml
we obtain Listings 446 and 447.
LISTING 446: env-mlb.tex using Listing 444
before words \begin{myenv}body of myenv%
\end{myenv} after words
LISTING 447: env-mlb.tex using Listing 445
before words \begin{myenv}body of myenv\end{myenv}%
after words
Note that line breaks have been added as in Listings 442 and 443, but this time a comment symbol
has been added before adding the line break; in both cases, trailing horizontal space has been
stripped before doing so.
example 126
Let’s now change each of the 1 values in Listings 440 and 441 so that they are 3 and save them
into env-mlb11.yaml and env-mlb12.yaml respectively (see Listings 448 and 449).
N: 2017-08-21
[git] main @ 78d452f 2024-07-18 V3.24.4
6.3 Poly-switches 113
-m
LISTING 448: env-mlb11.yaml
modifyLineBreaks:
environments:
EndStartsOnOwnLine: 3
-m
LISTING 449: env-mlb12.yaml
modifyLineBreaks:
environments:
EndFinishesWithLineBreak: 3
Upon running the commands
cmh:$ latexindent.pl -m env-mlb.tex -l env-mlb11.yaml
cmh:$ latexindent.pl -m env-mlb.tex -l env-mlb12.yaml
we obtain Listings 450 and 451.
LISTING 450: env-mlb.tex using
Listing 448
before words \begin{myenv}body of myenv
\end{myenv} after words
LISTING 451: env-mlb.tex using Listing 449
before words \begin{myenv}body of myenv\end{myenv}
after words
Note that line breaks have been added as in Listings 442 and 443, and that a blank line has been
added after the line break.
example 127
Let’s now change each of the 1 values in Listings 448 and 449 so that they are 4 and save them
into env-end4.yaml and env-end-f4.yaml respectively (see Listings 452 and 453).
N: 2019-07-13
-m
LISTING 452: env-end4.yaml
modifyLineBreaks:
environments:
EndStartsOnOwnLine: 4
-m
LISTING 453: env-end-f4.yaml
modifyLineBreaks:
environments:
EndFinishesWithLineBreak: 4
We will demonstrate this poly-switch value using the code from Listing 437 on page 111.
Upon running the commands
cmh:$ latexindent.pl -m env-mlb1.tex -l env-end4.yaml
cmh:$ latexindent.pl -m env-mlb.1tex -l env-end-f4.yaml
then we receive the respective outputs in Listings 454 and 455.
LISTING 454: env-mlb1.tex using
Listing 452
before words
\begin{myenv}
body of myenv
\end{myenv}
after words
LISTING 455: env-mlb1.tex using
Listing 453
before words
\begin{myenv}
body of myenv
\end{myenv}
after words
We note in particular that, by design, for this value of the poly-switches:
1. in Listing 454 a blank line has been inserted before the \end statement, even though the
\end statement was already on its own line;
2. in Listing 455 a blank line has been inserted after the \end statement, even though it already
began on its own line.
6.3.1.3 poly-switches 1, 2, and 3 only add line breaks when necessary
If you ask latexindent.pl to add a line break (possibly with a comment) using a poly-switch value
of 1 (or 2 or 3), it will only do so if necessary.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.3 Poly-switches 114
example 128
For example, if you process the file in Listing 456 using poly-switch values of 1, 2, or 3, it will be
left unchanged.
LISTING 456: env-mlb2.tex
before words
\begin{myenv}
body of myenv
\end{myenv}
after words
LISTING 457: env-mlb3.tex
before words
\begin{myenv} %
body of myenv%
\end{myenv}%
after words
Setting the poly-switches to a value of 4 instructs latexindent.pl to add a line break even if the
<part of thing> is already on its own line; see Listings 438 and 439 and Listings 454 and 455.
example 129
In contrast, the output from processing the file in Listing 457 will vary depending on the poly-
switches used; in Listing 458 you’ll see that the comment symbol after the \begin{myenv} has
been moved to the next line, as BodyStartsOnOwnLine is set to 1. In Listing 459 you’ll see that
the comment has been accounted for correctly because BodyStartsOnOwnLine has been set to 2,
and the comment symbol has not been moved to its own line. You’re encouraged to experiment
with Listing 457 and by setting the other poly-switches considered so far to 2 in turn.
LISTING 458: env-mlb3.tex using
Listing 424 on page 109
before words
\begin{myenv}
%
body of myenv%
\end{myenv}%
after words
LISTING 459: env-mlb3.tex using
Listing 428 on page 110
before words
\begin{myenv} %
body of myenv%
\end{myenv}%
after words
The details of the discussion in this section have concerned global poly-switches in the environments
field; each switch can also be specified on a per-name basis, which would take priority over the
global values; with reference to Listing 421 on page 109, an example is shown for the equation*
environment.
6.3.1.4 Removing line breaks (poly-switches set to 1)
Setting poly-switches to 1 tells latexindent.pl to remove line breaks of the <part of the thing>,
if necessary.
example 130
We will consider the example code given in Listing 460, noting in particular the positions of the
line break highlighters, , , and , together with the associated YAML files in Listings 461
to 464.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.3 Poly-switches 115
LISTING 460: env-mlb4.tex
before words
\begin{myenv}
body of myenv
\end{myenv}
after words
-m
LISTING 461: env-mlb13.yaml
modifyLineBreaks:
environments:
BeginStartsOnOwnLine: -1
-m
LISTING 462: env-mlb14.yaml
modifyLineBreaks:
environments:
BodyStartsOnOwnLine: -1
-m
LISTING 463: env-mlb15.yaml
modifyLineBreaks:
environments:
EndStartsOnOwnLine: -1
-m
LISTING 464: env-mlb16.yaml
modifyLineBreaks:
environments:
EndFinishesWithLineBreak:
-1
After running the commands
cmh:$ latexindent.pl -m env-mlb4.tex -l env-mlb13.yaml
cmh:$ latexindent.pl -m env-mlb4.tex -l env-mlb14.yaml
cmh:$ latexindent.pl -m env-mlb4.tex -l env-mlb15.yaml
cmh:$ latexindent.pl -m env-mlb4.tex -l env-mlb16.yaml
we obtain the respective output in Listings 465 to 468.
LISTING 465: env-mlb4.tex using
Listing 461
before words\begin{myenv}
body of myenv
\end{myenv}
after words
LISTING 466: env-mlb4.tex using
Listing 462
before words
\begin{myenv}body of myenv
\end{myenv}
after words
LISTING 467: env-mlb4.tex using
Listing 463
before words
\begin{myenv}
body of myenv\end{myenv}
after words
LISTING 468: env-mlb4.tex using
Listing 464
before words
\begin{myenv}
body of myenv
\end{myenv}after words
Notice that in:
Listing 465 the line break denoted by in Listing 460 has been removed;
Listing 466 the line break denoted by in Listing 460 has been removed;
Listing 467 the line break denoted by in Listing 460 has been removed;
Listing 468 the line break denoted by in Listing 460 has been removed.
We examined each of these cases separately for clarity of explanation, but you can combine all of
the YAML settings in Listings 461 to 464 into one file; alternatively, you could tell latexindent.pl
to load them all by using the following command, for example
[git] main @ 78d452f 2024-07-18 V3.24.4
6.3 Poly-switches 116
cmh:$
latexindent.pl -m env-mlb4.tex -l env-mlb13.yaml,env-mlb14.yaml,env-mlb15.yaml,env-mlb16.yaml
which gives the output in Listing 422 on page 109.
6.3.1.5 About trailing horizontal space
Recall that on page 33 we discussed the YAML field removeTrailingWhitespace, and that it has
two (binary) switches to determine if horizontal space should be removed beforeProcessing and
afterProcessing. The beforeProcessing is particularly relevant when considering the -m switch.
example 131
We consider the file shown in Listing 469, which highlights trailing spaces.
LISTING 469: env-mlb5.tex
before␣words␣␣␣
\begin{myenv}␣␣␣␣␣␣␣␣␣␣␣
body␣of␣myenv␣␣␣␣␣␣
\end{myenv}␣␣␣␣␣
after␣words
LISTING 470: removeTWS-before.yaml
removeTrailingWhitespace:
beforeProcessing: 1
The output from the following commands
cmh:$ latexindent.pl -m env-mlb5.tex -l env-mlb13,env-mlb14,env-mlb15,env-mlb16
cmh:$ latexindent.pl -m env-mlb5.tex -l env-mlb13,env-mlb14,env-mlb15,env-mlb16,removeTWS-before
is shown, respectively, in Listings 471 and 472; note that the trailing horizontal white space has
been preserved (by default) in Listing 471, while in Listing 472, it has been removed using the
switch specified in Listing 470.
LISTING 471: env-mlb5.tex using Listings 465 to 468
before␣words␣␣␣\begin{myenv}␣␣␣␣␣␣␣␣␣␣␣body␣of␣myenv␣␣␣␣␣␣\end{myenv}␣␣␣␣␣after␣words
LISTING 472: env-mlb5.tex using Listings 465 to 468 and Listing 470
before␣words\begin{myenv}body␣of␣myenv\end{myenv}after␣words
6.3.1.6 poly-switch line break removal and blank lines
example 132
Now let’s consider the file in Listing 473, which contains blank lines.
LISTING 473: env-mlb6.tex
before words
\begin{myenv}
body of myenv
\end{myenv}
after words
-m
LISTING 474:
UnpreserveBlankLines.yaml
modifyLineBreaks:
preserveBlankLines: 0
Upon running the following commands
[git] main @ 78d452f 2024-07-18 V3.24.4
6.3 Poly-switches 117
cmh:$ latexindent.pl -m env-mlb6.tex -l env-mlb13,env-mlb14,env-mlb15,env-mlb16
cmh:$
latexindent.pl -m env-mlb6.tex -l env-mlb13,env-mlb14,env-mlb15,env-mlb16,UnpreserveBlankLines
we receive the respective outputs in Listings 475 and 476. In Listing 475 we see that the multiple
blank lines have each been condensed into one blank line, but that blank lines have not been
removed by the poly-switches – this is because, by default, preserveBlankLines is set to 1. By
contrast, in Listing 476, we have allowed the poly-switches to remove blank lines because, in
Listing 474, we have set preserveBlankLines to 0.
LISTING 475: env-mlb6.tex using
Listings 465 to 468
before words
\begin{myenv}
body of myenv
\end{myenv}
after words
LISTING 476: env-mlb6.tex using Listings 465 to 468 and Listing 474
before words\begin{myenv}body of myenv\end{myenv}after words
example 133
We can explore this further using the blank-line poly-switch value of 3; let’s use the file given in
Listing 477.
LISTING 477: env-mlb7.tex
\begin{one} one text \end{one} \begin{two} two text \end{two}
Upon running the following commands
cmh:$ latexindent.pl -m env-mlb7.tex -l env-mlb12.yaml,env-mlb13.yaml
cmh:$
latexindent.pl -m env-mlb7.tex -l env-mlb13,env-mlb14,UnpreserveBlankLines
we receive the outputs given in Listings 478 and 479.
LISTING 478: env-mlb7-preserve.tex
\begin{one} one text \end{one}
\begin{two} two text \end{two}
LISTING 479: env-mlb7-no-preserve.tex
\begin{one} one text \end{one} \begin{two} two text \end{two}
Notice that in:
Listing 478 that \end{one} has added a blank line, because of the value of EndFinishesWithLineBreak
in Listing 449 on page 113, and even though the line break ahead of \begin{two} should
have been removed (because of BeginStartsOnOwnLine in Listing 461 on page 115), the
blank line has been preserved by default;
Listing 479, by contrast, has had the additional line-break removed, because of the settings
in Listing 474.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.3 Poly-switches 118
6.3.2 Poly-switches for double backslash
With reference to lookForAlignDelims (see Listing 58 on page 33)
N: 2019-07-13
you can specify poly-switches
to dictate the line-break behaviour of double backslashes in environments (Listing 60 on page 34),
commands (Listing 94 on page 40), or special code blocks (Listing 139 on page 48).
6
Consider the code given in Listing 480.
LISTING 480: tabular3.tex
\begin{tabular}{cc}
1 & 2 Æ\\ 3 & 4 Æ\\
\end{tabular}
Referencing Listing 480:
DBS stands for double backslash;
line breaks ahead of the double backslash are annotated by Æ, and are controlled by DBSStartsOnOwnLine;
line breaks after the double backslash are annotated by , and are controlled by DBSFinishesWithLineBreak.
Let’s explore each of these in turn.
6.3.2.1 Double backslash starts on own line
example 134
We explore DBSStartsOnOwnLine (Æ in Listing 480); starting with the code in Listing 480, to-
gether with the YAML files given in Listing 482 and Listing 484 and running the following com-
mands
cmh:$ latexindent.pl -m tabular3.tex -l DBS1.yaml
cmh:$ latexindent.pl -m tabular3.tex -l DBS2.yaml
then we receive the respective output given in Listing 481 and Listing 483.
LISTING 481: tabular3.tex using
Listing 482
\begin{tabular}{cc}
1 & 2
\\ 3 & 4
\\
\end{tabular}
-m
LISTING 482: DBS1.yaml
modifyLineBreaks:
environments:
DBSStartsOnOwnLine: 1
LISTING 483: tabular3.tex using
Listing 484
\begin{tabular}{cc}
1 & 2 %
\\ 3 & 4%
\\
\end{tabular}
-m
LISTING 484: DBS2.yaml
modifyLineBreaks:
environments:
tabular:
DBSStartsOnOwnLine: 2
We note that
Listing 482 specifies DBSStartsOnOwnLine for every environment (that is within lookForAlignDelims,
Listing 61 on page 34); the double backslashes from Listing 480 have been moved to their
own line in Listing 481;
Listing 484 specifies DBSStartsOnOwnLine on a per-name basis for tabular (that is within
lookForAlignDelims, Listing 61 on page 34); the double backslashes from Listing 480
have been moved to their own line in Listing 483, having added comment symbols before
6
There is no longer any need for the code block to be specified within lookForAlignDelims for DBS poly-switches to
activate.
U: 2023-01-01
[git] main @ 78d452f 2024-07-18 V3.24.4
6.3 Poly-switches 119
moving them.
example 135
We can combine DBS poly-switches with, for example, the alignContentAfterDoubleBackSlash
in Section 5.5.6 on page 45.
For example, starting with the file Listing 485, and using the settings in Listings 130 and 132 on
page 46 and running
cmh:$ latexindent.pl -s -m -l alignContentAfterDBS1.yaml,DBS1.yaml tabular6.tex -o=+-mod1
cmh:$ latexindent.pl -s -m -l alignContentAfterDBS2.yaml,DBS1.yaml tabular6.tex -o=+-mod2
gives the respective outputs shown in Listings 486 and 487.
LISTING 485: tabular6.tex
\begin{tabular}{cc}
1&22\\333&4444\\55555&666666
\end{tabular}
LISTING 486: tabular6-mod1.tex
\begin{tabular}{cc}
1 & 22
\\ 333 & 4444
\\ 55555 & 666666
\end{tabular}
LISTING 487: tabular6-mod2.tex
\begin{tabular}{cc}
1 & 22
\\ 333 & 4444
\\ 55555 & 666666
\end{tabular}
We note that:
in Listing 486 the content after the double back slash has been aligned;
in Listing 487 we see that 3 spaces have been added after the double back slash.
6.3.2.2 Double backslash finishes with line break
example 136
Let’s now explore DBSFinishesWithLineBreak ( in Listing 480); starting with the code in
Listing 480, together with the YAML files given in Listing 489 and Listing 491 and running the
following commands
cmh:$ latexindent.pl -m tabular3.tex -l DBS3.yaml
cmh:$ latexindent.pl -m tabular3.tex -l DBS4.yaml
then we receive the respective output given in Listing 488 and Listing 490.
LISTING 488: tabular3.tex using
Listing 489
\begin{tabular}{cc}
1 & 2 \\
3 & 4 \\
\end{tabular}
-m
LISTING 489: DBS3.yaml
modifyLineBreaks:
environments:
DBSFinishesWithLineBreak: 1
LISTING 490: tabular3.tex using
Listing 491
\begin{tabular}{cc}
1 & 2 \\%
3 & 4 \\
\end{tabular}
-m
LISTING 491: DBS4.yaml
modifyLineBreaks:
environments:
tabular:
DBSFinishesWithLineBreak:
2
We note that
Listing 489 specifies DBSFinishesWithLineBreak for every environment (that is within
lookForAlignDelims, Listing 61 on page 34); the code following the double backslashes
from Listing 480 has been moved to their own line in Listing 488;
[git] main @ 78d452f 2024-07-18 V3.24.4
6.3 Poly-switches 120
Listing 491 specifies DBSFinishesWithLineBreak on a per-name basis for tabular (that
is within lookForAlignDelims, Listing 61 on page 34); the first double backslashes from
Listing 480 have moved code following them to their own line in Listing 490, having added
comment symbols before moving them; the final double backslashes have not added a line
break as they are at the end of the body within the code block.
6.3.2.3 Double backslash poly-switches for specialBeginEnd
example 137
Let’s explore the double backslash poly-switches for code blocks within specialBeginEnd code
blocks (Listing 137 on page 47); we begin with the code within Listing 492.
LISTING 492: special4.tex
\< a& =b \\ & =c\\ & =d\\ & =e \>
Upon using the YAML settings in Listing 494, and running the command
cmh:$ latexindent.pl -m special4.tex -l DBS5.yaml
then we receive the output given in Listing 493.
LISTING 493: special4.tex
using Listing 494
\<
a & =b \\
& =c \\
& =d \\
& =e %
\>
-m
LISTING 494: DBS5.yaml
specialBeginEnd:
cmhMath:
lookForThis: 1
begin: ’\\<’
end: ’\\>’
lookForAlignDelims:
cmhMath: 1
modifyLineBreaks:
specialBeginEnd:
cmhMath:
DBSFinishesWithLineBreak: 1
SpecialBodyStartsOnOwnLine: 1
SpecialEndStartsOnOwnLine: 2
There are a few things to note:
in Listing 494 we have specified cmhMath within lookForAlignDelims; without this, the
double backslash poly-switches would be ignored for this code block;
the DBSFinishesWithLineBreak poly-switch has controlled the line breaks following the
double backslashes;
the SpecialEndStartsOnOwnLine poly-switch has controlled the addition of a comment
symbol, followed by a line break, as it is set to a value of 2.
6.3.2.4 Double backslash poly-switches for optional and mandatory arguments
For clarity, we provide a demonstration of controlling the double backslash poly-switches for optional
and mandatory arguments.
example 138
We use with the code in Listing 495.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.3 Poly-switches 121
LISTING 495: mycommand2.tex
\mycommand [
1&2 &3\\ 4&5&6]{
7&8 &9\\ 10&11&12
}
Upon using the YAML settings in Listings 497 and 499, and running the command
cmh:$ latexindent.pl -m mycommand2.tex -l DBS6.yaml
cmh:$ latexindent.pl -m mycommand2.tex -l DBS7.yaml
then we receive the output given in Listings 496 and 498.
LISTING 496: mycommand2.tex
using Listing 497
\mycommand [
1 & 2 & 3 %
\\%
4 & 5 & 6]{
7 & 8 & 9 \\ 10&11&12
}
-m
LISTING 497: DBS6.yaml
lookForAlignDelims:
mycommand: 1
modifyLineBreaks:
optionalArguments:
DBSStartsOnOwnLine: 2
DBSFinishesWithLineBreak: 2
LISTING 498: mycommand2.tex
using Listing 499
\mycommand [
1&2 &3\\ 4&5&6]{
7 & 8 & 9 %
\\%
10 & 11 & 12
}
-m
LISTING 499: DBS7.yaml
lookForAlignDelims:
mycommand: 1
modifyLineBreaks:
mandatoryArguments:
DBSStartsOnOwnLine: 2
DBSFinishesWithLineBreak: 2
6.3.2.5 Double backslash optional square brackets
The pattern matching for the double backslash will also, optionally, allow trailing square brackets
that contain a measurement of vertical spacing, for example \\[3pt].
example 139
For example, beginning with the code in Listing 500
LISTING 500: pmatrix3.tex
\begin{pmatrix}
1 & 2 \\[2pt] 3 & 4 \\ [ 3 ex] 5&6\\[ 4 pt ] 7 & 8
\end{pmatrix}
and running the following command, using Listing 489,
cmh:$ latexindent.pl -m pmatrix3.tex -l DBS3.yaml
then we receive the output given in Listing 501.
LISTING 501: pmatrix3.tex using Listing 489
\begin{pmatrix}
1 & 2 \\[2pt]
3 & 4 \\ [ 3 ex]
5 & 6 \\[ 4 pt ]
7 & 8
\end{pmatrix}
[git] main @ 78d452f 2024-07-18 V3.24.4
6.3 Poly-switches 122
You can customise the pattern for the double backslash by exploring the fine tuning field detailed in
Listing 566 on page 144.
6.3.3 Poly-switches for other code blocks
Rather than repeat the examples shown for the environment code blocks (in Section 6.3.1 on page 109),
we choose to detail the poly-switches for all other code blocks in Section 6.3.3; note that each and
every one of these poly-switches is off by default, i.e, set to 0.
Note also that, by design, line breaks involving, filecontents and ‘comment-marked’ code blocks
(Listing 95 on page 41) can not be modified using latexindent.pl.
U: 2019-05-05
However, there are two poly-
switches available for verbatim code blocks: environments (Listing 37 on page 29), commands
(Listing 38 on page 29) and specialBeginEnd (Listing 154 on page 51).
[git] main @ 78d452f 2024-07-18 V3.24.4
6.3 Poly-switches 123
TABLE 3: Poly-switch mappings for all code-block types
Code block Sample Poly-switch mapping
environment before words BeginStartsOnOwnLine
\begin{myenv} BodyStartsOnOwnLine
body of myenv EndStartsOnOwnLine
\end{myenv} EndFinishesWithLineBreak
after words
ifelsefi before words IfStartsOnOwnLine
\if... BodyStartsOnOwnLine
body of if/or statement OrStartsOnOwnLine
N: 2018-04-27
\or OrFinishesWithLineBreak
body of if/or statementÆ Æ ElseStartsOnOwnLine
\else ElseFinishesWithLineBreak
body of else statement FiStartsOnOwnLine
\fi FiFinishesWithLineBreak
after words
optionalArguments ... LSqBStartsOnOwnLine
7
[ OptArgBodyStartsOnOwnLine
N: 2019-07-13
value before commaÆ, Æ CommaStartsOnOwnLine
CommaFinishesWithLineBreak
end of body of opt arg RSqBStartsOnOwnLine
] RSqBFinishesWithLineBreak
...
mandatoryArguments ... LCuBStartsOnOwnLine
8
{ MandArgBodyStartsOnOwnLine
N: 2019-07-13
value before commaÆ, Æ CommaStartsOnOwnLine
CommaFinishesWithLineBreak
end of body of mand arg RCuBStartsOnOwnLine
} RCuBFinishesWithLineBreak
...
commands before words CommandStartsOnOwnLine
\mycommand CommandNameFinishesWithLineBreak
arguments
namedGroupingBracesBrackets before words NameStartsOnOwnLine
myname NameFinishesWithLineBreak
braces/brackets
keyEqualsValuesBracesBrackets before words KeyStartsOnOwnLine
key= EqualsStartsOnOwnLine
braces/brackets EqualsFinishesWithLineBreak
items before words ItemStartsOnOwnLine
\item ItemFinishesWithLineBreak
...
specialBeginEnd before words SpecialBeginStartsOnOwnLine
\[ SpecialBodyStartsOnOwnLine
body of special/middleÆ Æ SpecialMiddleStartsOnOwnLine
N: 2018-04-27
\middle SpecialMiddleFinishesWithLineBreak
body of special/middle SpecialEndStartsOnOwnLine
\] SpecialEndFinishesWithLineBreak
after words
verbatim before words\begin{verbatim} VerbatimBeginStartsOnOwnLine
7
LSqB stands for Left Square Bracket
8
LCuB stands for Left Curly Brace
[git] main @ 78d452f 2024-07-18 V3.24.4
6.3 Poly-switches 124
N: 2019-05-05
body of verbatim \end{verbatim} VerbatimEndFinishesWithLineBreak
after words
6.3.4 Partnering BodyStartsOnOwnLine with argument-based poly-switches
Some poly-switches need to be partnered together; in particular, when line breaks involving the
first argument of a code block need to be accounted for using both BodyStartsOnOwnLine (or its
equivalent, see Section 6.3.3 on the preceding page) and LCuBStartsOnOwnLine for mandatory
arguments, and LSqBStartsOnOwnLine for optional arguments.
example 140
Let’s begin with the code in Listing 502 and the YAML settings in Listing 504; with reference to
Section 6.3.3 on the previous page, the key CommandNameFinishesWithLineBreak is an alias
for BodyStartsOnOwnLine.
LISTING 502: mycommand1.tex
\mycommand
{
mand arg text
mand arg text}
{
mand arg text
mand arg text}
Upon running the command
cmh:$ latexindent.pl -m -l=mycom-mlb1.yaml mycommand1.tex
we obtain Listing 503; note that the second mandatory argument beginning brace { has had its
leading line break removed, but that the first brace has not.
LISTING 503: mycommand1.tex
using Listing 504
\mycommand
{
mand arg text
mand arg text}{
mand arg text
mand arg text}
-m
LISTING 504: mycom-mlb1.yaml
modifyLineBreaks:
commands:
CommandNameFinishesWithLineBreak: 0
mandatoryArguments:
LCuBStartsOnOwnLine: -1
example 141
Now let’s change the YAML file so that it is as in Listing 506; upon running the command
cmh:$ latexindent.pl -m -l=mycom-mlb2.yaml mycommand1.tex
we obtain Listing 505; both beginning braces { have had their leading line breaks removed.
LISTING 505: mycommand1.tex
using Listing 506
\mycommand{
mand arg text
mand arg text}{
mand arg text
mand arg text}
-m
LISTING 506: mycom-mlb2.yaml
modifyLineBreaks:
commands:
CommandNameFinishesWithLineBreak: -1
mandatoryArguments:
LCuBStartsOnOwnLine: -1
example 142
Now let’s change the YAML file so that it is as in Listing 508; upon running the command
[git] main @ 78d452f 2024-07-18 V3.24.4
6.3 Poly-switches 125
cmh:$ latexindent.pl -m -l=mycom-mlb3.yaml mycommand1.tex
we obtain Listing 507.
LISTING 507: mycommand1.tex
using Listing 508
\mycommand
{
mand arg text
mand arg text}
{
mand arg text
mand arg text}
-m
LISTING 508: mycom-mlb3.yaml
modifyLineBreaks:
commands:
CommandNameFinishesWithLineBreak: -1
mandatoryArguments:
LCuBStartsOnOwnLine: 1
6.3.5 Conflicting poly-switches: sequential code blocks
It is very easy to have conflicting poly-switches.
example 143
We use the example from Listing 502 on the preceding page, and consider the YAML settings
given in Listing 510. The output from running
cmh:$ latexindent.pl -m -l=mycom-mlb4.yaml mycommand1.tex
is given in Listing 510.
LISTING 509: mycommand1.tex using
Listing 510
\mycommand
{
mand arg text
mand arg text}{
mand arg text
mand arg text}
-m
LISTING 510: mycom-mlb4.yaml
modifyLineBreaks:
mandatoryArguments:
LCuBStartsOnOwnLine: -1
RCuBFinishesWithLineBreak: 1
Studying Listing 510, we see that the two poly-switches are at opposition with one another:
on the one hand, LCuBStartsOnOwnLine should not start on its own line (as poly-switch
is set to 1);
on the other hand, RCuBFinishesWithLineBreak should finish with a line break.
So, which should win the conflict? As demonstrated in Listing 509, it is clear that LCuBStartsOnOwnLine
won this conflict, and the reason is that the second argument was processed after the first – in gen-
eral, the most recently-processed code block and associated poly-switch takes priority.
example 144
We can explore this further by considering the YAML settings in Listing 512; upon running the
command
cmh:$ latexindent.pl -m -l=mycom-mlb5.yaml mycommand1.tex
we obtain the output given in Listing 511.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.3 Poly-switches 126
LISTING 511: mycommand1.tex using
Listing 512
\mycommand
{
mand arg text
mand arg text}
{
mand arg text
mand arg text}
-m
LISTING 512: mycom-mlb5.yaml
modifyLineBreaks:
mandatoryArguments:
LCuBStartsOnOwnLine: 1
RCuBFinishesWithLineBreak:
-1
As previously, the most-recently-processed code block takes priority – as before, the second (i.e,
last) argument.
Exploring this further, we consider the YAML settings in Listing 514, and run the command
cmh:$ latexindent.pl -m -l=mycom-mlb6.yaml mycommand1.tex
which gives the output in Listing 513.
LISTING 513: mycommand1.tex using
Listing 514
\mycommand
{
mand arg text
mand arg text}%
{
mand arg text
mand arg text}
-m
LISTING 514: mycom-mlb6.yaml
modifyLineBreaks:
mandatoryArguments:
LCuBStartsOnOwnLine: 2
RCuBFinishesWithLineBreak:
-1
Note that a % has been added to the trailing first }; this is because:
while processing the first argument, the trailing line break has been removed (RCuBFinishesWithLineBreak
set to 1);
while processing the second argument, latexindent.pl finds that it does not begin on its
own line, and so because LCuBStartsOnOwnLine is set to 2, it adds a comment, followed
by a line break.
6.3.6 Conflicting poly-switches: nested code blocks
example 145
Now let’s consider an example when nested code blocks have conflicting poly-switches; we’ll use
the code in Listing 515, noting that it contains nested environments.
LISTING 515: nested-env.tex
\begin{one}
one text
\begin{two}
two text
\end{two}
\end{one}
Let’s use the YAML settings given in Listing 517, which upon running the command
cmh:$ latexindent.pl -m -l=nested-env-mlb1.yaml nested-env.tex
gives the output in Listing 516.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.3 Poly-switches 127
LISTING 516: nested-env.tex using
Listing 517
\begin{one}
one text
\begin{two}
two text\end{two}\end{one}
-m
LISTING 517: nested-env-mlb1.yaml
modifyLineBreaks:
environments:
EndStartsOnOwnLine: -1
EndFinishesWithLineBreak: 1
In Listing 516, let’s first of all note that both environments have received the appropriate (default)
indentation; secondly, note that the poly-switch EndStartsOnOwnLine appears to have won the
conflict, as \end{one} has had its leading line break removed.
To understand it, let’s talk about the three basic phases of latexindent.pl:
1. Phase 1: packing, in which code blocks are replaced with unique ids, working from the inside
to the outside, and then sequentially for example, in Listing 515, the two environment is
found before the one environment; if the -m switch is active, then during this phase:
line breaks at the beginning of the body can be added (if BodyStartsOnOwnLine is 1 or
2) or removed (if BodyStartsOnOwnLine is 1);
line breaks at the end of the body can be added (if EndStartsOnOwnLine is 1 or 2) or
removed (if EndStartsOnOwnLine is 1);
line breaks after the end statement can be added (if EndFinishesWithLineBreak is 1
or 2).
2. Phase 2: indentation, in which white space is added to the begin, body, and end statements;
3. Phase 3: unpacking, in which unique ids are replaced by their indented code blocks; if the -m
switch is active, then during this phase,
line breaks before begin statements can be added or removed (depending upon BeginStartsOnOwnLine);
line breaks after end statements can be removed but NOT added (see EndFinishesWithLineBreak).
With reference to Listing 516, this means that during Phase 1:
the two environment is found first, and the line break ahead of the \end{two} statement
is removed because EndStartsOnOwnLine is set to 1. Importantly, because, at this stage,
\end{two} does finish with a line break, EndFinishesWithLineBreak causes no action.
next, the one environment is found; the line break ahead of \end{one} is removed because
EndStartsOnOwnLine is set to 1.
The indentation is done in Phase 2; in Phase 3 there is no option to add a line break after the end
statements. We can justify this by remembering that during Phase 3, the one environment will be
found and processed first, followed by the two environment. If the two environment were to add
a line break after the \end{two} statement, then latexindent.pl would have no way of knowing
how much indentation to add to the subsequent text (in this case, \end{one}).
example 146
We can explore this further using the poly-switches in Listing 519; upon running the command
cmh:$ latexindent.pl -m -l=nested-env-mlb2.yaml nested-env.tex
we obtain the output given in Listing 518.
[git] main @ 78d452f 2024-07-18 V3.24.4
6.3 Poly-switches 128
LISTING 518: nested-env.tex using
Listing 519
\begin{one}
one text
\begin{two}
two text
\end{two}\end{one}
-m
LISTING 519: nested-env-mlb2.yaml
modifyLineBreaks:
environments:
EndStartsOnOwnLine: 1
EndFinishesWithLineBreak: -1
During Phase 1:
the two environment is found first, and the line break ahead of the \end{two} statement is
not changed because EndStartsOnOwnLine is set to 1. Importantly, because, at this stage,
\end{two} does finish with a line break, EndFinishesWithLineBreak causes no action.
next, the one environment is found; the line break ahead of \end{one} is already present,
and no action is needed.
The indentation is done in Phase 2, and then in Phase 3, the one environment is found and
processed first, followed by the two environment. At this stage, the two environment finds
EndFinishesWithLineBreak is 1, so it removes the trailing line break; remember, at this point,
latexindent.pl has completely finished with the one environment.
[git] main @ 78d452f 2024-07-18 V3.24.4
SECTION 7
The -r, -rv and -rr switches
You can instruct latexindent.pl to perform replacements/substitutions on your
N: 2019-07-13
file by using any
of the -r, -rv or -rr switches:
the -r switch will perform indentation and replacements, not respecting verbatim code blocks;
the -rv switch will perform indentation and replacements, and will respect verbatim code
blocks;
the -rr switch will not perform indentation, and will perform replacements not respecting
verbatim code blocks.
We will demonstrate each of the -r, -rv and -rr switches, but a summary is given in Table 4.
TABLE 4: The replacement mode switches
switch indentation? respect verbatim?
-r Ë é
-rv Ë Ë
-rr é é
The default value of the replacements field is shown in Listing 520; as with all of the other fields,
you are encouraged to customise and change this as you see fit. The options in this field will only be
considered if the -r, -rv or -rr switches are active; when discussing YAML settings related to the
replacement-mode switches, we will use the style given in Listing 520.
-r
LISTING 520: replacements
622 replacements:
623 - amalgamate: 1
624 - this: latexindent.pl
625 that: pl.latexindent
626 lookForThis: 0
627 when: before
The first entry within the replacements field is amalgamate, and is optional; by default it is set to
1, so that replacements will be amalgamated from each settings file that you specify. As you’ll see in
the demonstrations that follow, there is no need to specify this field.
You’ll notice that, by default, there is only one entry in the replacements field, but it can take as
many entries as you would like; each one needs to begin with a - on its own line.
7.1 Introduction to replacements
Let’s explore the action of the default settings, and then we’ll demonstrate the feature with further
examples.
example 147
Beginning with the code in Listing 521 and running the command
cmh:$ latexindent.pl -r replace1.tex
gives the output given in Listing 522.
[git] main @ 78d452f 2024-07-18 V3.24.4
7.2 The two types of replacements 130
LISTING 521: replace1.tex
Before text, latexindent.pl,
after text.
LISTING 522: replace1.tex default
Before text, latexindent.pl,
after text.
We note that in Listing 520, because lookForThis is set to 0, the specified replacement has not
been made, and there is no difference between Listings 521 and 522.
If we do wish to perform this replacement, then we can tweak the default settings of Listing 520
on the previous page by changing lookForThis to 1; we perform this action in Listing 524, and
run the command
cmh:$ latexindent.pl -r replace1.tex -l=replace1.yaml
which gives the output in Listing 523.
LISTING 523: replace1.tex using
Listing 524
Before text, pl.latexindent,
after text.
-r
LISTING 524: replace1.yaml
replacements:
-
amalgamate: 0
-
this: latexindent.pl
that: pl.latexindent
lookForThis: 1
Note that in Listing 524 we have specified amalgamate as 0 so that the default replacements are
overwritten.
We haven’t yet discussed the when field; don’t worry, we’ll get to it as part of the discussion in what
follows.
7.2 The two types of replacements
There are two types of replacements:
1. string-based replacements, which replace the string in this with the string in that. If you specify
this and you do not specify that, then the that field will be assumed to be empty.
2. regex-based replacements, which use the substitution field.
We will demonstrate both in the examples that follow.
latexindent.pl chooses which type of replacement to make based on which fields have been
specified; if the this field is specified, then it will make string-based replacements, regardless of
if substitution is present or not.
7.3 Examples of replacements
example 148
We begin with code given in Listing 525
LISTING 525: colsep.tex
\begin{env}
1 2 3\arraycolsep=3pt
4 5 6\arraycolsep=5pt
\end{env}
Let’s assume that our goal is to remove both of the arraycolsep statements; we can achieve this
in a few different ways.
[git] main @ 78d452f 2024-07-18 V3.24.4
7.3 Examples of replacements 131
Using the YAML in Listing 527, and running the command
cmh:$ latexindent.pl -r colsep.tex -l=colsep.yaml
then we achieve the output in Listing 526.
LISTING 526: colsep.tex using
Listing 527
\begin{env}
1 2 3
4 5 6
\end{env}
-r
LISTING 527: colsep.yaml
replacements:
-
this: \arraycolsep=3pt
-
this: \arraycolsep=5pt
Note that in Listing 527, we have specified two separate fields, each with their own this field;
furthermore, for both of the separate fields, we have not specified that’, so the that field is
assumed to be blank by latexindent.pl;
We can make the YAML in Listing 527 more concise by exploring the substitution field. Using
the settings in Listing 529 and running the command
cmh:$ latexindent.pl -r colsep.tex -l=colsep1.yaml
then we achieve the output in Listing 528.
LISTING 528: colsep.tex using
Listing 529
\begin{env}
1 2 3
4 5 6
\end{env}
-r
LISTING 529: colsep1.yaml
replacements:
-
substitution:
s/\\arraycolsep=\d+pt//sg
The code given in Listing 529 is an example of a regular expression, which we may abbreviate
to regex in what follows. This manual is not intended to be a tutorial on regular expressions;
you might like to read, for example, [35] for a detailed covering of the topic. With reference to
Listing 529, we do note the following:
the general form of the substitution field is s/regex/replacement/modifiers. You can
place any regular expression you like within this;
we have ‘escaped’ the backslash by using \\
we have used \d+ to represent at least one digit
the s modifier (in the sg at the end of the line) instructs latexindent.pl to treat your file
as one single line;
the g modifier (in the sg at the end of the line) instructs latexindent.pl to make the
substitution globally throughout your file; you might try removing the g modifier from
Listing 529 and observing the difference in output.
You might like to see https://perldoc.perl.org/perlre.html#Modifiers for details of modifiers; in
general, I recommend starting with the sg modifiers for this feature.
example 149
We’ll keep working with the file in Listing 525 on the preceding page for this example.
Using the YAML in Listing 531, and running the command
[git] main @ 78d452f 2024-07-18 V3.24.4
7.3 Examples of replacements 132
cmh:$ latexindent.pl -r colsep.tex -l=multi-line.yaml
then we achieve the output in Listing 530.
LISTING 530: colsep.tex using
Listing 531
multi-line!
-r
LISTING 531: multi-line.yaml
replacements:
-
this: |-
\begin{env}
1 2 3\arraycolsep=3pt
4 5 6\arraycolsep=5pt
\end{env}
that: ’multi-line!’
With reference to Listing 531, we have specified a multi-line version of this by employing the
literal YAML style |-. See, for example, https://stackoverflow.com/questions/3790454/in-yaml-
how-do-i-break-a-string-over-multiple-lines for further options, all of which can be used in your
YAML file.
This is a natural point to explore the when field, specified in Listing 520 on page 129. This field
can take two values: before and after, which respectively instruct latexindent.pl to perform
the replacements before indentation or after it. The default value is before.
Using the YAML in Listing 533, and running the command
cmh:$ latexindent.pl -r colsep.tex -l=multi-line1.yaml
then we achieve the output in Listing 532.
LISTING 532: colsep.tex using
Listing 533
\begin{env}
1 2 3\arraycolsep=3pt
4 5 6\arraycolsep=5pt
\end{env}
-r
LISTING 533: multi-line1.yaml
replacements:
-
this: |-
\begin{env}
1 2 3\arraycolsep=3pt
4 5 6\arraycolsep=5pt
\end{env}
that: ’multi-line!’
when: after
We note that, because we have specified when: after, that latexindent.pl has not found
the string specified in Listing 533 within the file in Listing 525 on page 130. As it has looked
for the string within Listing 533 after the indentation has been performed. After indentation, the
string as written in Listing 533 is no longer part of the file, and has therefore not been replaced.
As a final note on this example, if you use the -rr switch, as follows,
cmh:$ latexindent.pl -rr colsep.tex -l=multi-line1.yaml
then the when field is ignored, no indentation is done, and the output is as in Listing 530.
example 150
An important part of the substitution routine is in capture groups.
Assuming that we start with the code in Listing 534, let’s assume that our goal is to replace
each occurrence of $$...$$ with \begin{equation*}...\end{equation*}. This example is partly
motivated by tex stackexchange question 242150.
[git] main @ 78d452f 2024-07-18 V3.24.4
7.3 Examples of replacements 133
LISTING 534: displaymath.tex
before text $$a^2+b^2=4$$ and $$c^2$$
$$
d^2+e^2 = f^2
$$
and also $$ g^2
$$ and some inline math: $h^2$
We use the settings in Listing 536 and run the command
cmh:$ latexindent.pl -r displaymath.tex -l=displaymath1.yaml
to receive the output given in Listing 535.
LISTING 535: displaymath.tex using Listing 536
before text \begin{equation*}a^2+b^2=4\end{equation*}
and \begin{equation*}c^2\end{equation*}
\begin{equation*}
d^2+e^2 = f^2
\end{equation*}
and also \begin{equation*} g^2
\end{equation*} and some inline math: $h^2$
-r
LISTING 536: displaymath1.yaml
replacements:
-
substitution: |-
s/\$\$
(.*?)
\$\$/\\begin{equation*}$1\\end{equation*}/sgx
A few notes about Listing 536:
1. we have used the x modifier, which allows us to have white space within the regex;
2. we have used a capture group, (.*?) which captures the content between the $$...$$ into
the special variable, $1;
3. we have used the content of the capture group, $1, in the replacement text.
See https://perldoc.perl.org/perlre.html#Capture-groups for a discussion of capture groups.
The features of the replacement switches can, of course, be combined with others from the toolkit
of latexindent.pl. For example, we can combine the poly-switches of Section 6.3 on page 108,
which we do in Listing 538; upon running the command
cmh:$ latexindent.pl -r -m displaymath.tex -l=displaymath1.yaml,equation.yaml
then we receive the output in Listing 537.
[git] main @ 78d452f 2024-07-18 V3.24.4
7.3 Examples of replacements 134
LISTING 537:
displaymath.tex using
Listings 536 and 538
before text%
\begin{equation*}%
a^2+b^2=4%
\end{equation*}%
and%
\begin{equation*}%
c^2%
\end{equation*}
\begin{equation*}
d^2+e^2 = f^2
\end{equation*}
and also%
\begin{equation*}%
g^2
\end{equation*}%
and some inline math: $h^2$
-m
LISTING 538: equation.yaml
modifyLineBreaks:
environments:
equation*:
BeginStartsOnOwnLine: 2
BodyStartsOnOwnLine: 2
EndStartsOnOwnLine: 2
EndFinishesWithLineBreak: 2
example 151
This example is motivated by tex stackexchange question 490086. We begin with the code in
Listing 539.
LISTING 539: phrase.tex
phrase 1 phrase 2 phrase 3 phrase 100
phrase 1 phrase 2 phrase 3 phrase 100
phrase 1 phrase 2 phrase 3 phrase 100
phrase 1 phrase 2 phrase 3 phrase 100
Our goal is to make the spacing uniform between the phrases. To achieve this, we employ the
settings in Listing 541, and run the command
cmh:$ latexindent.pl -r phrase.tex -l=hspace.yaml
which gives the output in Listing 540.
LISTING 540: phrase.tex using
Listing 541
phrase 1 phrase 2 phrase 3 phrase 100
phrase 1 phrase 2 phrase 3 phrase 100
phrase 1 phrase 2 phrase 3 phrase 100
phrase 1 phrase 2 phrase 3 phrase 100
-r
LISTING 541: hspace.yaml
replacements:
-
substitution: s/\h+/ /sg
The \h+ setting in Listing 541 say to replace at least one horizontal space with a single space.
example 152
We begin with the code in Listing 542.
[git] main @ 78d452f 2024-07-18 V3.24.4
7.3 Examples of replacements 135
LISTING 542: references.tex
equation \eqref{eq:aa} and Figure \ref{fig:bb}
and table~\ref{tab:cc}
Our goal is to change each reference so that both the text and the reference are contained within
one hyperlink. We achieve this by employing Listing 544 and running the command
cmh:$ latexindent.pl -r references.tex -l=reference.yaml
which gives the output in Listing 543.
LISTING 543: references.tex using Listing 544
\hyperref{equation \ref*{eq:aa}} and \hyperref{Figure \ref*{fig:bb}}
and \hyperref{table \ref*{tab:cc}}
-r
LISTING 544: reference.yaml
replacements:
-
substitution: |-
s/(
equation
|
table
|
figure
|
section
)
(\h|~)*
\\(?:eq)?
ref\{(.*?)\}/\\hyperref{$1 \\ref\*{$3}}/sgxi
Referencing Listing 544, the | means or, we have used capture groups, together with an example
of an optional pattern, (?:eq)?.
example 153
Let’s explore the three replacement mode switches (see Table 4 on page 129) in the context of an
example that contains a verbatim code block, Listing 545; we will use the settings in Listing 546.
LISTING 545: verb1.tex
\begin{myenv}
body of verbatim
\end{myenv}
some verbatim
\begin{verbatim}
body
of
verbatim
text
\end{verbatim}
text
-r
LISTING 546: verbatim1.yaml
replacements:
-
this: ’body’
that: ’head’
Upon running the following commands,
cmh:$ latexindent.pl -r verb1.tex -l=verbatim1.yaml -o=+mod1
cmh:$ latexindent.pl -rv verb1.tex -l=verbatim1.yaml -o=+-rv-mod1
cmh:$ latexindent.pl -rr verb1.tex -l=verbatim1.yaml -o=+-rr-mod1
[git] main @ 78d452f 2024-07-18 V3.24.4
7.3 Examples of replacements 136
we receive the respective output in Listings 547 to 549
LISTING 547: verb1-mod1.tex
\begin{myenv}
head of verbatim
\end{myenv}
some verbatim
\begin{verbatim}
head
of
verbatim
text
\end{verbatim}
text
LISTING 548: verb1-rv-mod1.tex
\begin{myenv}
head of verbatim
\end{myenv}
some verbatim
\begin{verbatim}
body
of
verbatim
text
\end{verbatim}
text
LISTING 549: verb1-rr-mod1.tex
\begin{myenv}
head of verbatim
\end{myenv}
some verbatim
\begin{verbatim}
head
of
verbatim
text
\end{verbatim}
text
We note that:
1. in Listing 547 indentation has been performed, and that the replacements specified in List-
ing 546 have been performed, even within the verbatim code block;
2. in Listing 548 indentation has been performed, but that the replacements have not been per-
formed within the verbatim environment, because the rv switch is active;
3. in Listing 549 indentation has not been performed, but that replacements have been performed,
not respecting the verbatim code block.
See the summary within Table 4 on page 129.
example 154
Let’s explore the amalgamate field from Listing 520 on page 129 in the context of the file specified
in Listing 550.
LISTING 550: amalg1.tex
one two three
Let’s consider the YAML files given in Listings 551 to 553.
-r
LISTING 551: amalg1-yaml.yaml
replacements:
-
this: one
that: 1
-r
LISTING 552: amalg2-yaml.yaml
replacements:
-
this: two
that: 2
-r
LISTING 553: amalg3-yaml.yaml
replacements:
-
amalgamate: 0
-
this: three
that: 3
Upon running the following commands,
cmh:$ latexindent.pl -r amalg1.tex -l=amalg1-yaml
cmh:$ latexindent.pl -r amalg1.tex -l=amalg1-yaml,amalg2-yaml
cmh:$ latexindent.pl -r amalg1.tex -l=amalg1-yaml,amalg2-yaml,amalg3-yaml
we receive the respective output in Listings 554 to 556.
LISTING 554: amalg1.tex using
Listing 551
1 two three
LISTING 555: amalg1.tex using
Listings 551 and 552
1 2 three
LISTING 556: amalg1.tex using
Listings 551 to 553
one two 3
We note that:
1. in Listing 554 the replacements from Listing 551 have been used;
2. in Listing 555 the replacements from Listings 551 and 552 have both been used, because
[git] main @ 78d452f 2024-07-18 V3.24.4
7.3 Examples of replacements 137
the default value of amalgamate is 1;
3. in Listing 556 only the replacements from Listing 553 have been used, because the value
of amalgamate has been set to 0.
[git] main @ 78d452f 2024-07-18 V3.24.4
SECTION 8
The –lines switch
latexindent.pl
N: 2021-09-16
can operate on a selection of lines of the file using the –lines or -n switch.
The basic syntax is –lines MIN-MAX, so for example
cmh:$ latexindent.pl --lines 3-7 myfile.tex
cmh:$ latexindent.pl -n 3-7 myfile.tex
will only operate upon lines 3 to 7 in myfile.tex. All of the other lines will not be operated upon
by latexindent.pl.
The options for the lines switch are:
line range, as in –lines 3-7
single line, as in –lines 5
multiple line ranges separated by commas, as in –lines 3-5,8-10
negated line ranges, as in –lines !3-5 which translates to –lines 1-2,6-N, where N is the
number of lines in your file.
We demonstrate this feature, and the available variations in what follows. We will use the file in
Listing 557.
LISTING 557: myfile.tex
1 Before the environments
2 \begin{one}
3 first block, first line
4 first block, second line
5 first block, third line
6 \begin{two}
7 second block, first line
8 second block, second line
9 second block, third line
10 second block, fourth line
11 \end{two}
12 \end{one}
example 155
We demonstrate the basic usage using the command
cmh:$ latexindent.pl --lines 3-7 myfile.tex -o=+-mod1
which instructs latexindent.pl to only operate on lines 3 to 7; the output is given in Listing 558.
[git] main @ 78d452f 2024-07-18 V3.24.4
139
LISTING 558: myfile-mod1.tex
1 Before the environments
2 \begin{one}
3 first block, first line
4 first block, second line
5 first block, third line
6 \begin{two}
7 second block, first line
8 second block, second line
9 second block, third line
10 second block, fourth line
11 \end{two}
12 \end{one}
The following two calls to latexindent.pl are equivalent
cmh:$ latexindent.pl --lines 3-7 myfile.tex -o=+-mod1
cmh:$ latexindent.pl --lines 7-3 myfile.tex -o=+-mod1
as latexindent.pl performs a check to put the lowest number first.
example 156
You can call the lines switch with only one number and in which case only that line will be
operated upon. For example
cmh:$ latexindent.pl --lines 5 myfile.tex -o=+-mod2
instructs latexindent.pl to only operate on line 5; the output is given in Listing 559.
LISTING 559: myfile-mod2.tex
1 Before the environments
2 \begin{one}
3 first block, first line
4 first block, second line
5 first block, third line
6 \begin{two}
7 second block, first line
8 second block, second line
9 second block, third line
10 second block, fourth line
11 \end{two}
12 \end{one}
The following two calls are equivalent:
cmh:$ latexindent.pl --lines 5 myfile.tex
cmh:$ latexindent.pl --lines 5-5 myfile.tex
example 157
If you specify a value outside of the line range of the file then latexindent.pl will ignore the
lines argument, detail as such in the log file, and proceed to operate on the entire file.
For example, in the following call
cmh:$ latexindent.pl --lines 11-13 myfile.tex
latexindent.pl will ignore the lines argument, and operate on the entire file because List-
[git] main @ 78d452f 2024-07-18 V3.24.4
140
ing 557 only has 12 lines.
Similarly, in the call
cmh:$ latexindent.pl --lines -1-3 myfile.tex
latexindent.pl will ignore the lines argument, and operate on the entire file because we as-
sume that negatively numbered lines in a file do not exist.
example 158
You can specify multiple line ranges as in the following
cmh:$ latexindent.pl --lines 3-5,8-10 myfile.tex -o=+-mod3
which instructs latexindent.pl to operate upon lines 3 to 5 and lines 8 to 10; the output is
given in Listing 560.
LISTING 560: myfile-mod3.tex
1 Before the environments
2 \begin{one}
3 first block, first line
4 first block, second line
5 first block, third line
6 \begin{two}
7 second block, first line
8 second block, second line
9 second block, third line
10 second block, fourth line
11 \end{two}
12 \end{one}
The following calls to latexindent.pl are all equivalent
cmh:$ latexindent.pl --lines 3-5,8-10 myfile.tex
cmh:$ latexindent.pl --lines 8-10,3-5 myfile.tex
cmh:$ latexindent.pl --lines 10-8,3-5 myfile.tex
cmh:$ latexindent.pl --lines 10-8,5-3 myfile.tex
as latexindent.pl performs a check to put the lowest line ranges first, and within each line
range, it puts the lowest number first.
example 159
There’s no limit to the number of line ranges that you can specify, they just need to be separated
by commas. For example
cmh:$ latexindent.pl --lines 1-2,4-5,9-10,12 myfile.tex -o=+-mod4
has four line ranges: lines 1 to 2, lines 4 to 5, lines 9 to 10 and line 12. The output is given in
Listing 561.
[git] main @ 78d452f 2024-07-18 V3.24.4
141
LISTING 561: myfile-mod4.tex
1 Before the environments
2 \begin{one}
3 first block, first line
4 first block, second line
5 first block, third line
6 \begin{two}
7 second block, first line
8 second block, second line
9 second block, third line
10 second block, fourth line
11 \end{two}
12 \end{one}
As previously, the ordering does not matter, and the following calls to latexindent.pl are all
equivalent
cmh:$ latexindent.pl --lines 1-2,4-5,9-10,12 myfile.tex
cmh:$ latexindent.pl --lines 2-1,4-5,9-10,12 myfile.tex
cmh:$ latexindent.pl --lines 4-5,1-2,9-10,12 myfile.tex
cmh:$ latexindent.pl --lines 12,4-5,1-2,9-10 myfile.tex
as latexindent.pl performs a check to put the lowest line ranges first, and within each line
range, it puts the lowest number first.
example 160
You can specify negated line ranges by using ! as in
cmh:$ latexindent.pl --lines !5-7 myfile.tex -o=+-mod5
which instructs latexindent.pl to operate upon all of the lines except lines 5 to 7.
In other words, latexindent.pl will operate on lines 1 to 4, and 8 to 12, so the following two
calls are equivalent:
cmh:$ latexindent.pl --lines !5-7 myfile.tex
cmh:$ latexindent.pl --lines 1-4,8-12 myfile.tex
The output is given in Listing 562.
LISTING 562: myfile-mod5.tex
1 Before the environments
2 \begin{one}
3 first block, first line
4 first block, second line
5 first block, third line
6 \begin{two}
7 second block, first line
8 second block, second line
9 second block, third line
10 second block, fourth line
11 \end{two}
12 \end{one}
example 161
You can specify multiple negated line ranges such as
[git] main @ 78d452f 2024-07-18 V3.24.4
142
cmh:$ latexindent.pl --lines !5-7,!9-10 myfile.tex -o=+-mod6
which is equivalent to:
cmh:$ latexindent.pl --lines 1-4,8,11-12 myfile.tex -o=+-mod6
The output is given in Listing 563.
LISTING 563: myfile-mod6.tex
1 Before the environments
2 \begin{one}
3 first block, first line
4 first block, second line
5 first block, third line
6 \begin{two}
7 second block, first line
8 second block, second line
9 second block, third line
10 second block, fourth line
11 \end{two}
12 \end{one}
example 162
If you specify a line range with anything other than an integer, then latexindent.pl will ignore
the lines argument, and operate on the entire file.
Sample calls that result in the lines argument being ignored include the following:
cmh:$ latexindent.pl --lines 1-x myfile.tex
cmh:$ latexindent.pl --lines !y-3 myfile.tex
example 163
We can, of course, use the lines switch in combination with other switches.
For example, let’s use with the file in Listing 564.
LISTING 564: myfile1.tex
1 Before the environments
2 \begin{one}
3 first block, first line
4 first block, second line
5 first block, third line
6 \begin{two} body \end{two}
7 \end{one}
We can demonstrate interaction with the -m switch (see Section 6 on page 79); in particular, if
we use Listing 456 on page 114, Listing 440 on page 112 and Listing 441 on page 112 and run
cmh:$ latexindent.pl --lines 6 myfile1.tex -o=+-mod1 -m -l env-mlb2,env-mlb7,env-mlb8 -o=+-mod1
then we receive the output in Listing 565.
[git] main @ 78d452f 2024-07-18 V3.24.4
143
LISTING 565: myfile1-mod1.tex
1 Before the environments
2 \begin{one}
3 first block, first line
4 first block, second line
5 first block, third line
6 \begin{two}
7 body
8 \end{two}
9 \end{one}
[git] main @ 78d452f 2024-07-18 V3.24.4
SECTION 9
Fine tuning
latexindent.pl operates by looking for the code blocks detailed in Table 2 on page 56.
N: 2019-07-13
The fine
tuning of the details of such code blocks is controlled by the fineTuning field, detailed in Listing 566.
This field is for those that would like to peek under the bonnet/hood and make some fine tuning to
latexindent.pl’s operating.
Warning!
Making changes to the fine tuning may have significant consequences for your inden-
tation scheme, proceed with caution!
LISTING 566: fineTuning
631 fineTuning:
632 environments:
633 name: [a-zA-Z@\*0-9_\\]+
634 ifElseFi:
635 name: (?!@?if[a-zA-Z@]*?\{)@?if[a-zA-Z@]*?
636 commands:
637 name: [+a-zA-Z@\*0-9_\:]+?
638 items:
639 canBeFollowedBy: (?:\[[^]]*?\])|(?:<[^>]*?>)
640 keyEqualsValuesBracesBrackets:
641 name: [a-zA-Z@\*0-9_\/.:\#-]+[a-zA-Z@\*0-9_\/.\h\{\}:\#-]*?
642 follow: (?:(?<!\\)\{)|,|(?:(?<!\\)\[)
643 namedGroupingBracesBrackets:
644 name: [0-9\.a-zA-Z@\*><]+?
645 follow: \h|\R|\{|\[|\$|\)|\(
646 UnNamedGroupingBracesBrackets:
647 follow: \{|\[|,|&|\)|\(|\$
648 arguments:
649 before: (?:#\d\h*;?,?\/?)+|\<.*?\>
650 between: _|\^|\*
651 trailingComments:
652 notPrecededBy: (?<!\\)
653 afterComment: .*?
654 modifyLineBreaks:
655 doubleBackSlash: \\\\(?:\h*\[\h*\d+\h*[a-zA-Z]+\h*\])?
656 comma: ’,’
657 betterFullStop: |-
658 (?x) # ignore spaces in the below
659 (?: #
660 \.\) # .)
661 (?!\h*[a-z]) # not *followed by* a-z
662 ) #
663 | # OR
664 (?: #
665 (?<! # not *preceded by*
666 (?: #
667 (?:[eE]\.[gG]) # e.g OR E.g OR e.G OR E.G
668 | #
[git] main @ 78d452f 2024-07-18 V3.24.4
145
669 (?:[iI]\.[eE]) # i.e OR I.e OR i.E OR I.E
670 | #
671 (?:etc) # etc
672 | #
673 (?:[wW]\.[rR]\.[tT]) # w.r.t OR W.r.t OR w.R.t OR w.r.T OR W.R.t OR W.r.T
OR w.R.T OR W.R.T
674 ) #
675 ) #
676 ) #
677 \. # .
678 (?! # not *followed by*
679 (?: #
680 [a-zA-Z0-9-~,] #
681 | #
682 \), # ),
683 | #
684 \)\. # ).
685 ) #
686 ) #
The fields given in Listing 566 are all regular expressions. This manual is not intended to be a tutorial
on regular expressions; you might like to read, for example, [35] for a detailed covering of the topic.
We make the following comments with reference to Listing 566:
1. the environments:name field details that the name of an environment can contain:
(a) a-z lower case letters
(b) A-Z upper case letters
(c) @ the @ ’letter’
(d) \* stars
(e) 0-9 numbers
(f) _ underscores
(g) \ backslashes
The + at the end means at least one of the above characters.
2. the ifElseFi:name field:
(a) @? means that it can possibly begin with @
(b) followed by if
(c) followed by 0 or more characters from a-z, A-Z and @
(d) the ? the end means non-greedy, which means ‘stop the match as soon as possible’
3. the keyEqualsValuesBracesBrackets contains some interesting syntax:
(a) | means ‘or’
(b) (?:(?<!\\)\{) the (?:...) uses a non-capturing group you don’t necessarily need to
worry about what this means, but just know that for the fineTuning feature you should
only ever use non-capturing groups, and not capturing groups, which are simply (...)
(c) (?<!\\)\{) means a { but it can not be immediately preceded by a \
4. in the arguments:before field
(a) \d\h* means a digit (i.e. a number), followed by 0 or more horizontal spaces
(b) ;?,? means possibly a semi-colon, and possibly a comma
(c) \<.*?\> is designed for ’beamer’-type commands; the .*? means anything in between
<...>
[git] main @ 78d452f 2024-07-18 V3.24.4
146
5. the modifyLineBreaks field refers to fine tuning settings detailed in Section 6 on page 79. In
particular:
(a) betterFullStop is in relation to the one sentence per line routine, detailed in Section 6.2
on page 95
(b) doubleBackSlash is in relation to the DBSStartsOnOwnLine and DBSFinishesWithLineBreak
polyswitches surrounding double backslashes, see Section 6.3.2 on page 118
(c) comma is in relation to the CommaStartsOnOwnLine and CommaFinishesWithLineBreak
polyswitches surrounding commas in optional and mandatory arguments; see Section 6.3.3
on page 123
It is not obvious from Listing 566, but each of the follow, before and between fields allow trailing
comments, line breaks, and horizontal spaces between each character.
Warning!
For the fineTuning feature you should only ever use non-capturing groups, such as
(?:...) and not capturing groups, which are (...)
example 164
As a demonstration, consider the file given in Listing 567, together with its default output using
the command
cmh:$ latexindent.pl finetuning1.tex
is given in Listing 568.
LISTING 567: finetuning1.tex
\mycommand{
\rule{G -> +H[-G]CL}
\rule{H -> -G[+H]CL}
\rule{g -> +h[-g]cL}
\rule{h -> -g[+h]cL}
}
LISTING 568: finetuning1.tex default
\mycommand{
\rule{G -> +H[-G]CL}
\rule{H -> -G[+H]CL}
\rule{g -> +h[-g]cL}
\rule{h -> -g[+h]cL}
}
It’s clear from Listing 568 that the indentation scheme has not worked as expected. We can
fine tune the indentation scheme by employing the settings given in Listing 570 and running the
command
cmh:$ latexindent.pl finetuning1.tex -l=fine-tuning1.yaml
and the associated (desired) output is given in Listing 569.
LISTING 569: finetuning1.tex using
Listing 570
\mycommand{
\rule{G -> +H[-G]CL}
\rule{H -> -G[+H]CL}
\rule{g -> +h[-g]cL}
\rule{h -> -g[+h]cL}
}
LISTING 570: finetuning1.yaml
fineTuning:
arguments:
between:
’_|\^|\*|\->|\-|\+|h|H|g|G’
example 165
Let’s have another demonstration; consider the file given in Listing 571, together with its default
output using the command
cmh:$ latexindent.pl finetuning2.tex
[git] main @ 78d452f 2024-07-18 V3.24.4
147
is given in Listing 572.
LISTING 571: finetuning2.tex
@misc{ wikilatex,
author = "{Wikipedia contributors}",
title = "LaTeX --- {Wikipedia}{,}",
note = "[Online; accessed 3-March-2020]"
}
LISTING 572: finetuning2.tex default
@misc{ wikilatex,
author = "{Wikipedia contributors}",
title = "LaTeX --- {Wikipedia}{,}",
note = "[Online; accessed 3-March-2020]"
}
It’s clear from Listing 572 that the indentation scheme has not worked as expected. We can
fine tune the indentation scheme by employing the settings given in Listing 574 and running the
command
cmh:$ latexindent.pl finetuning2.tex -l=fine-tuning2.yaml
and the associated (desired) output is given in Listing 573.
LISTING 573: finetuning2.tex using Listing 574
@misc{ wikilatex,
author = "{Wikipedia contributors}",
title = "LaTeX --- {Wikipedia}{,}",
note = "[Online; accessed 3-March-2020]"
}
LISTING 574: finetuning2.yaml
fineTuning:
NamedGroupingBracesBrackets:
follow: ’\h|\R|\{|\[|\$|\)|\(|"’
UnNamedGroupingBracesBrackets:
follow: ’\{|\[|,|&|\)|\(|\$|"’
arguments:
between: ’_|\^|\*|---’
In particular, note that the settings in Listing 574 specify that NamedGroupingBracesBrackets
and UnNamedGroupingBracesBrackets can follow " and that we allow --- between arguments.
example 166
You can tweak the fineTuning using the -y switch, but to be sure to use quotes appropriately.
For example, starting with the code in Listing 575 and running the following command
cmh:$ latexindent.pl -m
-y=’modifyLineBreaks:oneSentencePerLine:manipulateSentences:␣1,␣
modifyLineBreaks:oneSentencePerLine:sentencesBeginWith:a-z:␣1,␣
fineTuning:modifyLineBreaks:betterFullStop:␣
"(?:\.|;|:(?![a-z]))|(?:(?<!(?:(?:e\.g)|(?:i\.e)|(?:etc))))\.(?!(?:[a-z]|[A-Z]|\-|~|\,|[0-9]))"’
issue-243.tex -o=+-mod1
gives the output shown in Listing 576.
LISTING 575: finetuning3.tex
We go; you see: this sentence \cite{tex:stackexchange} finishes here.
LISTING 576: finetuning3.tex using -y switch
We go;
you see:
this sentence \cite{tex:stackexchange} finishes here.
example 167
We can tweak the fineTuning for how trailing comments are classified. For motivation, let’s
consider the code given in Listing 577
[git] main @ 78d452f 2024-07-18 V3.24.4
148
LISTING 577: finetuning4.tex
some before text
\href{Handbook%20for%30Spoken%40document.pdf}{my document}
some after text
We will compare the settings given in Listings 578 and 579.
-m
LISTING 578: href1.yaml
modifyLineBreaks:
textWrapOptions:
columns: -1
blocksEndBefore:
verbatim: 0
blocksFollow:
verbatim: 0
removeTrailingWhitespace:
beforeProcessing: 1
-m
LISTING 579: href2.yaml
fineTuning:
trailingComments:
notPrecededBy:
’(?:(?<!Handbook)(?<!for)(?<!Spoken))’
modifyLineBreaks:
textWrapOptions:
columns: -1
blocksEndBefore:
verbatim: 0
blocksFollow:
verbatim: 0
removeTrailingWhitespace:
beforeProcessing: 1
Upon running the following commands
cmh:$ latexindent.pl -m finetuning4.tex -o=+-mod1 -l=href1
cmh:$ latexindent.pl -m finetuning4.tex -o=+-mod2 -l=href2
we receive the respective output in Listings 580 and 581.
LISTING 580: finetuning4.tex using Listing 578
some before text \href{Handbooksome after text%20for%30Spoken%40document.pdf}{my document}
LISTING 581: finetuning4.tex using Listing 579
some before text \href{Handbook%20for%30Spoken%40document.pdf}{my document} some after text
We note that in:
Listing 580 the trailing comments are assumed to be everything following the first comment
symbol, which has meant that everything following it has been moved to the end of the
line; this is undesirable, clearly!
Listing 581 has fine-tuned the trailing comment matching, and says that % cannot be im-
mediately preceded by the words ‘Handbook’, ‘for’ or ‘Spoken’, which means that none of
the % symbols have been treated as trailing comments, and the output is desirable.
example 168
Another approach to this situation, which does not use fineTuning, is to use noIndentBlock
which we discussed in Listing 43 on page 30; using the settings in Listing 582 and running the
command
cmh:$ latexindent.pl -m finetuning4.tex -o=+-mod3 -l=href3
then we receive the same output given in Listing 581.
[git] main @ 78d452f 2024-07-18 V3.24.4
149
-m
LISTING 582: href3.yaml
modifyLineBreaks:
textWrapOptions:
columns: -1
blocksEndBefore:
verbatim: 0
blocksFollow:
verbatim: 0
noIndentBlock:
href:
begin: ’\\href\{[^}]*?\}\{’
body: ’[^}]*?’
end: ’\}’
With reference to the body field in Listing 582, we note that the body field can be interpreted
as: the fewest number of zero or more characters that are not right braces. This is an example
of character class.
example 169
We can use the fineTuning field to assist in the formatting of bibliography files.
Starting with the file in Listing 583 and running the command
cmh:$ latexindent.pl bib1.tex -o=+-mod1
gives the output in Listing 584.
LISTING 583: bib1.bib
@online{paulo,
title="arararule,indent.yaml",
author="PauloCereda",
date={2013-05-23},
urldate={2021-03-19},
keywords={contributor},}
LISTING 584: bib1-mod1.bib
@online{paulo,
title="arararule,indent.yaml",
author="PauloCereda",
date={2013-05-23},
urldate={2021-03-19},
keywords={contributor},}
Let’s assume that we would like to format the output so as to align the = symbols. Using the
settings in Listing 586 and running the command
cmh:$ latexindent.pl bib1.bib -l bibsettings1.yaml -o=+-mod2
gives the output in Listing 585.
LISTING 585: bib1.bib using Listing 586
@online{paulo,
title = "arararule,indent.yaml",
author = "PauloCereda",
date = {2013-05-23},
urldate = {2021-03-19},
keywords = {contributor},}
LISTING 586: bibsettings1.yaml
lookForAlignDelims:
online:
delimiterRegEx: ’(=)’
fineTuning:
keyEqualsValuesBracesBrackets:
follow:
’(?:(?<!\\)\{)|(?:(?<!\\)\[)’
UnNamedGroupingBracesBrackets:
follow: ’\{|\[|,|&|\)|\(|\$|=’
Some notes about Listing 586:
[git] main @ 78d452f 2024-07-18 V3.24.4
150
we have populated the lookForAlignDelims field with the online command, and have
used the delimiterRegEx, discussed in Section 5.5.4 on page 43;
we have tweaked the keyEqualsValuesBracesBrackets code block so that it will not be
found following a comma; this means that, in contrast to the default behaviour, the lines
such as date={2013-05-23}, will not be treated as key-equals-value braces;
the adjustment to keyEqualsValuesBracesBrackets necessitates the associated change
to the UnNamedGroupingBracesBrackets field so that they will be searched for following
= symbols.
example 170
We can build upon Listing 586 for slightly more complicated bibliography files.
Starting with the file in Listing 587 and running the command
cmh:$ latexindent.pl bib2.bib -l bibsettings1.yaml -o=+-mod1
gives the output in Listing 588.
LISTING 587: bib2.bib
@online{cmh:videodemo,
title="Videodemonstrationofpl.latexindentonyoutube",
url="https://www.youtube.com/watch?v=wo38aaH2F4E&spfreload=10",
urldate={2017-02-21},
}
LISTING 588: bib2-mod1.bib
@online{cmh:videodemo,
title = "Videodemonstrationofpl.latexindentonyoutube",
url = "https://www.youtube.com/watch?v = wo38aaH2F4E&spfreload = 10",
urldate = {2017-02-21},
}
The output in Listing 588 is not ideal, as the = symbol within the url field has been incorrectly
used as an alignment delimiter.
We address this by tweaking the delimiterRegEx field in Listing 589.
LISTING 589: bibsettings2.yaml
lookForAlignDelims:
online:
delimiterRegEx: ’(?<!v)(?<!spfreload)(=)’
Upon running the command
cmh:$ latexindent.pl bib2.bib -l bibsettings1.yaml,bibsettings2.yaml -o=+-mod2
we receive the desired output in Listing 590.
LISTING 590: bib2-mod2.bib
@online{cmh:videodemo,
title = "Videodemonstrationofpl.latexindentonyoutube",
url = "https://www.youtube.com/watch?v=wo38aaH2F4E&spfreload=10",
urldate = {2017-02-21},
}
With reference to Listing 589 we note that the delimiterRegEx has been adjusted so that =
symbols are used as the delimiter, but only when they are not preceded by either v or spfreload.
[git] main @ 78d452f 2024-07-18 V3.24.4
151
example 171
We can use the fineTuning settings to tweak how latexindent.pl finds trailing comments.
N: 2023-06-01
We begin with the file in Listing 591
LISTING 591: finetuning5.tex
\chapter{chapter text} % 123
chapter text
\section{section text} % 456
section text
% end
% end
Using the settings in Listing 593 and running the command
cmh:$ latexindent.pl finetuning5.tex -l=fine-tuning3.yaml
gives the output in Listing 592.
LISTING 592: finetuning5-mod1.tex
\chapter{chapter text} % 123
chapter text
\section{section text} % 456
section text
% end
% end
LISTING 593: finetuning3.yaml
fineTuning:
trailingComments:
notPrecededBy: (?<!\\)
afterComment: (?!(?:\hend)).*?
specialBeginEnd:
customSection:
begin: \\(?:section|chapter)
end: \%\h+end
specialBeforeCommand: 1
The settings in Listing 593 detail that trailing comments can not be followed by a single space,
and then the text ‘end’. This means that the specialBeginEnd routine will be able to find the
pattern % end as the end part. The trailing comments 123 and 456 are still treated as trailing
comments.
example 172
We can use the fineTuning settings to tweak how latexindent.pl finds environments.
We begin with the file in Listing 594.
N: 2023-10-13
LISTING 594: finetuning6.tex
\begin{myenv}\label{mylabel}The body of my environment...\end{myenv}
Using the settings in Listing 596 and running the command
cmh:$ latexindent.pl finetuning6.tex -m -l=fine-tuning4.yaml
gives the output in Listing 595.
LISTING 595: finetuning6-mod1.tex
\begin{myenv}\label{mylabel}
The body of my environment...
\end{myenv}
-m
LISTING 596: fine-tuning4.yaml
modifyLineBreaks:
environments:
BodyStartsOnOwnLine: 1
EndStartsOnOwnLine: 1
fineTuning:
environments:
begin: \\begin\{([a-zA-Z@\*0-9_\\]+)\}\s*\\label\{[^}]+?\}
end: \\end\{\2\}
[git] main @ 78d452f 2024-07-18 V3.24.4
152
By using the settings in Listing 596 it means that the default poly-switch location of BodyStartsOnOwnLine
for environments (denoted in Section 6.3.3) has been overwritten so that it is after the label
command.
Referencing Listing 596, unless both begin and end are specified, then the default value of name
will be used.
[git] main @ 78d452f 2024-07-18 V3.24.4
SECTION 10
Conclusions and known limitations
There are a number of known limitations of the script, and almost certainly quite a few that are
unknown! The known issues include:
multicolumn alignment when working with code blocks in which multicolumn commands overlap,
the algorithm can fail; see Listing 71 on page 36.
textWrap after when operating with indentRules (see Section 5.8 on page 55) may not always
cooperate with one another; if you have a specific example that does not work, please report
it to [36].
efficiency particularly when the -m switch is active, as this adds many checks and processes. The
current implementation relies upon finding and storing every code block (see the discussion
on page 127); I hope that, in a future version, only nested code blocks will need to be stored
in the ‘packing’ phase, and that this will improve the efficiency of the script.
You can run latexindent on any file;
U: 2019-07-13
if you don’t specify an extension, then the extensions that
you specify in fileExtensionPreference (see Listing 35 on page 27) will be consulted. If you find a
case in which the script struggles, please feel free to report it at [36], and in the meantime, consider
using a noIndentBlock (see page 30).
I hope that this script is useful to some; if you find an example where the script does not behave as
you think it should, the best way to contact me is to report an issue on [36]; otherwise, feel free to
find me on the http://tex.stackexchange.com/users/6621/cmhughes.
[git] main @ 78d452f 2024-07-18 V3.24.4
SECTION 11
References
11.1 perl-related links
[32] CPAN: Comprehensive Perl Archive Network. URL: http://www.cpan.org/ (visited on 01/23/2017).
[33] Data Dumper demonstration. URL: https://stackoverflow.com/questions/7466825/
how-do-you-sort-the-output-of-datadumper (visited on 06/18/2021).
[34] Data::Dumper module. URL: https : / / perldoc . perl . org / Data :: Dumper (visited on
06/18/2021).
[35] Jeffrey E. F. Friedl. Mastering Regular Expressions. ISBN: 0596002890.
[41] Log4perl Perl module. URL: http://search.cpan.org/~mschilli/Log-Log4perl-1.49/
lib/Log/Log4perl.pm (visited on 09/24/2017).
[42] Perlbrew. URL: http://perlbrew.pl/ (visited on 01/23/2017).
[43] perldoc Encode::Supported. URL: https://perldoc.perl.org/Encode::Supported (visited
on 05/06/2021).
[46] Strawberry Perl. URL: http://strawberryperl.com/ (visited on 01/23/2017).
[47] Text::Tabs Perl module. URL: http://search.cpan.org/~muir/Text- Tabs+Wrap- 2013.
0523/lib.old/Text/Tabs.pm (visited on 07/06/2017).
[48] Text::Wrap Perl module. URL: http://perldoc.perl.org/Text/Wrap.html (visited on
05/01/2017).
11.2 conda-related links
[30] anacoda. URL: https://www.anaconda.com/products/individual (visited on 12/22/2021).
[31] conda forge. URL: https://github.com/conda-forge/miniforge (visited on 12/22/2021).
[38] How to install Anaconda on Ubuntu? URL: https://askubuntu.com/questions/505919/
how-to-install-anaconda-on-ubuntu (visited on 01/21/2022).
[45] Solving environment: failed with initial frozen solve. Retrying with flexible solve. URL: https:
/ / github . com / conda / conda / issues / 9367 # issuecomment - 558863143 (visited on
01/21/2022).
11.3 VScode-related links
[37] How to create your own auto-completion for JSON and YAML files on VS Code with the help
of JSON Schema. URL: https : / / dev . to / brpaz / how - to - create - your - own - auto -
completion- for- json- and- yaml- files- on- vs- code- with- the- help - of- json-
schema-k1i (visited on 01/01/2022).
[50] VSCode YAML extension. URL: https://marketplace.visualstudio.com/items?itemName=
redhat.vscode-yaml (visited on 01/01/2022).
11.4 Other links
[29] A Perl script for indenting tex files. URL: http://tex.blogoverflow.com/2012/08/a-perl-
script-for-indenting-tex-files/ (visited on 01/23/2017).
[36] Home of latexindent.pl. URL: https://github.com/cmhughes/latexindent.pl (visited on
01/23/2017).
[39] How to use latexindent on Windows? URL: https://tex.stackexchange.com/questions/
577250/how-to-use-latexindent-on-windows (visited on 01/08/2022).
[40] latexindent.pl ghcr (GitHub Container Repository) location. URL: https : / / github . com /
cmhughes?tab=packages (visited on 06/12/2022).
[44] pre-commit: A framework for managing and maintaining multi-language pre-commit hooks. URL:
https://pre-commit.com/ (visited on 01/08/2022).
[git] main @ 78d452f 2024-07-18 V3.24.4
11.5 Contributors (in chronological order) 155
[49] Video demonstration of latexindent.pl on youtube. URL: https://www.youtube.com/watch?
v=wo38aaH2F4E&spfreload=10 (visited on 02/21/2017).
[51] Windows line breaks on Linux prevent removal of white space from end of line. URL: https:
//github.com/cmhughes/latexindent.pl/issues/256 (visited on 06/18/2021).
11.5 Contributors (in chronological order)
[1] Paulo Cereda. arara rule, indent.yaml. May 23, 2013. URL: https://github.com/islandoftex/
arara/blob/master/rules/arara-rule-indent.yaml (visited on 03/19/2021).
[2] Harish Kumar. Early version testing. Nov. 10, 2013. URL: https://github.com/harishkumarholla
(visited on 06/30/2017).
[3] Michel Voßkuhle. Remove trailing white space. Nov. 10, 2013. URL: https://github.com/
cmhughes/latexindent.pl/pull/12 (visited on 01/23/2017).
[4] Jacobo Diaz. Changed shebang to make the script more portable. July 23, 2014. URL: https:
//github.com/cmhughes/latexindent.pl/pull/17 (visited on 01/23/2017).
[5] Jacobo Diaz. Hiddenconfig. July 21, 2014. URL: https://github.com/cmhughes/latexindent.
pl/pull/18 (visited on 01/23/2017).
[6] Jason Juang. add in PATH installation. Nov. 24, 2015. URL: https : / / github . com /
cmhughes/latexindent.pl/pull/38 (visited on 01/23/2017).
[7] mlep. One sentence per line. Aug. 16, 2017. URL: https : / / github . com / cmhughes /
latexindent.pl/issues/81 (visited on 01/08/2018).
[8] John Owens. Paragraph line break routine removal. May 27, 2017. URL: https://github.
com/cmhughes/latexindent.pl/issues/33 (visited on 05/27/2017).
[9] Cheng Xu (xu cheng). always output log/help text to STDERR. July 13, 2018. URL: https:
//github.com/cmhughes/latexindent.pl/pull/121 (visited on 08/05/2018).
[10] Tom Zöhner (zoehneto). Improving text wrap. Feb. 4, 2018. URL: https://github.com/
cmhughes/latexindent.pl/issues/103 (visited on 08/04/2018).
[11] Sam Abey. Print usage tip to STDERR only if STDIN is TTY. Sept. 17, 2019. URL: https:
//github.com/cmhughes/latexindent.pl/pull/174 (visited on 03/19/2021).
[12] Randolf J. Alpine-linux instructions. Aug. 10, 2020. URL: https://github.com/cmhughes/
latexindent.pl/pull/214 (visited on 08/10/2020).
[13] jeanlego. Search localSettings in CWD as well. Sept. 15, 2020. URL: https://github.com/
cmhughes/latexindent.pl/pull/221 (visited on 03/19/2021).
[14] newptcai. Update appendices.tex. Feb. 16, 2021. URL: https://github.com/cmhughes/
latexindent.pl/pull/221 (visited on 03/19/2021).
[15] qiancy98. Locale encoding of file system. May 6, 2021. URL: https : / / github . com /
cmhughes/latexindent.pl/pull/273 (visited on 05/06/2021).
[16] Alexander Regueiro. Update help screen. Mar. 18, 2021. URL: https : / / github . com /
cmhughes/latexindent.pl/pull/261 (visited on 03/19/2021).
[17] XuehaiPan. -y switch upgrade. Nov. 12, 2021. URL: https://github.com/cmhughes/
latexindent.pl/pull/297 (visited on 11/12/2021).
[18] XuehaiPan. Verbatim block upgrade. Oct. 3, 2021. URL: https://github.com/cmhughes/
latexindent.pl/pull/290 (visited on 10/03/2021).
[19] eggplants. Add Dockerfile and its updater/releaser. June 12, 2022. URL: https://github.
com/cmhughes/latexindent.pl/pull/370 (visited on 06/12/2022).
[20] Tom de Geus. Adding Perl installation + pre-commit hook. Jan. 21, 2022. URL: https :
//github.com/cmhughes/latexindent.pl/pull/322 (visited on 01/21/2022).
[21] Jan Holthuis. Fix pre-commit usage. Mar. 31, 2022. URL: https://github.com/cmhughes/
latexindent.pl/pull/354 (visited on 04/02/2022).
[22] Nehctargl. Added support for the XDG specification. Dec. 23, 2022. URL: https://github.
com/cmhughes/latexindent.pl/pull/397 (visited on 12/23/2022).
[23] Junfeng Qiao. Add w.r.t to betterFullStop. May 25, 2023. URL: https:// github.com/
cmhughes/latexindent.pl/pull/447 (visited on 05/25/2023).
[24] Henrik Sloot. feat: add devcontainer configuration. May 20, 2023. URL: https://github.
com/cmhughes/latexindent.pl/pull/443 (visited on 05/20/2023).
[25] Henrik Sloot. fix: find local settings when working file dir is not working dir. Feb. 15, 2023.
URL: https://github.com/cmhughes/latexindent.pl/pull/422 (visited on 02/15/2023).
[git] main @ 78d452f 2024-07-18 V3.24.4
11.5 Contributors (in chronological order) 156
[26] Jesse Stricker. Create cruft directory if it does not exist. July 12, 2023. URL: https : / /
github.com/cmhughes/latexindent.pl/pull/453 (visited on 07/12/2023).
[27] valtterikantanen. fix: decode the name of the backup file. Apr. 7, 2023. URL: https : / /
github.com/cmhughes/latexindent.pl/pull/439 (visited on 04/07/2023).
[28] fengzyf. Encoding work. June 15, 2024. URL: https://github.com/cmhughes/latexindent.
pl/pull/548 (visited on 06/15/2024).
[git] main @ 78d452f 2024-07-18 V3.24.4
SECTION A
Required Perl modules
If you intend to use latexindent.pl and not one of the supplied standalone executable files (latexindent.exe
is available for Windows users without Perl, see Section 3.1.2), then you will need a few standard
Perl modules.
If you can run the minimum code in Listing 597 as in
cmh:$ perl helloworld.pl
then you will be able to run latexindent.pl, otherwise you may need to install the missing mod-
ules; see appendices A.1 and A.2.
LISTING 597: helloworld.pl
#!/usr/bin/perl
use strict; # |
use warnings; # |
use Encode; # |
use Getopt::Long; # |
use Data::Dumper; # these modules are
use List::Util qw(max); # generally part
use PerlIO::encoding; # of a default perl distribution
use open ’:std’, ’:encoding(UTF-8)’;# |
use Text::Wrap; # |
use Text::Tabs; # |
use FindBin; # |
use File::Copy; # |
use File::Basename; # |
use File::Path; # |
use File::HomeDir; # <--- typically requires install via cpanm
use YAML::Tiny; # <--- typically requires install via cpanm
print "hello␣world";
exit;
A.1 Module installer script
N: 2018-01-13
latexindent.pl ships with a helper script that will install any missing perl modules on your sys-
tem; if you run
cmh:$ perl latexindent-module-installer.pl
or
C:\Users\cmh> perl la t ex ind ent -m o du l e- ins ta l le r . pl
then, once you have answered Y, the appropriate modules will be installed onto your distribution.
[git] main @ 78d452f 2024-07-18 V3.24.4
A.2 Manually installing modules 158
A.2 Manually installing modules
Manually installing the modules given in Listing 597 will vary depending on your operating system
and Perl distribution.
A.2.1 Linux
A.2.1.1 perlbrew
Linux users may be interested in exploring Perlbrew [ 42]; an example installation would be:
cmh:$ sudo apt-get install perlbrew
cmh:$ perlbrew init
cmh:$ perlbrew install perl-5.40.0
cmh:$ perlbrew switch perl-5.40.0
cmh:$ sudo apt-get install curl
cmh:$ curl -L http://cpanmin.us | perl - App::cpanminus
cmh:$ cpanm YAML::Tiny
cmh:$ cpanm File::HomeDir
A.2.1.2 Ubuntu/Debian
For other distributions, the Ubuntu/Debian approach may work as follows
cmh:$ sudo apt install perl
cmh:$ sudo cpan -i App::cpanminus
cmh:$ sudo cpanm YAML::Tiny
cmh:$ sudo cpanm File::HomeDir
or else by running, for example,
cmh:$ sudo perl -MCPAN -e’install␣"File::HomeDir"’
A.2.1.3 Ubuntu: using the texlive from apt-get
Ubuntu users that install texlive using apt-get as in the following
cmh:$ sudo apt install texlive
cmh:$ sudo apt install texlive-latex-recommended
may need the following additional command to work with latexindent.pl
cmh:$ sudo apt install texlive-extra-utils
A.2.1.4 Ubuntu: users without perl
latexindent-linux is a standalone executable
N: 2022-10-30
for Ubuntu Linux (and therefore does not require a
Perl distribution) and caches copies of the Perl modules onto your system. It is available from [36].
A.2.1.5 Arch-based distributions
latexindent is included in Arch-packaged TeX Live, and can be installed by:
cmh:$ sudo pacman -S texlive-binextra perl-yaml-tiny perl-file-homedir
To enable optional –GCString switch, install perl-unicode-linebreak:
cmh:$ sudo pacman -S perl-unicode-linebreak
[git] main @ 78d452f 2024-07-18 V3.24.4
A.2 Manually installing modules 159
A.2.1.6 Alpine
If you are using Alpine, some Perl modules are not build-compatible with Alpine, but replacements
are available through apk. For example, you might use the commands given in Listing 598; thanks
to [12] for providing these details.
LISTING 598: alpine-install.sh
# Installing perl
apk --no-cache add miniperl perl-utils
# Installing incompatible latexindent perl dependencies via apk
apk --no-cache add \
perl-log-dispatch \
perl-namespace-autoclean \
perl-specio \
perl-unicode-linebreak
# Installing remaining latexindent perl dependencies via cpan
apk --no-cache add curl wget make
ls /usr/share/texmf-dist/scripts/latexindent
cd /usr/local/bin && \
curl -L https://cpanmin.us/ -o cpanm && \
chmod +x cpanm
cpanm -n App::cpanminus
cpanm -n File::HomeDir
cpanm -n Params::ValidationCompiler
cpanm -n YAML::Tiny
Users of NixOS might like to see https://github.com/cmhughes/latexindent.pl/issues/222 for tips.
A.2.2 Mac
Users of the Macintosh operating system might like to explore the following commands, for example:
cmh:$ brew install perl
cmh:$ brew install cpanm
cmh:$
cmh:$ cpanm YAML::Tiny
cmh:$ cpanm File::HomeDir
Alternatively,
cmh:$ brew install latexindent
latexindent-macos is a standalone executable
N: 2022-10-30
for macOS (and therefore does not require a Perl
distribution) and caches copies of the Perl modules onto your system. It is available from [36].
A.2.3 Windows
Strawberry Perl users on Windows might use CPAN client. All of the modules are readily available
on CPAN [32]. indent.log will contain details of the location of the Perl modules on your system.
latexindent.exe is a standalone executable for Windows (and therefore does not require a Perl
distribution) and caches copies of the Perl modules onto your system; if you wish to see where they
are cached, use the trace option, e.g
C:\Users\cmh> la te xi ndent . exe -t myfile . tex
[git] main @ 78d452f 2024-07-18 V3.24.4
A.3 The GCString switch 160
A.3 The GCString switch
If you find that the lookForAlignDelims (as in Section 5.5) does not work correctly for your lan-
guage, then you may wish to use the Unicode::GCString module
N: 2022-03-25
.
This can be loaded by calling latexindent.pl with the GCString switch as in
cmh:$ latexindent.pl --GCString myfile.tex
In this case, you will need to have the Unicode::GCString installed in your perl distribution by
using, for example,
cmh:$ cpanm Unicode::GCString
Note: this switch does nothing for latexindent.exe which loads the module by default. Users of
latexindent.exe should not see any difference in behaviour whether they use this switch or not,
as latexindent.exe loads the Unicode::GCString module.
[git] main @ 78d452f 2024-07-18 V3.24.4
SECTION B
Updating the path variable
latexindent.pl has a few scripts (available at [36]) that can update the path variables. Thank
you to [6] for this feature. If you’re on a Linux or Mac machine, then you’ll want CMakeLists.txt
from [36].
B.1 Add to path for Linux
To add latexindent.pl to the path for Linux, follow these steps:
1. download latexindent.pl and its associated modules, defaultSettings.yaml, to your cho-
sen directory from [36] ;
2. within your directory, create a directory called path-helper-files and download CMakeLists.txt
and cmake_uninstall.cmake.in from [36]/path-helper-files to this directory;
3. run
cmh:$ ls /usr/local/bin
to see what is currently in there;
4. run the following commands
cmh:$ sudo apt-get update
cmh:$ sudo apt-get install --no-install-recommends cmake make # or any
other generator
cmh:$ mkdir build && cd build
cmh:$ cmake ../path-helper-files
cmh:$ sudo make install
5. run
cmh:$ ls /usr/local/bin
again to check that latexindent.pl, its modules and defaultSettings.yaml have been
added.
To remove the files, run
cmh:$ sudo make uninstall
B.2 Add to path for Windows
To add latexindent.exe to the path for Windows, follow these steps:
1. download latexindent.exe, defaultSettings.yaml, add-to-path.bat from [36] to your
chosen directory;
2. open a command prompt and run the following command to see what is currently in your
%path% variable;
[git] main @ 78d452f 2024-07-18 V3.24.4
B.2 Add to path for Windows 162
C:\Users\cmh> echo %path%
3. right click on add-to-path.bat and Run as administrator;
4. log out, and log back in;
5. open a command prompt and run
C:\Users\cmh> echo %path%
to check that the appropriate directory has been added to your %path%.
To remove the directory from your %path%, run remove-from-path.bat as administrator.
[git] main @ 78d452f 2024-07-18 V3.24.4
SECTION C
Batches of files
You can
N: 2022-03-25
instruct latexindent.pl to operate on multiple files. For example, the following calls are
all valid
cmh:$ latexindent.pl myfile1.tex
cmh:$ latexindent.pl myfile1.tex myfile2.tex
cmh:$ latexindent.pl myfile*.tex
We note the following features of the script in relation to the switches detailed in Section 3.
C.1 location of indent.log
If the -c switch is not active, then indent.log goes to the directory of the final file called.
If the -c switch is active, then indent.log goes to the specified directory.
C.2 interaction with -w switch
If the -w switch is active, as in
cmh:$ latexindent.pl -w myfile*.tex
then files will be overwritten individually. Back-up files can be re-directed via the -c switch.
C.3 interaction with -o switch
If latexindent.pl is called using the -o switch as in
cmh:$ latexindent.pl myfile*.tex -o=my-output-file.tex
and there are multiple files to operate upon, then the -o switch is ignored because there is only one
output file specified.
More generally, if the -o switch does not have a + symbol at the beginning, then the -o switch will
be ignored, and is turned it off.
For example
cmh:$ latexindent.pl myfile*.tex -o=+myfile
will work fine because each .tex file will output to <basename>myfile.tex
Similarly,
cmh:$ latexindent.pl myfile*.tex -o=++
will work because the ‘existence check/incrementation’ routine will be applied.
C.4 interaction with lines switch
This behaves as expected by attempting to operate on the line numbers specified for each file. See
the examples in Section 8.
[git] main @ 78d452f 2024-07-18 V3.24.4
C.5 interaction with check switches 164
C.5 interaction with check switches
The exit codes for latexindent.pl are given in Table 1 on page 22.
When operating on multiple files with the check switch active, as in
cmh:$ latexindent.pl myfile*.tex --check
then
exit code 0 means that the text from none of the files has been changed;
exit code 1 means that the text from at least one of the files been file changed.
The interaction with checkv switch is as in the check switch, but with verbose output.
C.6 when a file does not exist
What happens if one of the files can not be operated upon?
if at least one of the files does not exist and latexindent.pl has been called to act upon
multiple files, then the exit code is 3; note that latexindent.pl will try to operate on each
file that it is called upon, and will not exit with a fatal message in this case;
if at least one of the files can not be read and latexindent.pl has been called to act upon
multiple files, then the exit code is 4; note that latexindent.pl will try to operate on each
file that it is called upon, and will not exit with a fatal message in this case;
if latexindent.pl has been told to operate on multiple files, and some do not exist and some
cannot be read, then the exit code will be either 3 or 4, depending upon which it scenario it
encountered most recently.
[git] main @ 78d452f 2024-07-18 V3.24.4
SECTION D
latexindent-yaml-schema.json
latexindent.pl
N: 2022-01-02
ships with latexindent-yaml-schema.json which might help you when con-
structing your YAML files.
D.1 VSCode demonstration
To use latexindent-yaml-schema.json with VSCode, you can use the following steps:
1. download latexindent-yaml-schema.json from the documentation folder of [36], save it
in whichever directory you would like, noting it for reference;
2. following the instructions from [37], for example, you should install the VSCode YAML exten-
sion [50];
3. set up your settings.json file using the directory you saved the file by adapting Listing 599;
on my Ubuntu laptop this file lives at /home/cmhughes/.config/Code/User/settings.json.
LISTING 599: settings.json
{
"yaml.schemas": {
"/home/cmhughes/projects/latexindent/documentation/latexindent-yaml-schema.json":
"/home/cmhughes/projects/latexindent/defaultSettings.yaml"
},
"redhat.telemetry.enabled": true
}
Alternatively, if you would prefer not to download the json file, you might be able to use an adapted
version of Listing 600.
LISTING 600: settings-alt.json
{
"yaml.schemas": {
"https://raw.githubusercontent.com/cmhughes/latexindent.pl/main/documentation/latexindent-yaml-schema.json":
"/home/cmhughes/projects/latexindent/defaultSettings.yaml"
}
}
Finally, if your TeX distribution is up to date, then latexindent-yaml-schema.json should be in
the documentation folder of your installation, so an adapted version of Listing 601 may work.
LISTING 601: settings-alt1.json
{
"yaml.schemas": {
"/usr/local/texlive/2021/texmf-dist/doc/support/latexindent/latexindent-yaml-schema.json":
"/home/cmhughes/projects/latexindent/defaultSettings.yaml"
}
}
If you have details of how to implement this schema in other editors, please feel encouraged to
contribute to this documentation.
[git] main @ 78d452f 2024-07-18 V3.24.4
SECTION E
Using conda
If you use conda you’ll only need
cmh:$ conda install latexindent.pl -c conda-forge
This will install the executable and all its dependencies (including perl) in the activate environment.
You don’t even have to worry about defaultSettings.yaml as it included too, you can thus skip
appendices A and B.
You can get a conda installation for example from [31] or from [30].
E.1 Sample conda installation on Ubuntu
On Ubuntu I followed the 64-bit installation instructions at [38] and then I ran the following com-
mands:
cmh:$ conda create -n latexindent.pl
cmh:$ conda activate latexindent.pl
cmh:$ conda install latexindent.pl -c conda-forge
cmh:$ conda info --envs
cmh:$ conda list
cmh:$ conda run latexindent.pl -vv
I found the details given at [45] to be helpful.
[git] main @ 78d452f 2024-07-18 V3.24.4
SECTION F
Using docker
If you use docker you’ll only need
N: 2022-06-12
cmh:$ docker pull ghcr.io/cmhughes/latexindent.pl
This will download the image packed latexindent’s executable and its all dependencies. Thank you
to [ 19] for contributing this feature; see also [40]. For reference, ghcr stands for GitHub Container
Repository.
F.1 Sample docker installation on Ubuntu
To pull the image and show latexindent’s help on Ubuntu:
LISTING 602: docker-install.sh
# setup docker if not already installed
if ! command -v docker &> /dev/null; then
sudo apt install docker.io -y
sudo groupadd docker
sudo gpasswd -a "$USER" docker
sudo systemctl restart docker
newgrp docker
fi
# download image and execute
docker pull ghcr.io/cmhughes/latexindent.pl
docker run ghcr.io/cmhughes/latexindent.pl -h
Once I have run the above, on subsequent logins I run
LISTING 603: docker-install.sh
newgrp docker
docker run ghcr.io/cmhughes/latexindent.pl -h
F.2 How to format on Docker
When you use latexindent with the docker image, you have to mount target tex file like this:
cmh:$ docker run -v /path/to/local/myfile.tex:/myfile.tex
ghcr.io/cmhughes/latexindent.pl -s -w myfile.tex
[git] main @ 78d452f 2024-07-18 V3.24.4
SECTION G
pre-commit
Users of .git may be interested
N: 2022-01-21
in exploring the pre-commit tool [44], which is supported by
latexindent.pl. Thank you to [20] for contributing this feature, and to [21] for their contribution
to it.
To use the pre-commit tool, you will need to install pre-commit; sample instructions for Ubuntu
are given in appendix G.1. Once installed, there are two ways to use pre-commit: using CPAN or
using conda, detailed in appendix G.3 and appendix G.4 respectively.
G.1 Sample pre-commit installation on Ubuntu
On Ubuntu I ran the following command:
cmh:$ python3 -m pip install pre-commit
I then updated my path via .bashrc so that it includes the line in Listing 604.
LISTING 604: .bashrc update
...
export PATH=$PATH:/home/cmhughes/.local/bin
G.2 pre-commit defaults
The default values that are employed by pre-commit are shown in Listing 605.
LISTING 605: .pre-commit-hooks.yaml (default)
- id: latexindent
name: latexindent.pl
description: Run latexindent.pl (get dependencies using CPAN)
minimum_pre_commit_version: 2.1.0
entry: latexindent.pl
args: ["--overwriteIfDifferent", "--silent", "--local"]
language: perl
types: [tex]
- id: latexindent-conda
name: latexindent.pl
description: Run latexindent.pl (get dependencies using Conda)
minimum_pre_commit_version: 2.1.0
entry: latexindent.pl
args: ["--overwriteIfDifferent", "--silent", "--local"]
language: conda
types: [tex]
- id: latexindent-docker
name: latexindent.pl
description: Run latexindent.pl (get dependencies using Docker)
minimum_pre_commit_version: 2.1.0
entry: ghcr.io/cmhughes/latexindent.pl
language: docker_image
types: [tex]
args: ["--overwriteIfDifferent", "--silent", "--local"]
[git] main @ 78d452f 2024-07-18 V3.24.4
G.3 pre-commit using CPAN 169
In particular, the decision has deliberately been made (in collaboration with [21]) to have the default
to employ the following switches: overwriteIfDifferent, silent, local; this is detailed in the
lines that specify args in Listing 605.
Warning!
Users of pre-commit will, by default, have the overwriteIfDifferent switch em-
ployed. It is assumed that such users have version control in place, and are intending
to overwrite their files.
G.3 pre-commit using CPAN
To use latexindent.pl with pre-commit, create the file .pre-commit-config.yaml given in List-
ing 606 in your git-repository.
LISTING 606: .pre-commit-config.yaml (cpan)
- repo: https://github.com/cmhughes/latexindent.pl
rev: V3.24.4
hooks:
- id: latexindent
args: [-s]
Once created, you should then be able to run the following command:
cmh:$ pre-commit run --all-files
A few notes about Listing 606:
the settings given in Listing 606 instruct pre-commit to use CPAN to get dependencies;
this requires pre-commit and perl to be installed on your system;
the args lists selected command-line options; the settings in Listing 606 are equivalent to
calling
cmh:$ latexindent.pl -s myfile.tex
for each .tex file in your repository;
to instruct latexindent.pl to overwrite the files in your repository, then you can update
Listing 606 so that args: [-s, -w].
Naturally you can add options, or omit -s and -w, according to your preference.
G.4 pre-commit using conda
You can also rely on conda (detailed in appendix E) instead of CPAN for all dependencies, including
latexindent.pl itself.
LISTING 607: .pre-commit-config.yaml (conda)
- repo: https://github.com/cmhughes/latexindent.pl
rev: V3.24.4
hooks:
- id: latexindent-conda
args: [-s]
Once created, you should then be able to run the following command:
cmh:$ pre-commit run --all-files
A few notes about Listing 606:
[git] main @ 78d452f 2024-07-18 V3.24.4
G.5 pre-commit using docker 170
the settings given in Listing 607 instruct pre-commit to use conda to get dependencies;
this requires pre-commit and conda to be installed on your system;
the args lists selected command-line options; the settings in Listing 606 are equivalent to
calling
cmh:$ conda run latexindent.pl -s myfile.tex
for each .tex file in your repository;
to instruct latexindent.pl to overwrite the files in your repository, then you can update
Listing 606 so that args: [-s, -w].
G.5 pre-commit using docker
You can also rely on docker (detailed in appendix F) instead of CPAN for all dependencies, including
latexindent.pl itself.
LISTING 608: .pre-commit-config.yaml (docker)
- repo: https://github.com/cmhughes/latexindent.pl
rev: V3.24.4
hooks:
- id: latexindent-docker
args: [-s]
Once created, you should then be able to run the following command:
cmh:$ pre-commit run --all-files
A few notes about Listing 606:
the settings given in Listing 608 instruct pre-commit to use docker to get dependencies;
this requires pre-commit and docker to be installed on your system;
the args lists selected command-line options; the settings in Listing 606 are equivalent to
calling
cmh:$ docker run -v /path/to/myfile.tex:/myfile.tex
ghcr.io/cmhughes/latexindent.pl -s myfile.tex
for each .tex file in your repository;
to instruct latexindent.pl to overwrite the files in your repository, then you can update
Listing 606 so that args: [-s, -w].
G.6 pre-commit example using -l, -m switches
Let’s consider a small example, with local latexindent.pl settings in .latexindent.yaml.
example 173
We use the local settings given in Listing 609.
LISTING 609: .latexindent.yaml
onlyOneBackUp: 1
modifyLineBreaks:
oneSentencePerLine:
manipulateSentences: 1
and .pre-commit-config.yaml as in Listing 610:
[git] main @ 78d452f 2024-07-18 V3.24.4
G.6 pre-commit example using -l, -m switches 171
LISTING 610: .pre-commit-config.yaml (demo)
- repo: https://github.com/cmhughes/latexindent.pl
rev: V3.24.4
hooks:
- id: latexindent
args: [-l, -m, -s, -w]
Now running
cmh:$ pre-commit run --all-files
is equivalent to running
cmh:$ latexindent.pl -l -m -s -w myfile.tex
for each .tex file in your repository.
A few notes about Listing 610:
the -l option was added to use the local .latexindent.yaml (where it was specified to
only create one back-up file, as git typically takes care of this when you use pre-commit);
-m to modify line breaks; in addition to -s to suppress command-line output, and -w to
format files in place.
[git] main @ 78d452f 2024-07-18 V3.24.4
SECTION H
indentconfig options
This section describes the possible locations for the main configuration file, discussed in Section 4.
Thank you to [22] for this contribution.
N: 2023-01-01
The possible locations of indentconfig.yaml are read one after the other, and reading stops when
a valid file is found in one of the paths.
Before stating the list, we give summarise in Table 5.
TABLE 5: indentconfig environment variable summaries
environment variable type Linux macOS Windows
LATEXINDENT_CONFIG full path to file Ë Ë Ë
XDG_CONFIG_HOME directory path Ë é é
LOCALAPPDATA directory path é é Ë
The following list shows the checked options and is sorted by their respective priority. It uses cap-
italized and with a dollar symbol prefixed names (e.g. $LATEXINDENT_CONFIG) to symbolize envi-
ronment variables. In addition to that the variable name $homeDir is used to symbolize your home
directory.
1. The value of the environment variable $LATEXINDENT_CONFIG is treated as highest priority
source for the path to the configuration file.
2. The next options are dependent on your operating system:
Linux:
(a) The file at $XDG_CONFIG_HOME/latexindent/indentconfig.yaml
(b) The file at $homeDir/.config/latexindent/indentconfig.yaml
Windows:
(a) The file at $LOCALAPPDATA\latexindent\indentconfig.yaml
(b) The file at $homeDir\AppData\Local\latexindent\indentconfig.yaml
Mac:
(a) The file at $homeDir/Library/Preferences/latexindent/indentconfig.yaml
3. The file at $homeDir/indentconfig.yaml
4. The file at $homeDir/.indentconfig.yaml
H.1 Why to change the configuration location
This is mostly a question about what you prefer, some like to put all their configuration files in their
home directory (see $homeDir above), whilst some like to sort their configuration. And if you don’t
care about it, you can just continue using the same defaults.
[git] main @ 78d452f 2024-07-18 V3.24.4
H.2 How to change the configuration location 173
H.2 How to change the configuration location
This depends on your preferred location, if, for example, you would like to set a custom location,
you would have to change the $LATEXINDENT_CONFIG environment variable.
Although the following example only covers $LATEXINDENT_CONFIG, the same process can be ap-
plied to $XDG_CONFIG_HOME or $LOCALAPPDATA because both are environment variables. You just
have to change the path to your chosen configuration directory (e.g. $homeDir/.config or $homeDir\AppData\Local
on Linux or Windows respectively)
H.2.1 Linux
To change $LATEXINDENT_CONFIG on Linux you can run the following command in a terminal after
changing the path:
cmh:$ echo ’export␣LATEXINDENT_CONFIG="/home/cmh/latexindent-config.yaml"’ >> ~/.profile
Context: This command adds the given line to your .profile file (which is commonly stored in
$HOME/.profile). All commands in this file a run after login, so the environment variable will be
set after your next login.
You can check the value of $LATEXINDENT_CONFIG by typing
cmh:$ echo $LATEXINDENT_CONFIG
cmh:$ /home/cmh/latexindent-config.yaml
Linux users interested in $XDG_CONFIG_HOME can explore variations of the following commands
cmh:$ echo $XDG_CONFIG_HOME
cmh:$ echo ${XDG_CONFIG_HOME:=$HOME/.config}
cmh:$ echo $XDG_CONFIG_HOME
cmh:$ mkdir /home/cmh/.config/latexindent
cmh:$ touch /home/cmh/.config/latexindent/indentconfig.yaml
H.2.2 Windows
To change $LATEXINDENT_CONFIG on Windows you can run the following command in powershell.exe
after changing the path:
C:\Users\cmh>[ Environ me nt ] ::S et Env iro nm ent Va r ia ble
C:\Users\cmh> (" LA TE XI NDE NT _C ONF IG " , " \ your \ con fig \ path " , " User ")
This sets the environment variable for every user session.
H.2.3 Mac
To change $LATEXINDENT_CONFIG on macOS you can run the following command in a terminal after
changing the path:
cmh:$ echo ’export␣LATEXINDENT_CONFIG="/your/config/path"’ >> ~/.profile
Context: This command adds the line to your .profile file (which is commonly stored in $HOME/.profile).
All commands in this file a run after login, so the environment variable will be set after your next
login.
[git] main @ 78d452f 2024-07-18 V3.24.4
SECTION I
paths demonstration
As detailed in Section 4.1 on page 23
N: 2024-04-28
, the paths field can be specified in any of your YAML files.
We will use the file in Listing 611 for demonstration in what follows.
LISTING 611: paths-demo.tex
\pathdemo[
opt arg
]{
mand arg
}
example 174
Consider the settings given in Listing 612 and Listing 613.
LISTING 612: path1.yaml
defaultIndent: ’’
paths:
- path2.yaml
LISTING 613: path2.yaml
defaultIndent:␣’␣␣␣’
Upon calling
cmh:$ latexindent.pl -l=path1.yaml paths-demo.tex
then we will receive the output given in Listing 614.
LISTING 614: paths-demo-mod1.tex
\pathdemo[
␣␣␣opt␣arg
]{
␣␣␣mand␣arg
}
We note that the settings from Listing 613 have been called from Listing 612.
On inspection of indent.log from the above call, we see the details of this part of the process
given in Listing 615.
[git] main @ 78d452f 2024-07-18 V3.24.4
175
LISTING 615: path-test1.txt
YAML settings, reading from the following files:
Reading USER settings from path1.yaml
Reading path information from path1.yaml
---
defaultIndent: ’’
paths:
- path2.yaml
---
defaultIndent: ’’
paths:
- path2.yaml
Reading USER settings from path2.yaml
---
defaultIndent: ’
example 175
Consider the settings given in Listing 616 to Listing 618.
LISTING 616: path3.yaml
defaultIndent: ’’
paths:
- path4.yaml
LISTING 617: path4.yaml
defaultIndent:␣’␣␣␣’
paths:
-␣path5.yaml
LISTING 618: path5.yaml
defaultIndent:␣’␣’
Upon calling
cmh:$ latexindent.pl -l=path3.yaml paths-demo.tex
then we will receive the output given in Listing 619.
LISTING 619: paths-demo-mod3.tex
\pathdemo[
␣opt␣arg
]{
␣mand␣arg
}
We see that path3.yaml calls path4.yaml which in turn calls path5.yaml.
On inspection of indent.log from the above call, we see the details of this part of the process
given in Listing 620.
[git] main @ 78d452f 2024-07-18 V3.24.4
176
LISTING 620: path-test3.txt
YAML settings, reading from the following files:
Reading USER settings from path3.yaml
Reading path information from path3.yaml
---
defaultIndent: ’’
paths:
- path4.yaml
---
defaultIndent: ’’
paths:
- path4.yaml
Reading USER settings from path4.yaml
Reading path information from path4.yaml
---
defaultIndent: ’
paths:
- path5.yaml
---
defaultIndent: ’
paths:
- path5.yaml
Reading USER settings from path5.yaml
---
defaultIndent: ’ ’
[git] main @ 78d452f 2024-07-18 V3.24.4
SECTION J
logFilePreferences
Listing 36 on page 28 describes the options for customising the information given to the log file, and
we provide a few demonstrations here.
example 176
Let’s say that we start with the code given in Listing 621, and the settings specified in Listing 622.
LISTING 621: simple.tex
\begin{myenv}
body of myenv
\end{myenv}
LISTING 622: logfile-prefs1.yaml
logFilePreferences:
showDecorationStartCodeBlockTrace: "+++++"
showDecorationFinishCodeBlockTrace: "-----"
If we run the following command (noting that -t is active)
cmh:$ latexindent.pl -t -l=logfile-prefs1.yaml simple.tex
then on inspection of indent.log we will find the snippet given in Listing 623.
LISTING 623: indent.log
+++++
TRACE: environment found: myenv
No ancestors found for myenv
Storing settings for myenvenvironments
indentRulesGlobal specified (0) for environments, ...
Using defaultIndent for myenv
Putting linebreak after replacementText for myenv
looking for COMMANDS and key = {value}
TRACE: Searching for commands with optional and/or mandatory arguments AND key =
{value}
looking for SPECIAL begin/end
TRACE: Searching myenv for special begin/end (see specialBeginEnd)
TRACE: Searching myenv for optional and mandatory arguments
... no arguments found
-----
Notice that the information given about myenv is ‘framed’ using +++++ and ----- respectively.
[git] main @ 78d452f 2024-07-18 V3.24.4
SECTION K
Encoding
When using latexindent in different ways on different systems, the range of characters supported by
its switches/flags/options (see Section 3.2 on page 15) may vary.
For the Windows executable file latexindent.exe, its options support UTF-8 characters.
For the Windows Perl script latexindent.pl, its option switch supports the characters supported
by the encoding corresponding to the system code page. You can check the system code page by
running the following command in either cmd.exe or powershell.exe:
C:\Users\cmh> chcp
which may receive the following result
C:\Users\cmh> Active code page: 936
and then the characters supported by the code page can be found in https://learn.microsoft.com/en-
us/windows/win32/intl/code-page-identifiers. For example, the characters supported by the encod-
ing corresponding to code page 936 are: ANSI/OEM Simplified Chinese (PRC, Singapore); Chinese
Simplified (GB2312).
For Ubuntu Linux and macOS users, whether using the Perl script or the executable file, the options
support UTF-8 characters.
[git] main @ 78d452f 2024-07-18 V3.24.4
SECTION L
dos2unix linebreak adjustment
dos2unixlinebreaks: integer
If you use latexindent.pl on a dos-based Windows file on Linux
N: 2021-06-19
then you may find that trailing
horizontal space is not removed as you hope.
In such a case, you may wish to try setting dos2unixlinebreaks to 1 and employing, for example,
the following command.
cmh:$ latexindent.pl -y="dos2unixlinebreaks:1" myfile.tex
See [51] for further dertails.
[git] main @ 78d452f 2024-07-18 V3.24.4
SECTION M
Differences from Version 2.2 to 3.0
There are a few (small) changes to the interface when comparing Version 2.2 to Version 3.0. Explicitly,
in previous versions you might have run, for example,
cmh:$ latexindent.pl -o myfile.tex outputfile.tex
whereas in Version 3.0 you would run any of the following, for example,
cmh:$ latexindent.pl -o=outputfile.tex myfile.tex
cmh:$ latexindent.pl -o outputfile.tex myfile.tex
cmh:$ latexindent.pl myfile.tex -o outputfile.tex
cmh:$ latexindent.pl myfile.tex -o=outputfile.tex
cmh:$ latexindent.pl myfile.tex -outputfile=outputfile.tex
cmh:$ latexindent.pl myfile.tex -outputfile outputfile.tex
noting that the output file is given next to the -o switch.
The fields given in Listing 624 are obsolete from Version 3.0 onwards.
LISTING 624: Obsolete YAML fields from Version 3.0
alwaysLookforSplitBrackets
alwaysLookforSplitBrackets
checkunmatched
checkunmatchedELSE
checkunmatchedbracket
constructIfElseFi
There is a slight difference when specifying indentation after headings; specifically, we now write
indentAfterThisHeading instead of indent. See Listings 625 and 626
LISTING 625:
indentAfterThisHeading in Version
2.2
indentAfterHeadings:
part:
indent: 0
level: 1
LISTING 626:
indentAfterThisHeading in Version
3.0
indentAfterHeadings:
part:
indentAfterThisHeading: 0
level: 1
To specify noAdditionalIndent for display-math environments in Version 2.2, you would write
YAML as in Listing 627; as of Version 3.0, you would write YAML as in Listing 628 or, if you’re using
-m switch, Listing 629.
[git] main @ 78d452f 2024-07-18 V3.24.4
181
LISTING 627: noAdditionalIndent in
Version 2.2
noAdditionalIndent:
\[: 0
\]: 0
LISTING 628: noAdditionalIndent for
displayMath in Version 3.0
specialBeginEnd:
displayMath:
begin: ’\\\[’
end: ’\\\]’
lookForThis: 0
LISTING 629: noAdditionalIndent for
displayMath in Version 3.0
noAdditionalIndent:
displayMath: 1
End
[git] main @ 78d452f 2024-07-18 V3.24.4
Listings
LISTING 1: quick-start.tex · · · · · · · · · · · · · · · · · · · · · · 6
LISTING 2: quick-start-default.tex · · · · · · · · · · · · · 6
LISTING 3: quick-start-mod1.tex· · · · · · · · · · · · · · · · · 7
LISTING 4: quick-start1.yaml · · · · · · · · · · · · · · · · · · · · 7
LISTING 5: quick-start-mod2.tex· · · · · · · · · · · · · · · · · 7
LISTING 6: quick-start2.yaml · · · · · · · · · · · · · · · · · · · · 7
LISTING 7: quick-start-mod3.tex· · · · · · · · · · · · · · · · · 8
LISTING 8: quick-start3.yaml · · · · · · · · · · · · · · · · · · · · 8
LISTING 9: quick-start-mod4.tex· · · · · · · · · · · · · · · · · 8
LISTING 10: quick-start4.yaml · · · · · · · · · · · · · · · · · · · 8
LISTING 11: quick-start-mod5.tex· · · · · · · · · · · · · · · · 9
LISTING 12: quick-start5.yaml · · · · · · · · · · · · · · · · · · · 9
LISTING 13: quick-start-mod6.tex· · · · · · · · · · · · · · · · 9
LISTING 14: quick-start6.yaml · · · · · · · · · · · · · · · · · · · 9
LISTING 15: quick-start-mod7.tex· · · · · · · · · · · · · · · · 10
LISTING 16: quick-start7.yaml · · · · · · · · · · · · · · · · · · · 10
LISTING 17: quick-start-mod8.tex· · · · · · · · · · · · · · · · 10
LISTING 18: quick-start8.yaml · · · · · · · · · · · · · · · · · · · 10
LISTING 19: quick-start-mod9.tex· · · · · · · · · · · · · · · · 11
LISTING 20: quick-start9.yaml · · · · · · · · · · · · · · · · · · · 11
LISTING 21: Possible error messages · · · · · · · · · · · · · · · · · 11
LISTING 22: demo-tex.tex · · · · · · · · · · · · · · · · · · · · · · · · 11
LISTING 23: fileExtensionPreference · · · · · · · · · · · · 11
LISTING 24: modifyLineBreaks · · · · · · · · · · · · · · · · · · · · 12
LISTING 25: replacements · · · · · · · · · · · · · · · · · · · · · · · · 12
LISTING 26: filecontents1.tex · · · · · · · · · · · · · · · · · · · 13
LISTING 27: filecontents1.tex default output · · · · · · 13
LISTING 28: tikzset.tex · · · · · · · · · · · · · · · · · · · · · · · · · 13
LISTING 29: tikzset.tex default output · · · · · · · · · · · · 13
LISTING 30: pstricks.tex · · · · · · · · · · · · · · · · · · · · · · · · 13
LISTING 31: pstricks.tex default output · · · · · · · · · · · 13
LISTING 32: indentconfig.yaml (sample) · · · · · · · · · · 23
LISTING 33: mysettings.yaml (example) · · · · · · · · · · · 24
LISTING 35: fileExtensionPreference · · · · · · · · · · · · 27
LISTING 36: logFilePreferences · · · · · · · · · · · · · · · · · · 28
LISTING 37: verbatimEnvironments· · · · · · · · · · · · · · · · 29
LISTING 38: verbatimCommands · · · · · · · · · · · · · · · · · · · · 29
LISTING 39: nameAsRegex1.yaml · · · · · · · · · · · · · · · · · · · 29
LISTING 40: nameAsRegex2.yaml · · · · · · · · · · · · · · · · · · · 29
LISTING 41: nameAsRegex3.yaml · · · · · · · · · · · · · · · · · · · 30
LISTING 42: nameAsRegex4.yaml · · · · · · · · · · · · · · · · · · · 30
LISTING 43: noIndentBlock · · · · · · · · · · · · · · · · · · · · · · · 30
LISTING 44: noIndentBlock.tex · · · · · · · · · · · · · · · · · · · 30
LISTING 45: noIndentBlock1.tex · · · · · · · · · · · · · · · · · · 30
LISTING 46: noindent1.yaml · · · · · · · · · · · · · · · · · · · · · · 31
LISTING 47: noindent2.yaml · · · · · · · · · · · · · · · · · · · · · · 31
LISTING 48: noindent3.yaml · · · · · · · · · · · · · · · · · · · · · · 31
LISTING 49: noIndentBlock1.tex using Listing 46
or Listing 47 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 31
LISTING 50: noIndentBlock1.tex using Listing 48 · · · 31
LISTING 51: nameAsRegex5.yaml · · · · · · · · · · · · · · · · · · · 32
LISTING 52: nameAsRegex6.yaml · · · · · · · · · · · · · · · · · · · 32
LISTING 53: fileContentsEnvironments · · · · · · · · · · · 32
LISTING 54: lookForPreamble · · · · · · · · · · · · · · · · · · · · · · · 32
LISTING 55: Motivating preambleCommandsBeforeEnvironments
33
LISTING 56: removeTrailingWhitespace · · · · · · · · · · · · · · 33
LISTING 57: removeTrailingWhitespace (alt) · · · · · · · · · · 33
LISTING 59: tabular1.tex · · · · · · · · · · · · · · · · · · · · · · · · 34
LISTING 60: tabular1.tex default output · · · · · · · · · · · 34
LISTING 61: lookForAlignDelims (advanced) · · · · · · · 34
LISTING 62: tabular2.tex · · · · · · · · · · · · · · · · · · · · · · · · 35
LISTING 63: tabular2.yaml · · · · · · · · · · · · · · · · · · · · · · · 35
LISTING 64: tabular3.yaml · · · · · · · · · · · · · · · · · · · · · · · 35
LISTING 65: tabular4.yaml · · · · · · · · · · · · · · · · · · · · · · · 35
LISTING 66: tabular5.yaml · · · · · · · · · · · · · · · · · · · · · · · 35
LISTING 67: tabular6.yaml · · · · · · · · · · · · · · · · · · · · · · · 35
LISTING 68: tabular7.yaml · · · · · · · · · · · · · · · · · · · · · · · 35
LISTING 69: tabular8.yaml · · · · · · · · · · · · · · · · · · · · · · · 36
LISTING 70: tabular2.tex default output · · · · · · · · · · · 36
LISTING 71: tabular2.tex using Listing 63 · · · · · · · · · · 36
LISTING 72: tabular2.tex using Listing 64 · · · · · · · · · · 36
LISTING 73: tabular2.tex using Listings 63 and 65· · · 37
LISTING 74: tabular2.tex using Listings 63 and 66· · · 37
LISTING 75: tabular2.tex using Listings 63 and 67· · · 37
LISTING 76: tabular2.tex using Listings 63 and 68· · · 37
LISTING 77: tabular2.tex using Listings 63 and 69· · · 37
LISTING 78: aligned1.tex · · · · · · · · · · · · · · · · · · · · · · · · 38
LISTING 79: aligned1-default.tex· · · · · · · · · · · · · · · · 38
LISTING 80: sba1.yaml· · · · · · · · · · · · · · · · · · · · · · · · · · · · 38
LISTING 81: sba2.yaml· · · · · · · · · · · · · · · · · · · · · · · · · · · · 38
LISTING 82: sba3.yaml· · · · · · · · · · · · · · · · · · · · · · · · · · · · 38
[git] main @ 78d452f 2024-07-18 V3.24.4
LISTINGS 183
LISTING 83: sba4.yaml· · · · · · · · · · · · · · · · · · · · · · · · · · · · 38
LISTING 84: aligned1-mod1.tex · · · · · · · · · · · · · · · · · · · 39
LISTING 85: sba5.yaml· · · · · · · · · · · · · · · · · · · · · · · · · · · · 39
LISTING 86: sba6.yaml· · · · · · · · · · · · · · · · · · · · · · · · · · · · 39
LISTING 87: aligned1-mod5.tex · · · · · · · · · · · · · · · · · · · 40
LISTING 88: aligned1.tex using Listing 89 · · · · · · · · · · 40
LISTING 89: sba7.yaml· · · · · · · · · · · · · · · · · · · · · · · · · · · · 40
LISTING 90: tabular4.tex · · · · · · · · · · · · · · · · · · · · · · · · 40
LISTING 91: tabular4-default.tex· · · · · · · · · · · · · · · · 40
LISTING 92: tabular4-FDBS.tex · · · · · · · · · · · · · · · · · · · 40
LISTING 93: matrix1.tex · · · · · · · · · · · · · · · · · · · · · · · · · 40
LISTING 94: matrix1.tex default output · · · · · · · · · · · · 40
LISTING 95: align-block.tex · · · · · · · · · · · · · · · · · · · · · 41
LISTING 96: align-block.tex default output · · · · · · · · 41
LISTING 97: tabular-DM.tex · · · · · · · · · · · · · · · · · · · · · · 41
LISTING 98: tabular-DM.tex default output · · · · · · · · · 41
LISTING 99: tabular-DM.tex using Listing 100· · · · · · · 41
LISTING 100: dontMeasure1.yaml · · · · · · · · · · · · · · · · · · 41
LISTING 101: tabular-DM.tex using Listing 102 or
Listing 104 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 42
LISTING 102: dontMeasure2.yaml · · · · · · · · · · · · · · · · · · 42
LISTING 103: tabular-DM.tex using Listing 104 or
Listing 104 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 42
LISTING 104: dontMeasure3.yaml · · · · · · · · · · · · · · · · · · 42
LISTING 105: dontMeasure4.yaml · · · · · · · · · · · · · · · · · · 42
LISTING 106: tabular-DM.tex using Listing 107· · · · · · 42
LISTING 107: dontMeasure5.yaml · · · · · · · · · · · · · · · · · · 42
LISTING 108: tabular-DM.tex using Listing 109· · · · · · 43
LISTING 109: dontMeasure6.yaml · · · · · · · · · · · · · · · · · · 43
LISTING 110: tabbing.tex · · · · · · · · · · · · · · · · · · · · · · · · 43
LISTING 111: tabbing.tex default output · · · · · · · · · · · 43
LISTING 112: tabbing.tex using Listing 113 · · · · · · · · · 43
LISTING 113: delimiterRegEx1.yaml · · · · · · · · · · · · · · 43
LISTING 114: tabbing.tex using Listing 115 · · · · · · · · · 44
LISTING 115: delimiterRegEx2.yaml · · · · · · · · · · · · · · 44
LISTING 116: tabbing.tex using Listing 117 · · · · · · · · · 44
LISTING 117: delimiterRegEx3.yaml · · · · · · · · · · · · · · 44
LISTING 118: tabbing1.tex · · · · · · · · · · · · · · · · · · · · · · · 44
LISTING 119: tabbing1-mod4.tex · · · · · · · · · · · · · · · · · · 44
LISTING 120: delimiterRegEx4.yaml · · · · · · · · · · · · · · 44
LISTING 121: tabbing1-mod5.tex · · · · · · · · · · · · · · · · · · 45
LISTING 122: delimiterRegEx5.yaml · · · · · · · · · · · · · · 45
LISTING 123: tabular-DM-1.tex · · · · · · · · · · · · · · · · · · · 45
LISTING 124: tabular-DM-1-mod1.tex · · · · · · · · · · · · · 45
LISTING 125: tabular-DM-1-mod1a.tex · · · · · · · · · · · · 45
LISTING 126: dontMeasure1a.yaml· · · · · · · · · · · · · · · · · 45
LISTING 127: tabular5.tex · · · · · · · · · · · · · · · · · · · · · · · 46
LISTING 128: tabular5-default.tex · · · · · · · · · · · · · · 46
LISTING 129: tabular5-mod1.tex · · · · · · · · · · · · · · · · · · 46
LISTING 130: alignContentAfterDBS1.yaml · · · · · · · · 46
LISTING 131: tabular5-mod2.tex · · · · · · · · · · · · · · · · · · 46
LISTING 132: alignContentAfterDBS2.yaml · · · · · · · · 46
LISTING 133: indentAfterItems · · · · · · · · · · · · · · · · · · · 46
LISTING 134: items1.tex · · · · · · · · · · · · · · · · · · · · · · · · · 46
LISTING 135: items1.tex default output · · · · · · · · · · · · 46
LISTING 136: itemNames · · · · · · · · · · · · · · · · · · · · · · · · · · 47
LISTING 137: specialBeginEnd · · · · · · · · · · · · · · · · · · · · 47
LISTING 138: special1.tex before · · · · · · · · · · · · · · · · · 48
LISTING 139: special1.tex default output · · · · · · · · · · 48
LISTING 140: specialLR.tex · · · · · · · · · · · · · · · · · · · · · · 48
LISTING 141: specialsLeftRight.yaml · · · · · · · · · · · · 48
LISTING 142: specialBeforeCommand.yaml · · · · · · · · · 48
LISTING 143: specialLR.tex using Listing 141· · · · · · · 48
LISTING 144: specialLR.tex using Listings 141
and 142 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 48
LISTING 145: special2.tex · · · · · · · · · · · · · · · · · · · · · · · 49
LISTING 146: special2.tex using Listing 147· · · · · · · · 49
LISTING 147: middle.yaml · · · · · · · · · · · · · · · · · · · · · · · · 49
LISTING 148: special2.tex using Listing 149· · · · · · · · 49
LISTING 149: middle1.yaml · · · · · · · · · · · · · · · · · · · · · · · 49
LISTING 150: specialAlgo.tex · · · · · · · · · · · · · · · · · · · · 50
LISTING 151: specialAlgo.tex using Listing 152 · · · · 50
LISTING 152: algo.yaml · · · · · · · · · · · · · · · · · · · · · · · · · · 50
LISTING 153: special3.tex and output using List-
ing 154 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 51
LISTING 154: special-verb1.yaml· · · · · · · · · · · · · · · · · 51
LISTING 155: special-align.tex · · · · · · · · · · · · · · · · · · 51
LISTING 156: special-align.tex using Listing 157 · · 51
LISTING 157: edge-node1.yaml · · · · · · · · · · · · · · · · · · · · 51
LISTING 158: special-align.tex using Listing 159 · · 52
LISTING 159: edge-node2.yaml · · · · · · · · · · · · · · · · · · · · 52
LISTING 160: special-body.tex · · · · · · · · · · · · · · · · · · · 52
LISTING 161: special-body.tex using Listing 162 · · · 53
LISTING 162: special-body1.yaml· · · · · · · · · · · · · · · · · 53
LISTING 163: special-body2.yaml· · · · · · · · · · · · · · · · · 53
LISTING 164: indentAfterHeadings· · · · · · · · · · · · · · · · 53
LISTING 165: headings1.tex · · · · · · · · · · · · · · · · · · · · · · 54
LISTING 166: headings1.yaml · · · · · · · · · · · · · · · · · · · · · 54
LISTING 167: headings1.tex using Listing 166· · · · · · · 54
LISTING 168: headings1.tex second modification · · · · 54
LISTING 169: mult-nested.tex · · · · · · · · · · · · · · · · · · · · 55
LISTING 170: mult-nested.tex default output · · · · · · · 55
LISTING 171: mult-nested.tex using Listing 172 · · · · 55
LISTING 172: max-indentation1.yaml · · · · · · · · · · · · · 55
LISTING 173: myenv.tex · · · · · · · · · · · · · · · · · · · · · · · · · · 57
LISTING 174: myenv-noAdd1.yaml · · · · · · · · · · · · · · · · · · 57
LISTING 175: myenv-noAdd2.yaml · · · · · · · · · · · · · · · · · · 57
LISTING 176: myenv.tex output (using either List-
ing 174 or Listing 175) · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 58
LISTING 177: myenv-noAdd3.yaml · · · · · · · · · · · · · · · · · · 58
[git] main @ 78d452f 2024-07-18 V3.24.4
LISTINGS 184
LISTING 178: myenv-noAdd4.yaml · · · · · · · · · · · · · · · · · · 58
LISTING 179: myenv.tex output (using either List-
ing 177 or Listing 178) · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 58
LISTING 180: myenv-args.tex · · · · · · · · · · · · · · · · · · · · · 58
LISTING 181: myenv-args.tex using Listing 174· · · · · · 59
LISTING 182: myenv-noAdd5.yaml · · · · · · · · · · · · · · · · · · 59
LISTING 183: myenv-noAdd6.yaml · · · · · · · · · · · · · · · · · · 59
LISTING 184: myenv-args.tex using Listing 182· · · · · · 59
LISTING 185: myenv-args.tex using Listing 183· · · · · · 59
LISTING 186: myenv-rules1.yaml · · · · · · · · · · · · · · · · · · 60
LISTING 187: myenv-rules2.yaml · · · · · · · · · · · · · · · · · · 60
LISTING 188: myenv.tex output (using either List-
ing 186 or Listing 187) · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 60
LISTING 189: myenv-args.tex using Listing 186· · · · · · 60
LISTING 190: myenv-rules3.yaml · · · · · · · · · · · · · · · · · · 61
LISTING 191: myenv-rules4.yaml · · · · · · · · · · · · · · · · · · 61
LISTING 192: myenv-args.tex using Listing 190· · · · · · 61
LISTING 193: myenv-args.tex using Listing 191· · · · · · 61
LISTING 194: noAdditionalIndentGlobal · · · · · · · · · · 61
LISTING 195: myenv-args.tex using Listing 194· · · · · · 62
LISTING 196: myenv-args.tex using Listings 186
and 194 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 62
LISTING 197: opt-args-no-add-glob.yaml · · · · · · · · · 62
LISTING 198: mand-args-no-add-glob.yaml · · · · · · · · 62
LISTING 199: myenv-args.tex using Listing 197· · · · · · 62
LISTING 200: myenv-args.tex using Listing 198· · · · · · 62
LISTING 201: indentRulesGlobal · · · · · · · · · · · · · · · · · · 62
LISTING 202: myenv-args.tex using Listing 201· · · · · · 63
LISTING 203: myenv-args.tex using Listings 186
and 201 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 63
LISTING 204: opt-args-indent-rules-glob.yaml · · 63
LISTING 205: mand-args-indent-rules-glob.yaml
63
LISTING 206: myenv-args.tex using Listing 204· · · · · · 63
LISTING 207: myenv-args.tex using Listing 205· · · · · · 63
LISTING 208: item-noAdd1.yaml · · · · · · · · · · · · · · · · · · · 64
LISTING 209: item-rules1.yaml · · · · · · · · · · · · · · · · · · · 64
LISTING 210: items1.tex using Listing 208 · · · · · · · · · · 64
LISTING 211: items1.tex using Listing 209 · · · · · · · · · · 64
LISTING 212: items-noAdditionalGlobal.yaml· · · · · 64
LISTING 213: items-indentRulesGlobal.yaml · · · · · · 64
LISTING 214: mycommand.tex · · · · · · · · · · · · · · · · · · · · · · 65
LISTING 215: mycommand.tex default output · · · · · · · · · 65
LISTING 216: mycommand-noAdd1.yaml · · · · · · · · · · · · · 65
LISTING 217: mycommand-noAdd2.yaml · · · · · · · · · · · · · 65
LISTING 218: mycommand.tex using Listing 216· · · · · · · 65
LISTING 219: mycommand.tex using Listing 217· · · · · · · 65
LISTING 220: mycommand-noAdd3.yaml · · · · · · · · · · · · · 66
LISTING 221: mycommand-noAdd4.yaml · · · · · · · · · · · · · 66
LISTING 222: mycommand.tex using Listing 220· · · · · · · 66
LISTING 223: mycommand.tex using Listing 221· · · · · · · 66
LISTING 224: mycommand-noAdd5.yaml · · · · · · · · · · · · · 66
LISTING 225: mycommand-noAdd6.yaml · · · · · · · · · · · · · 66
LISTING 226: mycommand.tex using Listing 224· · · · · · · 66
LISTING 227: mycommand.tex using Listing 225· · · · · · · 66
LISTING 228: ifelsefi1.tex · · · · · · · · · · · · · · · · · · · · · · 67
LISTING 229: ifelsefi1.tex default output · · · · · · · · · 67
LISTING 230: ifnum-noAdd.yaml · · · · · · · · · · · · · · · · · · · 67
LISTING 231: ifnum-indent-rules.yaml · · · · · · · · · · · 67
LISTING 232: ifelsefi1.tex using Listing 230· · · · · · · 67
LISTING 233: ifelsefi1.tex using Listing 231· · · · · · · 67
LISTING 234: ifelsefi-noAdd-glob.yaml · · · · · · · · · · 67
LISTING 235: ifelsefi-indent-rules-global.yaml
67
LISTING 236: ifelsefi1.tex using Listing 234· · · · · · · 68
LISTING 237: ifelsefi1.tex using Listing 235· · · · · · · 68
LISTING 238: ifelsefi2.tex · · · · · · · · · · · · · · · · · · · · · · 68
LISTING 239: ifelsefi2.tex default output · · · · · · · · · 68
LISTING 240: displayMath-noAdd.yaml · · · · · · · · · · · · 68
LISTING 241: displayMath-indent-rules.yaml· · · · · 68
LISTING 242: special1.tex using Listing 240· · · · · · · · 69
LISTING 243: special1.tex using Listing 241· · · · · · · · 69
LISTING 244: special-noAdd-glob.yaml · · · · · · · · · · · 69
LISTING 245: special-indent-rules-global.yaml
69
LISTING 246: special1.tex using Listing 244· · · · · · · · 69
LISTING 247: special1.tex using Listing 245· · · · · · · · 69
LISTING 248: headings2.tex · · · · · · · · · · · · · · · · · · · · · · 69
LISTING 249: headings2.tex using Listing 250· · · · · · · 70
LISTING 250: headings3.yaml · · · · · · · · · · · · · · · · · · · · · 70
LISTING 251: headings2.tex using Listing 252· · · · · · · 70
LISTING 252: headings4.yaml · · · · · · · · · · · · · · · · · · · · · 70
LISTING 253: headings2.tex using Listing 254· · · · · · · 70
LISTING 254: headings5.yaml · · · · · · · · · · · · · · · · · · · · · 70
LISTING 255: headings2.tex using Listing 256· · · · · · · 70
LISTING 256: headings6.yaml · · · · · · · · · · · · · · · · · · · · · 70
LISTING 257: headings2.tex using Listing 258· · · · · · · 71
LISTING 258: headings7.yaml · · · · · · · · · · · · · · · · · · · · · 71
LISTING 259: headings2.tex using Listing 260· · · · · · · 71
LISTING 260: headings8.yaml · · · · · · · · · · · · · · · · · · · · · 71
LISTING 261: headings2.tex using Listing 262· · · · · · · 71
LISTING 262: headings9.yaml · · · · · · · · · · · · · · · · · · · · · 71
LISTING 263: pgfkeys1.tex · · · · · · · · · · · · · · · · · · · · · · · 72
LISTING 264: pgfkeys1.tex default output · · · · · · · · · · 72
LISTING 265: child1.tex · · · · · · · · · · · · · · · · · · · · · · · · · 72
LISTING 266: child1.tex default output · · · · · · · · · · · · 72
LISTING 267: psforeach1.tex · · · · · · · · · · · · · · · · · · · · · 73
LISTING 268: psforeach1.tex default output · · · · · · · · 73
LISTING 269: noAdditionalIndentGlobal · · · · · · · · · · 73
LISTING 270: indentRulesGlobal · · · · · · · · · · · · · · · · · · 73
LISTING 271: commandCodeBlocks · · · · · · · · · · · · · · · · · · 74
[git] main @ 78d452f 2024-07-18 V3.24.4
LISTINGS 185
LISTING 272: pstricks1.tex · · · · · · · · · · · · · · · · · · · · · · 74
LISTING 273: pstricks1 default output · · · · · · · · · · · · · 74
LISTING 274: pstricks1.tex using Listing 275· · · · · · · 75
LISTING 275: noRoundParentheses.yaml · · · · · · · · · · · 75
LISTING 276: pstricks1.tex using Listing 277· · · · · · · 75
LISTING 277: defFunction.yaml · · · · · · · · · · · · · · · · · · · 75
LISTING 278: tikz-node1.tex · · · · · · · · · · · · · · · · · · · · · 75
LISTING 279: tikz-node1 default output · · · · · · · · · · · · 75
LISTING 280: tikz-node1.tex using Listing 281· · · · · · 76
LISTING 281: draw.yaml · · · · · · · · · · · · · · · · · · · · · · · · · · 76
LISTING 282: tikz-node1.tex using Listing 283· · · · · · 76
LISTING 283: no-strings.yaml · · · · · · · · · · · · · · · · · · · · 76
LISTING 284: amalgamate-demo.yaml · · · · · · · · · · · · · · 77
LISTING 285: amalgamate-demo1.yaml · · · · · · · · · · · · · 77
LISTING 286: amalgamate-demo2.yaml · · · · · · · · · · · · · 77
LISTING 287: amalgamate-demo3.yaml · · · · · · · · · · · · · 77
LISTING 288: for-each.tex · · · · · · · · · · · · · · · · · · · · · · · 77
LISTING 289: for-each default output· · · · · · · · · · · · · · · 77
LISTING 290: for-each.tex using Listing 291· · · · · · · · 77
LISTING 291: foreach.yaml · · · · · · · · · · · · · · · · · · · · · · · 77
LISTING 292: ifnextchar.tex · · · · · · · · · · · · · · · · · · · · · 78
LISTING 293: ifnextchar.tex default output · · · · · · · · 78
LISTING 294: ifnextchar.tex using Listing 295· · · · · · 78
LISTING 295: no-ifnextchar.yaml· · · · · · · · · · · · · · · · · 78
LISTING 296: modifyLineBreaks · · · · · · · · · · · · · · · · · · · 80
LISTING 297: mlb1.tex· · · · · · · · · · · · · · · · · · · · · · · · · · · · 81
LISTING 298: mlb1-mod1.tex · · · · · · · · · · · · · · · · · · · · · · 81
LISTING 299: textWrapOptions · · · · · · · · · · · · · · · · · · · · 81
LISTING 300: textwrap1.tex · · · · · · · · · · · · · · · · · · · · · · 82
LISTING 301: textwrap1-mod1.tex· · · · · · · · · · · · · · · · · 82
LISTING 302: textwrap1.yaml · · · · · · · · · · · · · · · · · · · · · 82
LISTING 303: textwrap1A.yaml · · · · · · · · · · · · · · · · · · · · 83
LISTING 304: textwrap1-mod1A.tex· · · · · · · · · · · · · · · · 83
LISTING 305: textwrap1-mod1B.tex· · · · · · · · · · · · · · · · 83
LISTING 306: textwrap1B.yaml · · · · · · · · · · · · · · · · · · · · 83
LISTING 307: tw-headings1.tex · · · · · · · · · · · · · · · · · · · 83
LISTING 308: tw-headings1-mod1.tex · · · · · · · · · · · · · 84
LISTING 309: tw-headings1-mod2.tex · · · · · · · · · · · · · 84
LISTING 310: bf-no-headings.yaml· · · · · · · · · · · · · · · · 84
LISTING 311: tw-comments1.tex · · · · · · · · · · · · · · · · · · · 84
LISTING 312: tw-comments1-mod1.tex · · · · · · · · · · · · · 85
LISTING 313: tw-comments1-mod2.tex · · · · · · · · · · · · · 85
LISTING 314: bf-no-comments.yaml· · · · · · · · · · · · · · · · 85
LISTING 315: tw-disp-math1.tex · · · · · · · · · · · · · · · · · · 85
LISTING 316: tw-disp-math1-mod1.tex · · · · · · · · · · · · 86
LISTING 317: tw-disp-math1-mod2.tex · · · · · · · · · · · · 86
LISTING 318: bf-no-disp-math.yaml · · · · · · · · · · · · · · 86
LISTING 319: tw-bf-myenv1.tex · · · · · · · · · · · · · · · · · · · 86
LISTING 320: tw-bf-myenv1-mod1.tex · · · · · · · · · · · · · 87
LISTING 321: tw-bf-myenv1-mod2.tex · · · · · · · · · · · · · 87
LISTING 322: tw-bf-myenv.yaml · · · · · · · · · · · · · · · · · · · 87
LISTING 323: tw-0-9.tex · · · · · · · · · · · · · · · · · · · · · · · · · 87
LISTING 324: tw-0-9-mod1.tex · · · · · · · · · · · · · · · · · · · · 88
LISTING 325: tw-0-9-mod2.tex · · · · · · · · · · · · · · · · · · · · 88
LISTING 326: bb-0-9.yaml.yaml · · · · · · · · · · · · · · · · · · · 88
LISTING 327: tw-bb-announce1.tex· · · · · · · · · · · · · · · · 88
LISTING 328: tw-bb-announce1-mod1.tex · · · · · · · · · · 88
LISTING 329: tw-bb-announce1-mod2.tex · · · · · · · · · · 89
LISTING 330: tw-bb-announce.yaml· · · · · · · · · · · · · · · · 89
LISTING 331: tw-be-equation.tex· · · · · · · · · · · · · · · · · 89
LISTING 332: tw-be-equation-mod1.tex · · · · · · · · · · · 89
LISTING 333: tw-be-equation.yaml· · · · · · · · · · · · · · · · 90
LISTING 334: tw-be-equation-mod2.tex · · · · · · · · · · · 90
LISTING 335: tw-tc1.tex · · · · · · · · · · · · · · · · · · · · · · · · · 90
LISTING 336: tw-tc1-mod1.tex · · · · · · · · · · · · · · · · · · · · 90
LISTING 337: tw-tc2.tex · · · · · · · · · · · · · · · · · · · · · · · · · 90
LISTING 338: tw-tc2-mod1.tex · · · · · · · · · · · · · · · · · · · · 90
LISTING 339: tw-tc3.tex · · · · · · · · · · · · · · · · · · · · · · · · · 90
LISTING 340: tw-tc3-mod1.tex · · · · · · · · · · · · · · · · · · · · 90
LISTING 341: tw-tc4.tex · · · · · · · · · · · · · · · · · · · · · · · · · 91
LISTING 342: tw-tc4-mod1.tex · · · · · · · · · · · · · · · · · · · · 91
LISTING 343: tw-tc5.tex · · · · · · · · · · · · · · · · · · · · · · · · · 91
LISTING 344: tw-tc5-mod1.tex · · · · · · · · · · · · · · · · · · · · 91
LISTING 345: tw-tc6.tex · · · · · · · · · · · · · · · · · · · · · · · · · 91
LISTING 346: tw-tc6-mod1.tex · · · · · · · · · · · · · · · · · · · · 91
LISTING 347: textwrap8.tex · · · · · · · · · · · · · · · · · · · · · · 92
LISTING 348: textwrap8-mod1.tex· · · · · · · · · · · · · · · · · 92
LISTING 349: tw-before1.yaml · · · · · · · · · · · · · · · · · · · · 92
LISTING 350: textwrap8-mod2.tex· · · · · · · · · · · · · · · · · 93
LISTING 351: tw-after1.yaml · · · · · · · · · · · · · · · · · · · · · 93
LISTING 352: textwrap9.tex · · · · · · · · · · · · · · · · · · · · · · 93
LISTING 353: textwrap9-mod1.tex· · · · · · · · · · · · · · · · · 93
LISTING 354: wrap-comments1.yaml· · · · · · · · · · · · · · · · 93
LISTING 355: textwrap10.tex · · · · · · · · · · · · · · · · · · · · · 93
LISTING 356: textwrap10-mod1.tex· · · · · · · · · · · · · · · · 94
LISTING 357: wrap-comments1.yaml· · · · · · · · · · · · · · · · 94
LISTING 358: textwrap10-mod2.tex· · · · · · · · · · · · · · · · 94
LISTING 359: wrap-comments2.yaml· · · · · · · · · · · · · · · · 94
LISTING 360: textwrap4-mod2A.tex· · · · · · · · · · · · · · · · 95
LISTING 361: textwrap2A.yaml · · · · · · · · · · · · · · · · · · · · 95
LISTING 362: textwrap4-mod2B.tex· · · · · · · · · · · · · · · · 95
LISTING 363: textwrap2B.yaml · · · · · · · · · · · · · · · · · · · · 95
LISTING 364: textwrap-ts.tex · · · · · · · · · · · · · · · · · · · · 95
LISTING 365: tabstop.yaml · · · · · · · · · · · · · · · · · · · · · · · 95
LISTING 366: textwrap-ts-mod1.tex · · · · · · · · · · · · · · 95
LISTING 367: oneSentencePerLine· · · · · · · · · · · · · · · · · 96
LISTING 368: multiple-sentences.tex · · · · · · · · · · · · 97
LISTING 369: multiple-sentences.tex using List-
ing 370 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 97
[git] main @ 78d452f 2024-07-18 V3.24.4
LISTINGS 186
LISTING 370: manipulate-sentences.yaml · · · · · · · · · 97
LISTING 371: multiple-sentences.tex using List-
ing 372 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 97
LISTING 372: keep-sen-line-breaks.yaml · · · · · · · · · 97
LISTING 373: sentencesFollow · · · · · · · · · · · · · · · · · · · · 98
LISTING 374: sentencesBeginWith· · · · · · · · · · · · · · · · · 98
LISTING 375: sentencesEndWith · · · · · · · · · · · · · · · · · · · 98
LISTING 376: multiple-sentences.tex using List-
ing 377 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 98
LISTING 377: sentences-follow1.yaml · · · · · · · · · · · · 98
LISTING 378: multiple-sentences1.tex · · · · · · · · · · · 99
LISTING 379: multiple-sentences1.tex using List-
ing 370 on page 97 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 99
LISTING 380: multiple-sentences1.tex using List-
ing 381 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 99
LISTING 381: sentences-follow2.yaml · · · · · · · · · · · · 99
LISTING 382: multiple-sentences2.tex · · · · · · · · · · · 99
LISTING 383: multiple-sentences2.tex using List-
ing 370 on page 97 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 100
LISTING 384: multiple-sentences2.tex using List-
ing 385 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 100
LISTING 385: sentences-begin1.yaml · · · · · · · · · · · · · 100
LISTING 386: multiple-sentences.tex using List-
ing 387 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 100
LISTING 387: sentences-end1.yaml· · · · · · · · · · · · · · · · 100
LISTING 388: multiple-sentences.tex using List-
ing 389 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 101
LISTING 389: sentences-end2.yaml· · · · · · · · · · · · · · · · 101
LISTING 390: url.tex· · · · · · · · · · · · · · · · · · · · · · · · · · · · · 101
LISTING 391: url.tex using Listing 370 on page 97 · · · 101
LISTING 392: url.tex using Listing 393 · · · · · · · · · · · · · 102
LISTING 393: alt-full-stop1.yaml· · · · · · · · · · · · · · · · 102
LISTING 394: sentencesDoNOTcontain · · · · · · · · · · · · · 102
LISTING 395: multiple-sentences4.tex · · · · · · · · · · · 102
LISTING 396: sentence-dnc1.tex · · · · · · · · · · · · · · · · · · 102
LISTING 397: sentence-dnc1-mod1.tex · · · · · · · · · · · · 103
LISTING 398: dnc1.yaml · · · · · · · · · · · · · · · · · · · · · · · · · · 103
LISTING 399: sentence-dnc2.tex · · · · · · · · · · · · · · · · · · 103
LISTING 400: sentence-dnc2-mod2.tex · · · · · · · · · · · · 103
LISTING 401: dnc2.yaml · · · · · · · · · · · · · · · · · · · · · · · · · · 103
LISTING 402: dnc-off.yaml · · · · · · · · · · · · · · · · · · · · · · · 103
LISTING 403: multiple-sentences3.tex · · · · · · · · · · · 104
LISTING 404: multiple-sentences3.tex using List-
ing 370 on page 97 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 104
LISTING 405: multiple-sentences5.tex · · · · · · · · · · · 104
LISTING 406: multiple-sentences5.tex using List-
ing 407 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 105
LISTING 407: sentence-wrap1.yaml· · · · · · · · · · · · · · · · 105
LISTING 408: multiple-sentences6.tex · · · · · · · · · · · 105
LISTING 409: multiple-sentences6-mod1.tex us-
ing Listing 407 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 105
LISTING 410: multiple-sentences6-mod2.tex us-
ing Listing 407 and no sentence indentation· · · · · · · · · · · 105
LISTING 411: itemize.yaml · · · · · · · · · · · · · · · · · · · · · · · 106
LISTING 412: multiple-sentences6-mod3.tex us-
ing Listing 407 and Listing 411 · · · · · · · · · · · · · · · · · · · · · · 106
LISTING 413: multiple-sentences8.tex · · · · · · · · · · · 107
LISTING 414: multiple-sentences8-mod1.tex · · · · · · 107
LISTING 415: sentence-wrap2.yaml· · · · · · · · · · · · · · · · 107
LISTING 416: multiple-sentences8-mod2.tex · · · · · · 108
LISTING 417: sentence-wrap3.yaml· · · · · · · · · · · · · · · · 108
LISTING 418: multiple-sentences9.tex · · · · · · · · · · · 108
LISTING 419: multiple-sentences9-mod1.tex · · · · · · 108
LISTING 420: sentence-wrap4.yaml· · · · · · · · · · · · · · · · 108
LISTING 421: environments · · · · · · · · · · · · · · · · · · · · · · · 109
LISTING 422: env-mlb1.tex · · · · · · · · · · · · · · · · · · · · · · · 109
LISTING 423: env-mlb1.yaml · · · · · · · · · · · · · · · · · · · · · · 109
LISTING 424: env-mlb2.yaml · · · · · · · · · · · · · · · · · · · · · · 109
LISTING 425: env-mlb.tex using Listing 423 · · · · · · · · · 110
LISTING 426: env-mlb.tex using Listing 424 · · · · · · · · · 110
LISTING 427: env-mlb3.yaml · · · · · · · · · · · · · · · · · · · · · · 110
LISTING 428: env-mlb4.yaml · · · · · · · · · · · · · · · · · · · · · · 110
LISTING 429: env-mlb.tex using Listing 427 · · · · · · · · · 110
LISTING 430: env-mlb.tex using Listing 428 · · · · · · · · · 110
LISTING 431: env-mlb5.yaml · · · · · · · · · · · · · · · · · · · · · · 110
LISTING 432: env-mlb6.yaml · · · · · · · · · · · · · · · · · · · · · · 110
LISTING 433: env-mlb.tex using Listing 431 · · · · · · · · · 111
LISTING 434: env-mlb.tex using Listing 432 · · · · · · · · · 111
LISTING 435: env-beg4.yaml · · · · · · · · · · · · · · · · · · · · · · 111
LISTING 436: env-body4.yaml · · · · · · · · · · · · · · · · · · · · · 111
LISTING 437: env-mlb1.tex · · · · · · · · · · · · · · · · · · · · · · · 111
LISTING 438: env-mlb1.tex using Listing 435· · · · · · · · 111
LISTING 439: env-mlb1.tex using Listing 436· · · · · · · · 111
LISTING 440: env-mlb7.yaml · · · · · · · · · · · · · · · · · · · · · · 112
LISTING 441: env-mlb8.yaml · · · · · · · · · · · · · · · · · · · · · · 112
LISTING 442: env-mlb.tex using Listing 440 · · · · · · · · · 112
LISTING 443: env-mlb.tex using Listing 441 · · · · · · · · · 112
LISTING 444: env-mlb9.yaml · · · · · · · · · · · · · · · · · · · · · · 112
LISTING 445: env-mlb10.yaml · · · · · · · · · · · · · · · · · · · · · 112
LISTING 446: env-mlb.tex using Listing 444 · · · · · · · · · 112
LISTING 447: env-mlb.tex using Listing 445 · · · · · · · · · 112
LISTING 448: env-mlb11.yaml · · · · · · · · · · · · · · · · · · · · · 113
LISTING 449: env-mlb12.yaml · · · · · · · · · · · · · · · · · · · · · 113
LISTING 450: env-mlb.tex using Listing 448 · · · · · · · · · 113
LISTING 451: env-mlb.tex using Listing 449 · · · · · · · · · 113
LISTING 452: env-end4.yaml · · · · · · · · · · · · · · · · · · · · · · 113
LISTING 453: env-end-f4.yaml · · · · · · · · · · · · · · · · · · · · 113
LISTING 454: env-mlb1.tex using Listing 452· · · · · · · · 113
LISTING 455: env-mlb1.tex using Listing 453· · · · · · · · 113
LISTING 456: env-mlb2.tex · · · · · · · · · · · · · · · · · · · · · · · 114
LISTING 457: env-mlb3.tex · · · · · · · · · · · · · · · · · · · · · · · 114
[git] main @ 78d452f 2024-07-18 V3.24.4
LISTINGS 187
LISTING 458: env-mlb3.tex using Listing 424 on
page 109 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 114
LISTING 459: env-mlb3.tex using Listing 428 on
page 110 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 114
LISTING 460: env-mlb4.tex · · · · · · · · · · · · · · · · · · · · · · · 115
LISTING 461: env-mlb13.yaml · · · · · · · · · · · · · · · · · · · · · 115
LISTING 462: env-mlb14.yaml · · · · · · · · · · · · · · · · · · · · · 115
LISTING 463: env-mlb15.yaml · · · · · · · · · · · · · · · · · · · · · 115
LISTING 464: env-mlb16.yaml · · · · · · · · · · · · · · · · · · · · · 115
LISTING 465: env-mlb4.tex using Listing 461· · · · · · · · 115
LISTING 466: env-mlb4.tex using Listing 462· · · · · · · · 115
LISTING 467: env-mlb4.tex using Listing 463· · · · · · · · 115
LISTING 468: env-mlb4.tex using Listing 464· · · · · · · · 115
LISTING 469: env-mlb5.tex · · · · · · · · · · · · · · · · · · · · · · · 116
LISTING 470: removeTWS-before.yaml · · · · · · · · · · · · · 116
LISTING 471: env-mlb5.tex using Listings 465 to 468· 116
LISTING 472: env-mlb5.tex using Listings 465 to 468
and Listing 470 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 116
LISTING 473: env-mlb6.tex · · · · · · · · · · · · · · · · · · · · · · · 116
LISTING 474: UnpreserveBlankLines.yaml · · · · · · · · · 116
LISTING 475: env-mlb6.tex using Listings 465 to 468· 117
LISTING 476: env-mlb6.tex using Listings 465 to 468
and Listing 474 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 117
LISTING 477: env-mlb7.tex · · · · · · · · · · · · · · · · · · · · · · · 117
LISTING 478: env-mlb7-preserve.tex · · · · · · · · · · · · · 117
LISTING 479: env-mlb7-no-preserve.tex · · · · · · · · · · 117
LISTING 480: tabular3.tex · · · · · · · · · · · · · · · · · · · · · · · 118
LISTING 481: tabular3.tex using Listing 482· · · · · · · · 118
LISTING 482: DBS1.yaml · · · · · · · · · · · · · · · · · · · · · · · · · · 118
LISTING 483: tabular3.tex using Listing 484· · · · · · · · 118
LISTING 484: DBS2.yaml · · · · · · · · · · · · · · · · · · · · · · · · · · 118
LISTING 485: tabular6.tex · · · · · · · · · · · · · · · · · · · · · · · 119
LISTING 486: tabular6-mod1.tex · · · · · · · · · · · · · · · · · · 119
LISTING 487: tabular6-mod2.tex · · · · · · · · · · · · · · · · · · 119
LISTING 488: tabular3.tex using Listing 489· · · · · · · · 119
LISTING 489: DBS3.yaml · · · · · · · · · · · · · · · · · · · · · · · · · · 119
LISTING 490: tabular3.tex using Listing 491· · · · · · · · 119
LISTING 491: DBS4.yaml · · · · · · · · · · · · · · · · · · · · · · · · · · 119
LISTING 492: special4.tex · · · · · · · · · · · · · · · · · · · · · · · 120
LISTING 493: special4.tex using Listing 494· · · · · · · · 120
LISTING 494: DBS5.yaml · · · · · · · · · · · · · · · · · · · · · · · · · · 120
LISTING 495: mycommand2.tex · · · · · · · · · · · · · · · · · · · · · 121
LISTING 496: mycommand2.tex using Listing 497· · · · · · 121
LISTING 497: DBS6.yaml · · · · · · · · · · · · · · · · · · · · · · · · · · 121
LISTING 498: mycommand2.tex using Listing 499· · · · · · 121
LISTING 499: DBS7.yaml · · · · · · · · · · · · · · · · · · · · · · · · · · 121
LISTING 500: pmatrix3.tex · · · · · · · · · · · · · · · · · · · · · · · 121
LISTING 501: pmatrix3.tex using Listing 489· · · · · · · · 121
LISTING 502: mycommand1.tex · · · · · · · · · · · · · · · · · · · · · 124
LISTING 503: mycommand1.tex using Listing 504· · · · · · 124
LISTING 504: mycom-mlb1.yaml · · · · · · · · · · · · · · · · · · · · 124
LISTING 505: mycommand1.tex using Listing 506· · · · · · 124
LISTING 506: mycom-mlb2.yaml · · · · · · · · · · · · · · · · · · · · 124
LISTING 507: mycommand1.tex using Listing 508· · · · · · 125
LISTING 508: mycom-mlb3.yaml · · · · · · · · · · · · · · · · · · · · 125
LISTING 509: mycommand1.tex using Listing 510· · · · · · 125
LISTING 510: mycom-mlb4.yaml · · · · · · · · · · · · · · · · · · · · 125
LISTING 511: mycommand1.tex using Listing 512· · · · · · 126
LISTING 512: mycom-mlb5.yaml · · · · · · · · · · · · · · · · · · · · 126
LISTING 513: mycommand1.tex using Listing 514· · · · · · 126
LISTING 514: mycom-mlb6.yaml · · · · · · · · · · · · · · · · · · · · 126
LISTING 515: nested-env.tex · · · · · · · · · · · · · · · · · · · · · 126
LISTING 516: nested-env.tex using Listing 517· · · · · · 127
LISTING 517: nested-env-mlb1.yaml · · · · · · · · · · · · · · 127
LISTING 518: nested-env.tex using Listing 519· · · · · · 128
LISTING 519: nested-env-mlb2.yaml · · · · · · · · · · · · · · 128
LISTING 520: replacements · · · · · · · · · · · · · · · · · · · · · · · 129
LISTING 521: replace1.tex · · · · · · · · · · · · · · · · · · · · · · · 130
LISTING 522: replace1.tex default· · · · · · · · · · · · · · · · · 130
LISTING 523: replace1.tex using Listing 524· · · · · · · · 130
LISTING 524: replace1.yaml · · · · · · · · · · · · · · · · · · · · · · 130
LISTING 525: colsep.tex · · · · · · · · · · · · · · · · · · · · · · · · · 130
LISTING 526: colsep.tex using Listing 527 · · · · · · · · · · 131
LISTING 527: colsep.yaml · · · · · · · · · · · · · · · · · · · · · · · · 131
LISTING 528: colsep.tex using Listing 529 · · · · · · · · · · 131
LISTING 529: colsep1.yaml · · · · · · · · · · · · · · · · · · · · · · · 131
LISTING 530: colsep.tex using Listing 531 · · · · · · · · · · 132
LISTING 531: multi-line.yaml · · · · · · · · · · · · · · · · · · · · 132
LISTING 532: colsep.tex using Listing 533 · · · · · · · · · · 132
LISTING 533: multi-line1.yaml · · · · · · · · · · · · · · · · · · · 132
LISTING 534: displaymath.tex · · · · · · · · · · · · · · · · · · · · 133
LISTING 535: displaymath.tex using Listing 536 · · · · 133
LISTING 536: displaymath1.yaml · · · · · · · · · · · · · · · · · · 133
LISTING 537: displaymath.tex using Listings 536
and 538 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 134
LISTING 538: equation.yaml · · · · · · · · · · · · · · · · · · · · · · 134
LISTING 539: phrase.tex · · · · · · · · · · · · · · · · · · · · · · · · · 134
LISTING 540: phrase.tex using Listing 541 · · · · · · · · · · 134
LISTING 541: hspace.yaml · · · · · · · · · · · · · · · · · · · · · · · · 134
LISTING 542: references.tex · · · · · · · · · · · · · · · · · · · · · 135
LISTING 543: references.tex using Listing 544· · · · · · 135
LISTING 544: reference.yaml · · · · · · · · · · · · · · · · · · · · · 135
LISTING 545: verb1.tex · · · · · · · · · · · · · · · · · · · · · · · · · · 135
LISTING 546: verbatim1.yaml · · · · · · · · · · · · · · · · · · · · · 135
LISTING 547: verb1-mod1.tex · · · · · · · · · · · · · · · · · · · · · 136
LISTING 548: verb1-rv-mod1.tex · · · · · · · · · · · · · · · · · · 136
LISTING 549: verb1-rr-mod1.tex · · · · · · · · · · · · · · · · · · 136
LISTING 550: amalg1.tex · · · · · · · · · · · · · · · · · · · · · · · · · 136
LISTING 551: amalg1-yaml.yaml · · · · · · · · · · · · · · · · · · · 136
LISTING 552: amalg2-yaml.yaml · · · · · · · · · · · · · · · · · · · 136
[git] main @ 78d452f 2024-07-18 V3.24.4
LISTINGS 188
LISTING 553: amalg3-yaml.yaml · · · · · · · · · · · · · · · · · · · 136
LISTING 554: amalg1.tex using Listing 551 · · · · · · · · · · 136
LISTING 555: amalg1.tex using Listings 551 and 552 · 136
LISTING 556: amalg1.tex using Listings 551 to 553 · · · 136
LISTING 557: myfile.tex · · · · · · · · · · · · · · · · · · · · · · · · · 138
LISTING 558: myfile-mod1.tex · · · · · · · · · · · · · · · · · · · · 139
LISTING 559: myfile-mod2.tex · · · · · · · · · · · · · · · · · · · · 139
LISTING 560: myfile-mod3.tex · · · · · · · · · · · · · · · · · · · · 140
LISTING 561: myfile-mod4.tex · · · · · · · · · · · · · · · · · · · · 141
LISTING 562: myfile-mod5.tex · · · · · · · · · · · · · · · · · · · · 141
LISTING 563: myfile-mod6.tex · · · · · · · · · · · · · · · · · · · · 142
LISTING 564: myfile1.tex · · · · · · · · · · · · · · · · · · · · · · · · 142
LISTING 565: myfile1-mod1.tex · · · · · · · · · · · · · · · · · · · 143
LISTING 566: fineTuning · · · · · · · · · · · · · · · · · · · · · · · · · 144
LISTING 567: finetuning1.tex · · · · · · · · · · · · · · · · · · · · 146
LISTING 568: finetuning1.tex default · · · · · · · · · · · · · 146
LISTING 569: finetuning1.tex using Listing 570 · · · · 146
LISTING 570: finetuning1.yaml · · · · · · · · · · · · · · · · · · · 146
LISTING 571: finetuning2.tex · · · · · · · · · · · · · · · · · · · · 147
LISTING 572: finetuning2.tex default · · · · · · · · · · · · · 147
LISTING 573: finetuning2.tex using Listing 574 · · · · 147
LISTING 574: finetuning2.yaml · · · · · · · · · · · · · · · · · · · 147
LISTING 575: finetuning3.tex · · · · · · · · · · · · · · · · · · · · 147
LISTING 576: finetuning3.tex using -y switch · · · · · · 147
LISTING 577: finetuning4.tex · · · · · · · · · · · · · · · · · · · · 148
LISTING 578: href1.yaml · · · · · · · · · · · · · · · · · · · · · · · · · 148
LISTING 579: href2.yaml · · · · · · · · · · · · · · · · · · · · · · · · · 148
LISTING 580: finetuning4.tex using Listing 578 · · · · 148
LISTING 581: finetuning4.tex using Listing 579 · · · · 148
LISTING 582: href3.yaml · · · · · · · · · · · · · · · · · · · · · · · · · 149
LISTING 583: bib1.bib· · · · · · · · · · · · · · · · · · · · · · · · · · · · 149
LISTING 584: bib1-mod1.bib · · · · · · · · · · · · · · · · · · · · · · 149
LISTING 585: bib1.bib using Listing 586 · · · · · · · · · · · · 149
LISTING 586: bibsettings1.yaml · · · · · · · · · · · · · · · · · · 149
LISTING 587: bib2.bib· · · · · · · · · · · · · · · · · · · · · · · · · · · · 150
LISTING 588: bib2-mod1.bib · · · · · · · · · · · · · · · · · · · · · · 150
LISTING 589: bibsettings2.yaml · · · · · · · · · · · · · · · · · · 150
LISTING 590: bib2-mod2.bib · · · · · · · · · · · · · · · · · · · · · · 150
LISTING 591: finetuning5.tex · · · · · · · · · · · · · · · · · · · · 151
LISTING 592: finetuning5-mod1.tex · · · · · · · · · · · · · · 151
LISTING 593: finetuning3.yaml · · · · · · · · · · · · · · · · · · · 151
LISTING 594: finetuning6.tex · · · · · · · · · · · · · · · · · · · · 151
LISTING 595: finetuning6-mod1.tex · · · · · · · · · · · · · · 151
LISTING 596: fine-tuning4.yaml · · · · · · · · · · · · · · · · · · 151
LISTING 597: helloworld.pl · · · · · · · · · · · · · · · · · · · · · · 157
LISTING 598: alpine-install.sh · · · · · · · · · · · · · · · · · · 159
LISTING 599: settings.json · · · · · · · · · · · · · · · · · · · · · · 165
LISTING 600: settings-alt.json · · · · · · · · · · · · · · · · · · 165
LISTING 601: settings-alt1.json· · · · · · · · · · · · · · · · · 165
LISTING 602: docker-install.sh · · · · · · · · · · · · · · · · · · 167
LISTING 603: docker-install.sh · · · · · · · · · · · · · · · · · · 167
LISTING 604: .bashrc update · · · · · · · · · · · · · · · · · · · · · · 168
LISTING 605: .pre-commit-hooks.yaml (default) · · · · 168
LISTING 606: .pre-commit-config.yaml (cpan) · · · · · 169
LISTING 607: .pre-commit-config.yaml (conda) · · · · 169
LISTING 608: .pre-commit-config.yaml (docker) · · · 170
LISTING 609: .latexindent.yaml · · · · · · · · · · · · · · · · · · 170
LISTING 610: .pre-commit-config.yaml (demo) · · · · 171
LISTING 611: paths-demo.tex · · · · · · · · · · · · · · · · · · · · · 174
LISTING 612: path1.yaml · · · · · · · · · · · · · · · · · · · · · · · · · 174
LISTING 613: path2.yaml · · · · · · · · · · · · · · · · · · · · · · · · · 174
LISTING 614: paths-demo-mod1.tex· · · · · · · · · · · · · · · · 174
LISTING 615: path-test1.txt · · · · · · · · · · · · · · · · · · · · · 175
LISTING 616: path3.yaml · · · · · · · · · · · · · · · · · · · · · · · · · 175
LISTING 617: path4.yaml · · · · · · · · · · · · · · · · · · · · · · · · · 175
LISTING 618: path5.yaml · · · · · · · · · · · · · · · · · · · · · · · · · 175
LISTING 619: paths-demo-mod3.tex· · · · · · · · · · · · · · · · 175
LISTING 620: path-test3.txt · · · · · · · · · · · · · · · · · · · · · 176
LISTING 621: simple.tex · · · · · · · · · · · · · · · · · · · · · · · · · 177
LISTING 622: logfile-prefs1.yaml· · · · · · · · · · · · · · · · 177
LISTING 623: indent.log · · · · · · · · · · · · · · · · · · · · · · · · · 177
LISTING 624: Obsolete YAML fields from Version 3.0 · · · 180
LISTING 625: indentAfterThisHeading in Version
2.2 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 180
LISTING 626: indentAfterThisHeading in Version
3.0 · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · 180
LISTING 627: noAdditionalIndent in Version 2.2 · · · · 181
LISTING 628: noAdditionalIndent for
displayMath in Version 3.0 · · · · · · · · · · · · · · · · · · · · · · · · 181
LISTING 629: noAdditionalIndent for
displayMath in Version 3.0 · · · · · · · · · · · · · · · · · · · · · · · · 181
[git] main @ 78d452f 2024-07-18 V3.24.4
Index
B
backup files
cycle through, 25
extension settings, 24
maximum number of backup files, 25
number of backup files, 25
overwrite switch, -w, 12
overwriteIfDifferent switch, -wd, 13
bibliography files, 142
C
capturing parenthesis (regex), 40
comments
text wrap, 89, 104
conda, 11, 147, 156, 159
contributors, 147
cpan, 148, 159
D
delimiters, 116
advanced settings, 31
advanced settings of lookForAlignDelims, 30
ampersand &, 31
default settings of lookForAlignDelims, 31
delimiter justification (left or right), 40
delimiterRegEx, 40, 142
dontMeasure feature, 38
double backslash demonstration, 37
lookForAlignDelims, 31
poly-switches for double backslash, 114
spacing demonstration, 33
with specialBeginEnd and the -m switch, 116
within specialBeginEnd blocks, 48
docker, 11, 157, 160
E
exit code, 18
summary, 18
G
git, 159, 160
I
indentation
customising indentation per-code block, 52
customising per-name, 52
default, 15
defaultIndent description, 30
defaultIndent using -y switch, 15
defaultIndent using YAML file, 20
maximum indetation, 51
no additional indent, 52
no additional indent global, 52
removing indentation per-code block, 52
summary, 69
J
json
schema for YAML files, 155
VSCode, 155
L
latexindent-linux, 11, 148
latexindent-macos, 11, 149
latexindent.exe, 11
linebreaks
summary of poly-switches, 116
linux, 11, 148
M
macOS, 11, 149
MiKTeX, 11, 147
modifying linebreaks
at the beginning of a code block, 105
at the end of a code block, 107
by using one sentence per line, 91
surrounding double backslash, 114
using poly-switches, 104
P
perl
Unicode GCString module, 150
poly-switches
adding comments and then line breaks: set to
2, 106, 108
adding blank lines (again!): set to 4, 107
adding blank lines: set to 3, 106
adding blank lines (again!): set to 4, 109
adding blank lines: set to 3, 108
adding line breaks: set to 1, 105, 107
blank lines, 112
conflicting switches, 120
conflicting partnering, 119
conflicting switches, 121
default values, 105
definition, 104
double backslash, 116
environment global example, 105
environment per-code block example, 105
for double back slash (delimiters), 114
for double backslash (delimiters), 116
for double backslash (delimiters), 115, 117
[git] main @ 78d452f 2024-07-18 V3.24.4
LISTINGS 190
off by default: set to 0, 104
removing line breaks: set to -1, 110
summary of all poly-switches, 117
values, 104
visualisation: , , , , 105
pre-commit, 147
conda, 159
cpan, 159
default, 158
docker, 160
warning, 159
R
regular expressions
capturing parenthesis, 40
character class demonstration, 142
delimiter regex at \= or \>, 40
delimiter regex at only \>, 40
dontMeasure feature, cell, 38
dontMeasure feature, row, 39
horizontal space \h, 101, 129
keyEqualsValuesBracesBrackets, 137
lowercase alph a-z, 38, 96
NamedGroupingBracesBrackets, 137
substitution field, arraycolsep, 125
substitution field, equation, 127
UnNamedGroupingBracesBrackets, 137
uppercase alph A-Z, 94, 101
regular expressions
a word about, 9
ampersand alignment, 142
ampersand alignment, 31
arguments, 137
at least one +, 128
at least one +, 48
at least one +, 125, 137139
capturing parenthesis, 142
commands, 137
delimiter regex at #, 41
delimiter alignment for edge or node, 48
delimiter regex at # or \>, 41
delimiterRegEx, 31, 142
environments, 137
fine tuning, 137
horizontal space \h, 137
horizontal space \h, 48, 52, 128
ifElseFi, 137
lowercase alph a-z, 137
lowercase alph a-z, 39, 52, 91, 94, 101
modifyLineBreaks, 137
numeric 0-9, 52, 137
numeric 0-9, 48, 96, 101
replacement switch, -r, 124
text wrap
blocksFollow, 81, 82, 85
uppercase alph A-Z, 48
uppercase alph A-Z, 52, 91
uppercase alph A-Z, 137
using -y switch, 22
S
sentences
begin with, 94
begin with, 95
comments, 104
end with, 94, 96
follow, 94
indenting, 100
one sentence per line, 91
oneSentencePerLine, 91
removing sentence line breaks, 93
text wrap, 104
text wrapping, 100
specialBeginEnd
Algorithms example, 46
alignment at delimiter, 48
combined with lookForAlignDelims, 48
default settings, 43
delimiterRegEx, 48
delimiterRegEx tweaked, 48
double backslash poly-switch demonstration,
116
IfElsFi example, 45
indentRules example, 64
indentRulesGlobal, 69
introduction, 43
lookForAlignDelims, 116
middle, 45, 46
noAdditionalIndent, 64
noAdditionalIndentGlobal, 69
poly-switch summary, 117
searching for special before commands, 44
specifying as verbatim, 47
tikz example, 48
update to displaymath V3.0, 170
switches
–GCString, 18
–GCString demonstration, 150
-c, –cruft definition and details, 16
-d, –onlydefault definition and details, 16
-g, –logfile definition and details, 16
-h, –help definition and details, 12
-k, –check definition and details, 17
-kv, –checkv definition and details, 18
-l demonstration, 115, 117
-l demonstration, 22, 33, 38, 48, 51, 58, 59,
101, 124127, 139, 140
-l demonstration, 21, 3841, 45, 47, 48, 50,
51, 5466, 71, 72, 74, 90, 91, 93100,
102, 106109, 111114, 116, 119122,
124130
-l in relation to other settings, 22
-l, –local definition and details, 14
-lines demonstration, 131
-lines demonstration, negation, 134
-m demonstration, 107, 109, 111
-m demonstration, 91, 95, 97, 119, 120
-m demonstration, 76, 90, 93, 94, 96102,
106, 108, 112117, 120122, 127
-m, –modifylinebreaks definition and details,
16
-n, –lines definition and details, 18
-o demonstration, 37
-o demonstration, 41, 48, 90, 91, 129, 170
-o, –output definition and details, 13
-r demonstration, 127
[git] main @ 78d452f 2024-07-18 V3.24.4
LISTINGS 191
-r demonstration, 123130
-r, –replacement definition and details, 17
-rr demonstration, 129
-rr demonstration, 126
-rr, –onlyreplacement definition and details,
17
-rv demonstration, 129
-rv, –replacementrespectverb definition and
details, 17
-s, –silent definition and details, 14
-sl, –screenlog definition and details, 16
-t, –trace definition and details, 14
-tt, –ttrace definition and details, 14
-v, –version definition and details, 12
-vv, –vversion definition and details, 12
-w, –overwrite definition and details, 12
-wd, –overwriteIfDifferent definition and
details, 13
-y demonstration, 22, 37, 101
-y, –yaml definition and details, 15
T
TeXLive, 11, 148, 149
text wrap
blocksFollow, 79
comments, 80
headings, 79
other, 81, 82, 85
comments, 89
text wrap
blocksBeginWith, 83
blocksEndBefore, 85
comments, 104
quick start, 78
setting columns to -1, 78
V
verbatim
commands, 26
comparison with -r and -rr switches, 129
environments, 26
in relation to oneSentencePerLine, 99
noIndentBlock, 27
poly-switch summary, 117
rv, replacementrespectverb switch, 123
rv, replacementrespectverb switch, 17
specialBeginEnd, 47
verbatimEnvironments demonstration (-l
switch), 21
verbatimEnvironments demonstration (-y
switch), 22
VSCode, 147, 155
W
warning
amalgamate field, 74
be sure to test before use, 2
capture groups, 139
capturing parenthesis for lookForAlignDelims,
40
changing huge (textwrap), 90
editing YAML files, 21
fine tuning, 137
pre-commit, 159
the m switch, 76
Windows, 11