使用react.js从另一个组件导入svg路径

时间:2019-04-18 03:15:43

标签: reactjs svg

我在switch语句下的组件中存储了多个图标。根据条件,我想在另一个组件的渲染功能中显示该图标。如果我手动添加svg和path元素,则该图标将正确显示。但是我想优化代码,以便在使用正确的参数调用该函数时,它会提取相应的svg元素及其path元素。

第一个组件(图标所在的位置):

export function getSymbolPlotly(symbol) { // eslint-disable-line
  let elm;
  const { color, shape } = symbol;

 switch (shape) {
    case 'x-dot':
      elm = <path
        className="point"
        transform="translate(8,8)"
        d="M0,3.39l3.39,3.39l3.39,-3.39l-3.39,-3.39l3.39,-3.39l-3.39,-3.39l-3.39,3.39l-3.39,-3.39l-3.39,3.39l3.39,3.39l-3.39,3.39l3.39,3.39ZM0,0.5L0.5,0L0,-0.5L-0.5,0Z"
        style={{
          opacity: 1,
          strokeWidth: '0px',
          fill: color,
          fillOpacity: 1
        }}></path>;
      break;
    case 'square':
      elm = <path
        className="point"
        transform="translate(8,8)"
        d="M6,6H-6V-6H6Z"
        style={{
          opacity: 1,
          strokeWidth: '0px',
          fill: color,
          fillOpacity: 1
        }}></path>;
      break;
    case 'hourglass':
      elm = <path
        className="point"
        transform="translate(6,8)"
        d="M6,6H-6L6,-6H-6Z"
        style={{
          opacity: 1,
          strokeWidth: '0px',
          fill: color,
          fillOpacity: 1
        }}></path>;
      break;
default:
      elm = <circle cx="6" cy="6" r="6" transform="translate(0,2)" fill={color}></circle>;
}````

Second component(render function where I need to display icons):
````switch (user.processState) {
        case 'DENIED':
            return <span><svg style={{ width: '15px', height: '15px' }}>
                    {getSymbolPlotly('hourglass')}
                  </svg></span>
        case 'CANCELLED':
            return <span><svg style={{ width: '15px', height: '15px' }}>
              <path className="point"
                      transform="translate(8,8)"
                      d="M0,3.39l3.39,3.39l3.39,-3.39l-3.39,-3.39l3.39,-3.39l-3.39,-3.39l-3.39,3.39l-3.39,-3.39l-3.39,3.39l3.39,3.39l-3.39,3.39l3.39,3.39ZM0,0.5L0.5,0L0,-0.5L-0.5,0Z"
                      style={{
                        opacity: 1,
                        strokeWidth: '0px',
                        fill: '#e5004c',
                        fillOpacity: 1
                      }}></path>
                  </svg>{this.state.message}</span>;

}

在上面的代码中,当我手动添加path元素时,case CANCELED可以完美显示图标。但是我想优化代码,因为我需要在多个位置显示图标,并在每个位置添加path元素会使代码变得乏味。如果我调用getSymbol函数并将图标的名称作为参数传递,它将不显示任何内容。即使参数不匹配,也不会显示默认的圆形元素。

是否可以从其他组件中以更简洁的方式提取svg和path元素?

1 个答案:

答案 0 :(得分:0)

getSymbolPlotly函数中,您解构了一个称为符号const { color, shape } = symbol;的对象。调用该函数时,传递一个名为getSymbolPlotly('hourglass')的字符串,这是第一个错误。

我不知道您是否为getSymbolPlotly函数粘贴了整个代码,但是您还必须返回该元素。要更“干净”地提取内容,您可以这样。

import React from "react";
export function getSymbolPlotly(symbol) {
  // eslint-disable-line
  const { color, shape } = symbol;

  switch (shape) {
    case "x-dot":
      return (
        <path
          className="point"
          transform="translate(8,8)"
          d="M0,3.39l3.39,3.39l3.39,-3.39l-3.39,-3.39l3.39,-3.39l-3.39,-3.39l-3.39,3.39l-3.39,-3.39l-3.39,3.39l3.39,3.39l-3.39,3.39l3.39,3.39ZM0,0.5L0.5,0L0,-0.5L-0.5,0Z"
          style={{
            opacity: 1,
            strokeWidth: "0px",
            fill: color,
            fillOpacity: 1
          }}
        />
      );
    case "square":
      return (
        <path
          className="point"
          transform="translate(8,8)"
          d="M6,6H-6V-6H6Z"
          style={{
            opacity: 1,
            strokeWidth: "0px",
            fill: color,
            fillOpacity: 1
          }}
        />
      );
    case "hourglass":
      return (
        <path
          className="point"
          transform="translate(6,8)"
          d="M6,6H-6L6,-6H-6Z"
          style={{
            opacity: 1,
            strokeWidth: "0px",
            fill: color,
            fillOpacity: 1
          }}
        />
      );

    default:
      return (
        <circle cx="6" cy="6" r="6" transform="translate(0,2)" fill={color} />
      );
  }
}

在其他组件中,您可以这样称呼它。

return (
    <div className="App">
      <div>
        <svg style={{ width: "15px", height: "15px" }}>
          {getSymbolPlotly({ shape: "hourglass", color: "red" })}
        </svg>
      </div>
      <div>
        <svg style={{ width: "15px", height: "15px" }}>
          {getSymbolPlotly({ shape: "x-dot", color: "purple" })}
        </svg>
      </div>
    </div>
  );

我用working demo here创建了一个Codesandbox。