沿不同路径同步两个SVG动画

如何解决沿不同路径同步两个SVG动画

希望我正确地解释了这一点。 我有两个沿两个不同路径运行的脉冲动画。我已经播放了动画的持续时间,但似乎可以让它们在它们加入的位置“同步”,以便只有一个圆圈到达顶部。 这可能吗?

这是我的代码:

<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
   xmlns:dc="http://purl.org/dc/elements/1.1/"
   xmlns:cc="http://creativecommons.org/ns#"
   xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
   xmlns:svg="http://www.w3.org/2000/svg"
   xmlns="http://www.w3.org/2000/svg"
   xmlns:xlink="http://www.w3.org/1999/xlink"
   xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
   xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
   width="300"
   height="300"
   viewBox="0 0 120 120"
   version="1.1"
   id="svg11"
   sodipodi:docname="testAn.svg"
   inkscape:version="0.92.5 (2060ec1f9f,2020-04-08)">
  <metadata
     id="metadata17">
    <rdf:RDF>
      <cc:Work
         rdf:about="">
        <dc:format>image/svg+xml</dc:format>
        <dc:type
           rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
      </cc:Work>
    </rdf:RDF>
  </metadata>
  <defs
     id="defs15" />
  <sodipodi:namedview
     pagecolor="#ffffff"
     bordercolor="#666666"
     borderopacity="1"
     objecttolerance="10"
     gridtolerance="10"
     guidetolerance="10"
     inkscape:pageopacity="0"
     inkscape:pageshadow="2"
     inkscape:window-width="1600"
     inkscape:window-height="837"
     id="namedview13"
     showgrid="false"
     inkscape:zoom="2.4857496"
     inkscape:cx="201.80878"
     inkscape:cy="187.12268"
     inkscape:window-x="-8"
     inkscape:window-y="-8"
     inkscape:window-maximized="1"
     inkscape:current-layer="svg11" />
  <g
     id="g140"
     transform="translate(35.662173,31.252367)">
    <path
       id="theMotionPath-sa"
       d="M 10,10 V 40 H 52"
       inkscape:connector-curvature="0"
       style="fill:none;stroke:#4789d0;stroke-width:1" />
    <circle
       id="circle119"
       r="2"
       cy="0"
       cx="0"
       style="fill:#4789d0">
      <!-- Define the motion path animation -->
      <animateMotion
         keyTimes="0;1"
         calcMode="linear"
         keyPoints="1;0"
         repeatCount="indefinite"
         dur="3s"
         begin="0s">
        <mpath
           xlink:href="#theMotionPath-sa" />
      </animateMotion>
    </circle>
    <circle
       id="circle121"
       r="2"
       cy="0"
       cx="0"
       style="fill:#4789d0">
      <!-- Define the motion path animation -->
      <animateMotion
         keyTimes="0;1"
         calcMode="linear"
         keyPoints="1;0"
         repeatCount="indefinite"
         dur="3s"
         begin="1s">
        <mpath
           xlink:href="#theMotionPath-sa" />
      </animateMotion>
    </circle>
    <circle
       id="circle123"
       r="2"
       cy="0"
       cx="0"
       style="fill:#4789d0">
      <!-- Define the motion path animation -->
      <animateMotion
         keyTimes="0;1"
         calcMode="linear"
         keyPoints="1;0"
         repeatCount="indefinite"
         dur="3s"
         begin="2s">
        <mpath
           xlink:href="#theMotionPath-sa" />
      </animateMotion>
    </circle>
    <circle
       id="circle125"
       r="2"
       cy="0"
       cx="0"
       style="fill:#4789d0">
      <!-- Define the motion path animation -->
      <animateMotion
         keyTimes="0;1"
         calcMode="linear"
         keyPoints="1;0"
         repeatCount="indefinite"
         dur="3s"
         begin="3s">
        <mpath
           xlink:href="#theMotionPath-sa" />
      </animateMotion>
    </circle>
  </g>
  <g
     id="g57"
     transform="translate(15.662173,36.252367)">
    <path
       id="theMotionPath-ch"
       d="M 10,35 H 30 V 3"
       inkscape:connector-curvature="0"
       style="fill:none;stroke:#4789d0;stroke-width:1" />
    <circle
       id="circle36"
       r="2"
       cy="0"
       cx="0"
       style="fill:#4789d0">
      <!-- Define the motion path animation -->
      <animateMotion
         keyTimes="0;1"
         calcMode="linear"
         keyPoints="0;1"
         repeatCount="indefinite"
         dur="3s"
         begin="0s">
        <mpath
           xlink:href="#theMotionPath-ch" />
      </animateMotion>
    </circle>
    <circle
       id="circle38"
       r="2"
       cy="0"
       cx="0"
       style="fill:#4789d0">
      <!-- Define the motion path animation -->
      <animateMotion
         keyTimes="0;1"
         calcMode="linear"
         keyPoints="0;1"
         repeatCount="indefinite"
         dur="3s"
         begin="1s">
        <mpath
           xlink:href="#theMotionPath-ch" />
      </animateMotion>
    </circle>
    <circle
       id="circle40"
       r="2"
       cy="0"
       cx="0"
       style="fill:#4789d0">
      <!-- Define the motion path animation -->
      <animateMotion
         keyTimes="0;1"
         calcMode="linear"
         keyPoints="0;1"
         repeatCount="indefinite"
         dur="3s"
         begin="2s">
        <mpath
           xlink:href="#theMotionPath-ch" />
      </animateMotion>
    </circle>
    <circle
       id="circle42"
       r="2"
       cy="0"
       cx="0"
       style="fill:#4789d0">
      <!-- Define the motion path animation -->
      <animateMotion
         keyTimes="0;1"
         calcMode="linear"
         keyPoints="0;1"
         repeatCount="indefinite"
         dur="3s"
         begin="3s">
        <mpath
           xlink:href="#theMotionPath-ch" />
      </animateMotion>
    </circle>
  </g>
