[Tex/LaTex] Tikz externalization and directory questions

tikz-externaltikz-pgf

I store my exercices in the following way :

  • Super directory Base_Exos on witch points the $TEXINPUTS variable.
  • Sub-directories, one by class level.
  • Sub-Sub-directies, one by chapter
  • Sub-Sub-Sub-directories, one by exercice. This S-S-S-directory contains the text called texte.tex with eventually the correction called corrige.tex and eventually some pictures.

I can use any exercice in a main.tex file witch is far from Base_Exos by :

\input{3_eme/Droites/exo-002/texte}

if this texte.tex contains a picture reference, it is :

\includegraphics{3_eme/Droites/exo-002/picture-1}

Now, I want to use external tikz library and it has still compatible with my Personal Directory System and I don't want to externalize all tikzpicture, just the heavy ones.

That means, that want that the pdf picture produced by the externalization procedure are produced in the same directory than witch the texte.tex file is
stored, not in the directory where main.tex is.

So far, I did in main.tex :

My pranbule
\usetikzlibrary{external}
\tikzexternalize % activate
\tikzexternaldisable % disable for most pictures
\begin{document}
\input{3_eme/Droites/exo-002/texte}
\end{document}

in 3_eme/Droites/exo-002/texte file

...
\tikzexternaldisable
\begin{tikzpicture}
...
\end{tikzpicture}
\tikzexternaldisable
...

But the pdf is produced in the main.tex file directory instead of in the texte.tex one.

Questions

  1. How to set the multiple option command to produce the pdf file in the texte.tex directory ?
  2. How to have this pdf files independant from the main.tex file, ie if I include the same texte.tex in two different main.tex, no new pdf file will be produced, then no second loss of time ?

Best Answer

I hope I fully understood what you requested. Here goes.

\tikzexternalize accepts a prefix parameter which tells pdflatex where to store the externalised graphics. So even if you use \input in main.tex to include exercises with tikzpictures, you can set prefix=<something> in main.tex to let pdflatex know that externalised graphics should be stored in that directory – specifically, you want them in the directory of the exercise. You can also separate the code from the processing by saving the externalised graphics in a sub-directory where all exercises of a chapter are stored. Here I use external as the directory.

% Macro holding the exercises directory name (in main.tex).
\newcommand{\exercisesdirectory}{aclass/achapter/exercises/}
% Macro holding the externalized sub-directory (in main.tex).
\newcommand{\externaldirectory}{aclass/achapter/exercises/external/}
\usepackage{tikz}
\usetikzlibrary{external}
% All externalized graphics go go the \externaldirectory
\tikzexternalize[prefix=\externaldirectory]
% Externalise only on-demand.
\tikzexternaldisable

There is a caveat, however: if your main file is not always named main.tex, then the external library will re-externalise graphics with a new filename (I believe the format is \jobname-figureX where X is a running counter starting from 0. This is not what you want; you want to avoid re-externalisation. Thankfully, this issue can be easily circumvented by letting pdflatex know what the externalised graphic should be named using \tikzsetnextfilename:

\tikzexternalenable
\tikzsetnextfilename{ex1fig1} % This graphic will always be named ex1fig1.
\begin{tikzpicture}
  % Move along. Nothing to see here.
\end{tikzpicture}%
\tikzexternaldisable

This means that if this exercise is \input in a file main.tex and a file file.tex compiled with pdflatex -shell-escape, the external library will only create the figure if ex1fig1.pdf does not exist (or if something has changed in the tikzpicture environment etc.)


With all that in mind, your main .tex file would look like this:

main.tex

\documentclass{article}

% The path to the exercises.
\newcommand{\exercisesdirectory}{aclass/achapter/exercises/}
% The path where externalised graphics will be stored.
\newcommand{\externaldirectory}{aclass/achapter/exercises/external/}
% Will be used to store the path to the exercise to be processed.
\newcommand{\pathtoexercise}{}

\usepackage{tikz,pgfplots}
\usetikzlibrary{external}
% All auxiliary files and externalised graphics go to \externaldirectory.
\tikzexternalize[prefix=\externaldirectory]
% Only externalise on-demand.
\tikzexternaldisable

% In case you want to include externalised graphics directly.
\graphicspath{ {\externaldirectory} }

\begin{document}
% This will combine the \exercisesdirectory and "firstexercise.tex" strings,
% and store them in \pathtoexercise.
\expandafter\def\expandafter\pathtoexercise\expandafter{\exercisesdirectory firstexercise.tex}
% Then we simply input \pathtoexercise.
\input{\pathtoexercise}
\end{document}

Where firstexercise.tex is stored in aclass/achapter/exercises/.

firstexercise.tex:

This is some text from the first exercise. Below are some cool graphics.

\tikzexternalenable
\tikzsetnextfilename{ex1fig1}
\begin{tikzpicture}
  \begin{axis}[%
    scale only axis,
    width=5cm,
    height=5cm,
  ]

    \addplot[red,samples=10] {rnd};

  \end{axis}
\end{tikzpicture}%
\tikzexternaldisable

If you want to include only externalised graphics instead of the whole firstexercise.tex, all you need to do is to set the graphicspath in main.tex to the \externaldirectory, like so: \graphicspath{ {\externaldirectory} }. Thereafter, you simply use \includegraphics with the figure filename, like so:

% \includegraphics will automatically search in the graphicspath directory.
\begin{figure}
\centering
\includegraphics{ex1fig1.pdf} % This is actually in aclass/achapter/exercises/external/ex1fig1.pdf
\caption{Exercise $1$, Figure $1$}
\label{fig:ex1fig1}
\end{figure}

I hope this makes at least some sense and that it is in fact what you requested.