SVG线旋转和动画

时间:2015-09-14 02:30:34

标签: svg svg-animate

我试图让一条线在两点之间移动。

为了只需要一个渐变,我使用transform旋转线条。

详情请见:SVG gradients direction

现在,当我在线上应用动画时,它表现得很奇怪。 它不会去真正的目的地附近,我也不太了解发生了什么。

特别奇怪的是,如果我删除了rotate转换,那么这些线就会转到正确的位置(但显然它没有正确的渐变)。

<svg height="670.9" width="1920">
    <defs>
        <linearGradient y2="100%" x2="100%" y1="0%" x1="0%" id="linegradred">
            <stop style="stop-color:#F70D1A;stop-opacity:0" offset="0%" />
            <stop style="stop-color:#F70D1A;stop-opacity:0.3" offset="50%" />
            <stop style="stop-color:#F70D1A;stop-opacity:0.8" offset="100%" />
        </linearGradient>
    </defs>
    <circle cx="964" cy="426" r="4" stroke="black" fill="black" opacity="0.5" class="circle_loc"/>
    <circle cx="924" cy="230" r="4" stroke="black" fill="black" opacity="0.5" class="circle_loc" />
    <line class="svg_line_red" id="line_1442197044254" x1="964" y1="426" fill="url(#linegradred)" stroke="url(#linegradred)" x2="1030" y2="492" transform="rotate(-146.5346206536447 964 426)">
        <animate attributeName="x1" attributeType="XML" to="924" fill="freeze" dur="1.1s" />
        <animate attributeName="y1" attributeType="XML" to="230" fill="freeze" dur="1.1s" />
        <animate attributeName="x2" attributeType="XML" to="924" fill="freeze" dur="1s" />
        <animate attributeName="y2" attributeType="XML" to="230" fill="freeze" dur="1s" />
    </line>
    <circle cx="590" cy="344" r="4" stroke="black" fill="black" opacity="0.5" class="circle_loc" />
    <circle cx="924" cy="230" r="4" stroke="black" fill="black" opacity="0.5" class="circle_loc" />
    <line class="svg_line_red" id="line_1442197045251" x1="590" y1="344" fill="url(#linegradred)" stroke="url(#linegradred)" x2="707" y2="461" transform="rotate(-63.84566422168709 590 344)">
        <animate attributeName="x1" attributeType="XML" to="924" fill="freeze" dur="1.1s" />
        <animate attributeName="y1" attributeType="XML" to="230" fill="freeze" dur="1.1s" />
        <animate attributeName="x2" attributeType="XML" to="924" fill="freeze" dur="1s" />
        <animate attributeName="y2" attributeType="XML" to="230" fill="freeze" dur="1s" />
    </line>
    <circle cx="771" cy="363" r="4" stroke="black" fill="black" opacity="0.5" class="circle_loc" />
    <circle cx="924" cy="230" r="4" stroke="black" fill="black" opacity="0.5" class="circle_loc" />
    <line class="svg_line_red" id="line_1442197046253" x1="771" y1="363" fill="url(#linegradred)" stroke="url(#linegradred)" x2="838" y2="430" transform="rotate(-85.99981423948691 771 363)">
        <animate attributeName="x1" attributeType="XML" to="924" fill="freeze" dur="1.1s" />
        <animate attributeName="y1" attributeType="XML" to="230" fill="freeze" dur="1.1s" />
        <animate attributeName="x2" attributeType="XML" to="924" fill="freeze" dur="1s" />
        <animate attributeName="y2" attributeType="XML" to="230" fill="freeze" dur="1s" />
    </line>
</svg>

这是一个小提琴:https://jsfiddle.net/qj7z2hhr/

任何帮助,以了解为什么这样做会非常感激。

1 个答案:

答案 0 :(得分:1)

在SVG文件中,层次结构中较低的任何内容都会受到其祖先元素中的内容的影响。因此,动画中的所有坐标也会受到应用于其父元素(线条)的旋转的影响。

如果要修复它,则必须在之后(即高于)旋转时应用平移动画。你可以做的一种方法是用一个组围绕线。将旋转应用于该行,并将animateTransform应用于该组。

<强>更新

实际上我的建议是行不通的。我没有考虑到你是动画线的起点和终点这一事实。

但我有另一个建议。使每一行成为基于(0,0)的向量,并且长度与原始行匹配。即:

x1=0        y1=0
x2=(x2-x1)  y2=(y2-y2)

然后,您可以将所需动画创建为三个动画组件的组合。

  1. 原始起点和终点之间的转换。
  2. 从1到0的比例,使开始和结束收敛到单个点
  3. 固定旋转变换,使您的线和渐变点指向正确的方向
  4. 这是结果。我刚刚实现了两条线来向您展示它是如何工作的。我会让你决定这是否比只有多个渐变更简单。

    <svg viewBox="0 0 1920 670.9">
        <defs>
            <linearGradient y2="100%" x2="100%" y1="0%" x1="0%" id="linegradred">
                <stop style="stop-color:#F70D1A;stop-opacity:0" offset="0%" />
                <stop style="stop-color:#F70D1A;stop-opacity:0.3" offset="50%" />
                <stop style="stop-color:#F70D1A;stop-opacity:0.8" offset="100%" />
            </linearGradient>
        </defs>
    
        <circle cx="964" cy="426" r="4" stroke="black" fill="black" opacity="0.5" class="circle_loc"/>
        <circle cx="924" cy="230" r="4" stroke="black" fill="black" opacity="0.5" class="circle_loc" />
    
        <line class="svg_line_red" id="line_1442197044254"
              x2="66" y2="66"
              fill="url(#linegradred)" stroke="url(#linegradred)">
            <animateTransform attributeName="transform" attributeType="XML"
                              type="translate" from="964 426" to="924 230" dur="1.1s"
                              additive="sum" fill="freeze" />
            <animateTransform attributeName="transform" attributeType="XML"
                              type="scale" from="1" to="0" dur="1.1s"
                              additive="sum" fill="freeze" />
            <animateTransform attributeName="transform" attributeType="XML"
                              type="rotate" from="-146.5" to="-146.5" dur="1.1s"
                              additive="sum" fill="freeze" />
        </line>
    
        <circle cx="590" cy="344" r="4" stroke="black" fill="black" opacity="0.5" class="circle_loc" />
        <circle cx="924" cy="230" r="4" stroke="black" fill="black" opacity="0.5" class="circle_loc" />
    
        <line class="svg_line_red" id="line_1442197045251"
              x2="117" y2="116"
              fill="url(#linegradred)" stroke="url(#linegradred)">
            <animateTransform attributeName="transform" attributeType="XML"
                              type="translate" from="590 344" to="924 230" dur="1.1s"
                              additive="sum" fill="freeze" />
            <animateTransform attributeName="transform" attributeType="XML"
                              type="scale" from="1" to="0" dur="1.1s"
                              additive="sum" fill="freeze" />
            <animateTransform attributeName="transform" attributeType="XML"
                              type="rotate" from="-63.8" to="-63.8" dur="1.1s"
                              additive="sum" fill="freeze" />
        </line>
    
    </svg>