From 87f65775e00404063104486954eefe2b649e93f3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fr=C3=A9d=C3=A9ric=20van=20der=20Essen?= Date: Fri, 24 Feb 2012 10:53:10 +0100 Subject: [PATCH] Correct viewport integration, cosmetic changes, node loops bzr revid: fva@openerp.com-20120224095310-r3bdlx09n5eaxrvk --- addons/web/static/src/js/view_form.js | 4 + addons/web_diagram/__openerp__.py | 3 +- .../static/src/css/base_diagram.css | 46 +++++----- addons/web_diagram/static/src/js/diagram.js | 25 ++++-- addons/web_diagram/static/src/js/graph.js | 84 ++++++++++++++++--- .../static/src/js/jquery.mousewheel.js | 84 +++++++++++++++++++ .../web_diagram/static/src/js/vec2js/vec2.js | 2 - .../static/src/xml/base_diagram.xml | 4 +- 8 files changed, 205 insertions(+), 47 deletions(-) create mode 100644 addons/web_diagram/static/src/js/jquery.mousewheel.js diff --git a/addons/web/static/src/js/view_form.js b/addons/web/static/src/js/view_form.js index 6b7acd5a244..d98c597c8a6 100644 --- a/addons/web/static/src/js/view_form.js +++ b/addons/web/static/src/js/view_form.js @@ -2835,6 +2835,10 @@ openerp.web.form.SelectCreatePopup = openerp.web.OldWidget.extend(/** @lends ope this.new_object(); } }, + stop: function () { + this.$element.dialog('close'); + this._super(); + }, setup_search_view: function(search_defaults) { var self = this; if (this.searchview) { diff --git a/addons/web_diagram/__openerp__.py b/addons/web_diagram/__openerp__.py index 0aae81eb946..22f061c6475 100644 --- a/addons/web_diagram/__openerp__.py +++ b/addons/web_diagram/__openerp__.py @@ -9,9 +9,10 @@ 'static/lib/js/dracula_graffle.js', 'static/lib/js/dracula_graph.js', 'static/lib/js/dracula_algorithms.js', + 'static/src/js/jquery.mousewheel.js', 'static/src/js/vec2js/vec2.js', 'static/src/js/graph.js', - 'static/src/js/diagram.js' + 'static/src/js/diagram.js', ], 'css' : [ "static/src/css/base_diagram.css", diff --git a/addons/web_diagram/static/src/css/base_diagram.css b/addons/web_diagram/static/src/css/base_diagram.css index 6be8d4873d2..9604823d040 100644 --- a/addons/web_diagram/static/src/css/base_diagram.css +++ b/addons/web_diagram/static/src/css/base_diagram.css @@ -1,35 +1,33 @@ .openerp .oe_diagram_pager { - text-align: right; + float:right; + /*text-align: right;*/ white-space: nowrap; } .openerp .oe_diagram_buttons { float: left; } +.openerp .clear{ + clear:both; +} +.openerp .diagram{ + margin:0; + padding:0; + position:absolute; + top:178px; + bottom:26px; + left:201px; + right:0; + background-color:white; + border-style:none; + border-top-style:solid; + border-top-width:1px; + border-top-color:#DCDCDC; + overflow:hidden; -/*.openerp .dhx_canvas_text { - padding:30px 0 0 10px; - -webkit-transform: rotate(60deg); - -moz-transform: rotate(60deg); - -o-transform: rotate(60deg); - -ms-transform: rotate(60deg); - transform: rotate(60deg); +} +#widget-19_view_diagram { + position:relative; } -.openerp .dhx_canvas_text.dhx_axis_item_y, .openerp .dhx_canvas_text.dhx_axis_title_x { - padding: 0px; - -webkit-transform: rotate(0deg); - -moz-transform: rotate(0deg); - -o-transform: rotate(0deg); - -ms-transform: rotate(0deg); - transform: rotate(0deg); -} -.openerp .dhx_canvas_text.dhx_axis_title_y { - padding: 0; - -webkit-transform: rotate(270deg); - -moz-transform: rotate(270deg); - -o-transform: rotate(270deg); - -ms-transform: rotate(270deg); - transform: rotate(270deg); -} */ diff --git a/addons/web_diagram/static/src/js/diagram.js b/addons/web_diagram/static/src/js/diagram.js index c53a802e3af..eee6f23afe2 100644 --- a/addons/web_diagram/static/src/js/diagram.js +++ b/addons/web_diagram/static/src/js/diagram.js @@ -123,25 +123,27 @@ openerp.web.DiagramView = openerp.web.View.extend({ var style = { "edge" : "#A0A0A0", "edge_label" : "#555", "text" : "#333", - "outline" : "#000", + "outline" : "#333", "selected" : "#0097BE", "gray" : "#DCDCDC", "white" : "#FFF", - "node_size_x" : 90, - "node_size_y" : 60, + "node_size_x" : 100, + "node_size_y" : 70, "edge_spacing" : 100, "edge_label_font_size" : 10 }; $('#dia-canvas *').remove(); // remove previous diagram - var r = new Raphael(document.getElementById("dia-canvas"), '100%','500px'); + var r = new Raphael(document.getElementById("dia-canvas"), '100%','100%'); + $(r.node).css("border","none"); + $(r.node).css("padding",0); var graph = new CuteGraph(r,style); _.each(res_nodes, function(node) { var n = new CuteNode( graph, - node.x, - node.y, - CuteGraph.wordwrap(node.name, 17), + node.x + 50, + node.y + 50, + CuteGraph.wordwrap(node.name, 16), node.shape === 'rectangle' ? 'rect' : 'circle', node.color === 'white' ? style.white : style.gray ); n.id = node.id; @@ -168,7 +170,9 @@ openerp.web.DiagramView = openerp.web.View.extend({ console.log("creating edge from:",node_start," to:",node_end); self.add_edit_node(null, self.connector, { act_from: node_start.id, - act_to: node_end.id + act_to: node_end.id, + activity_from_id: node_start.id, + activity_to_id: node_end.id, }); return {label:""}; // TODO destroy edge on cancel } @@ -200,6 +204,10 @@ openerp.web.DiagramView = openerp.web.View.extend({ pop.on_select_elements.add_last(function(element_ids) { self.dataset.read_index(_.keys(self.fields_view.fields)).pipe(self.on_diagram_loaded); }); + pop.$element.bind("dialogbeforeclose",function(){ + console.log("HAHHAAH"); + console.log(self.connectors.attrs); + }); } else { pop = new openerp.web.form.FormOpenPopup(this); pop.show_element( @@ -213,6 +221,7 @@ openerp.web.DiagramView = openerp.web.View.extend({ pop.on_write.add(function() { self.dataset.read_index(_.keys(self.fields_view.fields)).pipe(self.on_diagram_loaded); }); + } var form_controller = pop.view_form; diff --git a/addons/web_diagram/static/src/js/graph.js b/addons/web_diagram/static/src/js/graph.js index 1ff6e1466c1..1bae1cd3b9e 100644 --- a/addons/web_diagram/static/src/js/graph.js +++ b/addons/web_diagram/static/src/js/graph.js @@ -16,6 +16,7 @@ var visible = false; var conn_circle = graph.r.circle(node.get_pos().x + pos_x, node.get_pos().y + pos_y,4); conn_circle.attr({'opacity':0, 'fill':graph.style.outline,'stroke':'none'}); + conn_circle.transform(graph.get_transform()); var self = this; this.update_pos = function(){ @@ -59,7 +60,7 @@ if(!visible){ return; } graph.creating_edge = false; self.edge_tmp.remove(); - if(graph.target_node && graph.target_node != node){ + if(graph.target_node){ edge_prop = GraphEdge.creation_callback(node,graph.target_node); if(edge_prop){ new GraphEdge(graph,edge_prop.label, node,graph.target_node); @@ -80,22 +81,65 @@ visible = false; } } - this.show = show; this.hide = hide; } function Graph(r,style){ + var self = this; var nodes = []; // list of all nodes in the graph var edges = []; // list of all edges in the graph var graph = {}; // graph[n1.uid][n2.uid] -> list of all edges from n1 to n2 var links = {} // links[n.uid] -> list of all edges from or to n var uid = 1; // all nodes and edges have an uid used to order their display when they are curved - this.creating_edge = false; // true if we are dragging a new edge onto a node - this.target_node = null; // this holds the target node when creating an edge and hovering a connector - this.r = r; // the raphael instance - this.style = style; // definition of the colors, spacing, fonts, ... used by the elements + self.creating_edge = false; // true if we are dragging a new edge onto a node + self.target_node = null; // this holds the target node when creating an edge and hovering a connector + self.r = r; // the raphael instance + self.style = style; // definition of the colors, spacing, fonts, ... used by the elements + var tr_x = 0, tr_y = 0; // global translation coordinate + var scale = 1; // global scale + + var background = r.rect(0,0,'100%','100%').attr({'fill':'white', 'stroke':'none', 'opacity':0}); + + // return the global transform of the scene + this.get_transform = function(){ + return "T"+tr_x+","+tr_y + } + + // translate every element of the graph except the background. + // elements inserted in the graph after a translate_all() must manually apply transformation + // via get_transform() + var translate_all = function(dx,dy){ + tr_x += dx; + tr_y += dy; + tstr = self.get_transform(); + + r.forEach(function(el){ + if(el != background){ + el.transform(tstr); + } + }); + } + + // Graph translation when background is dragged + var bg_drag_down = function(){ + px = py = 0; + } + var bg_drag_move = function(x,y){ + var dx = x - px; + var dy = y - py; + px = x; + py = y; + translate_all(dx,dy); + } + var bg_drag_up = function(){} + background.drag( bg_drag_move, bg_drag_down, bg_drag_up); + + $(background.node).bind('mousewheel',function(event,delta){ + translate_all(0,delta*20); + }); + //adds a node to the graph and sets its uid. this.add_node = function (n){ @@ -121,6 +165,15 @@ links[n2.uid].push(e); } }; + //removes an edge from the graph + this.remove_edge = function(edge){ + edges = _.without(edges,edge); + var n1 = edge.get_start(); + var n2 = edge.get_end(); + links[n1.uid] = _.without(links[n1.uid],edge); + links[n2.uid] = _.without(links[n2.uid],edge); + graph[n1.uid][n2.uid] = _without(graph[n1.uid][n2.uid],edge); + } //return the list of edges from n1 to n2 this.get_edge_list = function(n1,n2){ var list = []; @@ -212,14 +265,12 @@ // creates a new Graph Node on Raphael document r, centered on [pos_x,pos_y], with label 'label', // and of type 'circle' or 'rect', and of color 'color' - // TODO pass graph in constructor function GraphNode(graph,pos_x, pos_y,label,type,color){ + var self = this; var r = graph.r; var sy = graph.style.node_size_y; var sx = graph.style.node_size_x; var node_fig = null; - //var node_shadow = null; - var self = this; var selected = false; this.update_time = 0; this.connectors = []; @@ -233,9 +284,14 @@ node_fig = r.rect(pos_x-sx/2,pos_y-sy/2,sx,sy); } node_fig.attr({'fill':color, 'stroke':graph.style.outline,'stroke-width':1,'cursor':'pointer'}); + node_fig.transform(graph.get_transform()); + + $(node_fig.node).addClass('foobar'); var node_label = r.text(pos_x,pos_y,label); node_label.attr({'fill':graph.style.text,'cursor':'pointer'}); + node_label.transform(graph.get_transform()); + $(node_label.node).css('text-shadow',"1px 2px 3px rgba(0,0,0,0.3)"); // sets the center position of the node @@ -388,7 +444,7 @@ } // creates a new edge with label 'label' from start to end. start and end must implement get_pos_*, - // if tmp is true, the edge is not added to the graph, used for drag edges. TODO pass graph in constructor, + // if tmp is true, the edge is not added to the graph, used for drag edges. // replace tmp == false by graph == null function GraphEdge(graph,label,start,end,tmp){ var self = this; @@ -470,7 +526,6 @@ edge_path = make_line(); } }else{ // start == end - console.log("loop!"); var rad = graph.style.edge_loop_radius || 100; s = start.get_pos(); e = end.get_pos(); @@ -499,6 +554,10 @@ var edge = r.path(edge_path).attr({'stroke':graph.style.edge, 'stroke-width':2, 'arrow-end':'block-wide-long', 'cursor':'pointer'}).insertBefore(graph.get_node_list()[0].get_fig()); var labelpos = get_label_pos(edge); var edge_label = r.text(labelpos.x, labelpos.y - elfs, label).attr({'fill':graph.style.edge_label, 'cursor':'pointer', 'font-size':elfs}); + + edge.transform(graph.get_transform()); + edge_label.transform(graph.get_transform()); + $(edge_label.node).css('text-shadow',"1px 2px 3px rgba(0,0,0,0.3)"); //since we create an edge we need to recompute the edges that have the same start and end positions as this one @@ -539,6 +598,9 @@ function remove(){ edge.remove(); edge_label.remove(); + if(!tmp){ + graph.remove_edge(self); + } } function double_click(){ diff --git a/addons/web_diagram/static/src/js/jquery.mousewheel.js b/addons/web_diagram/static/src/js/jquery.mousewheel.js new file mode 100644 index 00000000000..38b60951b20 --- /dev/null +++ b/addons/web_diagram/static/src/js/jquery.mousewheel.js @@ -0,0 +1,84 @@ +/*! Copyright (c) 2011 Brandon Aaron (http://brandonaaron.net) + * Licensed under the MIT License (LICENSE.txt). + * + * Thanks to: http://adomas.org/javascript-mouse-wheel/ for some pointers. + * Thanks to: Mathias Bank(http://www.mathias-bank.de) for a scope bug fix. + * Thanks to: Seamus Leahy for adding deltaX and deltaY + * + * Version: 3.0.6 + * + * Requires: 1.2.2+ + */ + +(function($) { + +var types = ['DOMMouseScroll', 'mousewheel']; + +if ($.event.fixHooks) { + for ( var i=types.length; i; ) { + $.event.fixHooks[ types[--i] ] = $.event.mouseHooks; + } +} + +$.event.special.mousewheel = { + setup: function() { + if ( this.addEventListener ) { + for ( var i=types.length; i; ) { + this.addEventListener( types[--i], handler, false ); + } + } else { + this.onmousewheel = handler; + } + }, + + teardown: function() { + if ( this.removeEventListener ) { + for ( var i=types.length; i; ) { + this.removeEventListener( types[--i], handler, false ); + } + } else { + this.onmousewheel = null; + } + } +}; + +$.fn.extend({ + mousewheel: function(fn) { + return fn ? this.bind("mousewheel", fn) : this.trigger("mousewheel"); + }, + + unmousewheel: function(fn) { + return this.unbind("mousewheel", fn); + } +}); + + +function handler(event) { + var orgEvent = event || window.event, args = [].slice.call( arguments, 1 ), delta = 0, returnValue = true, deltaX = 0, deltaY = 0; + event = $.event.fix(orgEvent); + event.type = "mousewheel"; + + // Old school scrollwheel delta + if ( orgEvent.wheelDelta ) { delta = orgEvent.wheelDelta/120; } + if ( orgEvent.detail ) { delta = -orgEvent.detail/3; } + + // New school multidimensional scroll (touchpads) deltas + deltaY = delta; + + // Gecko + if ( orgEvent.axis !== undefined && orgEvent.axis === orgEvent.HORIZONTAL_AXIS ) { + deltaY = 0; + deltaX = -1*delta; + } + + // Webkit + if ( orgEvent.wheelDeltaY !== undefined ) { deltaY = orgEvent.wheelDeltaY/120; } + if ( orgEvent.wheelDeltaX !== undefined ) { deltaX = -1*orgEvent.wheelDeltaX/120; } + + // Add event and delta to the front of the arguments + args.unshift(event, delta, deltaX, deltaY); + + return ($.event.dispatch || $.event.handle).apply(this, args); +} + +})(jQuery); diff --git a/addons/web_diagram/static/src/js/vec2js/vec2.js b/addons/web_diagram/static/src/js/vec2js/vec2.js index c37b9674425..73b13d04125 100644 --- a/addons/web_diagram/static/src/js/vec2js/vec2.js +++ b/addons/web_diagram/static/src/js/vec2js/vec2.js @@ -1,6 +1,4 @@ - - (function(window){ // A Javascript 2D vector library diff --git a/addons/web_diagram/static/src/xml/base_diagram.xml b/addons/web_diagram/static/src/xml/base_diagram.xml index 6d0e36e2f17..e414cdcb13f 100644 --- a/addons/web_diagram/static/src/xml/base_diagram.xml +++ b/addons/web_diagram/static/src/xml/base_diagram.xml @@ -9,7 +9,9 @@ 0 / 0 +
-
+ +