问题描述
希望我正确地解释了这一点。 我有两个沿两个不同路径运行的脉冲动画。我已经播放了动画的持续时间,但似乎可以让它们在它们加入的位置“同步”,以便只有一个圆圈到达顶部。 这可能吗?
这是我的代码:
<?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的答案开始构建,您还可以使用keyTimes
和keyPoints
来更改水平和垂直部分中动画的速度。您需要了解以下几点:
-
首先,您需要将
#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>
您可以修改长度,但仍会保持同步