将 tikz 曲线与随机变化相结合

将 tikz 曲线与随机变化相结合

我想将定义的曲线与\draw沿路径的随机变化结合起来。

到目前为止,我在 tex.SE 上发现了一些有趣的讨论,例如如何在 tikz/pgf 中绘制布朗运动如何修复由 Beamer 框架中的 tikz 的“rand”函数生成的布朗运动的轨迹,并且(感谢 Kpym,我监督了这一点)模拟手绘线条,但它们没有按预期工作。

使用 tikz-decorations 看起来很有希望,但仅适用于相对笔直的曲线。

以下 MWE 给出了此结果:

在此处输入图片描述

\documentclass{article}
\usepackage{tikz}
\usetikzlibrary{decorations.pathmorphing}

\begin{document}
\begin{tikzpicture}[x=5mm,y=5mm,decoration={random steps,segment length=3mm,amplitude=1mm}]
  \draw[thick,green] (0, 1) -- (14.5, 1);
  \draw[thick,red,decorate,rounded corners]   (0,-0.5) -- (14.5,-0.5);
  \draw[thick,blue,decorate,rounded corners] (0, 0.5) -- (1,0.5) -- (1.5,-4) -- (2,-3.5) -- (3.5,-2) -- (14.5, 0);
\end{tikzpicture}
\end{document}

第三个(蓝色)\draw命令没有产生我想要的结果 - 甚至红线在 x 方向的约 75% 处也出现了“故障”。

根据 tikz-manual 的原因是:每个步骤的末尾都会在 x 和 y 方向上受到从区间 [−d,d] 中均匀绘制的两个值的扰动,其中 d 是振幅的值。这与曲线选项相冲突,因为曲线选项中仅改变 y 值就应产生所需的输出。由于图表描述的是值随时间的变化,因此它们可能不会转向负 x 方向。

有没有办法限制random steps装饰仅操纵 x 值而不操纵 y 值?另一种方法是通过离散间隔的随机扭曲(如布朗运动)覆盖曲线……

希望结果在某种程度上是稳定的(这与随机转变的想法相冲突 - 哈哈)没有必要控制种子......

答案1

这是对问题的回答:在 y 方向上可以有随机步骤吗?答案是肯定的,只需复制随机步骤的定义并将偏移设置x为零即可。

\documentclass{article}
\usepackage{tikz}
\usetikzlibrary{decorations.pathmorphing}
\pgfdeclaredecoration{random y steps}{start}
{%
  \state{start}[width=+0pt,next state=step,persistent precomputation=\pgfdecoratepathhascornerstrue]{}%
  \state{step}[auto end on length=1.5\pgfdecorationsegmentlength,
               auto corner on length=1.5\pgfdecorationsegmentlength,
               width=+\pgfdecorationsegmentlength]
  {
    \pgfpathlineto{
      \pgfpointadd
      {\pgfpoint{\pgfdecorationsegmentlength}{0pt}}
      {\pgfpoint{0pt}{rand*\pgfdecorationsegmentamplitude}}
    }
  }%
  \state{final}
  {}%
}%

\begin{document}
\begin{tikzpicture}[x=5mm,y=5mm,decoration={random y steps,segment length=3mm,amplitude=1mm}]
  \draw[thick,green] (0, 1) -- (14.5, 1);
  \draw[thick,red,decorate,rounded corners]   (0,-0.5) -- (14.5,-0.5);
  \draw[thick,blue,decorate,rounded corners] (0, 0.5) -- (1,0.5) -- (1.5,-4) -- (2,-3.5) -- (3.5,-2) -- (14.5, 0);
\end{tikzpicture}
\end{document}

在此处输入图片描述

当然,也可以画出平滑的随机曲线。此时,这需要分两步进行。

  1. \path[decorate] <path>;
  2. \draw[<options>] plot[variable=\x,samples at={1,...,\arabic{randymark}},smooth] (randymark\x);

\documentclass[tikz,border=3.14mm]{standalone}
\usetikzlibrary{decorations.pathmorphing}
\newcounter{randymark}
\pgfdeclaredecoration{mark random y steps}{start}
{%
  \state{start}[width=+0pt,next state=step,%
  persistent precomputation={\pgfdecoratepathhascornerstrue%
  \setcounter{randymark}{0}}]{
  \stepcounter{randymark}
  \pgfcoordinate{randymark\arabic{randymark}}{\pgfpoint{0pt}{0pt}}
  }%
  \state{step}[auto end on length=1.5\pgfdecorationsegmentlength,
               auto corner on length=1.5\pgfdecorationsegmentlength,
               width=+\pgfdecorationsegmentlength]
  { \stepcounter{randymark}
    \pgfcoordinate{randymark\arabic{randymark}}{\pgfpoint{\pgfdecorationsegmentlength}{rand*\pgfdecorationsegmentamplitude}}
  }%
  \state{final}
  {
    \stepcounter{randymark}
    \pgfcoordinate{randymark\arabic{randymark}}{\pgfpointdecoratedpathlast}}%
}%

\begin{document}
\begin{tikzpicture}[x=5mm,y=5mm,decoration={mark random y steps,segment length=3mm,amplitude=1mm}]
  \path[decorate]   (0,-0.5) -- (14.5,-0.5);
  \draw[red,thick] plot[variable=\x,samples at={1,...,\arabic{randymark}},smooth] 
   (randymark\x);
  \path[decorate] (0, 0.5) -- (1,0.5) -- (1.5,-4) -- (2,-3.5) -- (3.5,-2) -- (14.5, 0);
  \draw[blue,thick] plot[variable=\x,samples at={1,...,\arabic{randymark}},smooth] 
   (randymark\x);
  \path[decorate] (4,4) circle(3cm); 
  \draw[orange,thick] plot[variable=\x,samples at={1,...,\arabic{randymark}},smooth] 
   (randymark\x);
\end{tikzpicture}
\end{document}

在此处输入图片描述

请注意,这当然不是第一篇通过路径绘制平滑随机曲线的文章,之前已经有几篇这样的文章了,包括这个这个,答案这个问题以及答案这个问题

相关内容