VChart icon indicating copy to clipboard operation
VChart copied to clipboard

使用markArea进去区域绘制并且动态更新area时, 内存会明显增长

Open YuiFn opened this issue 11 months ago • 1 comments

环境

浏览器: Microsoft Edge( 版本 122.0.2365.63 (正式版本) (arm64))
系统: macOS Sonoma 14.3.1

版本

lastest

场景描述:

有一个 区域的图, 数据是设备采集一整晚的数据, 用markArea标记出一块表示当前显示的区域是哪一个区间的时间, 并支持点击切换任意的时刻(充当一个时间选择器来使用)

初始内存 image

开启动态标记后 image

内存增长的速度会随着数据的规模和变动的次数, 越发明显, 有些时候回直接导致页面崩溃

代码


function func(x) {
  x /= 20;
  return Math.cos(x + 1) * Math.sin(x + 1) * 50;
}

function generateData(i) {
  return {
    name: +now + minute * i,
    value: func(i)
  };
}

let now = new Date(2023, 5, 16);
const minute = 60 * 1000;
const data = [];
let i = 0;
for (; i < 100000; i++) {
  data.push(generateData(i));
}

const duration = 500;

const spec = {
  type: 'area',
  data: {
    id: 'id0',
    values: data
  },
  xField: 'name',
  yField: 'value',
  line: {
    style: {
      lineWidth: 2
    }
  },
  point: {
    visible: false
  },
  animationAppear: {
    line: {
      duration
    }
  },
  axes: [
    {
      orient: 'left',
      type: 'linear',
      visible: true,
      min: -50,
      max: 50,
      grid: {
        style: {
          lineDash: [0]
        }
      },
      label: {
        visible: true
      },
      animation: false
    },
    {
      orient: 'bottom',
      type: 'time',
      animation: true,
      nice: false,
      layers: [
        // 双层轴每层的配置
        {
          timeFormat: '%m-%d '
        },
        {
          timeFormat: '%H:%M'
        }
      ],
      label: {
        visible: true
      }
    }
  ],
    animation: false,
    markArea:{id:'time-line', coordinates:[
      { ...data[0], value:50 },
      { ...data[2000], value:50 },
      { ...data[2000], value:-50 },
      { ...data[0], value:-50 },
    ],area: { style: { fill: '#FE2C55', opacity: 0.1 } }}
};

const vchart = new VChart(spec, { dom: CONTAINER_ID });
vchart.renderSync();
setInterval(function () {
  // for (let j = 0; j < 5; j++) {
  //   data.shift();
  //   data.push(generateData(++i));
  // }
  const half =  Math.floor(data.length * 0.5);
  const startIdx  = Math.floor(Math.random() * half);
  const endIdx = startIdx + 2000

   const coordinates = [
        { ...data[startIdx], value:50 },
         { ...data[endIdx], value:50 },
        { ...data[endIdx], value:-50 },
        { ...data[startIdx], value:-50 },
    ]; 
    const area = { id: 'time-line', coordinates: coordinates, area: { style: { fill: '#FE2C55', opacity: 0.1 } } };
    spec.markArea=area
    // vchart.updateModelSpecSync('time-line',area); 这样更新没有用
    vchart.updateSpecSync(spec)
    // vchart.renderAsync()
}, duration);

// Just for the convenience of console debugging, DO NOT COPY!
window['vchart'] = vchart;

vchart中有 updateModelSpecSync 来更新局部的配置, 但是对mark*之类的好像不生效, 不知道是不是我用的方式不对. 针对这个场景还好, 因为只有1个, 个别场景需要支持用户通过 brush, 动态添加和修改markArea的区域, 不知道有没有更好的方式来实现这中场景.

YuiFn avatar Mar 08 '24 05:03 YuiFn

@YuiFn 试一下最新的 1.10.5 版本

xile611 avatar Apr 26 '24 07:04 xile611