List.js 7.5 KB
Newer Older
L
lang 已提交
1 2 3 4
define(function(require) {
    'use strict';

    var zrUtil = require('zrender/core/util');
L
lang 已提交
5
    var Model = require('../model/Model');
L
lang 已提交
6
    var DataDiffer = require('./DataDiffer');
L
lang 已提交
7 8 9 10 11 12 13 14

    function createArrayIterWithDepth(maxDepth, properties, cb, context, iterType) {
        // Simple optimization to avoid read the undefined value in properties array
        var nestedProperties = properties.length > 0;
        return function eachAxis(array, depth) {
            if (depth === maxDepth) {
                return zrUtil[iterType](array, cb, context);
            }
L
lang 已提交
15 16 17 18 19 20 21
            else if (array) {
                var property = properties[depth];
                for (var i = 0; i < array.length; i++) {
                    var item = array[i];
                    // Access property of each item
                    if (nestedProperties && property && item) {
                        item = item[property];
L
lang 已提交
22
                    }
L
lang 已提交
23
                    array[i] = eachAxis(item, depth);
L
lang 已提交
24 25 26 27 28
                }
            }
        }
    }

L
lang 已提交
29 30 31 32
    /**
     * @name echarts/data/List~Entry
     * @extends {module:echarts/model/Model}
     */
L
lang 已提交
33 34 35 36
    var Entry = Model.extend({

        layout: null,

L
lang 已提交
37 38
        dimension: 1,

L
lang 已提交
39
        init: function (option, parentModel, dataIndex) {
L
lang 已提交
40 41 42 43 44 45

            /**
             * @type {string}
             * @memeberOf module:echarts/data/List~Entry
             * @public
             */
L
lang 已提交
46 47
            this.name = option.name || '';

L
lang 已提交
48
            this.option = option;
L
lang 已提交
49

L
lang 已提交
50 51 52 53 54
            /**
             * @type {number|Array}
             * @memeberOf module:echarts/data/List~Entry
             * @private
             */
L
lang 已提交
55
            this._value = option.value == null ? option : option.value
L
lang 已提交
56

L
lang 已提交
57 58 59 60
            /**
             * @private
             * @readOnly
             */
L
lang 已提交
61
            this.dataIndex = dataIndex || 0;
L
lang 已提交
62 63 64 65 66 67 68 69
        },

        /**
         * @return {number}
         */
        getX: function () {
            // Use idx as x if data is 1d
            // Usually when xAxis is category axis
L
lang 已提交
70
            return this.dimension === 1 ? this.dataIndex : this._value[0];
L
lang 已提交
71 72
        },

L
lang 已提交
73 74 75
        /**
         * @param {number} x
         */
L
lang 已提交
76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94
        setX: function (x) {
            if (this.dimension > 1) {
                this._value[0] = x;
            }
        },

        /**
         * @return {number}
         */
        getY: function () {
            if (this.dimension > 1) {
                return this._value[1];
            }
            else {
                // Value is a single number if data is 1d
                return this._value;
            }
        },

L
lang 已提交
95 96 97
        /**
         * @param {number} y
         */
L
lang 已提交
98 99 100 101 102 103 104 105 106
        setY: function (y) {
            if (this.dimension > 1) {
                this._value[1] = y;
            }
            else {
                this._value = y;
            }
        },

L
lang 已提交
107 108 109
        /**
         * @return {number}
         */
L
lang 已提交
110 111 112 113 114 115
        getZ: function () {
            if (this.dimension > 2) {
                return this._value[2];
            }
        },

L
lang 已提交
116 117 118
        /**
         * @param {number} z
         */
L
lang 已提交
119 120 121 122 123 124
        setZ: function (z) {
            if (this.dimension > 2) {
                this._value[2] = z;
            }
        },

L
lang 已提交
125 126 127
        /**
         * @return {number}
         */
L
lang 已提交
128 129 130 131
        getValue: function () {
            return this._value[this.dimension];
        },

L
lang 已提交
132 133 134
        /**
         * @param {number} value
         */
L
lang 已提交
135
        setValue: function (value) {
L
lang 已提交
136 137 138 139 140 141 142
            this._value[this.dimension] = value
        },

        clone: function () {
            var entry = new Entry(
                this.option, this.parentModel, this.dataIndex
            );
L
lang 已提交
143
            entry.name = this.name;
L
lang 已提交
144 145
            entry.dimension = this.dimension;
            return entry;
L
lang 已提交
146 147 148
        }
    });

L
lang 已提交
149 150
    function List() {

L
lang 已提交
151
        this.elements = [];
L
lang 已提交
152 153 154 155 156 157 158 159 160 161 162 163 164 165

        // Depth and properties is useful in nested Array.
        // For example in eventRiver, data structure is a nested 2d array as following
        // [{evolution: []}, {evolution: []}]
        // In this situation. depth should be 2 and properties should be ['evolution']
        this.depth = 1;

        this.properties = [];
    }

    List.prototype = {

        constructor: List,

L
lang 已提交
166 167
        type: 'list',

L
lang 已提交
168 169 170 171 172 173 174 175 176 177 178 179 180 181 182
        each: function (cb, context) {
            context = context || this;
            if (this.depth > 1) {
                createArrayIterWithDepth(
                    this.depth, this.properties, cb, context, 'each'
                )(this.elements, 0);
            }
            else {
                zrUtil.each(this.elements, cb, context);
            }
        },

        /**
         * In-place filter
         */
L
lang 已提交
183
        filterInPlace: function (cb, context) {
L
lang 已提交
184 185 186 187 188 189 190 191 192 193 194 195 196 197
            context = context || this;
            if (this.depth > 1) {
                createArrayIterWithDepth(
                    this.depth, this.properties, cb, context, 'filter'
                )(this.elements, 0);
            }
            else {
                this.elements = zrUtil.filter(this.elements, cb, context);
            }
        },

        /**
         * In-place map
         */
L
lang 已提交
198
        mapInPlace: function (cb, context) {
L
lang 已提交
199 200 201 202 203 204 205 206 207 208 209
            context = context || this;
            if (this.depth > 1) {
                createArrayIterWithDepth(
                    this.depth, this.properties, cb, context, 'map'
                )(this.elements, 0);
            }
            else {
                this.elements = zrUtil.map(this.elements, cb, context);
            }
        },

L
lang 已提交
210 211 212 213 214 215 216 217 218 219 220
        /**
         * @return {module:echarts/data/List~Entry}
         */
        getByName: function (name) {
            // TODO deep hierarchy
            var elements = this.elements;
            for (var i = 0; i < elements.length; i++) {
                if (elements[i].name === name) {
                    return elements[i];
                }
            }
L
lang 已提交
221 222
        },

L
lang 已提交
223 224 225 226 227 228 229 230 231 232 233 234
        /**
         * @param {string} name
         * @param {*} option
         */
        append: function (name, option) {
            var elements = this.elements;
            var el = new Entry(option, null, elements.length);
            el.name = name;
            elements.push(el);
            return el;
        },

L
lang 已提交
235 236 237 238
        diff: function (oldList) {
            return new DataDiffer(oldList ? oldList.elements : [], this.elements);
        },

L
lang 已提交
239
        clone: function () {
L
lang 已提交
240 241 242 243 244 245 246 247
            var list = new List();
            var elements = this.elements;
            for (var i = 0; i < elements.length; i++) {
                list.elements.push(elements[i].clone());
            }
            list.depth = this.depth;
            list.properties = this.properties;
            return list;
L
lang 已提交
248 249 250
        }
    };

L
lang 已提交
251
    zrUtil.each(['X', 'Y', 'Z', 'Value'], function (name) {
L
lang 已提交
252 253
        // TODO Map and filter
        zrUtil.each(['each'], function (iterType) {
L
lang 已提交
254 255
            List.prototype[iterType + name] = function (cb, context) {
                this[iterType](function (item, idx) {
L
lang 已提交
256
                    return cb && cb.call(context || this, item['get' + name](idx));
L
lang 已提交
257 258 259 260 261
                }, context);
            };
        });
    });

L
lang 已提交
262
    List.fromArray = function (data, dimension, parentModel) {
L
lang 已提交
263 264
        var list = new List();
        // Normalize data
L
lang 已提交
265
        list.elements = zrUtil.map(data, function (dataItem, index) {
L
lang 已提交
266
            var entry = new Entry(dataItem, parentModel, index);
L
lang 已提交
267 268 269 270
            // TODO
            if (! dataItem.name) {
                entry.name = index;
            }
L
lang 已提交
271
            entry.dimension = dimension || 1;
L
lang 已提交
272
            return entry;
L
lang 已提交
273 274
        });
        return list;
L
lang 已提交
275 276 277
    };

    List.Entry = Entry;
L
lang 已提交
278 279 280

    return List;
});