diff --git a/app/assets/javascripts/Jit/graphsettings-event-handlers.js b/app/assets/javascripts/Jit/graphsettings-event-handlers.js new file mode 100644 index 00000000..2ed560d8 --- /dev/null +++ b/app/assets/javascripts/Jit/graphsettings-event-handlers.js @@ -0,0 +1,145 @@ +function selectEdgeOnClickHandler(adj, e) { + //editing overrides everything else + if (e.altKey) { + editEdge(adj, e); + return; + } + + var showDesc = adj.getData("showDesc"); + if (showDesc && e.shiftKey) { + //deselecting an edge with shift + deselectEdge(adj); + } else if (!showDesc && e.shiftKey) { + //selecting an edge with shift + selectEdge(adj); + } else if (showDesc && !e.shiftKey) { + //deselecting an edge without shift - unselect all + deselectAllEdges(); + } else if (!showDesc && !e.shiftKey) { + //selecting an edge without shift - unselect all but new one + deselectAllEdges(); + selectEdge(adj); + } + + Mconsole.plot(); +}//selectEdgeOnClickHandler + +function selectNodeOnClickHandler(node, e) { + //set final styles + if (!e.shiftKey) { + Mconsole.graph.eachNode(function (n) { + if (n.id != node.id) { + delete n.selected; + n.setData('onCanvas',false); + } + + n.setData('dim', 25, 'current'); + n.eachAdjacency(function (adj) { + deselectEdge(adj); + }); + }); + } + if (!node.selected) { + node.selected = true; + node.setData('dim', 30, 'current'); + node.setData('onCanvas',true); + node.eachAdjacency(function (adj) { + selectEdge(adj); + }); + Mconsole.plot(); + } else { + node.setData('dim', 25, 'current'); + delete node.selected; + node.setData('onCanvas',false); + } + //trigger animation to final styles + Mconsole.fx.animate({ + modes: ['edge-property:lineWidth:color'], + duration: 500 + }); + Mconsole.plot(); +}//selectNodeOnClickHandler + +function canvasDoubleClickHandler(canvasLoc,e) { + var DOUBLE_CLICK_TOLERANCE = 300; //0.3 seconds + + //grab the location and timestamp of the click + var storedTime = MetamapsModel.lastCanvasClick; + var now = Date.now(); //not compatible with IE8 FYI + + if (now - storedTime < DOUBLE_CLICK_TOLERANCE) { + //pop up node creation :) + $('#topic_grabTopic').val("null"); + $('#topic_addSynapse').val("false"); + $('#new_topic').css('left', e.clientX + "px"); + $('#new_topic').css('top', e.clientY + "px"); + $('#topic_x').val(canvasLoc.x); + $('#topic_y').val(canvasLoc.y); + $('#new_topic').fadeIn('fast'); + addMetacode(); + $('#topic_name').focus(); + } else { + MetamapsModel.lastCanvasClick = now; + $('#new_topic').fadeOut('fast'); + $('#new_synapse').fadeOut('fast'); + tempInit = false; + tempNode = null; + tempNode2 = null; + Mconsole.plot(); + } +}//canvasDoubleClickHandler + +function onDragMoveTopicHandler(node, eventInfo, e) { + if (node && !node.nodeFrom) { + $('#new_synapse').fadeOut('fast'); + $('#new_topic').fadeOut('fast'); + var pos = eventInfo.getPos(); + // if it's a left click, move the node + if (e.button == 0 && !e.altKey && (e.buttons == 0 || e.buttons == 1 || e.buttons == undefined)) { + dragged = node.id; + node.pos.setc(pos.x, pos.y); + node.data.$xloc = pos.x; + node.data.$yloc = pos.y; + Mconsole.plot(); + } + // if it's a right click or holding down alt, start synapse creation ->third option is for firefox + else if ((e.button == 2 || (e.button == 0 && e.altKey) || e.buttons == 2) && userid != null) { + if (tempInit == false) { + tempNode = node; + tempInit = true; + } + // + temp = eventInfo.getNode(); + if (temp != false && temp.id != node.id) { // this means a Node has been returned + tempNode2 = temp; + Mconsole.plot(); + renderMidArrow({ x: tempNode.pos.getc().x, y: tempNode.pos.getc().y }, { x: temp.pos.getc().x, y: temp.pos.getc().y }, 13, false, Mconsole.canvas); + // before making the highlighted one bigger, make sure all the others are regular size + Mconsole.graph.eachNode(function (n) { + n.setData('dim', 25, 'current'); + }); + temp.setData('dim',35,'current'); + Mconsole.fx.plotNode(tempNode, Mconsole.canvas); + Mconsole.fx.plotNode(temp, Mconsole.canvas); + } else if (!temp) { + tempNode2 = null; + Mconsole.graph.eachNode(function (n) { + n.setData('dim', 25, 'current'); + }); + //pop up node creation :) + $('#topic_grabTopic').val("null"); + var myX = e.clientX - 110; + var myY = e.clientY - 30; + $('#new_topic').css('left',myX + "px"); + $('#new_topic').css('top',myY + "px"); + $('#new_synapse').css('left',myX + "px"); + $('#new_synapse').css('top',myY + "px"); + $('#topic_x').val(eventInfo.getPos().x); + $('#topic_y').val(eventInfo.getPos().y); + Mconsole.plot(); + renderMidArrow({ x: tempNode.pos.getc().x, y: tempNode.pos.getc().y }, { x: pos.x, y: pos.y }, 13, false, Mconsole.canvas); + Mconsole.fx.plotNode(tempNode, Mconsole.canvas); + } + } + } +} diff --git a/app/assets/javascripts/Jit/graphsettings-model.js b/app/assets/javascripts/Jit/graphsettings-model.js new file mode 100644 index 00000000..3b234530 --- /dev/null +++ b/app/assets/javascripts/Jit/graphsettings-model.js @@ -0,0 +1,12 @@ +/* + * @file + * This file holds the Model object that is referenced in other graphsettings + * files. It lists selected nodes, selected edges, and stores data about + * double clicks on the canvas + */ + +var MetamapsModel = new Object(); +MetamapsModel.selectedEdges = new Array(); +MetamapsModel.lastCanvasClick = 0; +MetamapsModel.DOUBLE_CLICK_TOLERANCE = 300; +MetamapsModel.edgeHoveringOver = false; diff --git a/app/assets/javascripts/Jit/graphsettings.js b/app/assets/javascripts/Jit/graphsettings.js index e371300c..0a7cf916 100644 --- a/app/assets/javascripts/Jit/graphsettings.js +++ b/app/assets/javascripts/Jit/graphsettings.js @@ -1,286 +1,144 @@ +/* + * @file + * This function defines all settings and event callbacks for the JIT graph. Some are found in other files + * First is the common settings (the same as arranged or chaotic) + * Then if it's a centred graph additional settings are added. + */ + function graphSettings(type) { - var t; + var t = { + //id of the visualization container + injectInto: 'infovis', + //Enable zooming and panning + //by scrolling and DnD + Navigation: { + enable: true, + type: 'HTML', + //Enable panning events only if we're dragging the empty + //canvas (and not a node). + panning: 'avoid nodes', + zooming: 15 //zoom speed. higher is more sensible + }, + // Change node and edge styles such as + // color and width. + // These properties are also set per node + // with dollar prefixed data-properties in the + // JSON structure. + Node: { + overridable: true, + color: '#2D6A5D', + type: 'customNode', + dim: 25 + }, + Edge: { + overridable: true, + color: '#222222', + type: 'customEdge', + lineWidth: 2 + }, + //Native canvas text styling + Label: { + type: 'HTML', //Native or HTML + size: 20, + //style: 'bold' + }, + //Add Tips + Tips: { + enable: false, + onShow: function (tip, node) {} + }, + // Add node events + Events: { + enable: true, + enableForEdges: true, + type: 'HTML', + onMouseMove: function(node, eventInfo, e) { + onMouseMoveHandler(node, eventInfo, e); + }, + //Update node positions when dragged + onDragMove: function (node, eventInfo, e) { + onDragMoveTopicHandler(node, eventInfo, e); + }, + onDragEnd: function(node, eventInfo, e) { + onDragEndTopicHandler(node, eventInfo, e, false); + }, + onDragCancel: function(node, eventInfo, e) { + onDragCancelHandler(node, eventInfo, e, false); + }, + //Implement the same handler for touchscreens + onTouchMove: function (node, eventInfo, e) { + $jit.util.event.stop(e); //stop default touchmove event + this.onDragMove(node, eventInfo, e); + }, + //Add also a click handler to nodes + onClick: function (node, eventInfo, e) { + if (e.target.id != "infovis-canvas") return false; + //clicking on a node, or clicking on blank part of canvas? + if (node.nodeFrom) { + selectEdgeOnClickHandler(node, e); + } else if (node && !node.nodeFrom) { + selectNodeOnClickHandler(node, e); + } else { + canvasDoubleClickHandler(eventInfo.getPos(), e); + }//if + }, + //Number of iterations for the FD algorithm + iterations: 200, + //Edge length + levelDistance: 200, + // Add text to the labels. This method is only triggered + // on label creation and only for DOM labels (not native canvas ones). + onCreateLabel: function (domElement, node) { + alert ("onCreateLabel"); + console.log(onCreateLabelHandler); + onCreateLabelHandler(domElement, node); + }, + // Change node styles when DOM labels are placed or moved. + onPlaceLabel: function (domElement, node) { + alert ("onPlaceLabel"); + onPlaceLabelHandler(domElement, node); + } + }//end Events + }; - if (type == "arranged" || type == "chaotic") { - t = { - //id of the visualization container - injectInto: 'infovis', - //Enable zooming and panning - //by scrolling and DnD - Navigation: { - enable: true, - type: 'HTML', - //Enable panning events only if we're dragging the empty - //canvas (and not a node). - panning: 'avoid nodes', - zooming: 15 //zoom speed. higher is more sensible - }, - // Change node and edge styles such as - // color and width. - // These properties are also set per node - // with dollar prefixed data-properties in the - // JSON structure. - Node: { - overridable: true, - color: '#2D6A5D', - type: 'customNode', - dim: 25 - }, - Edge: { - overridable: true, - color: '#222222', - type: 'customEdge', - lineWidth: 2 - }, - //Native canvas text styling - Label: { - type: 'HTML', //Native or HTML - size: 20, - //style: 'bold' - }, - //Add Tips - Tips: { - enable: false, - onShow: function (tip, node) {} - }, - // Add node events - Events: { - enable: true, - enableForEdges: true, - type: 'HTML', - onMouseMove: function(node, eventInfo, e) { - onMouseMoveHandler(node, eventInfo, e); - }, - //Update node positions when dragged - onDragMove: function (node, eventInfo, e) { - clickDragOnTopic(node, eventInfo, e); - }, - onDragEnd: function() { - if (tempInit && tempNode2 == null) { - $('#topic_addSynapse').val("true"); - $('#new_topic').fadeIn('fast'); - addMetacode(); - $('#topic_name').focus(); - } - else if (tempInit && tempNode2 != null) { - $('#topic_addSynapse').val("false"); - $('#synapse_topic1id').val(tempNode.id); - $('#synapse_topic2id').val(tempNode2.id); - $('#new_synapse').fadeIn('fast'); - $('#synapse_desc').focus(); - tempNode = null; - tempNode2 = null; - tempInit = false; - } - else if (dragged != 0 && goRealtime) { saveLayout(dragged); } - }, - onDragCancel: function() { - tempNode = null; - tempNode2 = null; - tempInit = false; - $('#topic_addSynapse').val("false"); - $('#topic_topic1id').val(0); - $('#topic_topic2id').val(0); - Mconsole.plot(); - }, - //Implement the same handler for touchscreens - onTouchMove: function (node, eventInfo, e) { - $jit.util.event.stop(e); //stop default touchmove event - this.onDragMove(node, eventInfo, e); - }, - //Add also a click handler to nodes - onClick: function (node, eventInfo, e) { - if (e.target.id != "infovis-canvas") return false; - //clicking on a node, or clicking on blank part of canvas? - if (node.nodeFrom) { - selectEdgeOnClickHandler(node, e); - } - else if (node && !node.nodeFrom) { - selectNodeOnClickHandler(node, e); - } else { - canvasDoubleClickHandler(eventInfo.getPos(), e); - }//if - }//onClick - }, - //Number of iterations for the FD algorithm - iterations: 200, - //Edge length - levelDistance: 200, - // Add text to the labels. This method is only triggered - // on label creation and only for DOM labels (not native canvas ones). - onCreateLabel: function (domElement, node) { - onCreateLabelHandler(domElement, node); - }, - // Change node styles when DOM labels are placed - // or moved. - onPlaceLabel: function (domElement, node) { - var style = domElement.style; - var left = parseInt(style.left); - var top = parseInt(style.top); - var w = domElement.offsetWidth; - style.left = (left - w / 2 + 107) + 'px'; - //style.left = (left - w / 2) + 'px'; - style.top = (top-165) + 'px'; - style.display = ''; - var label = document.getElementById('topic_' + node.id + '_label'); - w = label.offsetWidth; - style = label.style; - style.left = (-(w / 2 + 106)) + 'px'; - } - }; - } else if (type = "centered") { - t = { - //id of the visualization container - injectInto: 'infovis', - //Optional: create a background canvas that plots - //concentric circles. - background: { - CanvasStyles: { - strokeStyle: '#333', - lineWidth: 1.5 - } - }, - //Enable zooming and panning - //by scrolling and DnD - Navigation: { - enable: true, - type: 'HTML', - //Enable panning events only if we're dragging the empty - //canvas (and not a node). - panning: 'avoid nodes', - zooming: 15 //zoom speed. higher is more sensible - }, - // Change node and edge styles such as - // color and width. - // These properties are also set per node - // with dollar prefixed data-properties in the - // JSON structure. - Node: { - overridable: true, - color: '#2D6A5D', - type: 'customNode', - dim: 25 - }, - Edge: { - overridable: true, - color: '#222222', - type: 'customEdge', - lineWidth: 2 - }, - //Native canvas text styling - Label: { - type: 'HTML', //Native or HTML - size: 20, - //style: 'bold' - }, - //Add Tips - Tips: { - enable: false, - onShow: function (tip, node) {} - }, - // Add node events - Events: { - enable: true, - type: 'HTML', - onMouseMove: function(node, eventInfo, e) { - onMouseMoveHandler(node, eventInfo, e); - }, - //Update node positions when dragged - onDragMove: function (node, eventInfo, e) { - clickDragOnTopic(node, eventInfo, e); - }, - onDragEnd: function() { - if (tempInit && tempNode2 == null) { - $('#topic_addSynapse').val("true"); - $('#new_topic').fadeIn('fast'); - addMetacode(); - $('#topic_name').focus(); - } - else if (tempInit && tempNode2 != null) { - $('#topic_addSynapse').val("false"); - $('#synapse_topic1id').val(tempNode.id); - $('#synapse_topic2id').val(tempNode2.id); - $('#new_synapse').fadeIn('fast'); - $('#synapse_desc').focus(); - tempNode = null; - tempNode2 = null; - tempInit = false; - } - }, - onDragCancel: function() { - tempNode = null; - tempNode2 = null; - tempInit = false; - Mconsole.plot(); - }, - //Implement the same handler for touchscreens - onTouchMove: function (node, eventInfo, e) { - $jit.util.event.stop(e); //stop default touchmove event - this.onDragMove(node, eventInfo, e); - }, - //Add also a click handler to nodes - onClick: function (node, eventInfo, e) { - if (e.target.id != "infovis-canvas") return false; - //clicking on an edge, a node, or clicking on blank part of canvas? - if (eventInfo.getNode() == false) { - if (eventInfo.getEdge() != false) selectEdgeOnClickHandler(eventInfo.getEdge(), e); - else if (node.nodeFrom) selectEdgeOnClickHandler(node, e); - } - else if (node && !node.nodeFrom) { - if (!Mconsole.busy) { - selectNodeOnClickHandler(node, e); - Mconsole.onClick(node.id, { - hideLabels: false - }); - } - } - else { - canvasDoubleClickHandler(eventInfo.getPos(), e); - }//if - }//onClick - }, - //Number of iterations for the FD algorithm - iterations: 200, - //Edge length - levelDistance: 200, - // Add text to the labels. This method is only triggered - // on label creation and only for DOM labels (not native canvas ones). - onCreateLabel: function (domElement, node) { - onCreateLabelHandler(domElement, node); - }, - // Change node styles when DOM labels are placed - // or moved. - onPlaceLabel: function (domElement, node) { - var style = domElement.style; - var left = parseInt(style.left); - var top = parseInt(style.top); - var w = domElement.offsetWidth; - style.left = (left - w / 2 + 107) + 'px'; - //style.left = (left - w / 2) + 'px'; - style.top = (top-165) + 'px'; - style.display = ''; - var label = document.getElementById('topic_' + node.id + '_label'); - w = label.offsetWidth; - style = label.style; - style.left = (-(w / 2 + 106)) + 'px'; - } - }; - } + if (type == "centered") { + t.background = { + CanvasStyles: { + strokeStyle: '#333', + lineWidth: 1.5 + } + }; + t.Events.enableForEdges = true; + t.Events.onDragEnd = function(node, eventInfo, e) { + //different because we can't go realtime + onDragEndTopicHandler(node, eventInfo, e, false); + }; + t.Events.onDragCancel = function(node, eventInfo, e) { + //different because we're centred + onDragCancelHandler(node, eventInfo, e, true); + }; + t.Events.onClick = function(node, eventInfo, e) { + //this is handled mostly differently than in arranged/chaotic + if (e.target.id != "infovis-canvas") return false; + //clicking on an edge, a node, or clicking on blank part of canvas? + if (node.nodeFrom) { + selectEdgeOnClickHandler(node, e); + } else if (node && !node.nodeFrom) { + //node is actually a node :) + if (!Mconsole.busy) { + selectNodeOnClickHandler(node, e); + Mconsole.onClick(node.id, { + hideLabels: false + }); + } + } else { + canvasDoubleClickHandler(eventInfo.getPos(), e); + } + }; + }//if - /*$('body').keypress(function(e) { - console.log(e); - switch(e.keyCode) { - case 114: case 82: - removeSelectedEdges(); - break; - case 100: case 68: - deleteSelectedEdges(); - break; - }//switch - });*/ - - return t; -} + return t; +}//graphSettings // defining code to draw edges with arrows pointing in the middle of them var renderMidArrow = function(from, to, dim, swap, canvas){ @@ -420,493 +278,31 @@ var nodeSettings = { } } -function editEdge(edge, e) { - //reset so we don't interfere with other edges - $('#edit_synapse').remove(); - - deselectEdge(edge); //so the label is missing while editing - var edit_div = document.createElement('div'); - edit_div.setAttribute('id', 'edit_synapse'); - $('.main .wrapper').append(edit_div); - $('#edit_synapse').attr('class', 'best_in_place best_in_place_desc'); - $('#edit_synapse').attr('data-object', 'synapse'); - $('#edit_synapse').attr('data-attribute', 'desc'); - $('#edit_synapse').attr('data-type', 'input'); - //TODO how to get blank data-nil - $('#edit_synapse').attr('data-nil', ' '); - $('#edit_synapse').attr('data-url', '/synapses/' + edge.getData("id")); - $('#edit_synapse').html(edge.getData("desc")); - - $('#edit_synapse').css('position', 'absolute'); - $('#edit_synapse').css('left', e.clientX); - $('#edit_synapse').css('top', e.clientY); - - $('#edit_synapse').bind("ajax:success", function() { - var desc = $(this).html(); - edge.setData("desc", desc); - selectEdge(edge); - Mconsole.plot(); - $('#edit_synapse').remove(); - }); - - $('#edit_synapse').focusout(function() { - //in case they cancel - $('#edit_synapse').hide(); - }); - - //css stuff above moves it, this activates it - $('#edit_synapse').click(); - $('#edit_synapse form').submit(function() { - //hide it once form submits. - //If you don't do this, and data is unchanged, it'll show up on canvas - $('#edit_synapse').hide(); - }); - $('#edit_synapse input').focus(); - $('#edit_synapse').show(); -} - -function selectEdgeOnClickHandler(adj, e) { - //editing overrides everything else - if (e.altKey) { - editEdge(adj, e); - return; - } - - var showDesc = adj.getData("showDesc"); - if (showDesc && e.shiftKey) { - //deselecting an edge with shift - deselectEdge(adj); - } else if (!showDesc && e.shiftKey) { - //selecting an edge with shift - selectEdge(adj); - } else if (showDesc && !e.shiftKey) { - //deselecting an edge without shift - unselect all - deselectAllEdges(); - } else if (!showDesc && !e.shiftKey) { - //selecting an edge without shift - unselect all but new one - deselectAllEdges(); - selectEdge(adj); - } - - Mconsole.plot(); -}//selectEdgeOnClickHandler - -function deselectAllEdges() { - for (var i = 0; i < selectedEdges.length; i += 1) { - var edge = selectedEdges[i]; - deselectEdge(edge); - } -} - -function selectNodeOnClickHandler(node, e) { - //set final styles - if (!e.shiftKey) { - Mconsole.graph.eachNode(function (n) { - if (n.id != node.id) { - delete n.selected; - n.setData('onCanvas',false); - } - - n.setData('dim', 25, 'current'); - n.eachAdjacency(function (adj) { - deselectEdge(adj); - }); - }); - } - if (!node.selected) { - node.selected = true; - node.setData('dim', 30, 'current'); - node.setData('onCanvas',true); - node.eachAdjacency(function (adj) { - selectEdge(adj); - }); - Mconsole.plot(); - } else { - node.setData('dim', 25, 'current'); - delete node.selected; - node.setData('onCanvas',false); - } - //trigger animation to final styles - Mconsole.fx.animate({ - modes: ['edge-property:lineWidth:color'], - duration: 500 - }); - Mconsole.plot(); -}//selectNodeOnClickHandler - -//for the canvasDoubleClickHandler function -var canvasDoubleClickHandlerObject = new Object(); -canvasDoubleClickHandlerObject.storedTime = 0; - -function canvasDoubleClickHandler(canvasLoc,e) { - var TOLERANCE = 300; //0.3 seconds - - //grab the location and timestamp of the click - var storedTime = canvasDoubleClickHandlerObject.storedTime; - var now = Date.now(); //not compatible with IE8 FYI - - if (now - storedTime < TOLERANCE) { - //pop up node creation :) - $('#topic_grabTopic').val("null"); - $('#topic_addSynapse').val("false"); - $('#new_topic').css('left',e.clientX + "px"); - $('#new_topic').css('top',e.clientY + "px"); - $('#topic_x').val(canvasLoc.x); - $('#topic_y').val(canvasLoc.y); - $('#new_topic').fadeIn('fast'); - addMetacode(); - $('#topic_name').focus(); - } else { - canvasDoubleClickHandlerObject.storedTime = now; - $('#new_topic').fadeOut('fast'); - $('#new_synapse').fadeOut('fast'); - tempInit = false; - tempNode = null; - tempNode2 = null; - Mconsole.plot(); - } -}//canvasDoubleClickHandler - -// ForceDirected Mode: for the creation of new topics and synapses through clicking and draggin with right clicks off of topics -function clickDragOnTopic(node, eventInfo, e) { - if (node && !node.nodeFrom) { - $('#new_synapse').fadeOut('fast'); - $('#new_topic').fadeOut('fast'); - var pos = eventInfo.getPos(); - // if it's a left click, move the node - if (e.button == 0 && !e.altKey && (e.buttons == 0 || e.buttons == 1 || e.buttons == undefined)) { - dragged = node.id; - node.pos.setc(pos.x, pos.y); - node.data.$xloc = pos.x; - node.data.$yloc = pos.y; - Mconsole.plot(); - } - // if it's a right click or holding down alt, start synapse creation ->third option is for firefox - else if ((e.button == 2 || (e.button == 0 && e.altKey) || e.buttons == 2) && userid != null) { - if (tempInit == false) { - tempNode = node; - tempInit = true; - } - // - temp = eventInfo.getNode(); - if (temp != false && temp.id != node.id) { // this means a Node has been returned - tempNode2 = temp; - Mconsole.plot(); - renderMidArrow({ x: tempNode.pos.getc().x, y: tempNode.pos.getc().y }, { x: temp.pos.getc().x, y: temp.pos.getc().y }, 13, false, Mconsole.canvas); - // before making the highlighted one bigger, make sure all the others are regular size - Mconsole.graph.eachNode(function (n) { - n.setData('dim', 25, 'current'); - }); - temp.setData('dim',35,'current'); - Mconsole.fx.plotNode(tempNode, Mconsole.canvas); - Mconsole.fx.plotNode(temp, Mconsole.canvas); - } else if (!temp) { - tempNode2 = null; - Mconsole.graph.eachNode(function (n) { - n.setData('dim', 25, 'current'); - }); - //pop up node creation :) - $('#topic_grabTopic').val("null"); - var myX = e.clientX - 110; - var myY = e.clientY - 30; - $('#new_topic').css('left',myX + "px"); - $('#new_topic').css('top',myY + "px"); - $('#new_synapse').css('left',myX + "px"); - $('#new_synapse').css('top',myY + "px"); - $('#topic_x').val(eventInfo.getPos().x); - $('#topic_y').val(eventInfo.getPos().y); - Mconsole.plot(); - renderMidArrow({ x: tempNode.pos.getc().x, y: tempNode.pos.getc().y }, { x: pos.x, y: pos.y }, 13, false, Mconsole.canvas); - Mconsole.fx.plotNode(tempNode, Mconsole.canvas); - } - } - } -} - -function onCreateLabelHandler(domElement, node) { - var html = ' \ -
\ -

$_metacode_$

\ - $_metacode_$ \ - \ - $_name_$ \ - \ - \ - \ -
\ -
\ -
\ - Added by: $_username_$ \ - \ -
\ -
\ -
\ - $_desc_$ \ -
\ -
\ -
\ - \ -
\ -
'; - - //link is rendered differently if user is logged out or in - var go_link, a_tag, close_a_tag; - if (userid == null) { - go_link = ''; - if (node.getData("link") != "") { - a_tag = ''; - close_a_tag = ''; - } - else { - a_tag = ''; - close_a_tag = ''; - } - } else { - go_link = '[go]'; - a_tag = ''; - close_a_tag = ''; - } - - //create metacode_choices array from imgArray - var metacodes = new Array(); - for (var key in imgArray) { - if (imgArray.hasOwnProperty(key)) { - if (key != node.getData("metacode")) { - metacodes.push(key); - } - } - } - - //Arrange it how we want it - metacodes.sort(); - metacodes.unshift(node.getData("metacode")); - - var metacode_choices = "'["; - for (var i in metacodes) { - metacode_choices += '["' + metacodes[i] + '","' + metacodes[i] + '"],'; - } - //remove trailing comma and add ] - metacode_choices = metacode_choices.slice(0, -1); - metacode_choices += "]'"; - - var desc_nil = "Click to add description."; - var link_nil = "Click to add link."; - - html = html.replace(/\$_id_\$/g, node.id); - html = html.replace(/\$_metacode_\$/g, node.getData("metacode")); - html = html.replace(/\$_imgsrc_\$/g, imgArray[node.getData("metacode")].src); - html = html.replace(/\$_name_\$/g, node.name); - html = html.replace(/\$_userid_\$/g, node.getData("userid")); - html = html.replace(/\$_username_\$/g, node.getData("username")); - html = html.replace(/\$_metacode_choices_\$/g, metacode_choices); - html = html.replace(/\$_go_link_\$/g, go_link); - html = html.replace(/\$_a_tag_\$/g, a_tag); - html = html.replace(/\$_close_a_tag_\$/g, close_a_tag); - if (node.getData("link") == "" && userid != null) { - html = html.replace(/\$_link_\$/g, link_nil); - } else { - html = html.replace(/\$_link_\$/g, node.getData("link")); - } - - html = html.replace(/\$_desc_nil_\$/g, desc_nil); - if (node.getData("desc") == "" && userid != null) { - //logged in but desc isn't there so it's invisible - html = html.replace(/\$_desc_\$/g, desc_nil); - } else { - html = html.replace(/\$_desc_\$/g, node.getData("desc")); - } - - var showCard = document.createElement('div'); - showCard.className = 'showcard topic_' + node.id; - showCard.innerHTML = html; - showCard.style.display = "none"; - domElement.appendChild(showCard); - - // add some events to the label - $(showCard).find('img.icon').click(function(){ - hideCard(node); - }); - - $(showCard).find('.scroll').mCustomScrollbar(); - - // Create a 'name' button and add it to the main node label - var nameContainer = document.createElement('span'), - style = nameContainer.style; - nameContainer.className = 'name topic_' + node.id; - nameContainer.id = 'topic_' + node.id + '_label'; - - var littleHTML = ' \ -
$_name_$
\ -
'; - if ((userid == null || mapid == null) && node.id != Mconsole.root) { - littleHTML += ' \ - \ - '; - } - else if (mapid != null && userid != null && node.id != Mconsole.root) { - littleHTML += ' \ - \ - \ - \ - '; - } - if (userid != null && node.id != Mconsole.root) { - littleHTML += ' \ - \ - '; - } - littleHTML += '
'; - littleHTML = littleHTML.replace(/\$_id_\$/g, node.id); - littleHTML = littleHTML.replace(/\$_mapid_\$/g, mapid); - littleHTML = littleHTML.replace(/\$_name_\$/g, node.name); - nameContainer.innerHTML = littleHTML; - domElement.appendChild(nameContainer); - style.fontSize = "0.9em"; - style.color = "#222222"; - - // add some events to the label - $(nameContainer).find('.label').click(function(e){ - $('.showcard').css('display','none'); - $('.name').css('display','block'); - $('.name.topic_' + node.id).css('display','none'); - $('.showcard.topic_' + node.id).fadeIn('fast'); - selectNodeOnClickHandler(node,e); - node.setData('dim', 1, 'current'); - }); - - nameContainer.onmouseover = function(){ - $('.name.topic_' + node.id + ' .nodeOptions').css('display','block'); - } - - nameContainer.onmouseout = function(){ - $('.name.topic_' + node.id + ' .nodeOptions').css('display','none'); - } - - //jQuery selector for the card thing at the top of a topic view - //only works if we're editing the topic whose page we are on - //e.g. on /topics/1 you only need to update .focus.topic_1 - var topcard = '.focus.topic_' + node.id; - - //bind best_in_place ajax callbacks - $(showCard).find('.best_in_place_metacode') - .bind("ajax:success", function() { - var metacode = $(this).html(); - //changing img alt, img src for top card (topic view page) - //and on-canvas card. Also changing image of node - $(showCard).find('img.icon').attr('alt', metacode); - $(showCard).find('img.icon').attr('src', imgArray[metacode].src); - $(topcard + ' img').attr('alt', metacode); - $(topcard + ' img').attr('src', imgArray[metacode].src); - $(topcard + ' .focusleft p').html(metacode); - node.setData("metacode", metacode); - Mconsole.plot(); - }); - - $(showCard).find('.best_in_place_name').bind("ajax:success", function() { - var name = $(this).html(); - $(nameContainer).find('.label').html(name); - $(topcard + ' .focusmiddle .title-text').html(name); - }); - - $(showCard).find('.best_in_place_desc').bind("ajax:success", function() { - var desc = $(this).html(); - $(topcard + ' .focusmiddle p').html(desc); - }); - - $(showCard).find('.best_in_place_link').bind("ajax:success", function() { - var link = $(this).html(); - $(topcard + ' .focusright a').html(link); - $(topcard + ' .focusright a').attr('href', link); - $(showCard).find('.go-link').attr('href', link); - }); - -}//onCreateLabelHandler - -function hideCard(node) { - var card = '.showcard'; - if (node != null) { - card += '.topic_' + node.id; - } - - $(card).fadeOut('fast', function(){ - node.setData('dim', 25, 'current'); - $('.name').show(); - Mconsole.plot(); - }); -} - -//edge that the mouse is currently hovering over -var edgeHover = false; function onMouseMoveHandler(node, eventInfo, e) { - var edge = eventInfo.getEdge(); var node = eventInfo.getNode(); + var edge = eventInfo.getEdge(); //if we're on top of a node object, act like there aren't edges under it if (node != false) { - if (edgeHover) { - onMouseLeave(edgeHover); + if (MetamapsModel.edgeHoveringOver) { + onMouseLeave(MetamapsModel.edgeHoveringOver); } return; } - if (edge == false && edgeHover != false) { + if (edge == false && MetamapsModel.edgeHoveringOver != false) { //mouse not on an edge, but we were on an edge previously - onMouseLeave(edgeHover); - } else if (edge != false && edgeHover == false) { + onMouseLeave(MetamapsModel.edgeHoveringOver); + } else if (edge != false && MetamapsModel.edgeHoveringOver == false) { //mouse is on an edge, but there isn't a stored edge onMouseEnter(edge); - } else if (edge != false && edgeHover != edge) { + } else if (edge != false && MetamapsModel.edgeHoveringOver != edge) { //mouse is on an edge, but a different edge is stored - onMouseLeave(edgeHover) + onMouseLeave(MetamapsModel.edgeHoveringOver) onMouseEnter(edge); } - edgeHover = edge; + MetamapsModel.edgeHoveringOver = edge; } function onMouseEnter(edge) { @@ -942,135 +338,50 @@ function onMouseLeave(edge) { } // this is for hiding one topic from your canvas -function removeEdge(edge) { - var id = edge.getData("id"); - $.ajax({ - type: "DELETE", - url: "/synapses/" + id, - success: function(){ - hideEdge(edge); - }, - }); -} +function onDragEndTopicHandler(node, eventInfo, e, allowRealtime) { + if (tempInit && tempNode2 == null) { + $('#topic_addSynapse').val("true"); + $('#new_topic').fadeIn('fast'); + addMetacode(); + $('#topic_name').focus(); + } else if (tempInit && tempNode2 != null) { + $('#topic_addSynapse').val("false"); + $('#synapse_topic1id').val(tempNode.id); + $('#synapse_topic2id').val(tempNode2.id); + $('#new_synapse').fadeIn('fast'); + $('#synapse_desc').focus(); + tempNode = null; + tempNode2 = null; + tempInit = false; + } else if (allowRealtime && dragged != 0 && goRealtime) { + saveLayout(dragged); + } +}//onDragEndTopicHandler -function hideEdge(edge) { - var from = edge.nodeFrom.id; - var to = edge.nodeTo.id; - edge.setData('alpha', 0, 'end'); - Mconsole.fx.animate({ - modes: ['edge-property:alpha'], - duration: 1000 - }); - Mconsole.graph.removeAdjacence(from, to); +function onDragCancelHandler(node, eventInfo, e, centred) { + tempNode = null; + tempNode2 = null; + tempInit = false; + + //not sure why this doesn't happen for centred graphs + if (!centred) { + $('#topic_addSynapse').val("false"); + $('#topic_topic1id').val(0); + $('#topic_topic2id').val(0); + } Mconsole.plot(); } -function hideSelectedEdges() { - for (var i = 0; i < selectedEdges.length; i += 1) { - var edge = selectedEdges[i]; - hideEdge(edge); - } - selectedEdges = new Array(); -} - -function removeSelectedEdges() { - for (var i = 0; i < selectedEdges.length; i += 1) { - if (mapid != null) { - var edge = selectedEdges[i]; - var id = edge.getData("id"); - //delete mapping of id mapid - $.ajax({ - type: "POST", - url: "/synapses/" + mapid + "/" + id + "/removefrommap", - }); - } - hideEdge(edge); - } - selectedEdges = new Array(); -} - -function deleteSelectedEdges() { - for (var i = 0; i < selectedEdges.length; i += 1) { - var edge = selectedEdges[i]; - var id = edge.getData("id"); - $.ajax({ - type: "DELETE", - url: "/synapses/" + id, - }); - hideEdge(edge); - } - selectedEdges = new Array(); -} - -//keeps track of all selected edges globally -var selectedEdges = new Array(); - -function selectEdge(edge) { - var showDesc = edge.getData("showDesc"); - if (! showDesc) { - edge.setData('showDesc', true, 'current'); - edge.setDataset('end', { - lineWidth: 4, - color: '#FFFFFF' - }); - Mconsole.fx.animate({ - modes: ['edge-property:lineWidth:color'], - duration: 100 - }); - } - selectedEdges.push(edge); -} - -function deselectEdge(edge) { - var showDesc = edge.getData("showDesc"); - if (showDesc) { - edge.setData('showDesc', false, 'current'); - edge.setDataset('end', { - lineWidth: 2, - color: '#222222' - }); - - if (edgeHover == edge) { - edge.setDataset('end', { - lineWidth: 4, - color: '#222222' - }); - } - - Mconsole.fx.animate({ - modes: ['edge-property:lineWidth:color'], - duration: 100 - }); - } - selectedEdges.splice(selectedEdges.indexOf(edge), 1); -} - -function hideSelectedNodes() { - Mconsole.graph.eachNode( function (n) { - if (n.data.$onCanvas == true && n.id != Mconsole.root) { - removeFromCanvas(n.id); - } - }); -} - -function removeSelectedNodes() { - Mconsole.graph.eachNode( function (n) { - if (n.data.$onCanvas == true && n.id != Mconsole.root) { - $.ajax({ - type: "POST", - url: "/topics/" + mapid + "/" + n.id + "/removefrommap", - }); - } - }); -} - -function deleteSelectedNodes() { - Mconsole.graph.eachNode( function (n) { - if (n.data.$onCanvas == true && n.id != Mconsole.root) { - $.ajax({ - type: "DELETE", - url: "/topics/" + n.id, - }); - } - }); +function onPlaceLabelHandler(domElement, node) { + var style = domElement.style; + var left = parseInt(style.left); + var top = parseInt(style.top); + var w = domElement.offsetWidth; + style.left = (left - w / 2 + 107) + 'px'; + style.top = (top-165) + 'px'; + style.display = ''; + var label = document.getElementById('topic_' + node.id + '_label'); + w = label.offsetWidth; + style = label.style; + style.left = (-(w / 2 + 106)) + 'px'; } diff --git a/app/assets/javascripts/Jit/loadgraphs.js b/app/assets/javascripts/Jit/loadgraphs.js index 63f7f630..3b9d0b5c 100644 --- a/app/assets/javascripts/Jit/loadgraphs.js +++ b/app/assets/javascripts/Jit/loadgraphs.js @@ -68,10 +68,12 @@ function initialize(type, loadLater){ if ( type == "centered") { // init Rgraph + alert("Going in, and we're centered"); Mconsole = new $jit.RGraph(graphSettings(type)); } else if ( type == "arranged" || type == "chaotic" ) { // init ForceDirected + alert("Going in, and we're arranged/chaotic"); Mconsole = new $jit.ForceDirected(graphSettings(type)); } else { diff --git a/app/assets/javascripts/Jit/onCreateLabelHandler.js b/app/assets/javascripts/Jit/onCreateLabelHandler.js new file mode 100644 index 00000000..fa291867 --- /dev/null +++ b/app/assets/javascripts/Jit/onCreateLabelHandler.js @@ -0,0 +1,279 @@ +/* + * @file + * There is a lot of code that goes into creating the "label" of a node + * This includes editable cards with all node details, and some controls + * onCreateLabelHandler is the main function of this file, and the file + * also contains a bunch of helper functions + * + * html and littleHTML are potentially confusing variables + * html is the contents of the card shown when you click on a node's label. + * littleHTML creates little controls for removing/hiding nodes from the canvas + * + * This function features PHP-style variable substitution because the strings + * are so damn long. Values are identified by $_id_$, and then a regular + * expression is substituted in later (for html, in a separate function). + */ + +function onCreateLabelHandler(domElement, node) { + var html = generateShowcardHTML(); + html = replaceVariables(html, node); + + var showCard = document.createElement('div'); + showCard.className = 'showcard topic_' + node.id; + showCard.innerHTML = html; + showCard.style.display = "none"; + domElement.appendChild(showCard); + + // Create a 'name' button and add it to the main node label + var nameContainer = document.createElement('span'), + style = nameContainer.style; + nameContainer.className = 'name topic_' + node.id; + nameContainer.id = 'topic_' + node.id + '_label'; + + nameContainer.innerHTML = generateLittleHTML (node); + domElement.appendChild(nameContainer); + style.fontSize = "0.9em"; + style.color = "#222222"; + + bindCallbacks(showCard, nameContainer, node); +} + +function generateShowcardHTML() { + return ' \ +
\ +

$_metacode_$

\ + $_metacode_$ \ + \ + $_name_$ \ + \ + \ + \ +
\ +
\ +
\ + Added by: $_username_$ \ + \ +
\ +
\ +
\ + $_desc_$ \ +
\ +
\ +
\ + \ +
\ +
'; +}//generateShowcardHTML + +function replaceVariables(html, node) { + //link is rendered differently if user is logged out or in + var go_link, a_tag, close_a_tag; + if (userid == null) { + go_link = ''; + if (node.getData("link") != "") { + a_tag = ''; + close_a_tag = ''; + } + else { + a_tag = ''; + close_a_tag = ''; + } + } else { + go_link = '[go]'; + a_tag = ''; + close_a_tag = ''; + } + + //create metacode_choices array from imgArray + var metacodes = new Array(); + for (var key in imgArray) { + if (imgArray.hasOwnProperty(key)) { + if (key != node.getData("metacode")) { + metacodes.push(key); + } + } + } + + //Arrange it how we want it + metacodes.sort(); + metacodes.unshift(node.getData("metacode")); + + var metacode_choices = "'["; + for (var i in metacodes) { + metacode_choices += '["' + metacodes[i] + '","' + metacodes[i] + '"],'; + } + //remove trailing comma and add ] + metacode_choices = metacode_choices.slice(0, -1); + metacode_choices += "]'"; + + var desc_nil = "Click to add description."; + var link_nil = "Click to add link."; + + html = html.replace(/\$_id_\$/g, node.id); + html = html.replace(/\$_metacode_\$/g, node.getData("metacode")); + html = html.replace(/\$_imgsrc_\$/g, imgArray[node.getData("metacode")].src); + html = html.replace(/\$_name_\$/g, node.name); + html = html.replace(/\$_userid_\$/g, node.getData("userid")); + html = html.replace(/\$_username_\$/g, node.getData("username")); + html = html.replace(/\$_metacode_choices_\$/g, metacode_choices); + html = html.replace(/\$_go_link_\$/g, go_link); + html = html.replace(/\$_a_tag_\$/g, a_tag); + html = html.replace(/\$_close_a_tag_\$/g, close_a_tag); + if (node.getData("link") == "" && userid != null) { + html = html.replace(/\$_link_\$/g, link_nil); + } else { + html = html.replace(/\$_link_\$/g, node.getData("link")); + } + + html = html.replace(/\$_desc_nil_\$/g, desc_nil); + if (node.getData("desc") == "" && userid != null) { + //logged in but desc isn't there so it's invisible + html = html.replace(/\$_desc_\$/g, desc_nil); + } else { + html = html.replace(/\$_desc_\$/g, node.getData("desc")); + } + return html; +} + +function generateLittleHTML(node) { + var littleHTML = ' \ +
$_name_$
\ +
'; + + if ((userid == null || mapid == null) && node.id != Mconsole.root) { + //unauthenticated, not on a map: can remove from canvas + littleHTML += ' \ + \ + '; + } else if (mapid != null && userid != null && node.id != Mconsole.root) { + //not on a map, authenticated, and not looking at root node + //(you can't delete the root node of a JIT graph) + littleHTML += ' \ + \ + \ + \ + '; + } + + if (userid != null && node.id != Mconsole.root) { + //logged in, whether you're on a map or not + littleHTML += ' \ + \ + '; + } + littleHTML += '
'; + littleHTML = littleHTML.replace(/\$_id_\$/g, node.id); + littleHTML = littleHTML.replace(/\$_mapid_\$/g, mapid); + littleHTML = littleHTML.replace(/\$_name_\$/g, node.name); +} + +function hideCard(id) { + var card = '.showcard'; + if (node != null) { + card += '.topic_' + id; + } + + $(card).fadeOut('fast', function(){ + node.setData('dim', 25, 'current'); + $('.name').show(); + Mconsole.plot(); + }); +} + +function bindCallbacks(showCard, nameContainer, node) { + // add some events to the label + $(showCard).find('img.icon').click(function(){ + hideCard(node.id); + }); + + $(showCard).find('.scroll').mCustomScrollbar(); + + // add some events to the label + $(nameContainer).find('.label').click(function(e){ + $('.showcard').css('display','none'); + $('.name').css('display','block'); + $('.name.topic_' + node.id).css('display','none'); + $('.showcard.topic_' + node.id).fadeIn('fast'); + selectNodeOnClickHandler(node,e); + node.setData('dim', 1, 'current'); + }); + + nameContainer.onmouseover = function(){ + $('.name.topic_' + node.id + ' .nodeOptions').css('display','block'); + } + + nameContainer.onmouseout = function(){ + $('.name.topic_' + node.id + ' .nodeOptions').css('display','none'); + } + + //bind best_in_place ajax callbacks + $(showCard).find('.best_in_place_metacode').bind("ajax:success", function() { + var metacode = $(this).html(); + //changing img alt, img src for top card (topic view page) + //and on-canvas card. Also changing image of node + $(showCard).find('img.icon').attr('alt', metacode); + $(showCard).find('img.icon').attr('src', imgArray[metacode].src); + node.setData("metacode", metacode); + Mconsole.plot(); + }); + + $(showCard).find('.best_in_place_name').bind("ajax:success", function() { + var name = $(this).html(); + $(nameContainer).find('.label').html(name); + }); + + //available if you want it :) + //$(showCard).find('.best_in_place_desc').bind("ajax:success", function() { + // var desc = $(this).html(); + //}); + + $(showCard).find('.best_in_place_link').bind("ajax:success", function() { + var link = $(this).html(); + $(showCard).find('.go-link').attr('href', link); + }); +} diff --git a/app/assets/javascripts/Jit/select-edit-delete-nodes-and-edges.js b/app/assets/javascripts/Jit/select-edit-delete-nodes-and-edges.js new file mode 100644 index 00000000..56da2ff8 --- /dev/null +++ b/app/assets/javascripts/Jit/select-edit-delete-nodes-and-edges.js @@ -0,0 +1,185 @@ +function editEdge(edge, e) { + //reset so we don't interfere with other edges + $('#edit_synapse').remove(); + + deselectEdge(edge); //so the label is missing while editing + var edit_div = document.createElement('div'); + edit_div.setAttribute('id', 'edit_synapse'); + $('.main .wrapper').append(edit_div); + $('#edit_synapse').attr('class', 'best_in_place best_in_place_desc'); + $('#edit_synapse').attr('data-object', 'synapse'); + $('#edit_synapse').attr('data-attribute', 'desc'); + $('#edit_synapse').attr('data-type', 'input'); + //TODO how to get blank data-nil + $('#edit_synapse').attr('data-nil', ' '); + $('#edit_synapse').attr('data-url', '/synapses/' + edge.getData("id")); + $('#edit_synapse').html(edge.getData("desc")); + + $('#edit_synapse').css('position', 'absolute'); + $('#edit_synapse').css('left', e.clientX); + $('#edit_synapse').css('top', e.clientY); + + $('#edit_synapse').bind("ajax:success", function() { + var desc = $(this).html(); + edge.setData("desc", desc); + selectEdge(edge); + Mconsole.plot(); + $('#edit_synapse').remove(); + }); + + $('#edit_synapse').focusout(function() { + //in case they cancel + $('#edit_synapse').hide(); + }); + + //css stuff above moves it, this activates it + $('#edit_synapse').click(); + $('#edit_synapse form').submit(function() { + //hide it once form submits. + //If you don't do this, and data is unchanged, it'll show up on canvas + $('#edit_synapse').hide(); + }); + $('#edit_synapse input').focus(); + $('#edit_synapse').show(); +} + +function deselectAllEdges() { + for (var i = 0; i < MetamapsModel.selectedEdges.length; i += 1) { + var edge = MetamapsModel.selectedEdges[i]; + deselectEdge(edge); + } +} + +// this is for hiding one topic from your canvas +function removeEdge(edge) { + var id = edge.getData("id"); + $.ajax({ + type: "DELETE", + url: "/synapses/" + id, + success: function(){ + hideEdge(edge); + }, + }); +} + +function hideEdge(edge) { + var from = edge.nodeFrom.id; + var to = edge.nodeTo.id; + edge.setData('alpha', 0, 'end'); + Mconsole.fx.animate({ + modes: ['edge-property:alpha'], + duration: 1000 + }); + Mconsole.graph.removeAdjacence(from, to); + Mconsole.plot(); +} + +function hideSelectedEdges() { + for (var i = 0; i < MetamapsModel.selectedEdges.length; i += 1) { + var edge = MetamapsModel.selectedEdges[i]; + hideEdge(edge); + } + MetamapsModel.selectedEdges = new Array(); +} + +function removeSelectedEdges() { + for (var i = 0; i < MetamapsModel.selectedEdges.length; i += 1) { + if (mapid != null) { + var edge = MetamapsModel.selectedEdges[i]; + var id = edge.getData("id"); + //delete mapping of id mapid + $.ajax({ + type: "POST", + url: "/synapses/" + mapid + "/" + id + "/removefrommap", + }); + } + hideEdge(edge); + } + MetamapsModel.selectedEdges = new Array(); +} + +function deleteSelectedEdges() { + for (var i = 0; i < MetamapsModel.selectedEdges.length; i += 1) { + var edge = MetamapsModel.selectedEdges[i]; + var id = edge.getData("id"); + $.ajax({ + type: "DELETE", + url: "/synapses/" + id, + }); + hideEdge(edge); + } + MetamapsModel.selectedEdges = new Array(); +} + +function selectEdge(edge) { + var showDesc = edge.getData("showDesc"); + if (! showDesc) { + edge.setData('showDesc', true, 'current'); + edge.setDataset('end', { + lineWidth: 4, + color: '#FFFFFF' + }); + Mconsole.fx.animate({ + modes: ['edge-property:lineWidth:color'], + duration: 100 + }); + } + MetamapsModel.selectedEdges.push(edge); +} + +function deselectEdge(edge) { + var showDesc = edge.getData("showDesc"); + if (showDesc) { + edge.setData('showDesc', false, 'current'); + edge.setDataset('end', { + lineWidth: 2, + color: '#222222' + }); + + if (MetamapsModel.edgeHoveringOver == edge) { + edge.setDataset('end', { + lineWidth: 4, + color: '#222222' + }); + } + + Mconsole.fx.animate({ + modes: ['edge-property:lineWidth:color'], + duration: 100 + }); + } + + //remove the edge + MetamapsModel.selectedEdges.splice( + MetamapsModel.selectedEdges.indexOf(edge), 1); +} + +function hideSelectedNodes() { + Mconsole.graph.eachNode( function (n) { + if (n.data.$onCanvas == true && n.id != Mconsole.root) { + removeFromCanvas(n.id); + } + }); +} + +function removeSelectedNodes() { + Mconsole.graph.eachNode( function (n) { + if (n.data.$onCanvas == true && n.id != Mconsole.root) { + $.ajax({ + type: "POST", + url: "/topics/" + mapid + "/" + n.id + "/removefrommap", + }); + } + }); +} + +function deleteSelectedNodes() { + Mconsole.graph.eachNode( function (n) { + if (n.data.$onCanvas == true && n.id != Mconsole.root) { + $.ajax({ + type: "DELETE", + url: "/topics/" + n.id, + }); + } + }); +}