如何将样式应用于SVG元素数组

时间:2019-07-18 23:47:03

标签: javascript css reactjs svg styled-components

我有一个.svg图标的数组,其中每个图标都有一些我需要覆盖的属性:

<svg width="24" height="24" viewBox="0 0 24 24"> ... </svg>
import styled from 'styled-components';

import Github from 'assets/github.svg';
import Facebook from 'assets/facebook.svg';
import Twitter from 'assets/twitter.svg';
...

const icons = [
  <Github />,
  <Facebook />,
  <Twitter />,
  ...
];

我想为每个图标应用相同的样式,而无需重复代码,并使用CSS-in-JS

到目前为止,我的解决方案存在一些问题:

// Works but,
// I want to use CSS-in-JS like styled-components
// for easier maintenance
const iconStyle = {
  width: 50,
  height: 50
};

const SocialBar = () => (
  <IconBar as={FlexBox}>
    {icons.map((icon, key) => (
      <div key={key}>{React.cloneElement(icon, iconStyle)}</div>
    ))}
  </IconBar>
);
// Works but,
// there are too many icons
const SocialBar = () => (
  <IconBar as={FlexBox}>
    <Github style={iconStyle} />
    <Facebook style={iconStyle} />
    ...
  </IconBar>
);

设置svg组件的样式无效:

// Won't override the width="24" height="24" properties
const StyledIcon = styled(Github)`
  width: 50;
  height: 50;
`;

3 个答案:

答案 0 :(得分:1)

您可以使用元素(例如i)包装SVG,并使用在样式组件中定义的一些CSS对其中的任何svg子元素进行样式设置(也可以定位{{1} }和g)。不幸的是,SVG的使用非常棘手,因此您可能可能将SVG xml手动复制/粘贴到JS文件中(如果您使用的是CRA,则可以导入ReactComponent from an SVG

工作示例(将SVG复制/粘贴到JS文件中-默认为第一个示例,第二个示例传递道具,第三个示例传递多个道具):

Edit Styled SVG Component


Icon / Icon.js (此组件接受样式生成的path以及放置在其中的任何className的样式组件)

children

Icon / index.js (这将为上面的import React from "react"; import PropTypes from "prop-types"; const Icon = ({ className, children }) => ( <i className={className}>{children}</i> ); Icon.propTypes = { className: PropTypes.string.isRequired, children: PropTypes.node.isRequired }; export default Icon; 组件设置样式;随后,将为Icon设置样式)

children

答案 1 :(得分:0)

这是一种实现方式。

//Github.js
import React from "react";
export default function Github({height, width}) {
    return (
        <svg width={width} height={height} viewBox="0 0 24 24"> ...  </svg>
    );
}

然后在您想使用它的地方。

<Github height={24} width={24} />

答案 2 :(得分:0)

相对于您已有的代码示例,我不确定您的要求是什么。您是否要避免使用React.cloneElement?使图标数组代替jsx元素作为函数。 map移至jsx版本,然后将样式应用于每种样式

const icons = [
  Github,
  Facebook,
  Twitter,
]

buildIcons() {
  const style = {
    //..
  }
  return icons.map((icon, idx) => (
    <icon style={style} key={idx}/>
  ))

}

使用索引作为键是有效的,但是如果您找到每个图标唯一的不同属性,那就更好了。