React ApexCharts обновляет график с интервалом - PullRequest
0 голосов
/ 05 мая 2020

Я создаю приложение для реагирования, которое будет отображать несколько диаграмм (с помощью ApexCharts), которые необходимо постоянно обновлять при вызове API. Они будут отображать данные датчиков из разных источников.

У меня есть диаграмма, стилизованная и настроенная так, как мне нужно, но если я обновлю данные, изменив массив состояний в выражении setInterval, за пару итераций диаграмма начинает вести себя странно, как если бы одновременно были конфликтующие обновления.

Это файл приложения. js в CodeSandBox:

//App.js
export default function App() {
  const [data, updateData] = useState([1, 2, 3, 4, 5, 6]);

  useEffect(() => {
    setInterval(() => {
      const val = Math.floor(Math.random() * (100 - 30 + 1)) + 30;
      let array = [...data, val];
      array.shift();
      updateData(array);
    }, 2000);
  });
  return (
    <div className="App">
      <ChartViewer data={data} title="Product Trends by Month" />
    </div>
  );
}

, а это ChartViewer component:

import Chart from "react-apexcharts";

export default function ApexChart(props) {
  const series = [
    {
      name: "xx",
      data: props.data
    }
  ];
  const options = {
    chart: {
      height: 350,
      type: "line",
      zoom: {
        enabled: true
      }
    },
    dataLabels: {
      enabled: false
    },
    stroke: {
      width: 2,
      curve: "smooth"
    },
    colors: ["#210124"],
    fill: {
      type: "gradient",
      gradient: {
        shadeIntensity: 1,
        inverseColors: true,
        gradientToColors: ["#DB162F"],
        opacityFrom: 1,
        opacityTo: 1,
        type: "vertical",
        stops: [0, 30]
      }
    }
  }
  return (
    <div id="chart">
      <Chart options={options} series={series} type="line" height={350} />
    </div>
  );
}

Кроме того, вот ссылка CodeSandbox, по которой вы можете увидеть поведение: https://codesandbox.io/s/purple-monad-5c1i3?file= / src / ChartViewer. js: 41-839

Заранее спасибо

Ответы [ 2 ]

1 голос
/ 05 мая 2020

Вы не передаете никаких зависимостей для useEffect. Это заставляет его запускаться при каждом рендеринге, что заставляет ваши диаграммы очень часто перерисовываться.

Чтобы исправить это, вам нужно немного изменить свой useEffect:

  useEffect(() => {
    const interval = setInterval(() => {
      const val = Math.floor(Math.random() * (100 - 30 + 1)) + 30;
      let array = [...data, val];
      array.shift();
      updateData(array);
    }, 2000);
    return () => {
      window.clearInterval(interval); // clear the interval in the cleanup function
    };
  }, [data]); // pass the data as a dependency (because you are using it inside the effect)

Вы можете увидеть обновленное поведение здесь: https://codesandbox.io/s/pedantic-mendeleev-tx5ck

0 голосов
/ 05 мая 2020

Вы забыли указать пустой массив как второй аргумент хука useEffect:

Теперь он работает. Попробуйте этот код:

import React, { useState, useEffect } from "react";
import "./styles.css";
import ChartViewer from "./ChartViewer";

export default function App() {
  const [data, updateData] = useState([1, 2, 3, 4, 5, 6]);

  useEffect(() => {
    setInterval(() => {
      const val = Math.floor(Math.random() * (100 - 30 + 1)) + 30;
      let array = [...data, val];
      console.log(array);
      array.shift();
      updateData(array);
    }, 2000);
  }, []);
  return (
    <div className="App">
      <ChartViewer data={data} title="Product Trends by Month" />
    </div>
  );
}

Вот рабочая песочница: https://codesandbox.io/s/peaceful-fire-fdw98

Не забудьте очистить вызов API setInterval при отключении этого компонента.

Спасибо

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...