</svg>

希望这很有道理!

解决方法

您的主要问题是,由于运动路径的长度不同,因此点的移动速度不同。我认为最明智的解决方案是定义三个单独的运动路径,一个用于左腿和右腿,一个用于上腿。然后,对动画进行时间调整,以使动画在左腿和右腿同时在中心点结束,并在向上同时在 start 腿。

这需要仔细计划运动速度和时间,并暗含有关路径长度的知识。为了使推理更容易,我已经解决了SVG中的转换问题,并对路径进行了重新定位和调整。另外,我已经反转了右腿的方向,因此您不需要反转运动的方向-节省您拼写keyPoints / keyTimes属性的可能性。

这就是我得到的:

id                   d              length   dur
theMotionPath-left   M 25 70 H 45   20       1.5s
theMotionPath-right  M 85 70 H 45   40       3s
theMotionPath-up     M 45 70 V 40   30       2s

不同腿部的速度确实完美匹配,仅近似一致。但这并没有威慑力,重要的是所有点都在每秒钟达到/离开中心点。

不过,左腿有问题。 repeatCount="indefinite"表示动画在完成后立即重新开始。从1.5s开始的动作将在3s处结束,然后在4.5s,6s,7.5s等之后再次出现。。。每秒钟的动作会与其他部分匹配。

解决此问题的方法是在每个动画开始之间增加一个延迟:运行1.5秒,等待1.5秒,再次运行等。

这可以通过技巧来完成。可以bind the start of an animation to the end of another animation-或同一动画的不同运行。忽略repeatCount属性,但定义一个{em}列表 begin次:

      <animateMotion id="leftDot1" dur="1.5s" begin="1.5s;leftDot1.end + 1.5s">
        <mpath xlink:href="#theMotionPath-left" />
      </animateMotion>

1.5秒后,动画将首次开始播放,此外,每次ID为leftDot1(本身)的动画结束时,动画都会等待1.5秒,然后再次开始播放。

