【问题标题】:SVG line cross animation for icons图标的 SVG 线交叉动画
【发布时间】:2020-03-03 03:11:44
【问题描述】:

我有两个icons,一个是原始状态,一个是划掉状态。 我想为交叉线设置动画,但更改 dash-offset 没有用,因为它们是两个不同的 svg。

我正在查看these 动画图标,但仍然无法弄清楚其中的神奇之处。我想问:

  • 过渡工作流程应该是什么?
  • 我更喜欢用纯CSS,可以吗?

一个工作示例将不胜感激。

【问题讨论】:

  • 如果唯一的变化是线条,为什么要使用两个图标?您可以在第一个图标上设置路径动画吗?
  • 因为如果你仔细观察,'off' 图标有完全不同的 svg 路径,并且它们之间有一个'gap'。

标签: css animation svg


【解决方案1】:

该页面上的动画图标非常复杂(更多的是它们需要是 IMO)。但基本上他们所做的是从右向左滑动一个矩形遮罩,覆盖第一个图标,并露出第二个图标。

这是一个使用纯 CSS 的简化版本,希望它更清晰。

svg {
  width: 100px;
  height: 100px;
}

/* slides the two masks to the left on hover */
svg:hover #bottom-rect,
svg:hover #top-rect
{
  transition: transform 500ms;
  transform: translate(-24px, 0px);
}

/* slides the two masks back to the right when not hovered */
svg #bottom-rect,
svg #top-rect {
  transition: transform 500ms;
  transform: translate(0px, 0px);
}
<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">
    <defs>
        <mask id="bottom">
          <rect id="bottom-rect" width="24" height="24" fill="white" stroke="none"/>
        </mask>
        <mask id="top">
          <rect id="top-rect" x="24" width="24" height="24" fill="white" stroke="none"/>
        </mask>
    </defs>    
   
    <g mask="url(#bottom)">
      <path d="M12 1a3 3 0 0 0-3 3v8a3 3 0 0 0 6 0V4a3 3 0 0 0-3-3z"></path>
      <path d="M19 10v2a7 7 0 0 1-14 0v-2"></path>
      <line x1="12" y1="19" x2="12" y2="23"></line>
      <line x1="8" y1="23" x2="16" y2="23"></line>
    </g>
    <g mask="url(#top)">
      <line x1="1" y1="1" x2="23" y2="23"></line>
      <path d="M9 9v3a3 3 0 0 0 5.12 2.12M15 9.34V4a3 3 0 0 0-5.94-.6"></path>
      <path d="M17 16.95A7 7 0 0 1 5 12v-2m14 0v2a7 7 0 0 1-.11 1.23"></path>
      <line x1="12" y1="19" x2="12" y2="23"></line>
      <line x1="8" y1="23" x2="16" y2="23"></line>
    </g>
</svg>

【讨论】:

    【解决方案2】:

    一种使用 CSS 的方法。

    您只需在悬停时显示/隐藏您想要的图标。要为线条设置动画,请使用带有stroke-dasharraystroke-dashoffset 的CSS 动画。代码中的注释。

    /* for demo */
    svg {
      width: 100px;
      height: 100px;
      border: 1px solid black;
    } 
    
    /* hide the off icon */
    svg .off {
      opacity: 0;
    }
    
    /* when user hovers SVG, the on icon is hidden... */
    svg:hover .on {
      opacity: 0;
    }
    
    /* ... and the off icon is shown */
    svg:hover .off {
      opacity: 1;
    }
    
    /* initial values for the stroke
       -- these can be obtained with JS, 
       -- or you can work them out manually for CSS
    */
    
    svg .line {
      stroke-dashoffset: 40px;
      stroke-dasharray: 40px;
    }
    
    /* when user hovers SVG, animate the line */
    svg:hover .line {
      animation: addLine 800ms forwards;
    }
    
    /* values for line animation */
    @keyframes addLine {
      from {
        stroke-dashoffset: 40px;
      }
      to {
        stroke-dashoffset: 0;
      }
    }
    <svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"> 
        <g class="on">
          <path d="M12 1a3 3 0 0 0-3 3v8a3 3 0 0 0 6 0V4a3 3 0 0 0-3-3z"></path>
          <path d="M19 10v2a7 7 0 0 1-14 0v-2"></path>
          <line x1="12" y1="19" x2="12" y2="23"></line>
          <line x1="8" y1="23" x2="16" y2="23"></line>
        </g>
        <g class="off">
          <line class="line" x1="1" y1="1" x2="23" y2="23"></line>
          <path d="M9 9v3a3 3 0 0 0 5.12 2.12M15 9.34V4a3 3 0 0 0-5.94-.6"></path>
          <path d="M17 16.95A7 7 0 0 1 5 12v-2m14 0v2a7 7 0 0 1-.11 1.23"></path>
          <line x1="12" y1="19" x2="12" y2="23"></line>
          <line x1="8" y1="23" x2="16" y2="23"></line>
        </g>
    </svg>

    【讨论】:

    • 我想过这个解决方案,但正如您在示例网站中看到的那样,它们的动画在线条交叉时更加流畅。
    猜你喜欢
    • 1970-01-01
    • 2016-12-02
    • 1970-01-01
    • 2021-11-13
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多