1

I would like to reproduce this figure :

enter image description here

In order to do so, I've only been able yet to do a shaded rectangle with this code :

\draw [bottom color=gray,top color=gray,middle color= white] (0,0) rectangle (3,0.3);

which gives me :

enter image description here

Is it possible to make a curved rectangle with an adjustable angle and length, if I wanted to make the border of a quarter circle with this pattern for example.

Thanks in advance.

1

2 Answers 2

5

Something like this?

\documentclass[tikz,border=3mm]{standalone}
\usetikzlibrary{decorations} 
\newcounter{icoord}
\pgfkeys{/tikz/.cd,
    curved pipe/.cd,
    radius/.store in=\CurvedPipeRadius,
    radius=10pt,
    step/.store in=\CurvedPipeStep,
    step=1pt,
    shade/.style={left color=gray,right color=gray,middle color=white}
}

\pgfdeclaredecoration{curved pipe}{initial}
{% 
\state{initial}[width=\CurvedPipeStep,next state=cont] {%
    \pgfmoveto{\pgfpoint{\CurvedPipeStep}{\CurvedPipeRadius}}%
    \pgfpathlineto{\pgfpoint{0.3\pgflinewidth}{\CurvedPipeRadius}}%
    \setcounter{icoord}{0}%
    \pgfcoordinate{lastup-\number\value{icoord}}{\pgfpoint{1pt}{\CurvedPipeRadius}}%
    \pgfcoordinate{lastdown-\number\value{icoord}}{\pgfpoint{1pt}{-1*\CurvedPipeRadius}}%
  }
  \state{cont}[width=\CurvedPipeStep]{%
     \stepcounter{icoord}%
    \pgfcoordinate{lastup-\number\value{icoord}}{\pgfpoint{\CurvedPipeStep}{\CurvedPipeRadius}}
     \pgfcoordinate{lastdown-\number\value{icoord}}{\pgfpoint{\CurvedPipeStep}{-1*\CurvedPipeRadius}}
     \pgfcoordinate{tmpup}{\pgfpoint{\CurvedPipeStep+0.3pt}{\CurvedPipeRadius}}
     \pgfcoordinate{tmpdown}{\pgfpoint{\CurvedPipeStep+0.3pt}{-1*\CurvedPipeRadius}}
     \pgfmathsetmacro\myshadingangle{0}%
     \path[curved pipe/shade,shading angle=\myshadingangle] 
        (lastup-\the\numexpr\value{icoord}-1) 
     -- (tmpup) to[out=180,in=180] (tmpdown) -- (lastdown-\the\numexpr\value{icoord}-1)
     to[out=180,in=180] cycle;%
     \pgfmoveto{\pgfpointanchor{lastup-\the\numexpr\value{icoord}-1}{center}}%
     \pgfpathlineto{\pgfpointanchor{lastup-\number\value{icoord}}{center}}%
     \pgfmoveto{\pgfpointanchor{lastdown-\the\numexpr\value{icoord}-1}{center}}%
     \pgfpathlineto{\pgfpointanchor{lastdown-\number\value{icoord}}{center}}%
  }
  \state{final}[width=\CurvedPipeStep]
  { % perhaps unnecessary but doesn't hurt either
    \pgfmoveto{\pgfpointdecoratedpathlast}
    \fill (tmpup) to[out=0,in=0] (tmpdown) to[out=-180,in=-180] cycle;
  }
}

\begin{document}
  \begin{tikzpicture}
    \draw[decorate,decoration=curved pipe,curved pipe/radius=3mm,looseness=0.7] 
     (0,0) to[bend right] (8,3);
  \end{tikzpicture}
\end{document}

enter image description here

Or without the pipe character, just shaded

\documentclass[tikz,border=3mm]{standalone}
\usetikzlibrary{decorations} 
\newcounter{icoord}
\pgfkeys{/tikz/.cd,
    curved and shaded/.cd,
    radius/.store in=\CurvedPipeRadius,
    radius=10pt,
    step/.store in=\CurvedPipeStep,
    step=1pt,
    shade/.style={left color=gray,right color=gray,middle color=white}
}

