23

I would like to use tikz * and o arrows to indicate included/excluded endpoints in plots of piecewise functions, like for example the following one:

Sample plot

However, it seems that tikz always aligns the "tip" of the arrow with the end of the line, so that the code

\documentclass{article} 
\usepackage{tikz}
\usetikzlibrary{arrows}
\begin{document}
\begin{tikzpicture}
   \draw[help lines] (-.1,-.1) grid (2.1,2.1);
   \draw[thick,-*] (0,1.5) -- (1,.5);
   \draw[thick,o-] (1,1.5) -- (2,.5);
\end{tikzpicture}
\end{document}

produces

tikz arrows (incorrect alignment)

where I would like the circles to be vertically aligned on the grid line.

Is there a parameter or code I can modify to get the desired behavior?

17

There are the shorten < and shorten > option which allow you to shorten the arrow length from the start and end of the line, respectively. It also accepts negative values which then extend the arrow head forwards:

\documentclass{standalone}
\usepackage{tikz}
\usetikzlibrary{arrows}
\begin{document}
\begin{tikzpicture}[shorten >=-3pt,shorten <=-3pt]
   \draw[help lines] (-.1,-.1) grid[step=.5] (2.1,2.1);
   \draw[thick,-*] (0,1.5) -- (1,.5);
   \draw[thick,o-] (1,1.5) -- (2,.5);
\end{tikzpicture}
\end{document}

The 3pt was just a lucky guess, but seems to be the correct value for this arrow heads.

Result:

Result

  • Thank you, I somehow missed the shorten > option. – Jan Hlavacek Feb 24 '11 at 3:58
  • 3
    The exact value is 1.8pt+1.4\pgflinewidth which is 2.92pt for a thick line. – Luigi May 20 '13 at 17:48
  • @Luigi: Where did you get the information about the exact value? – Dr. Manuel Kuehner May 21 '13 at 12:32
  • 1
    @ManuelKuehner from the code of the arrowhead. The radius of the circle line included is 4.5\pgfutil@tempdima + 0.5\pgflinewidth (see Jake's answer for the code), hence you have to move the center by this quantity taking into account that thick means line width=0.8pt. – Luigi May 21 '13 at 17:51
12

If you want to avoid having to guess the value for the shorten < key, you can define new arrow heads that will place the circles precisely at the specified coordinate:

\documentclass[]{standalone}

\usepackage{tikz}
\usepackage{pgfplots}
\usepgflibrary{arrows}

\makeatletter
\pgfarrowsdeclare{center*}{center*}
{
  \pgfarrowsleftextend{+-.5\pgflinewidth}
  \pgfutil@tempdima=0.4pt%
  \advance\pgfutil@tempdima by.2\pgflinewidth%
  \pgfarrowsrightextend{4.5\pgfutil@tempdima}
}
{
  \pgfutil@tempdima=0.4pt%
  \advance\pgfutil@tempdima by.2\pgflinewidth%
  \pgfsetdash{}{+0pt}
  \pgfpathcircle{\pgfqpoint{4.5\pgfutil@tempdima}{0bp}}{4.5\pgfutil@tempdima}
  \pgfusepathqfillstroke
}

\pgfarrowsdeclare{centero}{centero}
{
  \pgfarrowsleftextend{+-.5\pgflinewidth}
  \pgfutil@tempdima=0.4pt%
  \advance\pgfutil@tempdima by.2\pgflinewidth%
  \pgfarrowsrightextend{4.5\pgfutil@tempdima}
}
{
  \pgfutil@tempdima=0.4pt%
  \advance\pgfutil@tempdima by.2\pgflinewidth%
  \pgfsetdash{}{+0pt}
  \pgfpathcircle{\pgfqpoint{4.5\pgfutil@tempdima}{0bp}}{4.5\pgfutil@tempdima}
  \pgfusepathqstroke
}
\makeatother

\begin{document}
\begin{tikzpicture}
   \draw[help lines] (-.1,-.1) grid (2.1,2.1);
   \draw[thick,-center*] (0,1.5) -- (1,.5);
   \draw[thin,centero-] (1,1.5) -- (2,.5);
\end{tikzpicture}
\end{document}
  • I think it's not as simple as you imagine. – Luigi May 20 '13 at 18:24
  • Ok. I'm sorry. The left extend is correct, but the right extend should simply be 4.5\pgfutil@tempdima if you want the center of the circle at the end of the line (IMHO). – Luigi May 20 '13 at 18:34
  • @Luigi: Yes, that seems right. Edited, thank you! – Jake May 20 '13 at 18:40
  • 2
    Thanks, this is great! I packaged it and placed it on github: github.com/lahvak/intervalarrows – Jan Hlavacek Oct 9 '15 at 2:25

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

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