<svg width="300" height="300" viewBox="0 0 120 120"
     xmlns="http://www.w3.org/2000/svg"
     xmlns:xlink="http://www.w3.org/1999/xlink">
  <g>
    <path id="theMotionPath-left" d="M 25 70 H 45"
          style="fill:none;stroke:#4789d0;stroke-width:1" />
    <circle r="2" cy="0" cx="0" style="fill:#4789d0">
      <animateMotion id="leftDot1" dur="1.5s" begin="1.5s;leftDot1.end + 1.5s">
        <mpath xlink:href="#theMotionPath-left" />
      </animateMotion>
    </circle>
    <circle r="2" cy="0" cx="0" style="fill:#4789d0">
      <animateMotion id="leftDot2" dur="1.5s" begin="2.5s;leftDot2.end + 1.5s">
        <mpath xlink:href="#theMotionPath-left" />
      </animateMotion>
    </circle>
    <circle r="2" cy="0" cx="0" style="fill:#4789d0">
      <animateMotion id="leftDot3" dur="1.5s" begin="3.5s;leftDot3.end + 1.5s">
        <mpath xlink:href="#theMotionPath-left" />
      </animateMotion>
    </circle>
  </g>
  <g>
    <path id="theMotionPath-right" d="M 85 70 H 45"
          style="fill:none;stroke:#4789d0;stroke-width:1" />
    <circle r="2" cy="0" cx="0" style="fill:#4789d0">
      <animateMotion repeatCount="indefinite" dur="3s" begin="0s">
        <mpath xlink:href="#theMotionPath-right" />
      </animateMotion>
    </circle>
    <circle r="2" cy="0" cx="0" style="fill:#4789d0">
      <animateMotion repeatCount="indefinite" dur="3s" begin="1s">
        <mpath xlink:href="#theMotionPath-right" />
      </animateMotion>
    </circle>
    <circle r="2" cy="0" cx="0" style="fill:#4789d0">
      <animateMotion repeatCount="indefinite" dur="3s" begin="2s">
        <mpath xlink:href="#theMotionPath-right" />
      </animateMotion>
    </circle>
  </g>
  <g>
    <path id="theMotionPath-up" d="M 45 70 V 40"
          style="fill:none;stroke:#4789d0;stroke-width:1" />
    <circle r="2" cy="0" cx="0" style="fill:#4789d0">
      <animateMotion repeatCount="indefinite" dur="2s" begin="3s">
        <mpath xlink:href="#theMotionPath-up" />
      </animateMotion>
    </circle>
    <circle r="2" cy="0" cx="0" style="fill:#4789d0">
      <animateMotion repeatCount="indefinite" dur="2s" begin="4s">
        <mpath xlink:href="#theMotionPath-up" />
      </animateMotion>
    </circle>
  </g>
</svg>

,

从@ccprog的答案开始构建,您还可以使用keyTimeskeyPoints来更改水平和垂直部分中动画的速度。您需要了解以下几点:

  • 首先,您需要将#theMotionPath-ch的{​​{1}}属性设置为d,以使其到达与其他路径相同的垂直点

  • 然后,计算每条路径相对于其长度变化的点:d="M 10,35 H 30 V 5"中为0.4167,#theMotionPath-sa中为0.4。

  • 最后,添加一个额外的#theMotionPath-ch(我将其设置为keyTime,也就是说,将其设置为0.6和上一步中相应的0.6 * 3s = 1.8s。>

keyPoint

在查看示例之后,我发现只要每个动画的时间保持相同,并且每个动画运行的间隔也保持相同,那么路径的长度就不会有任何区别。将会改变的只是动画的速度。

这是另一个示例:

