markerHelper.js 6.1 KB
Newer Older
L
lang 已提交
1 2 3
define(function (require) {

    var zrUtil = require('zrender/core/util');
L
lang 已提交
4
    var numberUtil = require('../../util/number');
5
    var indexOf = zrUtil.indexOf;
L
lang 已提交
6

L
tweak  
lang 已提交
7
    function getPrecision(data, valueAxisDim, dataIndex) {
L
lang 已提交
8 9 10 11 12 13 14 15 16 17 18 19
        var precision = -1;
        do {
            precision = Math.max(
                numberUtil.getPrecision(data.get(
                    valueAxisDim, dataIndex
                )),
                precision
            );
            data = data.stackedOn;
        } while (data);

        return precision;
L
tweak  
lang 已提交
20
    }
L
lang 已提交
21

22 23 24
    function markerTypeCalculatorWithExtent(
        mlType, data, baseDataDim, valueDataDim, baseCoordIndex, valueCoordIndex
    ) {
25
        var coordArr = [];
26
        var value = numCalculate(data, valueDataDim, mlType);
27

28 29 30
        var dataIndex = data.indexOfNearest(valueDataDim, value, true);
        coordArr[baseCoordIndex] = data.get(baseDataDim, dataIndex, true);
        coordArr[valueCoordIndex] = data.get(valueDataDim, dataIndex, true);
L
lang 已提交
31

32
        var precision = getPrecision(data, valueDataDim, dataIndex);
L
lang 已提交
33
        if (precision >= 0) {
34
            coordArr[valueCoordIndex] = +coordArr[valueCoordIndex].toFixed(precision);
L
lang 已提交
35 36
        }

37
        return coordArr;
L
tweak  
lang 已提交
38
    }
L
lang 已提交
39

L
tweak  
lang 已提交
40
    var curry = zrUtil.curry;
L
lang 已提交
41
    // TODO Specified percent
L
lang 已提交
42 43 44 45 46 47 48
    var markerTypeCalculator = {
        /**
         * @method
         * @param {module:echarts/data/List} data
         * @param {string} baseAxisDim
         * @param {string} valueAxisDim
         */
49
        min: curry(markerTypeCalculatorWithExtent, 'min'),
L
lang 已提交
50 51 52 53 54 55
        /**
         * @method
         * @param {module:echarts/data/List} data
         * @param {string} baseAxisDim
         * @param {string} valueAxisDim
         */
56
        max: curry(markerTypeCalculatorWithExtent, 'max'),
L
lang 已提交
57 58 59 60 61 62
        /**
         * @method
         * @param {module:echarts/data/List} data
         * @param {string} baseAxisDim
         * @param {string} valueAxisDim
         */
63
        average: curry(markerTypeCalculatorWithExtent, 'average')
L
lang 已提交
64 65
    };

L
tweak  
lang 已提交
66 67 68
    /**
     * Transform markPoint data item to format used in List by do the following
     * 1. Calculate statistic like `max`, `min`, `average`
69
     * 2. Convert `item.xAxis`, `item.yAxis` to `item.coord` array
70
     * @param  {module:echarts/model/Series} seriesModel
L
tweak  
lang 已提交
71 72 73 74
     * @param  {module:echarts/coord/*} [coordSys]
     * @param  {Object} item
     * @return {Object}
     */
75 76 77 78
    var dataTransform = function (seriesModel, item) {
        var data = seriesModel.getData();
        var coordSys = seriesModel.coordinateSystem;

L
lang 已提交
79
        // 1. If not specify the position with pixel directly
80 81
        // 2. If `coord` is not a data array. Which uses `xAxis`,
        // `yAxis` to specify the coord on each dimension
82 83 84

        // parseFloat first because item.x and item.y can be percent string like '20%'
        if ((isNaN(parseFloat(item.x)) || isNaN(parseFloat(item.y)))
85
            && !zrUtil.isArray(item.coord)
L
tweak  
lang 已提交
86 87
            && coordSys
        ) {
88
            var axisInfo = getAxisInfo(item, data, coordSys, seriesModel);
89

L
lang 已提交
90 91
            // Clone the option
            // Transform the properties xAxis, yAxis, radiusAxis, angleAxis, geoCoord to value
92 93
            item = zrUtil.clone(item);

94 95 96 97
            if (item.type
                && markerTypeCalculator[item.type]
                && axisInfo.baseAxis && axisInfo.valueAxis
            ) {
98
                var dims = coordSys.dimensions;
99 100
                var baseCoordIndex = indexOf(dims, axisInfo.baseAxis.dim);
                var valueCoordIndex = indexOf(dims, axisInfo.valueAxis.dim);
101

102
                item.coord = markerTypeCalculator[item.type](
103 104
                    data, axisInfo.baseDataDim, axisInfo.valueDataDim,
                    baseCoordIndex, valueCoordIndex
L
lang 已提交
105
                );
106
                // Force to use the value of calculated value.
107
                item.value = item.coord[valueCoordIndex];
L
lang 已提交
108
            }
L
lang 已提交
109
            else {
L
lang 已提交
110
                // FIXME Only has one of xAxis and yAxis.
111
                item.coord = [
L
lang 已提交
112
                    item.xAxis != null ? item.xAxis : item.radiusAxis,
L
lang 已提交
113
                    item.yAxis != null ? item.yAxis : item.angleAxis
L
lang 已提交
114 115 116 117 118 119
                ];
            }
        }
        return item;
    };

120 121 122 123 124 125
    var getAxisInfo = function (item, data, coordSys, seriesModel) {
        var ret = {};

        if (item.valueIndex != null || item.valueDim != null) {
            ret.valueDataDim = item.valueIndex != null
                ? data.getDimension(item.valueIndex) : item.valueDim;
126
            ret.valueAxis = coordSys.getAxis(seriesModel.dataDimToCoordDim(ret.valueDataDim));
127
            ret.baseAxis = coordSys.getOtherAxis(ret.valueAxis);
128
            ret.baseDataDim = seriesModel.coordDimToDataDim(ret.baseAxis.dim)[0];
129 130 131 132
        }
        else {
            ret.baseAxis = seriesModel.getBaseAxis();
            ret.valueAxis = coordSys.getOtherAxis(ret.baseAxis);
133 134
            ret.baseDataDim = seriesModel.coordDimToDataDim(ret.baseAxis.dim)[0];
            ret.valueDataDim = seriesModel.coordDimToDataDim(ret.valueAxis.dim)[0];
135 136 137 138
        }

        return ret;
    };
L
tweak  
lang 已提交
139 140 141 142 143 144 145 146

    /**
     * Filter data which is out of coordinateSystem range
     * [dataFilter description]
     * @param  {module:echarts/coord/*} [coordSys]
     * @param  {Object} item
     * @return {boolean}
     */
L
lang 已提交
147
    var dataFilter = function (coordSys, item) {
L
tweak  
lang 已提交
148
        // Alwalys return true if there is no coordSys
L
lang 已提交
149
        return (coordSys && coordSys.containData && item.coord && (item.x == null || item.y == null))
150 151 152 153 154 155 156 157 158
            ? coordSys.containData(item.coord) : true;
    };

    var dimValueGetter = function (item, dimName, dataIndex, dimIndex) {
        // x, y, radius, angle
        if (dimIndex < 2) {
            return item.coord && item.coord[dimIndex];
        }
        else {
L
lang 已提交
159
            return item.value;
160
        }
L
Comma  
lang 已提交
161
    };
L
lang 已提交
162

163 164 165 166 167 168
    var numCalculate = function (data, valueDataDim, mlType) {
        return mlType === 'average'
            ? data.getSum(valueDataDim, true) / data.count()
            : data.getDataExtent(valueDataDim, true)[mlType === 'max' ? 1 : 0];
    };

L
lang 已提交
169 170
    return {
        dataTransform: dataTransform,
171
        dataFilter: dataFilter,
172 173 174
        dimValueGetter: dimValueGetter,
        getAxisInfo: getAxisInfo,
        numCalculate: numCalculate
L
lang 已提交
175 176
    };
});