Take the 2-minute tour ×
TeX - LaTeX Stack Exchange is a question and answer site for users of TeX, LaTeX, ConTeXt, and related typesetting systems. It's 100% free, no registration required.

I have a plot consisting of two y-axis. When I'm adding the legendentries in each axis environment, the first legendentry will be plotted "behind" the plot of the second axis. Thus I thought a solution might be the \ref \label to plot both legendentries at the end of the document, that they will appear in the very front of all plots and not hidden. Unfortunately using the tikz externalization gives the error "undefined references ...." and the legendentries are given with "??" only. I checked the manual for using \legend \ref with externalization, but it doesn't help. I tried to compile several times.

\documentclass[fontsize=12pt,openright,oneside,DIV11,a4paper,numbers=noenddot,headsepline,parskip=half]{scrbook}
\usepackage[latin1]{inputenc}
\usepackage[cmex10]{amsmath}
\usepackage{siunitx}
\usepackage{tikz}
\usetikzlibrary[shapes.arrows]
\usepackage{pgfplots}
\pgfplotsset{compat=1.3}

% set up externalization
\usetikzlibrary{pgfplots.external}
\tikzset{external/system call={lualatex \tikzexternalcheckshellescape -halt-on-error -interaction=batchmode -jobname "\image" "\texsource"}}
\tikzexternalize


\begin{document}
\thispagestyle{empty}
    \begin{tikzpicture}
        \begin{axis}[
                legend cell align=left,
            bar width=7pt,
            xmin=-3, xmax=30,
            axis y line*=left,
            xlabel=Laser current / \si{\milli\ampere},
            ylabel=Tuning range / \si{\nano\metre},
            nodes near coords align=left,
            nodes near coords,]
        \addplot[ybar, ybar legend, draw=gray, fill=gray, color=gray] table[x=current,y=tuning] {Tun_SMSR.txt};

%          \addlegendentry{Abstimmbereich};
       \label{Abstimmbereich};
    \end{axis}

    \begin{axis}[
            every axis legend/.append style={fill=white, anchor=north west, at={(0.35,0.18)}},
            legend cell align=left,
            ybar=5pt,
            ybar interval=0.6,
            bar width=7pt,
            xmin=-3, xmax=30,
            ymin=30, ymax=60,
            axis y line*=right,
            axis x line=none,
            ylabel=SMSR / \si{\deci\bel},
            nodes near coords align=left,
            nodes near coords,]
        \addplot[ybar, ybar legend, draw=black, color=black] table[x=current,y=SMSR] {Tun_SMSR.txt};
       \label{SMSR};
%          \addlegendentry{SMSR};

    \end{axis}

\node [draw,fill=white] at (rel axis cs: 0.7,0.15) {\shortstack[l]{
\ref{Abstimmbereich} Abstimmbereich\\
\ref{SMSR} SMSR
}};

    \end{tikzpicture}
\end{document}

I'm compiling with the command

lualatex -shell-escape "document name".tex

The resulting figure shows the legends but with no symbols and "??" instead.

share|improve this question
add comment

1 Answer

up vote 3 down vote accepted

You are referring to a label which has been externalized to a separate pdf - which is a complex task.

Here, "complex" means "too complex for the standard -shell-escape image externalization". In order to reference something inside of some external image, you have to take special steps.

To quote from the pgfplots manual: "For point a), a \ref inside of an externalized graphics works only if you issue the required system call manually or by make. The initial configuration mode=convert with system calldoes not support \ref. But you can copy­paste the system call generated by mode=convert with system call and issue it manually. The reason is that \ref information is stored in the main .aux file ­ but this auxiliary file is not completely written when mode=convert with system call is invoked (there is a race condition). Note that \pageref is not supported (sorry). Thus: if you have \ref inside of external graphics, consider using mode=list and make or copy­paste the system call for the image(s) and issue it manually."

Alternatively, you can wait (say) one week until the next version of pgfplots is released. It supports layered graphics such that the first legend will not appear behind the second axis.

Another altivernative solution might be to insert a legend entry for the first plot into the legend of the second image using \addlegendimage{<style>}:

\documentclass{standalone}
\usepackage{pgfplots}
\pgfplotsset{compat=1.3}

\begin{document}
    \begin{tikzpicture}
    \pgfplotsset{
        plot 0/.style={
            ybar, ybar legend, draw=gray, fill=gray, color=gray
        }
    }
       \begin{axis}[
                legend cell align=left,
            bar width=7pt,
            xmin=0, xmax=1,
            axis y line*=left,
            xlabel=Laser current,
            ylabel=Tuning range,
            nodes near coords align=left,
            nodes near coords,]
        \addplot[plot 0] {rand};

%          \addlegendentry{Abstimmbereich};
 %      \label{Abstimmbereich};
    \end{axis}

    \begin{axis}[
            every axis legend/.append style={fill=white, anchor=north west, at={(0.35,0.18)}},
            legend cell align=left,
            ybar=5pt,
            ybar interval=0.6,
            bar width=7pt,
            xmin=0, xmax=1,
            ymin=30, ymax=60,
            axis y line*=right,
            axis x line=none,
            ylabel=SMSR,
            nodes near coords align=left,
            nodes near coords,]

\addlegendentry{Abstimmbereich}
\addlegendimage{plot 0}
        \addplot[ybar, ybar legend, draw=black, color=black] {30 + rand*30};
       \label{SMSR};
          \addlegendentry{SMSR};

    \end{axis}

    \end{tikzpicture}
\end{document}

enter image description here

Note that I have deliberately stripped the example from your data files and some other stuff - the only point here is the special legend construction. This does also work with image externalization.

In order to share the common options, I extracted the style for your first plot and used it at two places (this has the same effect as \label{Abstimmbereich} and refstyle={Abstimmbereich}, but it integrates seamlessly into the image externalization workflow).

share|improve this answer
    
Hi Christian, this was what I read in the manual as well, but I didn't get the point what it means by "making it manually". I found out that I have to set up the lualatex first with: lualatex -halt-on-error -interaction=batchmode -jobname "filename-figure0" "\def \tikzexternalrealjob {filename}\input {filename}" and removed: \tikzset{external/system call={lualatex \tikzexternalcheckshellescape ... from the tex-document.Then I compiled with: lualatex -shell-escape filename.tex and the figure looks now as I want it to look like. I Guess thats what the manual is saying by manually? –  Christian Aug 17 '12 at 9:47
    
Ah, not quite. "make it manually" means that you have to open a windows command prompt (or linux shell) and type the command lualatex -halt-on-error -interaction=batchmode -jobname "filename-figure0" "\def \tikzexternalrealjob {filename}\input {filename}" –  Christian Feuersänger Aug 17 '12 at 9:58
    
Also see my edit: I added a fully working example which relies on \addlegendimage and avoids all problems of image externalization. –  Christian Feuersänger Aug 17 '12 at 9:59
    
Yes I forgot to mention that I used the command prompt. Thanks for your help! –  Christian Aug 20 '12 at 7:41
add comment

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.