5

Is there as simple way to create a pdf animation with tikz of an oscillating mass attached to a spring which extends and compresses as the mass oscillates. The number of "spring elements" should be constant during the oscillation.

I came up with this pretty solution so far. However, I do not quite understand how to chose the right units for the segment length parameter:

\documentclass[tikz]{standalone}
\usepackage{tikz}
\usetikzlibrary{shadings, calc, decorations.pathmorphing}

\begin{document}

\def\frames{50}
\def\amplitude{1.5}
\def\z0{3.0}
\def\nloops{5.0}

\foreach \n in {0, 1, ..., \frames}
{
    \begin{tikzpicture}[x=1cm, y=1cm]

    % %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
    % calculations
    % %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
    \pgfmathsetmacro{\height}{\amplitude * cos(2.0 * pi * \n / \frames r) - \z0};
    \pgfmathsetmacro{\seglength}{(-\amplitude * cos(2.0 * pi * \n / \frames r) + 3.0) / \nloops * 1cm};


    % %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
    % help lines
    % %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
    \draw[color=white,fill=white] (-1.70, 0.4) rectangle (2.00, -6.0);


    % %%%%%%%%%%%%%%%%%%%%%%%%%%%%%
    % the scene
    % %%%%%%%%%%%%%%%%%%%%%%%%%%%%%

    % the ceiling   
    \draw[color=black!70, line width=2.0pt, line cap=round] (-1.70, 0) -- (1.70, 0);
    \foreach \x in {-1.60, -1.20, ..., 2.0}
    {
        \draw[color=black!70, line width=1.00pt, line cap=round] (\x, 0) -- ++ (0.35, 0.4);
    }
    \draw[color=black!70, line width=2.00pt, line cap=round] (-0.5, 0) -- +(0.0, -0.2);
    \draw[color=black!70, line width=2.00pt, line cap=round] (+0.5, 0) -- +(0.0, -0.2);


    % the mass
    \draw[ball color=orange!90!black!70, rounded corners=1ex] (-1.0, \height) rectangle +(2.0, -0.75);
    \draw[color=black!70, line width=2.00pt, line cap=round] (-0.5, \height) -- +(0.0, 0.2);
    \draw[color=black!70, line width=2.00pt, line cap=round] (+0.5, \height) -- +(0.0, 0.2);

    % the spring
    \draw[decorate, color=red!70, line width=2.00pt, line cap=round, decoration={coil, amplitude=0.25cm, segment length=\seglength}] ($(-0.5, \height) + (0, 0.2)$) -- (-0.5, -0.2);

    \end{tikzpicture}
}
\end{document}

To the spring should have a minimum extension of 1.5 cm and a maximum extension of 4.5 cm. Here is an image of the spring at minimum extension:

enter image description here

Can someone point me into the right direction?

Daniel
  • 493
  • 2
    Related: http://tex.stackexchange.com/questions/41608/draw-mechanical-springs-in-tikz/58450#58450 Edit: http://tex.stackexchange.com/questions/54824/appending-a-line-of-fixed-length-to-a-spring-drawn-with-tikz-coil – Torbjørn T. Jun 08 '13 at 18:19
  • 1
    See also http://tex.stackexchange.com/a/33957/8425 – cjorssen Jun 08 '13 at 22:14
  • thanks for the links. the examples illustrate pretty much what I want as the final figure. However, my biggest problem is that the automatic calculation of the segment length seems to give the correct result when I print it but when I use it as an argument in "segement length=\seglength" it behaves inconsistently. I suppose that has to di with the fact that \seglength does not have cm units? – Daniel Jun 09 '13 at 00:21

1 Answers1

5

Thanks for the links to the related question. By studying these really nice solutions I could modify my figure. The result is not as sophisticated as the other solutions but much shorter. Thus, I thought I share it with you.

\documentclass[tikz]{standalone}
\usepackage{tikz}
\usetikzlibrary{shadings, calc, decorations.pathmorphing}

\begin{document}

\def\frames{50}
\def\r{0.5cm}

\foreach \n in {0, 1, ..., \frames}
{
    \begin{tikzpicture}

    % %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
    % calculations
    % %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
    \pgfmathsetlengthmacro{\height}{1.5cm * cos(2.0 * pi * \n / \frames r) - 2.9cm};
    \pgfmathsetlengthmacro{\seglength}{(-1 * \height - 0.4cm) / 4};

    % %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
    % the frame
    % %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
    \draw[color=white,fill=white] (-1.70, 0.4) rectangle (2.00, -6.0);

    % %%%%%%%%%%%%%%%%%%%%%%%%%%%%%
    % the scene
    % %%%%%%%%%%%%%%%%%%%%%%%%%%%%%
    % the ceiling   
    \draw[color=black!70, line width=2.0pt, line cap=round] (-1.70, 0) -- (1.70, 0);
    \foreach \x in {-1.60, -1.20, ..., 2.0}
    {
        \draw[color=black!70, line width=1.00pt, line cap=round] (\x, 0) -- ++ (0.35, 0.4);
    }
    \draw[color=black!70, line width=2.00pt, line cap=round] (0.0, 0.0) -- +(0.0, -0.2);

    % the mass
    \draw[ball color=orange!90!black!70, rounded corners=1ex] ($(0.0, \height) - (0.0, \r)$) circle[radius=\r];
    \draw[color=black!70, line width=2.00pt, line cap=round] (0.0, \height) -- +(0.0, 0.2);

    % the spring
    \draw[decorate, color=black!70, line width=2.00pt, line cap=round, decoration={zigzag, amplitude=0.25cm, segment length=\seglength}] ($(0.0, \height) + (0, 0.2)$) -- (0.0, -0.2);

    \end{tikzpicture}
}
\end{document}

The animation looks like this enter image description here

Daniel
  • 493