Data visualization case summary

React is the same as Vue

Fill a bug of the project, can appear after the interruption of data continues to draw a straight line If you don’t want to judge without electricity for simple and fast solution, determine whether the breakpoint: first to calculate all adjacent points difference min min, if the difference between two points is greater than the minimum min, shows a breakpoint, fill a null, which is not even straight line

Echarts

Case a

  • forEchartsCreate a DOM container with the height and width
<div :id="'myChart' + idkey " :style="{width: '300px', height: '200px'}"></div>
Copy the code

The ID must be unique, and since there are multiple charts in the project a single chart can be set by itself

  • Prepare the initial content SettingsEchartsstyle
Option: {// X axis in the rectangular coordinate system grid. Generally, a single grid component can only put up and down two X axes at most. If there are more than two X axes, configure the offset attribute to prevent overlapping of multiple X axes at the same position. XAxis: {data: this.charttimes,//falseAxisLabel: {// The content formatter of the calibration label supports both string template and callback functions:function(value, idx) {// The function parameters are the scale value (category), the scale indexlet newDate = new Date(Number(value))
              return [newDate.getMonth() + 1, newDate.getDate()].join('/')}, interval: 500'10%'.'10%'}, // xAxis yAxis: {show:false,
          boundaryGap: ['30%'.'30%']
        },
        series: {
          showSymbol: false// Whether to display symbol, iffalseDisplay the hoverAnimation only if the tooltip hover is used:falseData: this. Chartusages,// Array of data contents in series. Array items are usually concrete data itemstype: 'line'// Graph type lineStyle: {color:'#8C8C8C', width: 1}}, // Tooltip: {trigger:'axis'// Trigger the type of axis trigger formatter:function(datas) {// Prompt box float content formatter, supporting both string template and callback function formslet newDate = new Date(Number(datas[0].name))
            let dateFormatter = date2str(newDate, 'YYYY-MM-DD HH:mm:ss')
            return dateFormatter + '</br>' + datas[0].value + The '%'}, // Axis indicator configuration item axisPointer: {lineStyle: {color:'#3752ff'
            },
            shadowStyle: {
              color: '#3752ff'}}}}Copy the code