\pgfdeclaredecoration{curved and shaded}{initial}
{% 
\state{initial}[width=\CurvedPipeStep,next state=cont] {%
    \pgfmoveto{\pgfpoint{\CurvedPipeStep}{\CurvedPipeRadius}}%
    \pgfpathlineto{\pgfpoint{0.3\pgflinewidth}{\CurvedPipeRadius}}%
    \setcounter{icoord}{0}%
    \pgfcoordinate{lastup-\number\value{icoord}}{\pgfpoint{1pt}{\CurvedPipeRadius}}%
    \pgfcoordinate{lastdown-\number\value{icoord}}{\pgfpoint{1pt}{-1*\CurvedPipeRadius}}%
  }
  \state{cont}[width=\CurvedPipeStep]{%
     \stepcounter{icoord}%
    \pgfcoordinate{lastup-\number\value{icoord}}{\pgfpoint{\CurvedPipeStep}{\CurvedPipeRadius}}
     \pgfcoordinate{lastdown-\number\value{icoord}}{\pgfpoint{\CurvedPipeStep}{-1*\CurvedPipeRadius}}
     \pgfcoordinate{tmpup}{\pgfpoint{\CurvedPipeStep+0.3pt}{\CurvedPipeRadius}}
     \pgfcoordinate{tmpdown}{\pgfpoint{\CurvedPipeStep+0.3pt}{-1*\CurvedPipeRadius}}
     \pgfmathsetmacro\myshadingangle{0}%
     \path[curved and shaded/shade,shading angle=\myshadingangle] 
        (lastup-\the\numexpr\value{icoord}-1) 
     -- (tmpup) -- (tmpdown) -- (lastdown-\the\numexpr\value{icoord}-1)
     -- cycle;%
     \pgfmoveto{\pgfpointanchor{lastup-\the\numexpr\value{icoord}-1}{center}}%
     \pgfpathlineto{\pgfpointanchor{lastup-\number\value{icoord}}{center}}%
     \pgfmoveto{\pgfpointanchor{lastdown-\the\numexpr\value{icoord}-1}{center}}%
     \pgfpathlineto{\pgfpointanchor{lastdown-\number\value{icoord}}{center}}%
  }
  \state{final}[width=\CurvedPipeStep]
  { % perhaps unnecessary but doesn't hurt either
    \pgfmoveto{\pgfpointdecoratedpathlast}
  }
}

\begin{document}
  \begin{tikzpicture}
   \draw[decorate,decoration=curved and shaded,curved and shaded/radius=3mm] 
     (0,0) to[bend right] (8,3);
  \end{tikzpicture}
\end{document}

enter image description here

And here is another proposal, full credit goes to Paul Gaborit for this post. I changed a few things and stored some parameters in pgf keys: n is the number of recursions, f is the ratio of the current line width over the previous line width, color is, well, the color of the overlays and opacity the opacity. Yet conceptually it is really just Paul Gaborit's idea: redo the path in a different color and not with full opacity a couple of times while decreasing the line width.

\documentclass[tikz,border=3mm]{standalone}
\tikzset{% very much based on https://tex.stackexchange.com/a/80207/194703
  pipe beam action/.style={
    line width=\pgfkeysvalueof{/tikz/pipe/f}*\pgflinewidth,
    draw=\pgfkeysvalueof{/tikz/pipe/color},
  },
  pipe beam recurs/.code={%
    \pgfmathtruncatemacro{\level}{#1-1}%
    \ifnum\level=0%
    \tikzset{postaction={pipe beam action}}%
    \else
    \tikzset{postaction={pipe beam action,pipe beam recurs={\level}}}%
    \fi
  },
  pipe beam/.style={pipe/.cd,#1,/tikz/.cd,
  preaction={draw opacity=1,draw/.expanded=\pgfkeysvalueof{/tikz/pipe/color}},
  postaction={draw opacity=\pgfkeysvalueof{/tikz/pipe/opacity},
  pipe beam recurs={\pgfkeysvalueof{/tikz/pipe/n}}}},
  pipe/.cd,n/.initial=10,color/.initial=white,f/.initial=0.95,
  opacity/.initial=0.1
}
\begin{document}
\begin{tikzpicture}
 \path[draw=black,line width=5pt,pipe beam] 
    (-2,0) to[bend right] (2,2);
 \path[draw=black,line width=5pt,pipe beam={n=25,f=0.96}] 
    (-2,-1) to[bend right] (2,1);
\end{tikzpicture}
\end{document}

enter image description here

3
  • nice one... :-)
    – MadyYuvi
    Apr 2, 2020 at 15:49
  • Great answer, just for fun, for the shaded solution, if I change the line to circle, the output is strange. not sure if we can improve it to fit any shape.
    – lucky1928
    Apr 3, 2020 at 14:07
  • @lucky1928 Thanks! Yes, this shows how TikZ decomposes a circle into Bezier curves. I do not know if there is a simple way to improve this.
    – user194703
    Apr 3, 2020 at 14:34
1

Welcome to TeX.SE.

This suggestion only for the shaded rectangle:

\documentclass{book}
\usepackage[prologue]{xcolor}%
\RequirePackage{pstricks}%
\input pst-grad%

\begin{document}

\psframebox[linewidth=0pt,linecolor=white,fillstyle=gradient,gradbegin=black!20,gradend=black!5,gradmidpoint=90]
{\vbox
to 5pc{\vfill\hbox to 12pc{\hfill}\vfill}}


\end{document}

Output

enter image description here

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .