首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >电子图表:绘制信号的方差

电子图表:绘制信号的方差
EN

Stack Overflow用户
提问于 2020-05-11 15:50:45
回答 1查看 572关注 0票数 1

我想在图表中绘制多个信号的方差(或者基本上填充上下信号之间的空间)。有没有可能创建这样的图表?

我看到了置信区间示例(https://echarts.apache.org/examples/en/editor.html?c=confidence-band),然而这似乎只对图表中的一个信号有效。

另一种解决方案是使用markArea在信号周围绘制数以千计的小矩形,但这会降低图表的性能(例如,当滚动x轴时),并且看起来不是很平滑。

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2020-05-18 14:18:44

据我所知,Echarts社区的常见做法是绘制常用的图表类型(条形图、折线图等)。使用series (read docs)并通过custom series编写可视化逻辑以实现唯一性。此外,Echarts还有一些API方法(未记录),如registerVisualregisterLayout,可用于重新定义布局、计算等。

对于所描述的任务,您需要使用custom系列来计算波段坐标。这并不是很简单,因为(在我看来)具有置信度的强制性要求很少。

关于性能。默认情况下,Echarts使用Canvas呈现可视部件。通常Canvas在超文本标记语言中没有太多显示图表的部分,它只是浏览器呈现的imageData,几乎与需要显示多少个数据点无关。换句话说,我们看到PNG,而不是像SVG中那样使用几何基元的divsvgg和其他层,但繁重的计算复杂的业务逻辑可能会像其他图表一样影响UI的响应性。

下面的示例中,我将如何实现此功能。我不确定这是不是正确的方式,但它可以工作,可以调整。

代码语言:javascript
复制
    var dates = ['2020-01-03','2020-01-31','2020-02-17','2020-02-18','2020-03-13','2020-04-10','2020-05-01','2020-05-19','2020-05-22','2020-05-25'];
    var sensor1 = [0.6482086334797242, 0.9121368038482911, 0.3205730196548609, 0.8712238348969002, 0.4487714576177558, 0.9895025457815625, 0.0415490306934774, 0.1592908349676395, 0.5356690594518069, 0.9949108727912939];
    var sensor2 = [0.8278430459565170, 0.5700757488718124, 0.9803575576802187, 0.0770264671179814,0.2843735619252158,0.8140209568127250,0.6055633547296827,0.9554255125528607,0.1703504100638565,0.5653245914197297];

    // Calculate fake bands coordinates
    function calcContourCoords(seriesData, ctx){
      var addNoise = idx => Math.round(Math.random() * 8 * idx);
      var pixelCoords = seriesData.map((dataPoint, idx) => {
        return [
          ctx.convertToPixel({ xAxisIndex: 0 }, idx) + addNoise(idx),
          ctx.convertToPixel({ yAxisIndex: 0 }, dataPoint) + addNoise(idx)
        ]
      });

      var polyfilltype = ClipperLib.PolyFillType.pftEvenOdd;
      var linePath = new ClipperLib.Path();
      var delta = 15;
      var scale = 1;

      for (var i = 0; i < pixelCoords.length; i++){
        var point = new ClipperLib.IntPoint(...pixelCoords[i]);
        linePath.push(point);
      }

      var co = new ClipperLib.ClipperOffset(1.0, 0.25);
          co.AddPath(linePath, ClipperLib.JoinType.jtRound, ClipperLib.EndType.etOpenSquare);
          co.Execute(linePath, delta * scale);

      return co.m_destPoly.map(c => [c.X, c.Y])
    }

    // Render visual by calculated coords
    function renderItem(params, api){

      // Prevent multiple call
      if (params.context.rendered) return;
      params.context.rendered = true;

      // Get stored in series data for band
      var series = myChart.getModel().getSeriesByName(params.seriesName)[0];
      var seriesData = series.get('data');

      // Calculate band coordinates for series
      var bandCoords = calcContourCoords(seriesData, myChart);

      // Draw band
      return {
        type: 'polygon',
        shape: {
          points: echarts.graphic.clipPointsByRect(bandCoords, {
            x: params.coordSys.x,
            y: params.coordSys.y,
            width: params.coordSys.width,
            height: params.coordSys.height
          })
        },
        style: api.style({
          fill: series.option.itemStyle.color
        })
      };
    }

    // =============

  var option = {
      tooltip: {},
      legend: {
        data:['Label']
      },
      xAxis: [
        { name: 'x0', data: dates, boundaryGap: true },
        { name: 'x1', data: dates, boundaryGap: true, show: false },
      ],
      yAxis: [
        { name: 'y0' },
        { name: 'y1', show: false },
      ],
      series: [

        // First line
        {
          name: 'Sensor1',
          type: 'line',
          data: sensor1,
          itemStyle: { color: 'rgba(69, 170, 242, 1)' },
          yAxisIndex: 0,
          xAxisIndex: 0,
        },
        {
          name: 'BandSensor1',
          type: 'custom',
          data: sensor1,
          itemStyle: { color: 'rgba(69, 170, 242, 0.2)' },
          renderItem: renderItem,
          yAxisIndex: 0,
          xAxisIndex: 0,
        },

        // Second line
        {
          name: 'Sensor2',
          type: 'line',
          data: sensor2,
          itemStyle: { color: 'rgba(253, 151, 68, 1)' },
          yAxisIndex: 1,
          xAxisIndex: 1,
        },
        {
          name: 'BandSensor2',
          type: 'custom',
          data: sensor2,
          itemStyle: { color: 'rgba(253, 151, 68, 0.2)' },
          renderItem: renderItem,
          yAxisIndex: 1,
          xAxisIndex: 1,
        },
      ]
  };

  var myChart = echarts.init(document.getElementById('main'));
      myChart.setOption(option);
代码语言:javascript
复制
<script src="https://cdn.jsdelivr.net/npm/clipper-lib@6.4.2/clipper.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/echarts/4.7.0/echarts.min.js"></script>
<div id="main" style="width: 800px;height:600px;"></div>

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/61724715

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档