61

I want to create a TikZ picture in an external PDF file, which then can be included in my main document via \includegraphics. However, compiling a document with a TikZ picture in it produces a whole page, meaning lots of white space.

What I want to do can be done using the preview package as described in Standalone diagrams with TikZ?, on SO. But there are some problems with the preview package and XeTex (see Transparency in tikz, preview package and xelatex).

Since creating standalone pictures seems like a natural thing to ask, I am hoping for a different, and maybe more elegant, solution.

Emerson
  • 3,530

3 Answers3

78

You can use the standalone class for this. In v0.x it used preview internally, but for v1.x it also has an alternative crop option, which works similar to the preview option/package, but avoids its issues with XeTeX.

There is now (v1.0) also a tikz class option which turns any (outer) tikzpicture into a single tight page. This avoids issues with trailing implicit paragraphs. In addition it automatically loads the tikz package.

% tikzpic.tex
\documentclass[crop,tikz]{standalone}% 'crop' is the default for v1.0, before it was 'preview'
%\usetikzlibrary{...}% tikz package already loaded by 'tikz' option
\begin{document}
\begin{tikzpicture}
  \draw (0,0) -- (10,10); % ...
\end{tikzpicture}
\end{document}

Then compile it as usual with pdflatex or xelatex etc.

To include this tikzpicture into a main document load the standalone package there with the option mode=buildnew. Then use \includestandalone[<options>]{<filename>} instead of \includegraphics. This will compile all includes standalone files automatically as graphics and build these graphics if the source file is newer than the existing graphics file. This needs -shell-escape to be enabled to allow the main LaTeX run to call further LaTeX compilers. See the standalone manual for more details.

% main.tex
% compile with `pdflatex -shell-escape main` or `xelatex  -shell-escape main`
\documentclass{article}
\usepackage[mode=buildnew]{standalone}% requires -shell-escape
\usepackage{tikz}
%\usetikzlibrary{...}
\begin{document}
Lorem ipsum ...

\includestandalone[width=.8\textwidth]{tikzpic}

Lorem ipsum ...
\end{document}
Martin Scharrer
  • 262,582
  • 9
    mv standalone.cls swiss-army-knife.cls. Is there anything the standalone class can't do? – Andrew Stacey Apr 13 '12 at 11:48
  • @AndrewStacey: Yes, it doesn't include much support for math yet, especially displaymath. – Martin Scharrer Apr 13 '12 at 11:56
  • Unless I have something mis-configured (or my XeTeX is too old), mode=buildnew does not work with XeTeX. – Blair May 20 '13 at 01:39
  • @Blair: buildnew requires some pdfTeX primitive to read the file date which isn't available in XeTeX. I think I need to update the manual accordantly. – Martin Scharrer May 20 '13 at 08:25
  • @MartinScharrer OK, thanks for clarifying that. You might want to edit your final example here too :). Thanks for all the useful packages you have written also. – Blair May 20 '13 at 10:22
  • I tried to add this animation: http://www.texample.net/media/tikz/examples/TEX/animated-definite-integral.tex with this method to another document; but I was not successful. The resulting pdf was empty! Is there any idea? – Mahmood Amintoosi Aug 19 '15 at 20:01
  • 1
    The top code does not run in LuaLatex either. (I was unfortunately forced to switch to LuaLatex because it is required to use the tikz-feynman package.)

    I see in the comments above that a similar statement was made about XeTeX. But that was years ago, why does the answer still state quite optimistically: " Then compile it as usual with pdflatex or xelatex etc." when only pdflatex can be used.

    – Marten Sep 29 '17 at 15:38
  • @MartinScharrer Does this way of building a tikz file only if source file is newer work also if the tikz file is including data from another data file? – Abhinav May 31 '18 at 13:48
  • @Abhinav: No, it only checks the .tex and the .PDF file modification dates. – Martin Scharrer May 31 '18 at 15:54
8

I ended up using the external library, as diabonas suggested.

Here's an example with XeTeX:

\documentclass{article}

\usepackage{fontspec}
    \setmainfont[Mapping=tex-text]{Linux Libertine O}

\usepackage{tikz}
    \definecolor{blue}{cmyk}{1,1,0,0.07}

\usetikzlibrary{external}
\tikzexternalize
\tikzset{external/system call={xelatex \tikzexternalcheckshellescape -halt-on-error -interaction=batchmode -jobname "\image" "\texsource"}}
\tikzset{external/force remake=true} 

\begin{document}

\tikzstyle{place}=[circle,draw=blue,fill=blue!20,line width=2pt]

\begin{tikzpicture}
    \node at (0,0) [place] {Ti\textit{k}Z};
\end{tikzpicture}

\end{document}

One has to compile using -shellescape.

A minor inconvenience is, that the appropriately cropped file is named <filename>-figure0.

Emerson
  • 3,530
  • 3
    You can change the filenames, it's described in the manual how. Edit: Add \tikzsetnextfilename{file name} before a tikzpicture. The name will only apply to the next tikzpicture or \tikz command. – Torbjørn T. Oct 22 '11 at 16:09
  • @Torbjorn: Thanks, that's useful. Unfortunately, one still ends up with two output files. – Emerson Oct 23 '11 at 12:29
  • I usually get headache when using external library due to a) pdflatex runs out of memory very soon; and 2) When using lualatex, it stops working : which can be resolved by putting \RequirePackage{luatex85,shellescp} at the top of your documents (at least with texlive-2016 on openSUSE-42.2. – Dilawar Jan 19 '17 at 06:53
4

Perhaps a combination of standard article class and pdfcrop or the cropping facilities of adjustbox would be a work around.

So, you make the picture in a separate file with article class, for instance. Then you use clipbox from the adjustbox package to clip the image included via \includegraphics to the part you actually want...

Seamus
  • 73,242
  • But the standalone package uses preview internally so is subject to the same problems as preview with xelatex (see link in the question). – Andrew Stacey Oct 20 '11 at 09:41
  • @AndrewStacey Yes I'd misread the question. Fixed now. – Seamus Oct 20 '11 at 09:53
  • 2
    Before using pdfcrop, don't forget to include \thispagestyle{empty} in your source otherways you will get the page number which will be include into cropped result. – Ignasi Oct 20 '11 at 10:29