8

I am drawing shapes with TikZ and I would like to selectively draw the borders around it:

\documentclass{standalone}

\usepackage{tikz}

\begin{document}


\begin{tikzpicture}[scale=3., line width=1pt]

\coordinate (a) at (0,0);
\coordinate (b1) at (1,1);
\coordinate (c1) at (2,0);
\coordinate (b2a) at (0.7,-1);
\coordinate (b2b) at (0.9,-1.2);
\coordinate (b2c) at (1.1,-1.2);
\coordinate (b2d) at (1.3,-1);

\draw[fill=green!10!white] (a) .. controls +(0,0.5) and +(-0.5,0) ..
      (b1) .. controls +(0.5,0) and +(0.,0.5) ..
      (c1) .. controls +(0.,-0.5) and +(0.5,0.2) ..
      (b2d) .. controls +(-0.125,-0.05) and +(-0.,0.05) ..
      (b2c)
      -- % I want to skip this line!
      (b2b) .. controls +(0.,0.05) and +(0.125,-0.05) ..
      (b2a) .. controls +(-0.5,0.2) and +(0,-0.5) .. (a);

\end{tikzpicture}

\end{document}

enter image description here

But I would like to obtain:

enter image description here

For the bottom figure I drew three times: once the filling only (draw=none), then half of the border with no filling (stoping at coordinate (b2c)), then the other half (starting from coordinate (b2b)). I would like to be able to "connect" (b2c) and (b2b) without needing to draw the line between them. That is, I want to draw only once, and somehow tell tikz to skip the line drawing between those specific coordinates. How can I achieve that?

Edit:

This is just a simplification of my actual figure to illustrate my problem. I would in general like to skip an arbitrary number of borders belonging to a shape.

  • 1
    You may just comment or remove the -- operation. – Paul Gaborit Jun 25 '15 at 13:50
  • If you want separate paths you need edges or to paths to lift the pen. – percusse Jun 25 '15 at 13:54
  • 1
    @PaulGaborit no because you would get two fills both with an end in (a) causing an unshaded area inside the "baloon" – Bordaigorl Jun 25 '15 at 13:54
  • 1
    @percusse can you show how? – Bordaigorl Jun 25 '15 at 14:10
  • @percusse With edge [draw=none] I can prevent the line from being drawn but the problem with unshaded triangles arises. – Miguel Jun 25 '15 at 14:20
8

Here is a new decoration with which you can select the segments to not draw.

To fill a closed path and draw all segments except segments 2 and 5, the syntax is :

\path[fill,apply={draw} except on segments {2,5}] ... closed path ... ;

enter image description here

\documentclass{standalone}
\usepackage{etoolbox}
\usepackage{tikz}
\usetikzlibrary{decorations.pathreplacing}
\makeatletter
\newcounter{aaa}
\tikzset{
  apply/.style args={#1 except on segments #2}{postaction={
      /utils/exec={
        \@for\mattempa:=#2\do{\csdef{aaa@\mattempa}{}}
        \setcounter{aaa}{0}
      },
      decorate,decoration={show path construction,
        moveto code={},
        lineto code={
          \stepcounter{aaa}
          \ifcsdef{aaa@\theaaa}{}{
            \path[#1] (\tikzinputsegmentfirst) -- (\tikzinputsegmentlast);
          }
        },
        curveto code={
          \stepcounter{aaa}
          \ifcsdef{aaa@\theaaa}{}{
            \path [#1] (\tikzinputsegmentfirst) .. controls
            (\tikzinputsegmentsupporta) and (\tikzinputsegmentsupportb)
            ..(\tikzinputsegmentlast);
          }
        },
        closepath code={
          \stepcounter{aaa}
          \ifcsdef{aaa@\theaaa}{}{
            \path [#1] (\tikzinputsegmentfirst) -- (\tikzinputsegmentlast);
          }
        },
      },
    },
  },
}
\makeatother
\begin{document}


\begin{tikzpicture}[scale=3., line width=1pt]

\coordinate (a) at (0,0);
\coordinate (b1) at (1,1);
\coordinate (c1) at (2,0);
\coordinate (b2a) at (0.7,-1);
\coordinate (b2b) at (0.9,-1.2);
\coordinate (b2c) at (1.1,-1.2);
\coordinate (b2d) at (1.3,-1);

\path[fill=green!10!white,apply={draw=red} except on segments {5}]
  (a) .. controls +(0,0.5) and +(-0.5,0) ..
  (b1) .. controls +(0.5,0) and +(0.,0.5) ..
  (c1) .. controls +(0.,-0.5) and +(0.5,0.2) ..
  (b2d) .. controls +(-0.125,-0.05) and +(-0.,0.05) ..
  (b2c)
  -- % I want to skip this line!
  (b2b) .. controls +(0.,0.05) and +(0.125,-0.05) ..
  (b2a) .. controls +(-0.5,0.2) and +(0,-0.5) .. (a);

\end{tikzpicture}

\end{document}
  • Awesome, this should be included with the official TikZ distribution. – Miguel Jun 26 '15 at 9:42
5

You can simply start from b2b instead of a:

\draw[fill=green!10!white]
      (b2b) .. controls +(0.,0.05) and +(0.125,-0.05) ..
      (b2a) .. controls +(-0.5,0.2) and +(0,-0.5) ..
      (a) .. controls +(0,0.5) and +(-0.5,0) ..
      (b1) .. controls +(0.5,0) and +(0.,0.5) ..
      (c1) .. controls +(0.,-0.5) and +(0.5,0.2) ..
      (b2d) .. controls +(-0.125,-0.05) and +(-0.,0.05) ..
      (b2c);

Because of how fill works omitting the line with your comment would work for the outline but not for the shaded area.

In general you can draw an "intermittent" path just by using the move to operation:

\draw (a) -- (b) -- (c) (d) -- (e) -- (f);

will draw no line between (c) and (d).

When you fill such an interrupted path as in

\fill (a) -- (b) -- (c) (d) -- (e) -- (f);

You are saying "fill the triangle abc", then "fill the triangle def".

So to get your intended result you need

\draw (a) -- (b) -- (c) (d) -- (e) -- (f);
\fill (a) -- (b) -- (c) -- (d) -- (e) -- (f);
  • @Miguel I removed that one, I was writing that without testing (I was thinking of \filldraw anyway) – Bordaigorl Jun 25 '15 at 14:04
  • At the moment this is a bit less verbose than drawing thrice, but still I would like to see a more flexible way to modify a line's style (in a general sense, including no draw) along a path. I am actually surprised that no straightforward solution seems to be implemented. – Miguel Jun 25 '15 at 14:10
  • 1
    @Miguel I am expecting somebody to come up with a general solution using decorations any moment =P – Bordaigorl Jun 25 '15 at 14:12

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.