【问题标题】:How do I move an SVG group with CSS keyframes?如何使用 CSS 关键帧移动 SVG 组?
【发布时间】:2019-10-08 14:09:41
【问题描述】:

我想使用 CSS 关键帧在其容器中移动 SVG 元素。

如果我只有一个<circle />,我可以简单地在关键帧定义中使用cx / cy 属性。但是如果我有一个任意组(<g />)怎么办?一个组没有cx/cy,如果我想使用CSS'transform: translate(x,y),似乎我必须定义一个单元(如px)。

MWE(如何为bar 组设置动画?):

svg {
padding: 5px;
width: 150px;
height: 150px;
border: 1px solid #000;
}

.foo {
animation-duration: 3s;
animation-iteration-count: infinite;
animation-name: moveFoo;
}

.bar {
animation-duration: 3s;
animation-iteration-count: infinite;
animation-name: moveBar;
}

@keyframes moveFoo {
from {
cx: 10;
cy: 10;
}
to {
cx: 90;
cy: 90;
}
}

/* how to define this? */
@keyframes moveBar { }
<svg viewbox="0 0 100 100" xmlns="http://www.w3.org/2000/svg">
<circle class="foo" r="5" fill="red" />
<g class="bar" transform="translate(90 10)">
    <circle r="5" fill="blue" />
    <text
        y="1"
        text-anchor="middle"
        fill="white"
        font-family="monospace"
        font-size="5">
    AB
</text>
</g>
</svg>

【问题讨论】:

    标签: html css svg


    【解决方案1】:

    使用animateTransform 执行此操作:

    svg {
      padding: 5px;
      width: 150px;
      height: 150px;
      border: 1px solid #000;
    }
    <svg viewbox="0 0 100 100" xmlns="http://www.w3.org/2000/svg">
    <circle class="foo" r="5" fill="red" />
    <g id="bar" transform="translate(90 10)">
    
        <circle r="5" fill="blue" />
        <text
            y="1"
            text-anchor="middle"
            fill="white"
            font-family="monospace"
            font-size="5">
        AB
    </text>
    </g>
    <animateTransform xlink:href="#bar" 
        attributeName="transform" 
        type="translate"
        from="90,10" to="90,90"
        dur="2" repeatCount="indefinite"/>
    </svg>

    【讨论】:

    • 很好,我真的需要再看看 SVG 并开始学习像 &lt;animateTransform /&gt; 这样的效果。 +1
    【解决方案2】:

    如果我想使用,我似乎必须定义一个单位(如 px) CSS 的变换:translate(x,y)。

    是的,确实如此。

    但这不是问题,如果您已经在 &lt;svg&gt; 元素中声明了 viewbox 属性。

    如果您声明了viewbox1px 将代表 1 个视图框单元。

    工作示例:

    svg {
    padding: 5px;
    width: 150px;
    height: 150px;
    border: 1px solid #000;
    }
    
    .foo {
    fill: red;
    transform: translate(10px, 10px);
    animation-duration: 3s;
    animation-iteration-count: infinite;
    animation-name: moveFoo;
    }
    
    .bar {
    transform: translate(90px, 10px);
    animation-duration: 3s;
    animation-iteration-count: infinite;
    animation-name: moveBar;
    }
    
    .bar circle {
    fill: blue;
    }
    
    .bar text {
    fill: white;
    font-family: monospace;
    font-size: 5px;
    text-anchor: middle;
    }
    
    @keyframes moveFoo {
       0% {transform: translate(10px, 10px);}
      50% {transform: translate(90px, 90px);}
     100% {transform: translate(10px, 10px);}
    }
    
    @keyframes moveBar {
       0% {transform: translate(90px, 10px);}
      50% {transform: translate(10px, 90px);}
     100% {transform: translate(90px, 10px);}
    }
    <svg viewbox="0 0 100 100" xmlns="http://www.w3.org/2000/svg">
    
    <circle class="foo" r="5" />
    
    <g class="bar">
      <circle r="5" />
      <text y="1">AB</text>
    </g>
    
    </svg>

    【讨论】:

    • 非常感谢,我不知道与 viewbox 单元的关系 :)
    【解决方案3】:

    如果您需要使用 @keyframes 而不是为 cx 和 cy 属性设置动画,则必须从 transform:translate(0,0) 动画到 transform:translate(90px,90px)(例如)。

    否则 Temani Afif 的答案是完全有效的。 `

    svg {
    padding: 5px;
    width: 150px;
    height: 150px;
    border: 1px solid #000;
    }
    
    .foo {
    transform:translate(0,0);
    animation-duration: 3s;
    animation-iteration-count: infinite;
    animation-name: moveFoo;
    }
    
    .bar {
    transform:translate(0,0);
    animation-duration: 3s;
    animation-iteration-count: infinite;
    animation-name: moveBar;
    }
    
    
    
    @keyframes moveFoo {
    from {
    transform:translate(0,0)
    }
    to {
    transform:translate(90px,90px)
    }
    }
    
    /* how to define this? */
    @keyframes moveBar { 
    from {
    transform:translate(0,0)
    }
    to {
    transform:translate(90px,90px)
    }
    }
    <svg viewbox="0 0 100 100" xmlns="http://www.w3.org/2000/svg">
    <circle class="foo" r="5" fill="red" />
    <g class="bar" >
        <circle r="5" fill="blue" cx="10" cy="10" />
        <text
            x="10"
            y="11"
            text-anchor="middle"
            fill="white"
            font-family="monospace"
            font-size="5">
      AB
    </text>
    </g>
    </svg>

    【讨论】:

      猜你喜欢
      • 2015-01-15
      • 2013-03-08
      • 2015-01-05
      • 2014-05-25
      • 1970-01-01
      • 2017-01-26
      • 1970-01-01
      • 2013-08-12
      相关资源
      最近更新 更多