diff --git a/app/assets/javascripts/Jit/graphsettings.js b/app/assets/javascripts/Jit/graphsettings.js index 9ee000cf..19f1d25d 100644 --- a/app/assets/javascripts/Jit/graphsettings.js +++ b/app/assets/javascripts/Jit/graphsettings.js @@ -46,6 +46,7 @@ function graphSettings(type) { // Add node events Events: { enable: true, + enableForEdges: true, type: 'HTML', //Change cursor style when hovering a node onMouseEnter: function () { @@ -56,10 +57,77 @@ function graphSettings(type) { }, //Update node positions when dragged onDragMove: function (node, eventInfo, e) { - var pos = eventInfo.getPos(); - node.pos.setc(pos.x, pos.y); - Mconsole.plot(); + if (node && !node.nodeFrom) { + $('#new_item').fadeOut('fast'); + var pos = eventInfo.getPos(); + // if it's a left click, move the node + if (e.button == 0) { + node.pos.setc(pos.x, pos.y); + Mconsole.plot(); + } + // if it's a right click, start synapse creation + else if (e.button == 2) { + if (tempInit == false) { + tempNode = node; + console.log(tempNode); + 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.x, y: tempNode.pos.y }, { x: temp.pos.x, y: temp.pos.y }, 13, false, Mconsole.canvas); + temp.setData('dim',35,'current'); + Mconsole.fx.plotNode(tempNode, Mconsole.canvas); + Mconsole.fx.plotNode(temp, Mconsole.canvas); + } else if (!temp) { + if (tempNode2 != null) { + tempNode2.setData('dim',25,'current'); + Mconsole.fx.plotNode(tempNode2, Mconsole.canvas); + tempNode2 = null; + } + //pop up node creation :) + $('#item_grabItem').val("null"); + var myX = e.x - 110; + var myY = e.y - 30; + document.getElementById('new_item').style.left = myX + "px"; + document.getElementById('new_item').style.top = myY + "px"; + document.getElementById('new_synapse').style.left = myX + "px"; + document.getElementById('new_synapse').style.top = myY + "px"; + $('#item_x').val(eventInfo.getPos().x); + $('#item_y').val(eventInfo.getPos().y); + Mconsole.plot(); + renderMidArrow({ x: tempNode.pos.x, y: tempNode.pos.y }, { x: pos.x, y: pos.y }, 13, false, Mconsole.canvas); + Mconsole.fx.plotNode(tempNode, Mconsole.canvas); + } + } + } }, + onDragEnd: function() { + if (tempInit && tempNode2 == null) { + tempNode = null; + tempNode2 = null; + tempInit = false; + $('#new_item').fadeIn('fast'); + $('#item_name').focus(); + } + else if (tempInit && tempNode2 != null) { + $('#new_synapse').fadeIn('fast'); + $('#synapse_desc').focus(); + tempNode = null; + tempNode2 = null; + tempInit = false; + } + }, + onDragCancel: function() { + if (tempInit && tempNode2 == null) { + 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 @@ -68,7 +136,10 @@ function graphSettings(type) { //Add also a click handler to nodes onClick: function (node, eventInfo, e) { //clicking on a node, or clicking on blank part of canvas? - if (node) { + if (node.nodeFrom) { + selectEdgeOnClickHandler(node); + } + else if (node && !node.nodeFrom) { selectNodeOnClickHandler(node); } else { canvasDoubleClickHandler(eventInfo.getPos(), e); @@ -206,9 +277,11 @@ function graphSettings(type) { }, //Update node positions when dragged onDragMove: function (node, eventInfo, e) { - var pos = eventInfo.getPos(); - node.pos.setc(pos.x, pos.y); - Mconsole.plot(); + if (node && !node.nodeFrom) { + var pos = eventInfo.getPos(); + node.pos.setc(pos.x, pos.y); + Mconsole.plot(); + } }, //Implement the same handler for touchscreens onTouchMove: function (node, eventInfo, e) { @@ -217,8 +290,11 @@ function graphSettings(type) { }, //Add also a click handler to nodes onClick: function (node, eventInfo, e) { - //clicking on a node, or clicking on blank part of canvas? - if (node) { + //clicking on an edge, a node, or clicking on blank part of canvas? + if (node.nodeFrom) { + selectEdgeOnClickHandler(node); + } + else if (node && !node.nodeFrom) { if (!Mconsole.busy) { selectNodeOnClickHandler(node); Mconsole.onClick(node.id, { @@ -365,16 +441,27 @@ var nodeSettings = { var y = parseInt((pos.y + posChild.y) /2); canvas.getCtx().fillStyle = '#000'; canvas.getCtx().font = 'bold 14px arial'; - //canvas.getCtx().fillText(desc, x, y); + canvas.getCtx().fillText(desc, x, y); } }, 'contains' : function(adj, pos) { var from = adj.nodeFrom.pos.getc(true), to = adj.nodeTo.pos.getc(true); - return containsMidArrow(from, to, pos, this.edge.epsilon); + return this.edgeHelper.line.contains(from, to, pos, adj.Edge.epsilon); } } } +function selectEdgeOnClickHandler(adj) { + var showDesc = adj.getData("showDesc"); + if (showDesc) { + adj.setData('showDesc', false, 'current'); + Mconsole.plot(); + } else if (!showDesc) { + adj.setData('showDesc', true, 'current'); + Mconsole.plot(); + } +}//selectEdgeOnClickHandler + function selectNodeOnClickHandler(node) { $('.showcard').css('display','none'); diff --git a/app/assets/javascripts/Jit/loadgraphs.js b/app/assets/javascripts/Jit/loadgraphs.js index d9739633..4477bae8 100644 --- a/app/assets/javascripts/Jit/loadgraphs.js +++ b/app/assets/javascripts/Jit/loadgraphs.js @@ -1,4 +1,4 @@ -var labelType, useGradients, nativeTextSupport, animate, json, Mconsole, gType; +var labelType, useGradients, nativeTextSupport, animate, json, Mconsole, gType, tempNode, tempInit = false, tempNode2 = null; (function() { var ua = navigator.userAgent, @@ -84,10 +84,6 @@ midPoint.y - vect.y); ctx.stroke(); }; -var containsMidArrow = function(posFrom, posTo, pos, epsilon) { - return $jit.EdgeHelper.line.contains(posFrom, posTo, pos, epsilon); -}; - function initialize(type){ viewMode = "graph"; gType = type; diff --git a/app/assets/javascripts/application.js b/app/assets/javascripts/application.js index ba9675d2..979b0f23 100644 --- a/app/assets/javascripts/application.js +++ b/app/assets/javascripts/application.js @@ -21,6 +21,10 @@ var viewMode = "list"; $(document).ready(function() { + $('#new_item').bind('contextmenu', function(e){ + return false; + }); + /// this is for the topic creation autocomplete fielf $('#item_name').bind('railsAutocomplete.select', function(event, data){ if (data.item.id != undefined) { diff --git a/app/assets/stylesheets/application.css b/app/assets/stylesheets/application.css index a4477350..4e302e2d 100644 --- a/app/assets/stylesheets/application.css +++ b/app/assets/stylesheets/application.css @@ -33,15 +33,14 @@ h2 {display:block; text-align:center; font-family: "vinyl",sans-serif; backgroun a {color:#2d6a5d; text-decoration:none;} .clearfloat {clear:both;} -.new_session, .new_user, .new_synapse, .new_map, .edit_user, .edit_item, .edit_synapse, .edit_map, .invite { display: block; width: 350px; position:absolute; left:50%; top:0; margin:200px 0 0 -195px; background: url('bg.png'); padding: 20px; border-radius: 15px; color: #000; border:2px solid #000; } +.new_session, .new_user, .new_map, .edit_user, .edit_item, .edit_synapse, .edit_map, .invite { display: block; width: 350px; position:absolute; left:50%; top:0; margin:200px 0 0 -195px; background: url('bg.png'); padding: 20px; border-radius: 15px; color: #000; border:2px solid #000; } .invite p { margin:10px 0; } .invite strong { text-align:center; display:block; color:#67AF9F; } -.anypage .new_synapse { display: none; position:absolute; left:50%; top:0; margin:200px 0 0 -195px; border:2px solid #000; } #closenewtopic, #closenewsynapse { position:absolute; top: 3px; right:3px; } -.anypage .new_item { +.anypage .new_item, .anypage .new_synapse { display: none; position: absolute; background: url('bg.png'); diff --git a/app/controllers/items_controller.rb b/app/controllers/items_controller.rb index 791ad314..84b9ca1a 100644 --- a/app/controllers/items_controller.rb +++ b/app/controllers/items_controller.rb @@ -64,6 +64,13 @@ class ItemsController < ApplicationController @item.user = @user @item.save + end + + # pass the variables for synapse creation onto the javascript file + if params[:item][:addSynapse] != "false" + @synapse = Hash.new() + @synapse['item1id'] = params[:item][:item1id] + @synapse['item2id'] = params[:item][:item2id] end # also create an object to return the position to the canvas @@ -85,7 +92,7 @@ class ItemsController < ApplicationController respond_to do |format| format.html { respond_with(@user, location: user_item_url(@user, @item)) } - format.js { respond_with(@item, @mapping, @position) } + format.js { respond_with(@item, @mapping, @synapse, @position) } end end diff --git a/app/controllers/synapses_controller.rb b/app/controllers/synapses_controller.rb index 6db25b6f..7be76f9f 100644 --- a/app/controllers/synapses_controller.rb +++ b/app/controllers/synapses_controller.rb @@ -5,6 +5,8 @@ class SynapsesController < ApplicationController respond_to :html, :js, :json + autocomplete :synapse, :desc, :full => true + # GET users/:user_id/synapses def index @user = User.find(params[:user_id]) @@ -54,15 +56,11 @@ class SynapsesController < ApplicationController @user = current_user @synapse = Synapse.new() @synapse.desc = params[:synapse][:desc] - @synapse.category = params[:synapse][:category] - @synapse.item1 = Item.find(params[:node1_id]) - @synapse.item2 = Item.find(params[:node2_id]) - @synapse.permission = params[:synapse][:permission] + @synapse.item1 = Item.find(params[:synapse][:item1id]) + @synapse.item2 = Item.find(params[:synapse][:item2id]) @synapse.user = @user @synapse.save - @mapping1 = Mapping.new() - @mapping2 = Mapping.new() if params[:synapse][:map] @mapping = Mapping.new() @mapping.category = "Synapse" @@ -70,26 +68,11 @@ class SynapsesController < ApplicationController @mapping.map = Map.find(params[:synapse][:map]) @mapping.synapse = @synapse @mapping.save - - if not Map.find(params[:synapse][:map]).items.include?(@synapse.item1) - @mapping1.category = "Item" - @mapping1.user = @user - @mapping1.map = Map.find(params[:synapse][:map]) - @mapping1.item = @synapse.item1 - @mapping1.save - end - if not Map.find(params[:synapse][:map]).items.include?(@synapse.item2) - @mapping2.category = "Item" - @mapping2.user = @user - @mapping2.map = Map.find(params[:synapse][:map]) - @mapping2.item = @synapse.item2 - @mapping2.save - end end respond_to do |format| format.html { respond_with(@user, location: user_synapse_url(@user, @synapse)) } - format.js { respond_with(@synapse, @mapping1, @mapping2) } + format.js { respond_with(@synapse) } end end diff --git a/app/helpers/items_helper.rb b/app/helpers/items_helper.rb index 1e62b59e..f7608054 100644 --- a/app/helpers/items_helper.rb +++ b/app/helpers/items_helper.rb @@ -51,7 +51,12 @@ module ItemsHelper @synapsedata = Hash.new @synapsedata['$desc'] = synapse.desc - @synapsedata['$category'] = synapse.category + @synapsedata['$showDesc'] = false + @synapsedata['$category'] = synapse.category + @synapsedata['$id'] = synapse.id + @synapsedata['$userid'] = synapse.user.id + @synapsedata['$username'] = synapse.user.name + @synapsedata['$direction'] = [synapse.node1_id.to_s(), synapse.node2_id.to_s()] json.data @synapsedata end diff --git a/app/views/items/_new.html.erb b/app/views/items/_new.html.erb index 761c5494..551755da 100644 --- a/app/views/items/_new.html.erb +++ b/app/views/items/_new.html.erb @@ -4,5 +4,8 @@ <%= form.hidden_field :x, :value => 0 %> <%= form.hidden_field :y, :value => 0 %> <%= form.hidden_field :grabItem, :value => "null" %> + <%= form.hidden_field :addSynapse, :value => false %> + <%= form.hidden_field :item1id, :value => 0 %> + <%= form.hidden_field :item2id, :value => 0 %> <% end %> diff --git a/app/views/items/create.js.erb b/app/views/items/create.js.erb index 132788a7..3200c3f1 100644 --- a/app/views/items/create.js.erb +++ b/app/views/items/create.js.erb @@ -33,7 +33,7 @@ if(viewMode == "graph") { temp.setData('mappingid', '<%= @mapping.id %>'); temp.setPos(new $jit.Complex(x, y), 'current'); temp.setPos(new $jit.Complex(x, y), 'start'); - temp.setPos(new $jit.Complex(x, y), 'end'); + temp.setPos(new $jit.Complex(x, y), 'end');s } Mconsole.fx.plotNode(temp, Mconsole.canvas); diff --git a/app/views/synapses/_new.html.erb b/app/views/synapses/_new.html.erb index 27cd1d6d..2abf3434 100644 --- a/app/views/synapses/_new.html.erb +++ b/app/views/synapses/_new.html.erb @@ -1,21 +1,8 @@
<%= form_for Synapse.new, url: user_synapses_url(user), remote: true do |form| %> -

Add Synapse Between Topics

- <% if Item.visibleToUser(user, nil).count > 0 %> - - <%= select_tag :node1_id, options_from_collection_for_select(Item.order("name ASC").visibleToUser(user, nil), "id", "name") %> - <% end %> - - <%= form.select :category, options_for_select(['none', 'both', 'from-to']) %> - - <%= form.text_field :desc, class: "description" %> - <% if Item.visibleToUser(user, nil).count > 0 %> - - <%= select_tag :node2_id, options_from_collection_for_select(Item.order("name ASC").visibleToUser(user, nil), "id", "name") %> - <% end %> - - <%= form.select(:permission, options_for_select(['commons', 'public', 'private'])) %> - <%= form.submit "Add Synapse", class: "add" %> + <%= form.autocomplete_field :desc, autocomplete_synapse_desc_synapses_path, :placeholder => "Describe the connection..." %> + <%= form.hidden_field :item1id, :value => 0 %> + <%= form.hidden_field :item2id, :value => 0 %> <% end %>
\ No newline at end of file diff --git a/app/views/synapses/create.js.erb b/app/views/synapses/create.js.erb index f4f15e8a..2fc0ec8d 100644 --- a/app/views/synapses/create.js.erb +++ b/app/views/synapses/create.js.erb @@ -1,60 +1,13 @@ $('#new_synapse').fadeOut('fast'); $('#new_synapse')[0].reset(); -// if there's a map, add the synapse to that -map1 = document.getElementById('container'); - -if (map1 != null) { +if (viewMode == "graph") { - var newnode, temp1, temp2, temp; + var temp1, temp2, temp; if ( Mconsole != null) { temp1 = Mconsole.graph.getNode(<%= @synapse.item1.id %>); - if (temp1 == null) { - newnode = <%= @synapse.item1.self_as_json.html_safe %>; - Mconsole.graph.addNode(newnode); - temp = Mconsole.graph.getNode('<%= @synapse.item1.id %>'); - temp.setData('dim', 1, 'start'); - temp.setData('dim', 40, 'end'); - if (gType == "arranged" || gType == "chaotic") { - temp.setData('xloc',0); - temp.setData('yloc',0); - temp.setData('mappingid', '<%= @mapping1.id %>'); - temp.setPos(new $jit.Complex(0, 0), 'current'); - temp.setPos(new $jit.Complex(0, 0), 'start'); - temp.setPos(new $jit.Complex(0, 0), 'end'); - } - else if (gType == "centered") { - temp.setPos(new $jit.Polar(5.54, 347.6), 'current'); - temp.setPos(new $jit.Polar(5.54, 347.6), 'start'); - temp.setPos(new $jit.Polar(5.54, 347.6), 'end'); - } - Mconsole.fx.plotNode(temp, Mconsole.canvas); - temp1 = Mconsole.graph.getNode(<%= @synapse.item1.id %>); - } temp2 = Mconsole.graph.getNode(<%= @synapse.item2.id %>); - if (temp2 == null) { - newnode = <%= @synapse.item2.self_as_json.html_safe %>; - Mconsole.graph.addNode(newnode); - temp = Mconsole.graph.getNode('<%= @synapse.item2.id %>'); - temp.setData('dim', 1, 'start'); - temp.setData('dim', 40, 'end'); - if (gType == "arranged" || gType == "chaotic") { - temp.setData('xloc',0); - temp.setData('yloc',0); - temp.setData('mappingid', '<%= @mapping2.id %>'); - temp.setPos(new $jit.Complex(0, 0), 'current'); - temp.setPos(new $jit.Complex(0, 0), 'start'); - temp.setPos(new $jit.Complex(0, 0), 'end'); - } - else if (gType == "centered") { - temp.setPos(new $jit.Polar(5.54, 347.6), 'current'); - temp.setPos(new $jit.Polar(5.54, 347.6), 'start'); - temp.setPos(new $jit.Polar(5.54, 347.6), 'end'); - } - Mconsole.fx.plotNode(temp, Mconsole.canvas); - temp2 = Mconsole.graph.getNode(<%= @synapse.item2.id %>); - } Mconsole.graph.addAdjacence(temp1, temp2, {}); temp = Mconsole.graph.getAdjacence(temp1.id, temp2.id); temp.setDataset('start', { diff --git a/config/routes.rb b/config/routes.rb index d7fffc00..b77286be 100644 --- a/config/routes.rb +++ b/config/routes.rb @@ -15,6 +15,10 @@ ISSAD::Application.routes.draw do get :autocomplete_item_name, :on => :collection end + resources :synapses do + get :autocomplete_synapse_desc, :on => :collection + end + resources :maps do get :autocomplete_map_name, :on => :collection end