<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
   xmlns:dc="http://purl.org/dc/elements/1.1/"
   xmlns:cc="http://creativecommons.org/ns#"
   xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
   xmlns:svg="http://www.w3.org/2000/svg"
   xmlns="http://www.w3.org/2000/svg"
   xmlns:xlink="http://www.w3.org/1999/xlink"
   xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
   xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
   width="300"
   height="300"
   viewBox="0 0 120 120"
   version="1.1"
   id="svg11"
   sodipodi:docname="testAn.svg"
   inkscape:version="0.92.5 (2060ec1f9f,2020-04-08)">
  <metadata
     id="metadata17">
    <rdf:RDF>
      <cc:Work
         rdf:about="">
        <dc:format>image/svg+xml</dc:format>
        <dc:type
           rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
      </cc:Work>
    </rdf:RDF>
  </metadata>
  <defs
     id="defs15" />
  <sodipodi:namedview
     pagecolor="#ffffff"
     bordercolor="#666666"
     borderopacity="1"
     objecttolerance="10"
     gridtolerance="10"
     guidetolerance="10"
     inkscape:pageopacity="0"
     inkscape:pageshadow="2"
     inkscape:window-width="1600"
     inkscape:window-height="837"
     id="namedview13"
     showgrid="false"
     inkscape:zoom="2.4857496"
     inkscape:cx="201.80878"
     inkscape:cy="187.12268"
     inkscape:window-x="-8"
     inkscape:window-y="-8"
     inkscape:window-maximized="1"
     inkscape:current-layer="svg11" />
  <g
     id="g140"
     transform="translate(35.662173,31.252367)">
    <path
       id="theMotionPath-sa"
       d="M 10,10 V 40 H 52"
       inkscape:connector-curvature="0"
       style="fill:none;stroke:#4789d0;stroke-width:1" />
    <circle
       id="circle119"
       r="2"
       cy="0"
       cx="0"
       style="fill:#4789d0">
      <!-- Define the motion path animation -->
      <animateMotion
         keyTimes="0;0.6;1"
         calcMode="linear"
         keyPoints="1;0.4167;0"
         repeatCount="indefinite"
         dur="3s"
         begin="0s">
        <mpath
           xlink:href="#theMotionPath-sa" />
      </animateMotion>
    </circle>
    <circle
       id="circle121"
       r="2"
       cy="0"
       cx="0"
       style="fill:#4789d0">
      <!-- Define the motion path animation -->
      <animateMotion
         keyTimes="0;0.6;1"
         calcMode="linear"
         keyPoints="1;0.4167;0"
         repeatCount="indefinite"
         dur="3s"
         begin="1s">
        <mpath
           xlink:href="#theMotionPath-sa" />
      </animateMotion>
    </circle>
    <circle
       id="circle123"
       r="2"
       cy="0"
       cx="0"
       style="fill:#4789d0">
      <!-- Define the motion path animation -->
      <animateMotion
         keyTimes="0;0.6;1"
         calcMode="linear"
         keyPoints="1;0.4167;0"
         repeatCount="indefinite"
         dur="3s"
         begin="2s">
        <mpath
           xlink:href="#theMotionPath-sa" />
      </animateMotion>
    </circle>
    <circle
       id="circle125"
       r="2"
       cy="0"
       cx="0"
       style="fill:#4789d0">
      <!-- Define the motion path animation -->
      <animateMotion
         keyTimes="0;0.6;1"
         calcMode="linear"
         keyPoints="1;0.4167;0"
         repeatCount="indefinite"
         dur="3s"
         begin="3s">
        <mpath
           xlink:href="#theMotionPath-sa" />
      </animateMotion>
    </circle>
  </g>
  <g
     id="g57"
     transform="translate(15.662173,36.252367)">
    <path
       id="theMotionPath-ch"
       d="M 10,35 H 30 V 5"
       inkscape:connector-curvature="0"
       style="fill:none;stroke:#4789d0;stroke-width:1" />
    <circle
       id="circle36"
       r="2"
       cy="0"
       cx="0"
       style="fill:#4789d0">
      <!-- Define the motion path animation -->
      <animateMotion
         keyTimes="0;0.6;1"
         calcMode="linear"
         keyPoints="0;0.40;1"
         repeatCount="indefinite"
         dur="3s"
         begin="0s">
        <mpath
           xlink:href="#theMotionPath-ch" />
      </animateMotion>
    </circle>
    <circle
       id="circle38"
       r="2"
       cy="0"
       cx="0"
       style="fill:#4789d0">
      <!-- Define the motion path animation -->
      <animateMotion
         keyTimes="0;0.6;1"
         calcMode="linear"
         keyPoints="0;0.40;1"
         repeatCount="indefinite"
         dur="3s"
         begin="1s">
        <mpath
           xlink:href="#theMotionPath-ch" />
      </animateMotion>
    </circle>
    <circle
       id="circle40"
       r="2"
       cy="0"
       cx="0"
       style="fill:#4789d0">
      <!-- Define the motion path animation -->
      <animateMotion
         keyTimes="0;0.6;1"
         calcMode="linear"
         keyPoints="0;0.40;1"
         repeatCount="indefinite"
         dur="3s"
         begin="2s">
        <mpath
           xlink:href="#theMotionPath-ch" />
      </animateMotion>
    </circle>
    <circle
       id="circle42"
       r="2"
       cy="0"
       cx="0"
       style="fill:#4789d0">
      <!-- Define the motion path animation -->
      <animateMotion
         keyTimes="0;0.6;1"
         calcMode="linear"
         keyPoints="0;0.40;1"
         repeatCount="indefinite"
         dur="3s"
         begin="3s">
        <mpath
           xlink:href="#theMotionPath-ch" />
      </animateMotion>
    </circle>
  </g>