Some project configurations are used in the above There are some detailed explanation To mention prompt box here refers to when the mouse moved to the data part there will be a box show that point information in detail The indicator is a line The above configuration is almost a color dark blue Straight line parallel to the y axis Move with the mouse movement to follow

  • drawing
 drawEChart() {get the DOM containerlet myChart = echarts.init(document.getElementById(`myChart${this.idkey}This.option.series. Data = this.chartusages //)) this.option.series. Data = this.chartusages // Setting graph data without data to draw? MyChart. SetOption (enclosing option)/draw /}Copy the code

Case 2

  • Create a container

. I’m not going to write that code

  • Prepare configuration
// Component package data pass through the traversalletSeries = this.ydata.map((data, idx) => ({name: this.names[idx],// series = this.ydata.map((data, idx) => ({name: this.names[idx],// data: data,// datatype: 'line',
      symbol: 'circle',
      showSymbol: false/** Do not set the color directly when controlling the color change of a point */ lineStyle: this. VisualMap? {} : { color: this.colors[idx] }, itemStyle: { color: this.colors[idx], borderColor: this.colors[idx] }, ... (this.area ? { areaStyle: typeof this.area ==='object' ? this.area : {
        color: new LinearGradient(0, 0, 0, 1, [{
          offset: 0,
          color: '#65BDF6'
        }, {
          offset: 1,
          color: this.colors[idx]
        }])
      }} : {})
    }))
    let// / visualMap is a visual mapping component used for "visual coding", i.e. mapping data to visual elements (visual channels).let visualMap = {
      type: 'piecewise'// show:false,
      dimension: 0,
      pieces: this.pieces
    }
    Object.assign(this, {
      line: {
        title: {
          text: this.title
        },
        visualMap: that.visualMap ? visualMap : { show: false },
        tooltip: {
          trigger: 'axis',
          // textStyle: {
          //   color: '#0068FF'
          // },
          formatter: function (param) {
            return `${msec2str(Number(param[0].name), 'YYYY-MM-DD HH:mm:ss')}<br/>${param[0].value}{top: 40, bottom: 10, right: {top: 40, bottom: 10, right: {top: 40, bottom: 10, right: {top: 40, bottom: 10, right: 25, left: 10, containLabel:true
        },
        xAxis: {
          data: this.xdata,
          type: 'category',
          axisTick: {
            alignWithLabel: true
          },
          axisLabel: {
            interval: that.xinterval || 59,
            showMaxLabel: true,
            formatter: function (value, idx) {
              // return idx === 0 ? msec2str(Number(value), 'YYYY-MM-DD') : msec2str(Number(value), 'MM-DD HH:mm')
              return msec2str(Number(value), that.xformatter || 'HH:00')
            }
          }
        },
        yAxis: {
          type: 'value'
        },
        series: series
      }
    })
    return {}
Copy the code
  • So I don’t have to say (actually I’m lazy)

Dygraph

  • Create a DOM container (basically the same code as above)

<div class="chart"></div>

  • Prepare the configuration file
     plot() {// If there is a graph, delete it firstif(this.chart) {this.chart. Destroy () this.chart = null} // This.chart' '// Get datalet data = await getData()
      if (data.values.length === 0) {
        this.chartEl.innerHTML = '
      
No data
'
return} // Data format conversion (sorry, the back end of the data can not be directly used)let values = data.values.map(el => { let [a, b, c, , ...rest] = el return [a, b, c, ...rest] }) let scoreValues = data.values.map(el => { // eslint-disable-next-line let [a, , , b, ...rest] = el return[a, b]}) this. ScoreValues = scoreValues // upper and lower boundslet lowers = [] let uppers = [] for (let v of values) { lowers.push([v[0], v[3]]) uppers.push([v[0], v[4]]) v[0] = msec2date(v[0]) v[2] = v[2] ? v[1] : null } // tolerance update if (Object.keys(this.statistic).length > 0) { this.trimThreshold('upper', values, 4) this.trimThreshold('lower', values, 3) this.trimThreshold('upper', uppers, 1) this.trimThreshold('lower', lowers, 1)} // Style specifiedlet majorColor = '#136DFB' let minorColor = '#CCCCCC' let boundColor = '#408BFF' let anomalyColor = '#FF0000' let basebandColor = '#DCE9FE' let dylabels = [ 'x'.'value'.'abnormal' ] letSeries = {// Define options for each series. The key matches the Y-axis label name, the value is the dictionary itself, and contains options specific to that series.'value': { color: majorColor, strokeWidth: 1, drawPoints: false }, 'abnormal': { color: anomalyColor, strokeWidth: 2, drawPoints: true, pointSize: 2, highlightCircleSize: 4 }, 'scores': { color: majorColor, strokeWidth: 0, drawPoints: false, pointSize: 0, highlightCircleSize: 0 } } dylabels = dylabels.concat([ 'next'.'upper' ]) series['upper'] = { color: boundColor, strokeWidth: 0, drawPoints: false, pointSize: 0, highlightCircleSize: 0 } series['next'] = { color: boundColor, strokeWidth: 0, drawPoints: false, pointSize: 0, highlightCircleSize: 0} // Whether to fillif (this.filling) { let st = this.timerange.start if (dateLater(values[0][0], st)) { values.unshift([st, ...Array(values[0].length - 1).fill(null)]) } let ed = this.timerange.end if(dateLater(ed, values[values.length - 1][0])) { values.push([ed, Array(values[0].length - 1).fill(null)])}} // Initialize dygraph this.chart = new dygraph (this.chartEl, values, {labels: Dylabels,// Name of each data series, including separate (X) series connectSeparatedPoints:false, digitsAfterDecimal: 4, legend: 'follow'// When to display legends. By default, it is only when the user will be hovering in the chart display interactionModel: Dygraph. DefaultInteractionModel, labelsKMB:true// Show K/M/b. showRangeSelector on y axis:trueRangeSelectorHeight: 30, / / the height of the range selector widget rangeSelectorPlotStrokeColor: majorColor, rangeSelectorPlotFillColor: minorColor, rangeSelectorPlotLineWidth: 1, rangeSelectorForegroundStrokeColor: minorColor, rangeSelectorForegroundLineWidth: 1, rangeSelectorBackgroundStrokeColor: minorColor, rangeSelectorBackgroundLineWidth: 1, axisLineColor: minorColor, gridLineColor: minorColor, series: Axes: {axisLabelFormatter: this. AxisLabelFormatter}, y: {axisLabelWidth: 35}}, // This underlayCallback is called every time the user stops highlighting any point by hovering over the chart: (canvas, area, g) => { canvas.strokeStyle = basebandColor canvas.fillStyle = basebandColorlet lowPoints = [] let highPoints = [] letDrawBasebandBackgroundColor = () = > {/ / map baseband in red that piece / / lowPoints corresponding baseband, hightPoints corresponding on baseband / / points to draw: at least one side more than one can draw line/areaif (lowPoints.length > 1 || highPoints.length > 1) { canvas.save() canvas.beginPath() if(lowPoints.length > 1) { canvas.moveTo(... LowPoints [0]) // Left to rightfor (leti = 1; i < lowPoints.length; i++) { canvas.lineTo(... lowPoints[i]) } }if (highPoints.length > 1) { if(lowPoints.length > 1) { canvas.lineTo(... highPoints[highPoints.length - 1]) }else{ canvas.moveTo(... HighPoints [highpoint.length-1])} // From right to leftfor (leti = highPoints.length - 2; i >= 0; i--) { canvas.lineTo(... highPoints[i]) }if(lowPoints.length > 1) { canvas.lineTo(... LowPoints [0])}} // If a region can be formed, fill itif (lowPoints.length > 1 && highPoints.length > 1) { canvas.closePath() canvas.fill() } canvas.stroke() canvas.restore() lowPoints = [] highPoints = [] } } for (letj = 0; j < uppers.length; J++) {// if the baseband data changes as follows, draw the current segment to be drawnif( (lowPoints.length === highPoints.length && lowPoints.length > 0 && (lowers[j][1] === null || uppers[j][1] === null)) || // 2 -> 1/0 (lowPoints.length > 0 && highPoints.length === 0 && lowers[j][1] === null) || // 1 -> 0 (lowPoints.length === 0 && highPoints.length > 0 && uppers[j][1] === null) || // 1 -> 0 (lowPoints.length > 0 && highPoints.length === 0 && lowers[j][1] ! == null && uppers[j][1] ! == null) || // 1 -> 2 (lowPoints.length === 0 && highPoints.length > 0 && lowers[j][1] ! == null && uppers[j][1] ! == null) // 1 -> 2 ) { drawBasebandBackgroundColor() }let xx = 0 if(lowers[j][1] ! == null) {let x = g.toDomXCoord(lowers[j][0]) let y = g.toDomYCoord(lowers[j][1]) lowPoints.push([x, y]) xx = x } if(uppers[j][1] ! == null) {let x = g.toDomXCoord(uppers[j][0]) let y = g.toDomYCoord(uppers[j][1]) highPoints.push([x, y]) xx = x } if (xx >= area.x + area.w) { break } } drawBasebandBackgroundColor() } }) } Copy the code
  • Began to draw
this.chartEl = this.$el.getElementsByClassName('chart')[0]
this.plot()
Copy the code

D3

D3 business is a bit complicated to write next time

conclusion

I’ve probably used these three visualization libraries in my daily projects, and each of them has its own characteristics and it depends on the project. Welcome to talk about data visualization with me. Okay