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 want to plot geodesics on a cylinder. These are straight lines, circles or helices. I can plot the first two, but I don't know how to draw the helices.

To be precise, I would like to know how to draw an helix on this cylinder (passing thru two points A and B, but the location of the points is not relevant), using TikZ exclusively (maybe with pgfplots, but without using pstricks):

enter image description here

\node [cylinder,rotate=90,draw,aspect=2,minimum width=2cm,minimum height=3.5cm](C){};
\draw[fill] (-0.5,-0.5) circle [radius=0.045]node[below]{$A$};
\draw[fill] (0.5,0.75) circle [radius=0.045]node[below]{$B$};
share|improve this question
Would this help? tex.stackexchange.com/a/73584/34618 –  Jesse Aug 24 '13 at 9:21
@Jesse I already tried that, but the plots of the cylinder and the helix (using \begin{axis} and \end{axis}) appear separated, instead of superimposed... –  Grimolatto Aug 24 '13 at 9:25
Use begin{tikzpicture}[overlay] and try. –  Jesse Aug 24 '13 at 9:30
OK. With the overlay option the plots superimpose, but with different scalings, and different origins. Note that the axis of my cylinder is the z axis. The addplot+3 figure seems to have its own system of coordinates. The cylinder has radius 1, so a parameterization of the helix with (cos(t),sin(t),t/5) should fit on it. But it does not... –  Grimolatto Aug 24 '13 at 10:20
I think the problem comes from the fact that the cylinder is actually a 2D object (drawn with straight lines and ellipses), and these 2D and 3D descriptions collide... –  Grimolatto Aug 24 '13 at 10:27

3 Answers 3

up vote 10 down vote accepted

Here is a tikz-3dplot solution. In case people are interested in drawing a more general helix (not just a geodesic) between two points of the cylinder, I've included a macro called \n to specify the number of additional turns around the cylinder.

Edit: thanks to Qrrbrbirlbel for his very helpful comment.

enter image description here

\tikzset{every circle/.append style={x=1cm, y=1cm}}

% --- Independent parameters ---
\def\h{3}                          % cylinder height
\pgfmathtruncatemacro\tA{350}      % A angle
\def\zA{1}                         % A applicate
\pgfmathtruncatemacro\tB{150}      % B angle
\def\zB{2}                         % B applicate
\pgfmathtruncatemacro\n{0}         % number of additional turns
\pgfmathtruncatemacro\NbPt{51}     % number of dots for drawing the helix portion
\def\rhelixdots{0.02}              % radius of dots forming helix
\def\rAB{0.05}                     % radius of A and B dots

% --- Draw cylinder ---
% peripheral spokes
\foreach \t in {20,40,...,360} 
    \draw[gray,very thin,dashed] ({cos(\t)},{sin(\t)},0)

% lower circle
\draw[black,very thin] (1,0,0) 
    \foreach \t in {2,3,...,360}

% upper circle
\draw[black,very thin] (1,0,\h) 
    \foreach \t in {2,4,...,360}

