【问题标题】:Updating state of a react function component from parent class从父类更新反应功能组件的状态
【发布时间】:2020-05-19 14:53:11
【问题描述】:

目前正在学习 React 和 D3。我有以下代码:

App.js

import React, {useRef, useEffect, useState, Component} from 'react';
// import logo from './logo.svg';
import './App.css';

import ChartWrapper from './ChartWrapper'

class App extends Component() {
  render() {
    return (
      <div id="app">
        <ChartWrapper data = {[10, 13, 9.5, 11, 12, 14, 8, 13, 15, 14]}/>
      </div>
    )
  }
}

export default App;

ChartWrapper.js

import React, {Component, useEffect, useState} from 'react';
import { useRef } from 'react';
import LineChart from './LineChart'

function ChartWrapper(props)  {
    const [data, setData] = useState(props.data);
    const svgRef = useRef();
    //let data = [10, 13, 9.5, 11, 12, 14, 8, 13, 15, 14];
    console.log("works");

    useEffect( () => {
        const chart = new LineChart(svgRef, data);
        console.log(data);
    }, [data]);

    function updateChart(value) {
        data.push(value);
    }

    return (
        <div>
            <svg ref={svgRef} height = {300} width = {500}></svg>
        <button onClick={() => setData(data.map(value => value + 5))}>Update Data</button>
        </div>

    );
}

export default ChartWrapper;

LineChart.js

import React, {Component} from 'react'
import {line, select, selectAll, axisBottom, ScaleLinear, scaleLinear} from 'd3';

class LineChart {
    constructor (parent, data) {
        this.svg = select(parent.current);
        this.data = data;
        this.line  = this.getLine();
        this.xScale = this.getXScale();
        this.yScale = this.getYScale();

        // Plot the chart
        this.plot();
    }

    getLine() {
        return line()
                .x((value, index) => this.xScale(index))
                .y(value => this.yScale(value));
    }

    getXScale() {
        return scaleLinear()
                .domain([0, this.data.length - 1])
                .range([0, this.svg.attr('width')]);
    }

    getYScale() {
        return scaleLinear()
                .domain([0, 20])
                .range([this.svg.attr('height'), 0]);
    }


    plot() {
        this.svg.selectAll('path')
                .data([this.data])
                .join('path')
                .attr('d', value => this.line(value))
                .attr('fill', 'none')
                .attr('stroke', 'purple');
    }

}

export default LineChart;

我想知道是否可以从“App.js”文件中以某种方式调用“ChartWrapper.js”中的 updateChart() 函数,因为我希望能够随时随地更新图表值(不是再次渲染整个页面)?

假设您从服务器获取实时值并需要实时更新图表,那么创建灵活图表组件的最佳方法是什么?

【问题讨论】:

  • 你现在在哪里打电话updateChart(),我可以看到它的定义,但它没有在任何地方调用?
  • 目前,我没有在任何地方调用该函数。现在刚刚创建了一个静态聊天。

标签: javascript reactjs d3.js


【解决方案1】:

您可以在App.js 中同时定义状态钩子和updateChart,然后将它们作为道具传递给ChartWrapper.js:

// App.js

import React, { useState } from 'react';
import './App.css';

import ChartWrapper from './ChartWrapper'

const App = () => {
  const [data, setData] = useState([10, 13, 9.5, 11, 12, 14, 8, 13, 15, 14]);
  function updateChart() {
    setData(data.map(value => value + 5));
  }

  return (
    <div id="app">
      <ChartWrapper data={data} updateChart={() => updateChart()}/>
    </div>
  )
}

export default App;
// ChartWrapper.js

import React, { useEffect, useRef } from 'react';
import LineChart from './LineChart'

function ChartWrapper({ data, updateChart })  {

    const svgRef = useRef();
    //let data = [10, 13, 9.5, 11, 12, 14, 8, 13, 15, 14];
    console.log("works");

    useEffect( () => {
        const chart = new LineChart(svgRef, data);
        console.log(data);
    }, [data]);

    return (
        <div>
            <svg ref={svgRef} height = {300} width = {500}></svg>
        <button onClick={() => updateChart()}>Update Data</button>
        </div>

    );
}

export default ChartWrapper;

还请注意,您现在不应像在 updateChart 中那样在 data 数组上使用 .push,而应像在 onClick 回调中那样使用 setData。

希望这会有所帮助。祝你好运!

【讨论】:

    猜你喜欢
    • 2021-01-24
    • 1970-01-01
    • 2022-01-16
    • 1970-01-01
    • 2017-09-10
    • 2022-01-21
    • 2021-01-12
    • 2022-06-27
    • 1970-01-01
    相关资源
    最近更新 更多