【问题标题】:Problem drawing a SVG from file using React and JQuery使用 React 和 JQuery 从文件中绘制 SVG 的问题
【发布时间】:2019-03-04 15:36:38
【问题描述】:

我正在尝试使用 React 编写一个 SVG 操作应用程序,并且我正在使用 JQuery 来读取和过滤 svg 文件,但我不知道为什么当我使用 .map() 时不起作用,但是当我使用paths[0] 之类的方法绘制访问路径数组中元素的路径。

import React from 'react'
import $ from 'jquery'

class Tile extends React.Component {
constructor(props) {
    super(props)
    this.state = {
        paths: [],
        fills: [],
        transforms: [],
        strokeWidths: [],
        foo: ["1234", "2345"]
    }
}

componentDidMount() {
    var self = this;
    $.get("xml/svg.xml", (xml) => {
        $(xml).find('path').each((index, path) => {
            self.setState({ paths: [...self.state.paths, $(path).attr('d')] })
            self.setState({ fills: [...self.state.fills, $(path).attr('fill')] })
            const transform = ($(path).attr('transform') !== undefined) ? $(path).attr('transform') : "translate(0 0)"
            self.setState({
                transforms: [...self.state.transforms, transform]
            })
        });
    })
}

render() {
    return (
        <div className="tile">
            <svg width="100%" height="100%" version="1.1" viewBox="0 0 200 200" xmlns="http://www.w3.org/2000/svg">
                {this.state.paths.map((path, index) => {
                    <path d={path} transform={this.state.transforms[index]} fill={this.state.fills[index]} stroke={this.state.strokeWidths[index]}></path>
                })}
            </svg>
            <svg width="100%" height="100%" version="1.1" viewBox="0 0 200 200" xmlns="http://www.w3.org/2000/svg">
                <path d={this.state.paths[1]}></path>
            </svg>
        </div>
    )
}
}
export default Tile

SVG 文件:

<svg width="200" height="200" version="1.1" viewBox="0 0 200 200" xmlns="http://www.w3.org/2000/svg">
    <path d="m0-0.099609v19a19 19 0 0 0 19-19zm185 0.099609v15h15v-15zm15.041 170a30 30 0 0 0-30 30h30zm-200.04 15v15h15v-15z" fill="#d40000"/>
    <path d="m128.81 97.034a30.508 28.39 0 0 1-30.508 28.39 30.508 28.39 0 0 1-30.508-28.39 30.508 28.39 0 0 1 30.508-28.39 30.508 28.39 0 0 1 30.508 28.39z" fill="#ff7fff" stroke-width="0"/>
</svg>

任何建议或参考将不胜感激。

【问题讨论】:

  • 您是否遇到任何错误?我的猜测是在初始渲染时您可能会遇到一些未定义的错误。另外,在组件确实挂载时,我不会在 map 函数中调用 setState 。这将导致组件重新渲染永远添加的路径
  • 我损失了 1 天,因为我有很多“不重要”的警告,其中我有一些非常重要的东西:“./src/components/designApp/Tile.jsx 第 34 行:预计返回箭头函数 array-callback-return 中的值 第 35 行:期望一个赋值或函数调用,而是看到一个表达式 no-unused-expressions"。我错过了箭头函数的返回,因为我使用的是 {} 而不是 (),无论它看起来多么微不足道,我都不会忽略警告。非常感谢。

标签: javascript jquery reactjs svg


【解决方案1】:

我编辑了您的回调以仅获取一次设置状态的数据,并将您的渲染更改为仅在 paths 存在时渲染。我还注意到您发布的代码无法解析stroke-width,因此我在您的地图上添加了这一点,以及您在评论中提到的缺少的回报另外,我建议您不要依赖 jQuery。这是一个很好的参考:You might not need jQuery

import React from "react";
import $ from "jquery";

class Tile extends React.Component {
  constructor(props) {
    super(props);
    this.state = {
      paths: [],
      fills: [],
      transforms: [],
      strokeWidths: [],
      foo: ["1234", "2345"]
    };
  }

  componentDidMount() {
    var self = this;
    $.get("xml/svg.xml", xml => {

      const paths = [];
      const fills = [];
      const transforms = [];
      const strokeWidths = [];

      $(xml)
        .find("path")
        .each((index, path) => {
          const transform =
            path.getAttribute("transform") !== undefined
              ? path.getAttribute("transform")
              : "translate(0 0)";
          transforms.push(transform);
          paths.push(path.getAttribute("d"));
          fills.push(path.getAttribute("fill"));
          strokeWidths.push(path.getAttribute("stroke-width")); //?? not included in your original code
        });

      self.setState({ paths, fills, transforms, strokeWidths });
    });
  }

  render() {
    const { paths, fills, transforms, strokeWidths } = this.state;
    return (
      <div className="tile">
        {paths.length > 1 && [
          <svg
            key="svg1"
            width="100%"
            height="100%"
            version="1.1"
            viewBox="0 0 200 200"
            xmlns="http://www.w3.org/2000/svg"
          >
            {paths.map((path, index) => (
              <path
                d={path}
                transform={transforms[index]}
                fill={fills[index]}
                stroke={strokeWidths[index]}
              />;
            ))}
          </svg>,
          <svg
            key="svg2"
            width="100%"
            height="100%"
            version="1.1"
            viewBox="0 0 200 200"
            xmlns="http://www.w3.org/2000/svg"
          >
            <path d={paths[1]} />
          </svg>
        ]}
      </div>
    );
  }
}
export default Tile;

【讨论】:

  • 非常感谢!!,我刚从 React 开始,我正在研究“快速反应”这本书,但我对 Javascript 非常陌生,你能给我推荐一本关于Javascript?直到几天前,我从未使用过 javascript,而且大多数书籍对我来说看起来都很基础,我不想“浪费”时间学习循环,因为我已经了解 C++、C# 和 Java,但我总是害怕错过重要的如果我跳过一章信息。有什么建议吗?再次感谢您!
猜你喜欢
  • 2019-10-10
  • 2021-07-15
  • 2016-05-12
  • 1970-01-01
  • 1970-01-01
  • 2013-09-06
  • 2019-06-26
  • 1970-01-01
  • 2012-05-11
相关资源
最近更新 更多