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 part of my plot that I want to repeat several times.

To be exact, the part I want to replicate is:

\draw[yscale=2.0,yshift=-3,xscale=0.1,domain=0:10] plot[id=gauss1] function{exp(-(x-5)*(x-5)/2/2/2.0)/sqrt(pi)/2};
\draw[yscale=2.0,yshift=-3,xscale=0.1,domain=5:15] plot[id=gauss2] function{exp(-(x-10)*(x-10)/2/2/2.0)/sqrt(pi)/2};

I want to place this same function in multiple places in my tikz matrix (I want to repeat this two exact statements on multiple places)

What is the best way of doing this? Is there a way to not copy-paste this?

I tried including this with \input{sometexfile} but that does give compile errors.

share|improve this question
add comment

4 Answers

up vote 12 down vote accepted

To fill in @philosodad's first way, this does what you want and obeys DRY:

\begin{scope}[yscale=2.0,yshift=-3,xscale=0.1]
  \foreach \i/\mu/\xmin/\xmax in {1/5/0/10,2/10/5/15} {
    \draw[domain=\xmin:\xmax] plot[id=gauss\i] function{exp(-(x-\mu)*(x-\mu)/2/2/2.0)/sqrt(pi)/2};
  }
\end{scope}

The scope environment isn't required (you can put those options on the \draw line) but it does make the line shorter. :-)

If you want to put that in multiple places, just assign it to a box.

\usetikzlibrary{matrix}

\newsavebox{\gaussians}
\savebox{\gaussians}{
  \begin{tikzpicture}
    \begin{scope}[yscale=2.0,yshift=-3,xscale=0.1]
      \foreach \i/\mu/\xmin/\xmax in {1/5/0/10,2/10/5/15} {
        \draw[domain=\xmin:\xmax] plot[id=gauss\i] function{exp(-(x-\mu)*(x-\mu)/2/2/2.0)/sqrt(pi)/2};
      }
    \end{scope}
  \end{tikzpicture}
}

\begin{tikzpicture}
  \node[matrix of nodes] {
    \usebox{\gaussians} & foo & \usebox{\gaussians} \\
    bar & \usebox{\gaussians} & baz \\
  };
\end{tikzpicture}

Edit: Following Yossi's suggestion, I rewrote this to use a saved box rather than a macro.

share|improve this answer
    
Maybe I was not completely clear. It is not a single draw command I want to repeat, but the two draw commands together that I want to do in multiple tikz matrix cells. I can't think of doing that with foreach. –  Peter Smit Oct 26 '10 at 13:15
2  
Answer edited... –  Matthew Leingang Oct 26 '10 at 13:37
2  
you could even define newcommand{\gaussians}{\usebox{\gaussianbox}} –  Yossi Farjoun Oct 26 '10 at 21:24
1  
I might be wrong, but it looks like it does not work when you externalize the rendering of tikz pictures in order to produce PDFs (I need it to generate html with tex4ht). The tikz picture of the savebox is saved as PDF, whereas the tikz picture that uses the savebox gets lost. –  mmj Jun 16 '13 at 6:53
add comment

I think there are two ways to do this.

If you need to repeat the statements consistently enough to design a for loop, the Tikz foreach statement might be the correct move.

If you want to use basic text replacement, you should be able to define either a tikzstyle or a TeX macro to replace the longer statement.

share|improve this answer
2  
Perhaps supplement your answer with an example: \necommand{\repeatgraph}{\draw[yscale etc... –  Seamus Oct 26 '10 at 11:57
add comment

People seem to be answering a different question...I may be wrong but I think you are looking for \savebox? Would this not save latex from re-rendering the TikZ code every time? I don't know how many times you need to put those plots in your document, but if you are going to define a macro to do it, you may consider putting the whole thing in a \savebox:

\newsavebox{\myneatfigurethatineedalot}
\savebox{\myneatfigurethatineedalot}{

A bunch of latex code, tikz and 

what-not that you need to place on every corner of every page

}

\usebox{\myneatfigurethatineedalot} %use this wherever you want it!

I think that \savebox is better than a macro in this case, because a) what is in the box is self-contained (the typesetting of the content of the box does not depend on the location in the text) and b) it is relatively expensive to render and by using a \savebox you are telling the texengine to simply reuse the result of the rendering, while the macro would tell it to re-render everything from scratch.

share|improve this answer
2  
Not a bad idea. –  Matthew Leingang Oct 26 '10 at 20:13
    
Just to be sure, I checked it with a forloop, it is much much faster using savebox, than with a simple macro. ( I tried with a for loop that iterated 100 times). –  Yossi Farjoun Oct 26 '10 at 21:51
add comment

The PGF manual speaks of the two following commands:

\pgfsys@defobject{⟨name⟩}{⟨lower left⟩}{⟨upper right⟩}{⟨code⟩}
Declares an object for later use. The idea is that the object can be precached in some way and then be rendered more quickly when used several times. For example, an arrow head might be defined and prerendered in this way. The parameter ⟨name⟩ is the name for later use. ⟨lower left⟩ and ⟨upper right⟩ are pgf points specifying a bounding box for the object. ⟨code⟩ is the code for the object. The code should not be too fancy. This command has a default implementation and need not be implemented by a driver file.

\pgfsys@useobject{⟨name⟩}{⟨extra code⟩}
Renders a previously declared object. The first parameter is the name of the the object. The second parameter is extra code that should be executed right before the object is rendered. Typically, this will be some transformation code. This command has a default implementation and need not be implemented by a driver file.

Unfortunately I never understood how those work, so consider this as an extended comment or a new question related to the original.

share|improve this answer
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.