【问题标题】:svg: styling a path within <use>svg:在 <use> 中设置路径的样式
【发布时间】:2023-03-16 12:45:01
【问题描述】:

我正在尝试使用 CSS 来设置 &lt;symbol&gt; 中特定 &lt;path&gt;fill 的样式。我已将fill:inherit 分配给符号&lt;defs&gt; 中的路径,并且我可以查询SVG DOM 中符号的&lt;use&gt; 实例,但我似乎无法在这些实例中访问该路径。我查看了 inherit 的 CSS 和 currentColor 的填充 &lt;path&gt; 但没有运气。任何帮助表示赞赏。

<svg>
  <defs>
    <style>
      symbol#DateCard path.purple {
        fill:inherit;
      }
      use[*|href="#DateCard"] path.purple{
        fill:#ff0095;
        transition:fill .6s; 
      }
      use[*|href="#DateCard"] path.purple:hover{
        path:#ff0000;
      }
    </style>
    <symbol id="DateCard">
      <path class="purple" fill="currentColor" d="..."/>
    </symbol>
  </defs>
  <use xlink:href="#DateCard"/>
<svg>

我可以查询符号内的路径,但是当我查询 &lt;use&gt; 实例内的特定路径时,这将返回一个空的 NodeList:

document.querySelectorAll('use[*|href="#DateCard"] path.purple')

【问题讨论】:

  • 无法访问 Use 元素的 shadow DOM。
  • 我正在尝试阅读这篇文章,tympanus.net/codrops/2015/07/16/styling-svg-use-content-css,我希望有办法,但我还没有完全理解它。
  • 你可以使用inherit / currentColor技巧来设置use元素的样式,但如果我没记错的话,你不能定位use元素的子元素,你只能为整个使用元素。并且只是强调一下,JavaScript 无法访问 SVG shadowDOM(但至少据我所知)——因此 querySelector 不会对符号/使用的子元素起作用。

标签: css svg shadow-dom


【解决方案1】:

shadow DOM 内的样式需要在 shadow DOM 内完成。

我从Styling SVG Content with CSS | Codrops 学到的是 CSS 变量在这种情况下非常有用。因此,我在这里创建了不同的样式设置方式:在符号内部使用样式属性和样式元素,并结合符号“外部”的 CSS 变量。

.card1 {
  --path1-color: #0099CC;
  --path2-color: #FFDF34;
}

.card2 {
  --path1-color: #00008B;
  --path2-color: #FF8C00;
}

.card2:hover {
  --path1-color: #00BFFF;
}
<svg viewBox="0 0 200 100" width="400">
  <defs>
    <symbol id="DateCard">
      <style>
        .path2 {
          fill: var(--path2-color);
          transition: fill 1s;
        }
        .path2:hover {
          fill: #800000;
        }
      </style>
      <path class="path1" style="fill: var(--path1-color);transition: fill .6s;" d="M20 40 a 20 20 0 1 1 1 0"/>
      <path class="path2" d="M40 60 a 20 20 0 1 1 1 0"/>
    </symbol>
  </defs>
  <use href="#DateCard" class="card1"/>
  <use href="#DateCard" class="card2" transform="translate(80 0)"/>
<svg>

更新

OP 询问是否可以使用 SVG 中的属性来实现悬停效果。 :hover 伪类的替代方法是通过鼠标进入和离开动画元素来启动动画。不幸的是,它不像 CSS 那样灵活——很难设置&lt;animate&gt; 的样式。

下面是动画符号中第二个&lt;path&gt; 的示例:

.card1 {
  --path1-color: #0099CC;
  --path2-color: #FFDF34;
}

.card2 {
  --path1-color: #00008B;
  --path2-color: #FF8C00;
}

.card2:hover {
  --path1-color: #00BFFF;
}
<svg viewBox="0 0 200 100" width="400">
  <defs>
    <symbol id="DateCard">
      <style>
        .path2 {
          fill: var(--path2-color);
        }
      </style>
      <path class="path1" style="fill: var(--path1-color);transition: fill .6s;" d="M20 40 a 20 20 0 1 1 1 0"/>
      <path class="path2" d="M40 60 a 20 20 0 1 1 1 0">
        <animate attributeName="fill" dur="1s" values="#FF8C00;#800000" begin="mouseenter" fill="freeze" />
        <animate attributeName="fill" dur="1s" from="#800000" to="#FF8C00" begin="mouseleave" fill="freeze" />
      </path>
    </symbol>
  </defs>
  <use href="#DateCard" class="card1"/>
  <use href="#DateCard" class="card2" transform="translate(80 0)"/>
<svg>

【讨论】:

  • 是的,这就是我要找的。我还想知道在 :hover 伪类中使用什么属性进行 CSS 转换。
  • @itsmikem 我在回答中做了第二个例子,试图回答你的问题:-)
猜你喜欢
  • 2018-05-22
  • 1970-01-01
  • 2015-06-16
  • 2023-01-24
  • 2016-05-28
  • 1970-01-01
  • 2012-11-20
  • 2020-01-29
  • 1970-01-01
相关资源
最近更新 更多