Sometimes, I define new commands such as the following.
\newcommand{\comment}[1]{\textbf{#1}}
%\necommand{\comment}[1]{\emph{#1}}
The above commands enable me to change the style of parts of my code all at once. If I want to generate both of the possible styles, I have to compile my LaTeX document two times each time modifying the source code to enable the desired style.
Is there a way to avoid the source code modification in such cases? That is, can I pass latex some command-line arguments so that I can choose which style to use based on that argument?
That is, can I pass latex some command-line arguments so that I can choose which style to use based on that argument?
Yes. Three options:
One
In your source file, write
\providecommand{\comment}[1]{\emph{#1}}% fallback definition
and then compile the LaTeX document ("myfile.tex") as
pdflatex (whatever options you need) "\newcommand\comment[1]{\textbf{#1}}\input{myfile}"
Two
Alternatively,
pdflatex "\let\ifmyflag\iftrue\input{myfile}"
and then have in the source
\ifcsname ifmyflag\endcsname\else
\expandafter\let\csname ifmyflag\expandafter\endcsname
\csname iffalse\endcsname
\fi
...
\ifmyflag
\newcommand\comment[1]{\emph{#1}}
\else
\newcommand\comment[1]{\textbf{#1}}
\fi
Three
Or even
pdflatex "\def\myflag{}\input{myfile}"
with
\ifdefined\myflag
\newcommand\comment[1]{\emph{#1}}
\else
\newcommand\comment[1]{\textbf{#1}}
\fi
which is probably the shortest, albeit slightly fragile because you never know when a package might define \myflag
behind your back.
You should use Will's approaches when you need fairly flexible one-off options, like say changing the position line on your resume. If otoh you are producing the same selection of options over & over, then you should consider avoiding command line arguments, or working them into a build script or makefile.
I'll give two techniques for avoiding command line arguments :
Trick 1: If you're producing a fixed array of documents that must remain accessible, like your two styles example, then I'd recommend simply implementing Will's latex code inside another tex file, i.e. thesis.tex contains a \providecommand\comment[1]{\emph{#1}}
and thesis-ugly.tex consists of \newcommand\comment[1]{\textbf{#1}} \input thesis.tex
.
You must of course rerun tools like bibtex when using this technique, unless you symlink the intermediary files, ala ln -s thesis.aux thesis-ugly.aux
and ln -s thesis.bbl thesis-ugly.bbl
.
Trick 2: I found trick 1 awkward for changing document papersizes, so I wrote the following perl script, called simply papersize. The command papersize A4 teaching.tex
modifies teaching.tex in place, and symlinks teaching.pdf to teaching-A4.pdf, so that running pdflatex teaching
creates teaching-A4.pdf, but does not disturb the pre-existing teaching-letter.pdf and does not require rerunning bibtex teaching
. It does obviously require rerunning pdflatex twice for documents with internal references.
#!/usr/bin/perl -i~ -n
BEGIN {
die "Usage: papersize letter/A4/etc. [filename]\n" if ($#ARGV < 0);
$SIZE = shift @ARGV; @files=@ARGV;
$FLAG = "% paper size :: ";
}
if (/$FLAG(\w+)/) {
if ($1 eq $SIZE) {
s/^\% //;
} else {
s/^([^\%])/\% \1/;
}
}
print $_;
END {
foreach (@files) {
if (s/\.tex//) {
$l = "$_-$SIZE.pdf"; $_ .= ".pdf";
unlink($_) if (-l $_);
symlink($l,$_) if (! -e $_);
} }
}
You must add the special comments % paper size :: ...
to every file line that should be changed when you change the paper size.
\documentclass[letterpaper,11pt]{article} % paper size :: letter
% \documentclass[a4paper,11pt]{article} % paper size :: A4
\usepackage[text={6.5in,8.8in}]{geometry} % paper size :: letter
% \usepackage[text={16.4cm,24.5cm}]{geometry} % paper size :: A4
You could obviously work papersize into a build script or makefile too or modify the above script for .dvi files.. or generalize the script to other modifications.
To provide my dissertation in both the required, ugly, tree wasting format, and a compact prettier version, I used ifthen
an a kludge of make
and sed
that rewrote a bit of the header.
I think Will's approaches are all nicer.