% --- Draw helix ---
\foreach \t in {\tone,\ttwo,...,\tlast}{%
    \fill[red] ({cos(\t)},{sin(\t)},{\p*(\t-\tA)/360+\zA}) circle[radius=\rhelixdots];

% --- Draw A and B ---
\fill[blue] ({cos(\tA)},{sin(\tA)},\zA) circle [radius=\rAB]node[right]{$A$};
\fill[blue] ({cos(\tB)},{sin(\tB)},\zB) circle [radius=\rAB]node[left]{$B$};

share|improve this answer
I'm no expert in tikz-3dplot but without a unit the radius of the circles is taken in the x/y coordinate system of TikZ (which is changed by tikz-3dplot so that coordinates like (<x>, <y>, <z>) work as set up. Either use units (e.g. radius=3pt) or reset the coordinate system: circle[x=1cm, y=1cm, radius=\rAB]. A fix for all circles would be issuing \tikzset{every circle/.append style={x=1cm, y=1cm}}. –  Qrrbrbirlbel Aug 24 '13 at 19:13
@Qrrbrbirlbel Perfect! Thanks a lot. –  Jubobs Aug 24 '13 at 19:39
I see what happens (incompatibility between coordinates)... The problem is that, as already said, I have drawn the other curves without problem, just with TikZ, and this approach forces me to redo everything, including the cylinder. I am surprised that such a simple thing requires such a sophisticated construction. But I'll give it a try!... –  Grimolatto Aug 24 '13 at 20:23

Here is the solution exactly as I wanted it (it is based on the replies by Jubobs and Qrrbrbirlbel, but in a more simplified form). There are 5 different sectors depending on the color and the type of line (dashed or not). The points coordinates are computed so they lie on the helix:

Helix on a cylinder using <code>TikZ</code> and <code>3dplot</code>

\node [cylinder,rotate=90,draw,aspect=2,minimum width=2cm,minimum height=3.5cm](C){};
\foreach \t in {-90,-75,...,0}{%
\draw ({cos(\t)},{sin(\t)},{-0.25+\t/360})--({cos(\t+7)},{sin(\t +7)},{-0.23+\t/360});
\foreach \t in {15,16,...,98}{%
\draw[line width=1.5pt,color=red] ({cos(\t)},{sin(\t)},{-0.25+\t/360})--({cos(\t+1)},{sin(\t +1)},{-0.22+\t/360});
\foreach \t in {110,125,...,280}{%
\draw[line width=1pt,color=red] ({cos(\t)},{sin(\t)},{-0.25+\t/360})--({cos(\t+7)},{sin(\t +7)},{-0.22+\t/360});
\foreach \t in {303,304,...,340}{%
\draw[line width=1.6pt,color=red] ({cos(\t)},{sin(\t)},{-0.25+\t/360})--({cos(\t+1)},{sin(\t +1)},{-0.19+\t/360});
\foreach \t in {355,370}{%
\draw ({cos(\t)},{sin(\t)},{-0.25+\t/360})--({cos(\t+7)},{sin(\t +7)},{-0.23+\t/360});
\draw[fill] (0.9922,0.25,-0.2) circle [x=1cm,y=1cm,radius=0.045]node[below]{$A$};
\draw[fill] (0.2739,-0.5,0.32) circle [x=1cm,y=1cm,radius=0.045]node[below]{$B$};

There are some issues related to the density of lines near the turning points, but these can be easily adjusted by hand. When printed, this is OK:

share|improve this answer
Well done. Best of luck on your future tikz adventures. –  Jubobs Aug 27 '13 at 10:14

Here is a solution with pstricks in answer to a similar quesion:

\usepackage{pstricks-add, pst-3dplot}

\psset{xPlotpoints = 500, plotstyle=curve, linecolor = DarkSeaGreen3, algebraic, arrowinset=0.2, labelsep=3pt, dash=5pt 4pt}
\def\radius{2 }
\def\height {9.8}
\def\thetaend {0}
\def\thetaini {-305}
\psset{viewpoint=30 40 15 rtp2xyz, IIIDshowgrid = false}
    \pnodes(-4,-0.08){L1}(-4, 8.23){L2}(-2.2,-0.08){C1}(-2.2,8.23){C2}(-3,-0.08){S1}(-3, 3.36){S2}(-2,3.36){C3}(0,-0.08){O}(2,-0.08){R}
    \psCylinder[increment=5, opacity=0.3]{\radius}{\height}
    \ncline[linecolor=Coral1,linewidth=0.5pt]{*->}{O}{R}\nbput{large radius}
    \psset{linewidth=1.2pt, dimen=inner}
    \parametricplotThreeD[arrows=c-](0, 3.10){%
        \radius*cos(t - \phase) | \radius * sin(t - \phase) | t/\sp}
    \parametricplotThreeD[linecolor=DarkSeaGreen3!50!, linestyle=dashed](3.15,6.10){%
        \radius*cos(t-\phase) | \radius* sin(t-\phase) | t/\sp}
    \parametricplotThreeD(6.18, 9.36){%68
        \radius*cos(t-\phase) | \radius * sin(t-\phase) | t/\sp}
    \parametricplotThreeD[linecolor=DarkSeaGreen3!50!, linestyle=dashed](9.40, 12.35){%
        \radius*cos(t-\phase) | \radius * sin(t-\phase) | t/\sp}
    \parametricplotThreeD[arrows=-c](12.45, 15.56){%
        \radius*cos(t-\phase) | \radius * sin(t-\phase) | t/\sp}
    \psset{linewidth=0.5pt, linecolor=Coral1}


enter image description here

share|improve this answer

Your Answer


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.