避免使用动画重新计算 beamer 中的 addplot

避免使用动画重新计算 beamer 中的 addplot

使用 beamer 和animate,是否可以避免在每一步重新计算一些静态的昂贵部分?

梅威瑟:

\documentclass[10pt]{beamer}
\usepackage{pgfplots}
\usepackage{animate}

\begin{document}
\begin{frame}{}

   \begin{animateinline}[controls,loop]{15} % frame rate
      \multiframe{10}{rt=0+0.04}{%

       \begin{tikzpicture}
         \begin{axis}[height=5cm,width=5cm]
            
            % some expensive static computation recomputed at each frame!
            \addplot[domain=0:1,samples=5000] ({cos(deg(2*pi*x))},{sin(deg(2*pi*x))});

            % the only animated part, unexpensive
            \node at (axis cs:0,0) {\rt};

        \end{axis}
      \end{tikzpicture}
    }
  \end{animateinline}
\end{frame}

\end{document}

答案1

带轴的图形被排版到xlrbox(pkg xsavebox) 中,同时将标签位置和左下边界框角保存为命名坐标。然后,在动画中,一个简单的tikzpicture使用纯环境通过 Ti 放置保存的图形和动画标签Z 节点。

\documentclass[10pt]{beamer}

\usepackage{pgfplots}
\usepackage{animate}
\usepackage{xsavebox}

\begin{document}
\begin{frame}{}
  \begin{xlrbox}{Graph}
    \begin{tikzpicture}
      \begin{axis}[height=5cm,width=5cm]
         
         % some expensive static computation
         \addplot[domain=0:1,samples=5000] ({cos(deg(2*pi*x))},{sin(deg(2*pi*x))});

         % save label position
         \coordinate (label) at (axis cs:0,0);

      \end{axis}
      \coordinate (ll) at (current bounding box.south west);
    \end{tikzpicture}
  \end{xlrbox}%
%  
  \begin{animateinline}[controls,loop]{15} % frame rate
    \multiframe{10}{rt=0+0.04}{%
      \begin{tikzpicture}
        \node[inner sep=0pt, anchor=south west] at (ll) {\theGraph};
        \node at (label) {\rt};
      \end{tikzpicture}
    }
  \end{animateinline}
\end{frame}

\end{document}

xlrbox用来代替标准 LaTeX,lrbox因为它大大减少了 PDF 文件的大小(10 帧为 1/6,100 帧为 1/32)。

具有多个预定义标签位置的扩展示例:

\documentclass[10pt]{beamer}

\usepackage{pgfplots}
\usepackage{animate}
\usepackage{xsavebox}
\usepackage{multido}

\begin{document}
\begin{frame}{}
  \begin{xlrbox}{Graph}
    \begin{tikzpicture}
      \begin{axis}[height=5cm,width=5cm]
         
         % define several labels
         \multido{\i=0+1,\rphi=90+-45}{8}{
           \pgfmathsetmacro{\xpos}{0.8*cos(\rphi)}
           \pgfmathsetmacro{\ypos}{0.8*sin(\rphi)}
           \edef\arg{ (label-\i) at (axis cs:\xpos,\ypos)}
           \expandafter\coordinate\arg;
         }

         % some expensive static computation
         \addplot[domain=0:1,samples=5000] ({cos(deg(2*pi*x))},{sin(deg(2*pi*x))});

      \end{axis}
      \coordinate (ll) at (current bounding box.south west);
    \end{tikzpicture}
  \end{xlrbox}%
%  
  \begin{animateinline}[controls,loop]{4} % frame rate
    \multiframe{8}{i=0+1,rphi=90+-45}{%
      \begin{tikzpicture}
        \node[inner sep=0pt, anchor=south west] at (ll) {\theGraph};
        \node at (label-\i) {$\rphi$};
      \end{tikzpicture}
    }
  \end{animateinline}
\end{frame}

\end{document}

答案2

TikZ 允许您保存路径并在以后使用。这对于使用 创建的路径也有效\addplot。您可以仅在第一帧中创建并保存昂贵的路径,然后在以下帧中使用该路径:

\documentclass[10pt]{beamer}
\usepackage{pgfplots}
\usepackage{animate}

\begin{document}
\begin{frame}{}
   \begin{animateinline}[controls,loop]{15} % frame rate
      \multiframe{10}{rt=0+0.04}{%

       \begin{tikzpicture}
         \begin{axis}[
             height=5cm,width=5cm, clip=false, 
             xmin=-1.2, xmax=1.2,ymin=-1.2, ymax=1.2
           ]
           \ifdefined\ExpensivePath
             \draw[use path=\ExpensivePath];
           \else
             \addplot[domain=0:1,samples=5000,save path=\ExpensivePath] ({cos(deg(2*pi*x))},{sin(deg(2*pi*x))});
           \fi

            % the only animated part, unexpensive
           \node at (axis cs:0,0) {\rt};

        \end{axis}
      \end{tikzpicture}
    }
  \end{animateinline}
\end{frame}

\end{document}

相关内容