Beamer には次のアニメーションがあります:
次のコードを使用します (おそらく最適ではありません):
\documentclass{beamer}
\usepackage{tikz}
\usepackage{multimedia}
\begin{document}
\begin{frame}[label=persistence]
\animate<1-10>
\begin{columns}
\begin{column}{5cm}
\foreach \n in {1,...,10} {
\begin{tikzpicture}[radius=2pt]
\only<\n>{
\node at (-1,6){};
\node at (6.5,0){};
\begin{scope}[fill opacity=0.2]
\filldraw[fill=yellow,draw=black] (1,1) circle (2+3*\n pt);
\filldraw[fill=yellow,draw=black] (2.3,1.1) circle (2+3*\n pt);
\filldraw[fill=yellow,draw=black] (4.5,0.8) circle (2+3*\n pt);
\filldraw[fill=yellow,draw=black] (5.1,1.8) circle (2+3*\n pt);
\filldraw[fill=yellow,draw=black] (0.4,3.3) circle (2+3*\n pt);
\filldraw[fill=yellow,draw=black] (2.1,2.8) circle (2+3*\n pt);
\filldraw[fill=yellow,draw=black] (3.8,3.5) circle (2+3*\n pt);
\filldraw[fill=yellow,draw=black] (4.8,4.2) circle (2+3*\n pt);
\filldraw[fill=yellow,draw=black] (0.8,4.9) circle (2+3*\n pt);
\filldraw[fill=yellow,draw=black] (2.1,4.1) circle (2+3*\n pt);
\filldraw[fill=yellow,draw=black] (3.8,2.0) circle (2+3*\n pt);
\filldraw[fill=yellow,draw=black] (3.5,0.6) circle (2+3*\n pt);
\filldraw[fill=yellow,draw=black] (3.0,5.0) circle (2+3*\n pt);
\filldraw[fill=yellow,draw=black] (4.1,5.1) circle (2+3*\n pt);
\filldraw[fill=yellow,draw=black] (0.9,2.1) circle (2+3*\n pt);
\end{scope}
\filldraw[red] (1,1) circle ;
\filldraw[red] (2.3,1.1) circle ;
\filldraw[red] (4.5,0.8) circle ;
\filldraw[red] (5.1,1.8) circle ;
\filldraw[red] (0.4,3.3) circle ;
\filldraw[red] (2.1,2.8) circle ;
\filldraw[red] (3.8,3.5) circle ;
\filldraw[red] (4.8,4.2) circle ;
\filldraw[red] (0.8,4.9) circle ;
\filldraw[red] (2.1,4.1) circle ;
\filldraw[red] (3.8,2.0) circle ;
\filldraw[red] (3.5,0.6) circle ;
\filldraw[red] (3.0,5.0) circle ;
\filldraw[red] (4.1,5.1) circle ;
\filldraw[red] (0.9,2.1) circle ;
}
\end{tikzpicture}
}
\end{column}
\begin{column}{.4\textwidth}
\begin{tikzpicture}
\filldraw[red] (1,1) circle ;
\filldraw[red] (2.3,1.1) circle ;
\filldraw[red] (4.5,0.8) circle ;
\filldraw[red] (5.1,1.8) circle ;
\filldraw[red] (0.4,3.3) circle ;
\filldraw[red] (2.1,2.8) circle ;
\filldraw[red] (3.8,3.5) circle ;
\filldraw[red] (4.8,4.2) circle ;
\filldraw[red] (0.8,4.9) circle ;
\filldraw[red] (2.1,4.1) circle ;
\filldraw[red] (3.8,2.0) circle ;
\filldraw[red] (3.5,0.6) circle ;
\filldraw[red] (3.0,5.0) circle ;
\filldraw[red] (4.1,5.1) circle ;
\filldraw[red] (0.9,2.1) circle ;
\end{tikzpicture}
\end{column}
\end{columns}
\end{frame}
\end{document}
ここで、同じポイント セット (赤い円) を使用して、スライドの右側にアニメーション グラフを作成する必要があります。近傍間の交差点が空でない場合、ポイント $P$ と $Q$ の間にエッジが表示されます。Tikz で可能ですか? 私が考えている解決策は、ポイントのベクトルを定義し、ネストされた 2 つの for を使用することです。ただし、その方法がわかりません。
答え1
要件の最初の部分については、TikZ\foreach
コマンドはマクロに保存できる座標のリストを解析できます。次に、その方法を示します。必要なユースケースに合わせてコードを調整するのは簡単なはずです。
\documentclass[tikz,border=5]{standalone}
\begin{document}
\def\pointlist{
(1.0,1.0), (2.3,1.1), (4.5,0.8),
(5.1,1.8), (0.4,3.3), (2.1,2.8),
(3.8,3.5), (4.8,4.2), (0.8,4.9),
(2.1,4.1), (3.8,2.0), (3.5,0.6),
(3.0,5.0), (4.1,5.1), (0.9,2.1)
}
\begin{tikzpicture}[radius=2pt]
\begin{scope}[fill opacity=0.2]
\foreach \point in \pointlist
\filldraw[fill=yellow,draw=black] \point circle [radius=5pt];
\end{scope}
\foreach \point in \pointlist
\filldraw[red] \point circle;
\end{tikzpicture}
\end{document}
そして、私が2番目の部分を理解していると仮定します:
\documentclass[tikz,border=5]{standalone}
\begin{document}
\def\pointlist{
(1.0,1.0), (2.3,1.1), (4.5,0.8),
(5.1,1.8), (0.4,3.3), (2.1,2.8),
(3.8,3.5), (4.8,4.2), (0.8,4.9),
(2.1,4.1), (3.8,2.0), (3.5,0.6),
(3.0,5.0), (4.1,5.1), (0.9,2.1)
}
\foreach \N in {1,...,10}{
\begin{tikzpicture}[radius=2pt]
\useasboundingbox (-1,-.5) rectangle (6.25,6.25);
\begin{scope}[fill opacity=0.2]
\foreach \point in \pointlist
\filldraw[fill=yellow,draw=black] \point circle [radius=2pt+3*\N];
\end{scope}
\foreach \point in \pointlist
\filldraw[red] \point circle;
\foreach \P [count=\i] in \pointlist
\foreach \Q [count=\j]in \pointlist {
\ifnum\j>\i
\else
\path \P coordinate (P) \Q coordinate (Q);
\pgfpointdiff{\pgfpointanchor{P}{center}}{\pgfpointanchor{Q}{center}}
\pgfgetlastxy\x\y
\pgfmathparse{int(veclen(\x,\y)/2 < 2+3*\N)}
\ifnum\pgfmathresult=1
\draw [thick] (P) -- (Q);
\fi
\fi
}
\end{tikzpicture}
}
\end{document}
amorvincomni の回答に従って、ライブラリを使用して作業を行う別の方法を次に示しますmath
。
\documentclass[tikz,border=5]{standalone}
\usetikzlibrary{math}
\begin{document}
\def\pointlist{
(1.0,1.0), (2.3,1.1), (4.5,0.8),
(5.1,1.8), (0.4,3.3), (2.1,2.8),
(3.8,3.5), (4.8,4.2), (0.8,4.9),
(2.1,4.1), (3.8,2.0), (3.5,0.6),
(3.0,5.0), (4.1,5.1), (0.9,2.1)
}
\foreach \N in {1,...,10}{
\begin{tikzpicture}[radius=2pt]
\useasboundingbox (-1,-.5) rectangle (14.25,6.25);
\begin{scope}[fill opacity=0.2]
\foreach \point in \pointlist
\filldraw[fill=yellow,draw=black] \point circle [radius=2pt+3*\N];
\end{scope}
\foreach \point in \pointlist
\filldraw[red] \point circle;
\begin{scope}[xshift=8cm]
\foreach \point in \pointlist
\filldraw[red] \point circle;
\foreach \P [count=\i] in \pointlist
\foreach \Q [count=\j]in \pointlist {
\ifnum\j>\i
\tikzmath{%
coordinate \p, \q, \r;
\p = \P; \q = \Q;
\pq = veclen(\px-\qx, \py-\qy)/2;
\d = 2pt+3*\N;
if (\pq < \d) then {
{
\draw \P -- \Q;
\foreach \R [count=\k] in \pointlist {
\ifnum\k>\j
\tikzmath{%
\r = \R;
\pr = veclen(\px-\rx, \py-\ry)/2;
\qr = veclen(\qx-\rx, \qy-\ry)/2;
if (\pr < \d) && (\qr < \d) then {
{
\fill [fill=yellow, fill opacity=.2] \P -- \Q -- \R;
};
};
}
\fi
}
};
};
}
\fi
}
\end{scope}
\end{tikzpicture}
}
\end{document}
答え2
楽しみのために: Mark Wibrow の優れた回答から、次のコードを作成しました。最適ではありませんが、三角形の頂点に対応する 3 つの近傍の交差が空でない場合、塗りつぶされた三角形を作成します。
\begin{frame}[label=persistence]
\animate<1-27>
\scalebox{.8}{%
\begin{columns}
\begin{column}{5cm}
\begin{tikzpicture}[radius=2pt]%
\foreach \n in {1,...,27}%
{%
\only<\n>{%
\useasboundingbox (-1,-1.5) rectangle (6.25,7.25);
\begin{scope}[fill opacity=0.2]
\foreach \point in \pointlist {
\filldraw[fill=yellow,draw=black] \point circle (5+\n pt);
}
\end{scope}
\foreach \point in \pointlist {
\filldraw[red] \point circle;}
}
}
\end{tikzpicture}
\end{column}
\begin{column}{5cm}
\begin{tikzpicture}[radius=2pt]
\useasboundingbox (-1,-1.5) rectangle (6.25,7.25);
\foreach \n in {1,...,27}{%
\only<\n>{%
\foreach \point in \pointlist
\filldraw[red] \point circle;
\foreach \P [count=\i] in \pointlist
\foreach \Q [count=\j]in \pointlist {
\ifnum\j>\i
\path \P coordinate (P) \Q coordinate (Q);
\pgfpointdiff{\pgfpointanchor{P}{center}}{\pgfpointanchor{Q}{center}}
\pgfgetlastxy\x\y
\pgfmathparse{int(veclen(\x,\y)/2 < 5+\n)}
\ifnum\pgfmathresult=1
\draw [thick] (P) -- (Q);
\foreach \T [count=\k] in \pointlist {
\ifnum\k>\j
\path \P coordinate (P) \T coordinate (T);
\pgfpointdiff{\pgfpointanchor{P}{center}}{\pgfpointanchor{T}{center}}
\pgfgetlastxy\x\y
\pgfmathparse{int(veclen(\x,\y)/2 < 5+\n)}
\ifnum\pgfmathresult=1
\coordinate (A) at ($(P)!0.5!(Q)$);
\coordinate (C) at ($(P)!0.5!(T)$);
\coordinate (A') at ($(A)!2cm!90:(P)$);
\coordinate (C') at ($(C)!2cm!90:(P)$);
\coordinate (O) at (intersection of A--A' and C--C');
\pgfpointdiff{\pgfpointanchor{O}{center}}{\pgfpointanchor{T}{center}}
\pgfgetlastxy\x\y
\pgfmathparse{int(veclen(\x,\y) < 5+\n)}
\ifnum\pgfmathresult=1
\pgfpointdiff{\pgfpointanchor{O}{center}}{\pgfpointanchor{Q}{center}}
\pgfgetlastxy\x\y
\pgfmathparse{int(veclen(\x,\y) < 5+\n)}
\ifnum\pgfmathresult=1
\pgfpointdiff{\pgfpointanchor{O}{center}}{\pgfpointanchor{P}{center}}
\pgfgetlastxy\x\y
\pgfmathparse{int(veclen(\x,\y) < 5+\n)}
\ifnum\pgfmathresult=1
\begin{scope}[fill opacity=0.3]
\draw[fill=yellow] (P) -- (Q) -- (T) -- cycle;
\end{scope}
\fi
\fi
\fi
\fi
\fi
}%
\fi
\fi
}%
}
}
\end{tikzpicture}
\end{column}
\end{columns}
}
\end{frame}
\end{document}
結果は次のとおりです: