UNPKG

@antv/g6

Version:

graph visualization frame work

396 lines (353 loc) 10.9 kB
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } } function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; } function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; } /** * @fileOverview tree * @author huangtonger@aliyun.com */ var Util = require('./util/'); var Graph = require('./graph'); var Layouts = require('./layouts/'); var Tree = function (_Graph) { _inherits(Tree, _Graph); function Tree(inputCfg) { _classCallCheck(this, Tree); var cfg = Util.mix({ layout: new Layouts.CompactBoxTree({ getHGap: function getHGap() { return 10; }, getVGap: function getVGap() { return 10; } }) }, inputCfg); return _possibleConstructorReturn(this, _Graph.call(this, cfg)); } Tree.prototype.initEvent = function initEvent() { var _this2 = this; this.on('afterdrawinner', function () { var source = _this2.get('_sourceData'); source.roots.forEach(function (root) { var rootItem = _this2.find(root.id); _this2._setVisibleByCollapsed(rootItem); }); }); // this.on('afterchange', () => { // const roots = this.getRoots(); // roots.forEach(root => { // root.hierarchy = 1; // root.deepEach(child => { // const parent = child.getParent(); // child.hierarchy = parent.hierarchy + 1; // }); // }); // }); }; Tree.prototype._executeLayout = function _executeLayout(processer) { var source = this.get('_sourceData'); if (Util.isFunction(processer)) { processer(source.roots, this); } else if (Util.isObject(processer)) { processer.roots = source.roots; processer.graph = this; processer.execute(); } }; Tree.prototype.getHierarchy = function getHierarchy(item) { item = this.getItem(item); var dataMap = this.get('_dataMap'); var model = item.getModel(); var parent = model.parent; var hierarchy = 1; while (parent) { parent = dataMap[parent].parent; hierarchy++; } return hierarchy; }; Tree.prototype.parseSource = function parseSource(data) { var roots = data.roots; var dataMap = this.get('_dataMap'); var nodes = []; var edges = []; roots.forEach(function (root) { Util.traverseTree(root, function (child, parent) { if (!child.id) { child.id = Util.guid(); } if (!parent) { parent = dataMap[child.parent]; } if (parent) { child.parent = parent.id; if (!parent.id) { parent.id = Util.guid(); } edges.push({ source: parent.id, target: child.id, id: parent.id + '-' + child.id }); } nodes.push(child); }, function (parent) { return parent.children; }, true); }); return { nodes: nodes, edges: edges }; }; // input an item set it's children visiable Tree.prototype._setVisibleByCollapsed = function _setVisibleByCollapsed(item) { var model = item.getModel(); if (model.collapsed) { item.deepEach(function (node) { node.hide(); node.getEdges().forEach(function (edge) { edge.hide(); }); }); } else { item.deepEach(function (node) { if (node.collapsedParent) { node.hide(); node.getEdges().forEach(function (edge) { edge.hide(); }); } }); } }; /** * @param {object} data tree data */ Tree.prototype.source = function source(data) { var _data = this.parseSource(data); this.emit('beforesource'); this.set('_sourceData', data); this.set('_data', _data); this.emit('aftersource'); }; /** * @param {object} node item node * @param {object} nth nth */ Tree.prototype.setNodeNth = function setNodeNth(node, nth) { var model = node.getModel(); var parent = node.getParent(); var parentModel = parent.getModel(); var children = parentModel.children; Util.Array.remove(children, model); children.splice(nth, 0, model); }; /** * @param {object} node item node * @return {number} nth */ Tree.prototype.getNth = function getNth(node) { var model = node.getModel(); var parent = node.getParent(); var parentModel = parent.getModel(); return parentModel.children.indexOf(model); }; /** * @param {string} type item type * @param {object} model data model * @return {Graph} this */ Tree.prototype.add = function add(type, model) { var dataMap = this.get('_dataMap'); var parent = dataMap[model.parent]; var ev = { action: 'add', model: model }; var item = void 0; if (type !== 'node' && type !== 'guide') { console.warn('Tree do not support add type ' + type + '!'); return; } this.emit('beforechange', ev); if (type === 'node') { if (!parent) { throw new Error('please set available parent Id !'); } if (Util.isArray(parent.children)) { parent.children.push(model); } else { parent.children = [model]; } var data = this.parseSource({ roots: [model] }); this.addItems('node', data.nodes); this.addItems('edge', data.edges); item = this.find(model.id); this._setVisibleByCollapsed(item); // set node nth if (!Util.isNil(model.nth)) { this.setNodeNth(item, model.nth); } this.find(parent.id).forceUpdate(); } else { this.addItems(type, [model]); item = this.find(model.id); } ev.item = item; this.emit('afterchange', ev); this.draw(); return item; }; /** * @param {String|Item} item target item * @param {object} model data model * @return {Graph} this */ Tree.prototype.update = function update(item, model) { var _this3 = this; if (!model) { return; } item = this.getItem(item); var itemModel = item.getModel(); var originModel = Util.mix({}, itemModel); var ev = { action: 'update', item: item, originModel: originModel, updateModel: model }; model && this.emit('beforechange', ev); this.updateItem(item, model); if (item.isNode) { // deal collapsed if ('collapsed' in model) { if (model.collapsed) { item.deepEach(function (child) { child.hide(); child.getEdges().forEach(function (edge) { edge.hide(); }); }); } else { item.deepEach(function (child) { child.show(); child.getEdges(function (edge) { var model = edge.getModel(); return model.target === child.id; }).forEach(function (edge) { edge.show(); }); }, function (parent) { if (!parent.model.collapsed) { return parent.getChildren(); } return null; }); } } // exchange parent if (model.parent) { var originParent = this.find(originModel.id); var originParentModel = originParent.getModel(); var newParent = this.find(model.parent); var newParentModel = newParent.getModel(); Util.Array.remove(originParentModel.children, itemModel); if (newParentModel.children) { newParentModel.children.push(itemModel); } else { newParentModel.children = [itemModel]; } this.find(newParentModel.id).forceUpdate(); } // update children if (Util.isArray(model.children)) { if (originModel.children) { Util.each(originModel.children, function (child) { var removeItems = [_this3.find(child)]; child.getEdges().forEach(function (edge) { removeItems.push(edge); }); _this3.removeItems(removeItems); }); } Util.each(model.children, function (child) { var data = _this3.parseSource({ roots: [child] }); _this3.addItems('node', data.nodes); _this3.addItems('edge', data.edges); }); } // set node nth if (!Util.isNil(model.nth)) { this.setNodeNth(item, model.nth); } var parentItem = this.find(itemModel.parent); parentItem && parentItem.forceUpdate(); } this.emit('afterchange', ev); this.draw(); return this; }; /** * @param {String|Item} item target item * @return {Graph} this */ Tree.prototype.remove = function remove(item) { var dataMap = this.get('_dataMap'); var items = []; item = this.getItem(item); if (!item || item.destroyed) { return; } var ev = { action: 'remove', item: item }; this.emit('beforechange', ev); items.push(item); item.getEdges().forEach(function (edge) { items.push(edge); }); if (item.type === 'node') { var model = item.getModel(); var parent = dataMap[model.parent]; item.deepEach(function (child) { items.push(child); child.getEdges().forEach(function (edge) { items.push(edge); }); }); Util.Array.remove(parent.children, model); this.find(parent.id).forceUpdate(); } this.removeItems(Util.uniq(items)); this.emit('afterchange', ev); this.draw(); return this; }; Tree.prototype.getRoots = function getRoots() { var _this4 = this; var source = this.getSource(); return source.roots.map(function (root) { return _this4.find(root.id); }); }; Tree.prototype.save = function save() { var rst = { roots: Util.cloneDeep(this.getSource().roots), guides: this.getGuides().map(function (guide) { return guide.getModel(); }) }; rst.roots.length === 0 && delete rst.roots; rst.guides.length === 0 && delete rst.guides; return rst; }; return Tree; }(Graph); module.exports = Tree;