diff --git a/js/apps/system/_admin/aardvark/APP/aardvark.js b/js/apps/system/_admin/aardvark/APP/aardvark.js index 37665297e8..5eea09c4a4 100644 --- a/js/apps/system/_admin/aardvark/APP/aardvark.js +++ b/js/apps/system/_admin/aardvark/APP/aardvark.js @@ -315,8 +315,8 @@ authRouter.get('/graph/:name', function (req, res) { var graph = gm._graph(name); - var vertices = graph._vertexCollections(); - var vertexName = vertices[Math.floor(Math.random() * vertices.length)].name(); + var verticesCollections = graph._vertexCollections(); + var vertexName = verticesCollections[Math.floor(Math.random() * verticesCollections.length)].name(); var vertexCollections = []; _.each(graph._vertexCollections(), function (vertex) { @@ -373,6 +373,7 @@ authRouter.get('/graph/:name', function (req, res) { var nodesObj = {}; var nodesArr = []; + var nodeNames = {}; var edgesObj = {}; var edgesArr = []; @@ -447,68 +448,79 @@ authRouter.get('/graph/:name', function (req, res) { var nodeSize; var nodeObj; _.each(obj.vertices, function (node) { - if (config.nodeLabelByCollection === 'true') { - nodeLabel = node._id.split('/')[0]; - } else if (config.nodeLabel) { - if (config.nodeLabel.indexOf('.') > -1) { - nodeLabel = getAttributeByKey(node, config.nodeLabel); - if (nodeLabel === undefined || nodeLabel === '') { - nodeLabel = node._id; - } - } else { - nodeLabel = node[config.nodeLabel]; - } - } else { - nodeLabel = node._id; - } - - if (typeof nodeLabel === 'number') { - nodeLabel = JSON.stringify(nodeLabel); - } - - if (config.nodeSize) { - nodeSize = node[config.nodeSize]; - } - - nodeObj = { - id: node._id, - label: nodeLabel, - size: nodeSize || 10, - color: config.nodeColor || '#2ecc71', - x: Math.random(), - y: Math.random() - }; - - if (config.nodeColorByCollection === 'true') { - var coll = node._id.split('/')[0]; - if (tmpObjNodes.hasOwnProperty(coll)) { - nodeObj.color = tmpObjNodes[coll]; - } else { - tmpObjNodes[coll] = colors[Object.keys(tmpObjNodes).length]; - nodeObj.color = tmpObjNodes[coll]; - } - } else if (config.nodeColorAttribute !== '') { - var attr = node[config.nodeColorAttribute]; - if (attr) { - if (tmpObjNodes.hasOwnProperty(attr)) { - nodeObj.color = tmpObjNodes[attr]; + if (node !== null) { + nodeNames[node._id] = true; + if (config.nodeLabelByCollection === 'true') { + nodeLabel = node._id.split('/')[0]; + } else if (config.nodeLabel) { + if (config.nodeLabel.indexOf('.') > -1) { + nodeLabel = getAttributeByKey(node, config.nodeLabel); + if (nodeLabel === undefined || nodeLabel === '') { + nodeLabel = node._id; + } } else { - tmpObjNodes[attr] = colors[Object.keys(tmpObjNodes).length]; - nodeObj.color = tmpObjNodes[attr]; + nodeLabel = node[config.nodeLabel]; + } + } else { + nodeLabel = node._id; + } + + if (typeof nodeLabel === 'number') { + nodeLabel = JSON.stringify(nodeLabel); + } + + if (config.nodeSize) { + nodeSize = node[config.nodeSize]; + } + + nodeObj = { + id: node._id, + label: nodeLabel, + size: nodeSize || 10, + color: config.nodeColor || '#2ecc71', + x: Math.random(), + y: Math.random() + }; + + if (config.nodeColorByCollection === 'true') { + var coll = node._id.split('/')[0]; + if (tmpObjNodes.hasOwnProperty(coll)) { + nodeObj.color = tmpObjNodes[coll]; + } else { + tmpObjNodes[coll] = colors[Object.keys(tmpObjNodes).length]; + nodeObj.color = tmpObjNodes[coll]; + } + } else if (config.nodeColorAttribute !== '') { + var attr = node[config.nodeColorAttribute]; + if (attr) { + if (tmpObjNodes.hasOwnProperty(attr)) { + nodeObj.color = tmpObjNodes[attr]; + } else { + tmpObjNodes[attr] = colors[Object.keys(tmpObjNodes).length]; + nodeObj.color = tmpObjNodes[attr]; + } } } - } - nodesObj[node._id] = nodeObj; + nodesObj[node._id] = nodeObj; + } }); }); + _.each(nodesObj, function (node) { + nodesArr.push(node); + }); + + var nodeNamesArr = []; + _.each(nodeNames, function (found, key) { + nodeNamesArr.push(key); + }); + // array format for sigma.js _.each(edgesObj, function (edge) { - edgesArr.push(edge); - }); - _.each(nodesObj, function (node) { - nodesArr.push(node); + if (nodeNamesArr.indexOf(edge.source) > -1 && nodeNamesArr.indexOf(edge.target) > -1) { + edgesArr.push(edge); + } }); res.json({ diff --git a/js/apps/system/_admin/aardvark/APP/frontend/js/views/graphViewer2.js b/js/apps/system/_admin/aardvark/APP/frontend/js/views/graphViewer2.js index 6c81f8f374..9787c03459 100644 --- a/js/apps/system/_admin/aardvark/APP/frontend/js/views/graphViewer2.js +++ b/js/apps/system/_admin/aardvark/APP/frontend/js/views/graphViewer2.js @@ -45,6 +45,8 @@ random1: ['#292F36', '#4ECDC4', '#F7FFF7', '#DD6363', '#FFE66D'] }, + selectedNodes: {}, + aqlMode: false, events: { @@ -338,11 +340,19 @@ this.cursorY = e.y; }, - deleteNode: function () { + deleteNode: function (id) { var self = this; - var documentKey = $('#delete-node-attr-id').text(); - var collectionId = documentKey.split('/')[0]; - var documentId = documentKey.split('/')[1]; + var documentKey; + var collectionId; + var documentId; + + if (id) { + documentKey = id; + } else { + documentKey = $('#delete-node-attr-id').text(); + } + collectionId = documentKey.split('/')[0]; + documentId = documentKey.split('/')[1]; if ($('#delete-node-edges-attr').val() === 'yes') { $.ajax({ @@ -377,6 +387,43 @@ window.modalView.hide(); }, + deleteNodes: function () { + var self = this; + + try { + var arr = JSON.parse($('#delete-nodes-arr-id').text()); + _.each(arr, function (id) { + self.deleteNode(id); + }); + } catch (ignore) { + } + }, + + deleteNodesModal: function () { + var nodeIds = []; + + _.each(this.selectedNodes, function (id) { + nodeIds.push(id); + }); + + var buttons = []; var tableContent = []; + + tableContent.push( + window.modalView.createReadOnlyEntry('delete-nodes-arr-id', 'Really delete nodes', JSON.stringify(nodeIds)) + ); + + buttons.push( + window.modalView.createDeleteButton('Delete', this.deleteNodes.bind(this)) + ); + + window.modalView.show( + 'modalTable.ejs', + 'Delete nodes', + buttons, + tableContent + ); + }, + deleteNodeModal: function (nodeId) { var buttons = []; var tableContent = []; @@ -556,7 +603,7 @@ var callback = function (error, data) { if (!error) { // success - if (self.graphConfig.edgeEditable) { + if (self.graphConfig.edgeEditable === 'true') { self.currentGraph.graph.addEdge({ source: from, size: 1, @@ -574,8 +621,8 @@ } // rerender graph - if (this.graphConfig) { - if (this.graphConfig.edgeType === 'curve') { + if (self.graphConfig) { + if (self.graphConfig.edgeType === 'curve') { sigma.canvas.edges.autoCurve(self.currentGraph); } } @@ -682,6 +729,65 @@ }); }, + // right click background context menu + createNodesContextMenu: function (e) { + var self = this; + + // if right click + if (e.which === 3) { + var x = e.clientX - 50; + var y = e.clientY - 50; + this.clearOldContextMenu(); + + var generateMenu = function (e) { + var Wheelnav = wheelnav; + + var wheel = new Wheelnav('nodeContextMenu'); + wheel.maxPercent = 1.0; + wheel.wheelRadius = 50; + wheel.clockwise = false; + wheel.colors = self.colors.hotaru; + wheel.multiSelect = true; + wheel.clickModeRotate = false; + wheel.slicePathFunction = slicePath().DonutSlice; + if (self.viewStates.captureMode) { + wheel.createWheel([icon.plus, icon.trash]); + } else { + wheel.createWheel([icon.trash, icon.arrowleft2]); + } + + wheel.navItems[0].selected = false; + wheel.navItems[0].hovered = false; + // add menu events + + // function 0: remove all selectedNodes + wheel.navItems[0].navigateFunction = function (e) { + self.clearOldContextMenu(); + self.deleteNodesModal(); + }; + + // function 1: clear contextmenu + wheel.navItems[1].navigateFunction = function (e) { + self.clearOldContextMenu(); + }; + + // deselect active default entry + wheel.navItems[0].selected = false; + wheel.navItems[0].hovered = false; + }; + + $('#nodeContextMenu').css('position', 'fixed'); + $('#nodeContextMenu').css('left', x); + $('#nodeContextMenu').css('top', y); + $('#nodeContextMenu').width(100); + $('#nodeContextMenu').height(100); + + generateMenu(e); + } else { + self.clearOldContextMenu(); + } + }, + // right click background context menu createContextMenu: function (e) { var self = this; @@ -700,11 +806,7 @@ wheel.multiSelect = true; wheel.clickModeRotate = false; wheel.slicePathFunction = slicePath().DonutSlice; - if (self.viewStates.captureMode) { - wheel.createWheel([icon.plus, icon.trash]); - } else { - wheel.createWheel([icon.plus, '']); - } + wheel.createWheel([icon.plus, icon.arrowleft2]); wheel.navItems[0].selected = false; wheel.navItems[0].hovered = false; @@ -716,12 +818,10 @@ self.addNodeModal(); }; - if (self.viewStates.captureMode) { - // function 1: delete all selected nodes - wheel.navItems[1].navigateFunction = function (e) { - self.clearOldContextMenu(); - }; - } + // function 1: exit + wheel.navItems[1].navigateFunction = function (e) { + self.clearOldContextMenu(); + }; // deselect active default entry wheel.navItems[0].selected = false; @@ -976,6 +1076,10 @@ // Do something with the selected nodes var nodes = event.data; + _.each(nodes, function (val, key) { + self.selectedNodes[key] = val.id; + }); + // For instance, reset all node size as their initial size sigmaInstance.graph.nodes().forEach(function (node) { node.color = self.graphConfig.nodeColor ? self.graphConfig.nodeColor : 'rgb(46, 204, 113)'; @@ -994,6 +1098,7 @@ renderGraph: function (graph, toFocus) { var self = this; + console.log(graph); this.graphSettings = graph.settings; @@ -1387,11 +1492,32 @@ toggleLasso: function () { if (this.graphLasso.isActive) { + // remove event + var c = document.getElementsByClassName('sigma-lasso')[0]; + c.removeEventListener('mouseup', this.createNodesContextMenu.bind(this), false); + $('#selectNodes').removeClass('activated'); this.graphLasso.deactivate(); + + // clear selected nodes state + this.selectedNodes = {}; + + this.currentGraph.graph.nodes().forEach(function (n) { + n.color = n.originalColor; + }); + + this.currentGraph.graph.edges().forEach(function (e) { + e.color = e.originalColor; + }); + + this.currentGraph.refresh(); } else { $('#selectNodes').addClass('activated'); this.graphLasso.activate(); + + // add event + var x = document.getElementsByClassName('sigma-lasso')[0]; + x.addEventListener('mouseup', this.createNodesContextMenu.bind(this), false); } },