You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@echarts.apache.org by sh...@apache.org on 2020/09/17 06:03:03 UTC
[incubator-echarts] branch line-optimize updated: perf(line):
optimize performance of time series data on line.
This is an automated email from the ASF dual-hosted git repository.
shenyi pushed a commit to branch line-optimize
in repository https://gitbox.apache.org/repos/asf/incubator-echarts.git
The following commit(s) were added to refs/heads/line-optimize by this push:
new 7b7a747 perf(line): optimize performance of time series data on line.
7b7a747 is described below
commit 7b7a7470c100a84f5c040da835e9511a539a71f2
Author: pissang <bm...@gmail.com>
AuthorDate: Thu Sep 17 14:02:42 2020 +0800
perf(line): optimize performance of time series data on line.
---
src/chart/line/LineView.ts | 12 ++++++---
src/coord/cartesian/Cartesian2D.ts | 52 ++++++++++++++++++++++++++++++++++++++
src/coord/cartesian/Grid.ts | 10 +++++---
src/scale/Scale.ts | 2 ++
4 files changed, 68 insertions(+), 8 deletions(-)
diff --git a/src/chart/line/LineView.ts b/src/chart/line/LineView.ts
index 4616e2f..e9ebec9 100644
--- a/src/chart/line/LineView.ts
+++ b/src/chart/line/LineView.ts
@@ -43,7 +43,6 @@ import { CoordinateSystemClipArea } from '../../coord/CoordinateSystem';
import { setStatesStylesFromModel, setStatesFlag, enableHoverEmphasis } from '../../util/states';
import { getECData } from '../../util/ecData';
import { createFloat32Array } from '../../util/vendor';
-import { createSymbol } from '../../util/symbol';
type PolarArea = ReturnType<Polar['getArea']>;
@@ -433,7 +432,7 @@ class LineView extends ChartView {
const valueOrigin = areaStyleModel.get('origin');
const dataCoordInfo = prepareDataCoordInfo(coordSys, data, valueOrigin);
- let stackedOnPoints = getStackedOnPoints(coordSys, data, dataCoordInfo);
+ let stackedOnPoints = isAreaChart && getStackedOnPoints(coordSys, data, dataCoordInfo);
const showSymbol = seriesModel.get('showSymbol');
@@ -490,7 +489,10 @@ class LineView extends ChartView {
if (step) {
// TODO If stacked series is not step
points = turnPointsIntoStep(points, coordSys, step);
- stackedOnPoints = turnPointsIntoStep(stackedOnPoints, coordSys, step);
+
+ if (stackedOnPoints) {
+ stackedOnPoints = turnPointsIntoStep(stackedOnPoints, coordSys, step);
+ }
}
polyline = this._newPolyline(points);
@@ -548,7 +550,9 @@ class LineView extends ChartView {
if (step) {
// TODO If stacked series is not step
points = turnPointsIntoStep(points, coordSys, step);
- stackedOnPoints = turnPointsIntoStep(stackedOnPoints, coordSys, step);
+ if (stackedOnPoints) {
+ stackedOnPoints = turnPointsIntoStep(stackedOnPoints, coordSys, step);
+ }
}
polyline.setShape({
diff --git a/src/coord/cartesian/Cartesian2D.ts b/src/coord/cartesian/Cartesian2D.ts
index 9f421b9..f56118c 100644
--- a/src/coord/cartesian/Cartesian2D.ts
+++ b/src/coord/cartesian/Cartesian2D.ts
@@ -25,9 +25,16 @@ import Axis2D from './Axis2D';
import { CoordinateSystem } from '../CoordinateSystem';
import GridModel from './GridModel';
import Grid from './Grid';
+import Scale from '../../scale/Scale';
+import { invert } from 'zrender/src/core/matrix';
+import { applyTransform } from 'zrender/src/core/vector';
export const cartesian2DDimensions = ['x', 'y'];
+function canCalculateAffineTransform(scale: Scale) {
+ return scale.type === 'interval' || scale.type === 'time';
+}
+
class Cartesian2D extends Cartesian<Axis2D> implements CoordinateSystem {
readonly type = 'cartesian2d';
@@ -38,6 +45,45 @@ class Cartesian2D extends Cartesian<Axis2D> implements CoordinateSystem {
master: Grid;
+ private _transform: number[];
+ private _invTransform: number[];
+
+ /**
+ * Calculate an affine transform matrix if two axes are time or value.
+ * It's mainly for accelartion on the large time series data.
+ */
+ calcAffineTransform() {
+ this._transform = this._invTransform = null;
+
+ const xAxisScale = this.getAxis('x').scale;
+ const yAxisScale = this.getAxis('y').scale;
+
+ if (!canCalculateAffineTransform(xAxisScale) || !canCalculateAffineTransform(yAxisScale)) {
+ return;
+ }
+
+ const xScaleExtent = xAxisScale.getExtent();
+ const yScaleExtent = yAxisScale.getExtent();
+
+ const start = this.dataToPoint([xScaleExtent[0], yScaleExtent[0]]);
+ const end = this.dataToPoint([xScaleExtent[1], yScaleExtent[1]]);
+
+ const xScaleSpan = xScaleExtent[1] - xScaleExtent[0];
+ const yScaleSpan = yScaleExtent[1] - yScaleExtent[0];
+
+ if (!xScaleSpan || !yScaleSpan) {
+ return;
+ }
+ // Accelerate data to point calculation on the special large time series data.
+ const scaleX = (end[0] - start[0]) / xScaleSpan;
+ const scaleY = (end[1] - start[1]) / yScaleSpan;
+ const translateX = start[0] - xScaleExtent[0] * scaleX;
+ const translateY = start[1] - yScaleExtent[0] * scaleY;
+
+ const m = this._transform = [scaleX, 0, 0, scaleY, translateX, translateY];
+ this._invTransform = invert([], m);
+ }
+
/**
* Base axis will be used on stacking.
*/
@@ -60,6 +106,9 @@ class Cartesian2D extends Cartesian<Axis2D> implements CoordinateSystem {
}
dataToPoint(data: ScaleDataValue[], reserved?: unknown, out?: number[]): number[] {
+ if (this._transform) {
+ return applyTransform(out || [], data as number[], this._transform);
+ }
const xAxis = this.getAxis('x');
const yAxis = this.getAxis('y');
out = out || [];
@@ -89,6 +138,9 @@ class Cartesian2D extends Cartesian<Axis2D> implements CoordinateSystem {
}
pointToData(point: number[], out?: number[]): number[] {
+ if (this._invTransform) {
+ return applyTransform(out, point, this._invTransform);
+ }
const xAxis = this.getAxis('x');
const yAxis = this.getAxis('y');
out = out || [];
diff --git a/src/coord/cartesian/Grid.ts b/src/coord/cartesian/Grid.ts
index 7df314e..96801c8 100644
--- a/src/coord/cartesian/Grid.ts
+++ b/src/coord/cartesian/Grid.ts
@@ -152,6 +152,12 @@ class Grid implements CoordinateSystemMaster {
adjustAxes();
}
+ each(this._coordsList, function (coord) {
+ // Calculate affine matrix to accelerate the data to point transform.
+ // If all the axes scales are time or value.
+ coord.calcAffineTransform();
+ });
+
function adjustAxes() {
each(axesList, function (axis) {
const isHorizontal = axis.isHorizontal();
@@ -407,10 +413,6 @@ class Grid implements CoordinateSystemMaster {
* Update cartesian properties from series.
*/
private _updateScale(ecModel: GlobalModel, gridModel: GridModel): void {
- const sortedDataValue: number[] = [];
- const sortedDataIndex: number[] = [];
- let hasCategoryIndices = false;
-
// Reset scale
each(this._axesList, function (axis) {
axis.scale.setExtent(Infinity, -Infinity);
diff --git a/src/scale/Scale.ts b/src/scale/Scale.ts
index 1bce94d..458fd4a 100644
--- a/src/scale/Scale.ts
+++ b/src/scale/Scale.ts
@@ -97,6 +97,8 @@ abstract class Scale {
/**
* Get extent
+ *
+ * Extent is always in increase order.
*/
getExtent(): [number, number] {
return this._extent.slice() as [number, number];
---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscribe@echarts.apache.org
For additional commands, e-mail: commits-help@echarts.apache.org