</svg>

您可以修改长度,但仍会保持同步

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐


依赖报错 idea导入项目后依赖报错,解决方案:https://blog.csdn.net/weixin_42420249/article/details/81191861 依赖版本报错:更换其他版本 无法下载依赖可参考:https://blog.csdn.net/weixin_42628809/a
错误1:代码生成器依赖和mybatis依赖冲突 启动项目时报错如下 2021-12-03 13:33:33.927 ERROR 7228 [ main] o.s.b.d.LoggingFailureAnalysisReporter : *************************** APPL
错误1:gradle项目控制台输出为乱码 # 解决方案:https://blog.csdn.net/weixin_43501566/article/details/112482302 # 在gradle-wrapper.properties 添加以下内容 org.gradle.jvmargs=-Df
错误还原:在查询的过程中,传入的workType为0时,该条件不起作用 &lt;select id=&quot;xxx&quot;&gt; SELECT di.id, di.name, di.work_type, di.updated... &lt;where&gt; &lt;if test=&qu
报错如下,gcc版本太低 ^ server.c:5346:31: 错误:‘struct redisServer’没有名为‘server_cpulist’的成员 redisSetCpuAffinity(server.server_cpulist); ^ server.c: 在函数‘hasActiveC
解决方案1 1、改项目中.idea/workspace.xml配置文件,增加dynamic.classpath参数 2、搜索PropertiesComponent,添加如下 &lt;property name=&quot;dynamic.classpath&quot; value=&quot;tru
删除根组件app.vue中的默认代码后报错:Module Error (from ./node_modules/eslint-loader/index.js): 解决方案:关闭ESlint代码检测,在项目根目录创建vue.config.js,在文件中添加 module.exports = { lin
查看spark默认的python版本 [root@master day27]# pyspark /home/software/spark-2.3.4-bin-hadoop2.7/conf/spark-env.sh: line 2: /usr/local/hadoop/bin/hadoop: No s
使用本地python环境可以成功执行 import pandas as pd import matplotlib.pyplot as plt # 设置字体 plt.rcParams[&#39;font.sans-serif&#39;] = [&#39;SimHei&#39;] # 能正确显示负号 p
错误1:Request method ‘DELETE‘ not supported 错误还原:controller层有一个接口,访问该接口时报错:Request method ‘DELETE‘ not supported 错误原因:没有接收到前端传入的参数,修改为如下 参考 错误2:cannot r
错误1:启动docker镜像时报错:Error response from daemon: driver failed programming external connectivity on endpoint quirky_allen 解决方法:重启docker -&gt; systemctl r
错误1:private field ‘xxx‘ is never assigned 按Altʾnter快捷键,选择第2项 参考:https://blog.csdn.net/shi_hong_fei_hei/article/details/88814070 错误2:启动时报错,不能找到主启动类 #
报错如下,通过源不能下载,最后警告pip需升级版本 Requirement already satisfied: pip in c:\users\ychen\appdata\local\programs\python\python310\lib\site-packages (22.0.4) Coll
错误1:maven打包报错 错误还原:使用maven打包项目时报错如下 [ERROR] Failed to execute goal org.apache.maven.plugins:maven-resources-plugin:3.2.0:resources (default-resources)
错误1:服务调用时报错 服务消费者模块assess通过openFeign调用服务提供者模块hires 如下为服务提供者模块hires的控制层接口 @RestController @RequestMapping(&quot;/hires&quot;) public class FeignControl
错误1:运行项目后报如下错误 解决方案 报错2:Failed to execute goal org.apache.maven.plugins:maven-compiler-plugin:3.8.1:compile (default-compile) on project sb 解决方案:在pom.
参考 错误原因 过滤器或拦截器在生效时,redisTemplate还没有注入 解决方案:在注入容器时就生效 @Component //项目运行时就注入Spring容器 public class RedisBean { @Resource private RedisTemplate&lt;String
使用vite构建项目报错 C:\Users\ychen\work&gt;npm init @vitejs/app @vitejs/create-app is deprecated, use npm init vite instead C:\Users\ychen\AppData\Local\npm-