summaryrefslogtreecommitdiff
path: root/editor/mxDefaultToolbar.js
diff options
context:
space:
mode:
authoradhitya2016-04-12 07:02:39 +0000
committeradhitya2016-04-12 07:02:39 +0000
commitdd83478e3fcaac98de690aa59e6288ad41a1c351 (patch)
tree38653bdf0ae95053f66777c4ac3fe5be5d8fbd33 /editor/mxDefaultToolbar.js
parent92f3207b50a1caca07df5c5b238212af3358905b (diff)
downloadxcos-on-web-dd83478e3fcaac98de690aa59e6288ad41a1c351.tar.gz
xcos-on-web-dd83478e3fcaac98de690aa59e6288ad41a1c351.tar.bz2
xcos-on-web-dd83478e3fcaac98de690aa59e6288ad41a1c351.zip
Keyboard shortcuts work properly
Diffstat (limited to 'editor/mxDefaultToolbar.js')
-rw-r--r--editor/mxDefaultToolbar.js567
1 files changed, 567 insertions, 0 deletions
diff --git a/editor/mxDefaultToolbar.js b/editor/mxDefaultToolbar.js
new file mode 100644
index 0000000..3f8f901
--- /dev/null
+++ b/editor/mxDefaultToolbar.js
@@ -0,0 +1,567 @@
+/**
+ * $Id: mxDefaultToolbar.js,v 1.67 2012-04-11 07:00:52 gaudenz Exp $
+ * Copyright (c) 2006-2010, JGraph Ltd
+ */
+/**
+ * Class: mxDefaultToolbar
+ *
+ * Toolbar for the editor. This modifies the state of the graph
+ * or inserts new cells upon mouse clicks.
+ *
+ * Example:
+ *
+ * Create a toolbar with a button to copy the selection into the clipboard,
+ * and a combo box with one action to paste the selection from the clipboard
+ * into the graph.
+ *
+ * (code)
+ * var toolbar = new mxDefaultToolbar(container, editor);
+ * toolbar.addItem('Copy', null, 'copy');
+ *
+ * var combo = toolbar.addActionCombo('More actions...');
+ * toolbar.addActionOption(combo, 'Paste', 'paste');
+ * (end)
+ *
+ * Codec:
+ *
+ * This class uses the <mxDefaultToolbarCodec> to read configuration
+ * data into an existing instance. See <mxDefaultToolbarCodec> for a
+ * description of the configuration format.
+ *
+ * Constructor: mxDefaultToolbar
+ *
+ * Constructs a new toolbar for the given container and editor. The
+ * container and editor may be null if a prototypical instance for a
+ * <mxDefaultKeyHandlerCodec> is created.
+ *
+ * Parameters:
+ *
+ * container - DOM node that contains the toolbar.
+ * editor - Reference to the enclosing <mxEditor>.
+ */
+function mxDefaultToolbar(container, editor)
+{
+ this.editor = editor;
+
+ if (container != null &&
+ editor != null)
+ {
+ this.init(container);
+ }
+};
+
+/**
+ * Variable: editor
+ *
+ * Reference to the enclosing <mxEditor>.
+ */
+mxDefaultToolbar.prototype.editor = null;
+
+/**
+ * Variable: toolbar
+ *
+ * Holds the internal <mxToolbar>.
+ */
+mxDefaultToolbar.prototype.toolbar = null;
+
+/**
+ * Variable: resetHandler
+ *
+ * Reference to the function used to reset the <toolbar>.
+ */
+mxDefaultToolbar.prototype.resetHandler = null;
+
+/**
+ * Variable: spacing
+ *
+ * Defines the spacing between existing and new vertices in
+ * gridSize units when a new vertex is dropped on an existing
+ * cell. Default is 4 (40 pixels).
+ */
+mxDefaultToolbar.prototype.spacing = 4;
+
+/**
+ * Variable: connectOnDrop
+ *
+ * Specifies if elements should be connected if new cells are dropped onto
+ * connectable elements. Default is false.
+ */
+mxDefaultToolbar.prototype.connectOnDrop = false;
+
+/**
+ * Variable: init
+ *
+ * Constructs the <toolbar> for the given container and installs a listener
+ * that updates the <mxEditor.insertFunction> on <editor> if an item is
+ * selected in the toolbar. This assumes that <editor> is not null.
+ *
+ * Parameters:
+ *
+ * container - DOM node that contains the toolbar.
+ */
+mxDefaultToolbar.prototype.init = function(container)
+{
+ if (container != null)
+ {
+ this.toolbar = new mxToolbar(container);
+
+ // Installs the insert function in the editor if an item is
+ // selected in the toolbar
+ this.toolbar.addListener(mxEvent.SELECT,
+ mxUtils.bind(this, function(sender, evt)
+ {
+ var funct = evt.getProperty('function');
+
+ if (funct != null)
+ {
+ this.editor.insertFunction = mxUtils.bind(this, function()
+ {
+ funct.apply(this, arguments);
+ this.toolbar.resetMode();
+ });
+ }
+ else
+ {
+ this.editor.insertFunction = null;
+ }
+ })
+ );
+
+ // Resets the selected tool after a doubleclick or escape keystroke
+ this.resetHandler = mxUtils.bind(this, function()
+ {
+ if (this.toolbar != null)
+ {
+ this.toolbar.resetMode(true);
+ }
+ });
+
+ this.editor.graph.addListener(mxEvent.DOUBLE_CLICK, this.resetHandler);
+ this.editor.addListener(mxEvent.ESCAPE, this.resetHandler);
+ }
+};
+
+/**
+ * Function: addItem
+ *
+ * Adds a new item that executes the given action in <editor>. The title,
+ * icon and pressedIcon are used to display the toolbar item.
+ *
+ * Parameters:
+ *
+ * title - String that represents the title (tooltip) for the item.
+ * icon - URL of the icon to be used for displaying the item.
+ * action - Name of the action to execute when the item is clicked.
+ * pressed - Optional URL of the icon for the pressed state.
+ */
+mxDefaultToolbar.prototype.addItem = function(title, icon, action, pressed)
+{
+ var clickHandler = mxUtils.bind(this, function()
+ {
+ if (action != null && action.length > 0)
+ {
+ this.editor.execute(action);
+ }
+ });
+
+ return this.toolbar.addItem(title, icon, clickHandler, pressed);
+};
+
+/**
+ * Function: addSeparator
+ *
+ * Adds a vertical separator using the optional icon.
+ *
+ * Parameters:
+ *
+ * icon - Optional URL of the icon that represents the vertical separator.
+ * Default is <mxClient.imageBasePath> + '/separator.gif'.
+ */
+mxDefaultToolbar.prototype.addSeparator = function(icon)
+{
+ icon = icon || mxClient.imageBasePath + '/separator.gif';
+ this.toolbar.addSeparator(icon);
+};
+
+/**
+ * Function: addCombo
+ *
+ * Helper method to invoke <mxToolbar.addCombo> on <toolbar> and return the
+ * resulting DOM node.
+ */
+mxDefaultToolbar.prototype.addCombo = function()
+{
+ return this.toolbar.addCombo();
+};
+
+/**
+ * Function: addActionCombo
+ *
+ * Helper method to invoke <mxToolbar.addActionCombo> on <toolbar> using
+ * the given title and return the resulting DOM node.
+ *
+ * Parameters:
+ *
+ * title - String that represents the title of the combo.
+ */
+mxDefaultToolbar.prototype.addActionCombo = function(title)
+{
+ return this.toolbar.addActionCombo(title);
+};
+
+/**
+ * Function: addActionOption
+ *
+ * Binds the given action to a option with the specified label in the
+ * given combo. Combo is an object returned from an earlier call to
+ * <addCombo> or <addActionCombo>.
+ *
+ * Parameters:
+ *
+ * combo - DOM node that represents the combo box.
+ * title - String that represents the title of the combo.
+ * action - Name of the action to execute in <editor>.
+ */
+mxDefaultToolbar.prototype.addActionOption = function(combo, title, action)
+{
+ var clickHandler = mxUtils.bind(this, function()
+ {
+ this.editor.execute(action);
+ });
+
+ this.addOption(combo, title, clickHandler);
+};
+
+/**
+ * Function: addOption
+ *
+ * Helper method to invoke <mxToolbar.addOption> on <toolbar> and return
+ * the resulting DOM node that represents the option.
+ *
+ * Parameters:
+ *
+ * combo - DOM node that represents the combo box.
+ * title - String that represents the title of the combo.
+ * value - Object that represents the value of the option.
+ */
+mxDefaultToolbar.prototype.addOption = function(combo, title, value)
+{
+ return this.toolbar.addOption(combo, title, value);
+};
+
+/**
+ * Function: addMode
+ *
+ * Creates an item for selecting the given mode in the <editor>'s graph.
+ * Supported modenames are select, connect and pan.
+ *
+ * Parameters:
+ *
+ * title - String that represents the title of the item.
+ * icon - URL of the icon that represents the item.
+ * mode - String that represents the mode name to be used in
+ * <mxEditor.setMode>.
+ * pressed - Optional URL of the icon that represents the pressed state.
+ * funct - Optional JavaScript function that takes the <mxEditor> as the
+ * first and only argument that is executed after the mode has been
+ * selected.
+ */
+mxDefaultToolbar.prototype.addMode = function(title, icon, mode, pressed, funct)
+{
+ var clickHandler = mxUtils.bind(this, function()
+ {
+ this.editor.setMode(mode);
+
+ if (funct != null)
+ {
+ funct(this.editor);
+ }
+ });
+
+ return this.toolbar.addSwitchMode(title, icon, clickHandler, pressed);
+};
+
+/**
+ * Function: addPrototype
+ *
+ * Creates an item for inserting a clone of the specified prototype cell into
+ * the <editor>'s graph. The ptype may either be a cell or a function that
+ * returns a cell.
+ *
+ * Parameters:
+ *
+ * title - String that represents the title of the item.
+ * icon - URL of the icon that represents the item.
+ * ptype - Function or object that represents the prototype cell. If ptype
+ * is a function then it is invoked with no arguments to create new
+ * instances.
+ * pressed - Optional URL of the icon that represents the pressed state.
+ * insert - Optional JavaScript function that handles an insert of the new
+ * cell. This function takes the <mxEditor>, new cell to be inserted, mouse
+ * event and optional <mxCell> under the mouse pointer as arguments.
+ * toggle - Optional boolean that specifies if the item can be toggled.
+ * Default is true.
+ */
+mxDefaultToolbar.prototype.addPrototype = function(title, icon, ptype, pressed, insert, toggle)
+{
+ // Creates a wrapper function that is in charge of constructing
+ // the new cell instance to be inserted into the graph
+ var factory = function()
+ {
+ if (typeof(ptype) == 'function')
+ {
+ return ptype();
+ }
+ else if (ptype != null)
+ {
+ return ptype.clone();
+ }
+
+ return null;
+ };
+
+ // Defines the function for a click event on the graph
+ // after this item has been selected in the toolbar
+ var clickHandler = mxUtils.bind(this, function(evt, cell)
+ {
+ if (typeof(insert) == 'function')
+ {
+ insert(this.editor, factory(), evt, cell);
+ }
+ else
+ {
+ this.drop(factory(), evt, cell);
+ }
+
+ this.toolbar.resetMode();
+ mxEvent.consume(evt);
+ });
+
+ var img = this.toolbar.addMode(title, icon, clickHandler, pressed, null, toggle);
+
+ // Creates a wrapper function that calls the click handler without
+ // the graph argument
+ var dropHandler = function(graph, evt, cell)
+ {
+ clickHandler(evt, cell);
+ };
+
+ this.installDropHandler(img, dropHandler);
+
+ return img;
+};
+
+/**
+ * Function: drop
+ *
+ * Handles a drop from a toolbar item to the graph. The given vertex
+ * represents the new cell to be inserted. This invokes <insert> or
+ * <connect> depending on the given target cell.
+ *
+ * Parameters:
+ *
+ * vertex - <mxCell> to be inserted.
+ * evt - Mouse event that represents the drop.
+ * target - Optional <mxCell> that represents the drop target.
+ */
+mxDefaultToolbar.prototype.drop = function(vertex, evt, target)
+{
+ var graph = this.editor.graph;
+ var model = graph.getModel();
+
+ if (target == null ||
+ model.isEdge(target) ||
+ !this.connectOnDrop ||
+ !graph.isCellConnectable(target))
+ {
+ while (target != null &&
+ !graph.isValidDropTarget(target, [vertex], evt))
+ {
+ target = model.getParent(target);
+ }
+
+ this.insert(vertex, evt, target);
+ }
+ else
+ {
+ this.connect(vertex, evt, target);
+ }
+};
+
+/**
+ * Function: insert
+ *
+ * Handles a drop by inserting the given vertex into the given parent cell
+ * or the default parent if no parent is specified.
+ *
+ * Parameters:
+ *
+ * vertex - <mxCell> to be inserted.
+ * evt - Mouse event that represents the drop.
+ * parent - Optional <mxCell> that represents the parent.
+ */
+mxDefaultToolbar.prototype.insert = function(vertex, evt, target)
+{
+ var graph = this.editor.graph;
+
+ if (graph.canImportCell(vertex))
+ {
+ var x = mxEvent.getClientX(evt);
+ var y = mxEvent.getClientY(evt);
+ var pt = mxUtils.convertPoint(graph.container, x, y);
+
+ // Splits the target edge or inserts into target group
+ if (graph.isSplitEnabled() &&
+ graph.isSplitTarget(target, [vertex], evt))
+ {
+ return graph.splitEdge(target, [vertex], null, pt.x, pt.y);
+ }
+ else
+ {
+ return this.editor.addVertex(target, vertex, pt.x, pt.y);
+ }
+ }
+
+ return null;
+};
+
+/**
+ * Function: connect
+ *
+ * Handles a drop by connecting the given vertex to the given source cell.
+ *
+ * vertex - <mxCell> to be inserted.
+ * evt - Mouse event that represents the drop.
+ * source - Optional <mxCell> that represents the source terminal.
+ */
+mxDefaultToolbar.prototype.connect = function(vertex, evt, source)
+{
+ var graph = this.editor.graph;
+ var model = graph.getModel();
+
+ if (source != null &&
+ graph.isCellConnectable(vertex) &&
+ graph.isEdgeValid(null, source, vertex))
+ {
+ var edge = null;
+
+ model.beginUpdate();
+ try
+ {
+ var geo = model.getGeometry(source);
+ var g = model.getGeometry(vertex).clone();
+
+ // Moves the vertex away from the drop target that will
+ // be used as the source for the new connection
+ g.x = geo.x + (geo.width - g.width) / 2;
+ g.y = geo.y + (geo.height - g.height) / 2;
+
+ var step = this.spacing * graph.gridSize;
+ var dist = model.getDirectedEdgeCount(source, true) * 20;
+
+ if (this.editor.horizontalFlow)
+ {
+ g.x += (g.width + geo.width) / 2 + step + dist;
+ }
+ else
+ {
+ g.y += (g.height + geo.height) / 2 + step + dist;
+ }
+
+ vertex.setGeometry(g);
+
+ // Fires two add-events with the code below - should be fixed
+ // to only fire one add event for both inserts
+ var parent = model.getParent(source);
+ graph.addCell(vertex, parent);
+ graph.constrainChild(vertex);
+
+ // Creates the edge using the editor instance and calls
+ // the second function that fires an add event
+ edge = this.editor.createEdge(source, vertex);
+
+ if (model.getGeometry(edge) == null)
+ {
+ var edgeGeometry = new mxGeometry();
+ edgeGeometry.relative = true;
+
+ model.setGeometry(edge, edgeGeometry);
+ }
+
+ graph.addEdge(edge, parent, source, vertex);
+ }
+ finally
+ {
+ model.endUpdate();
+ }
+
+ graph.setSelectionCells([vertex, edge]);
+ graph.scrollCellToVisible(vertex);
+ }
+};
+
+/**
+ * Function: installDropHandler
+ *
+ * Makes the given img draggable using the given function for handling a
+ * drop event.
+ *
+ * Parameters:
+ *
+ * img - DOM node that represents the image.
+ * dropHandler - Function that handles a drop of the image.
+ */
+mxDefaultToolbar.prototype.installDropHandler = function (img, dropHandler)
+{
+ var sprite = document.createElement('img');
+ sprite.setAttribute('src', img.getAttribute('src'));
+
+ // Handles delayed loading of the images
+ var loader = mxUtils.bind(this, function(evt)
+ {
+ // Preview uses the image node with double size. Later this can be
+ // changed to use a separate preview and guides, but for this the
+ // dropHandler must use the additional x- and y-arguments and the
+ // dragsource which makeDraggable returns much be configured to
+ // use guides via mxDragSource.isGuidesEnabled.
+ sprite.style.width = (2 * img.offsetWidth) + 'px';
+ sprite.style.height = (2 * img.offsetHeight) + 'px';
+
+ mxUtils.makeDraggable(img, this.editor.graph, dropHandler,
+ sprite);
+ mxEvent.removeListener(sprite, 'load', loader);
+ });
+
+ if (mxClient.IS_IE)
+ {
+ loader();
+ }
+ else
+ {
+ mxEvent.addListener(sprite, 'load', loader);
+ }
+};
+
+/**
+ * Function: destroy
+ *
+ * Destroys the <toolbar> associated with this object and removes all
+ * installed listeners. This does normally not need to be called, the
+ * <toolbar> is destroyed automatically when the window unloads (in IE) by
+ * <mxEditor>.
+ */
+mxDefaultToolbar.prototype.destroy = function ()
+{
+ if (this.resetHandler != null)
+ {
+ this.editor.graph.removeListener('dblclick', this.resetHandler);
+ this.editor.removeListener('escape', this.resetHandler);
+ this.resetHandler = null;
+ }
+
+ if (this.toolbar != null)
+ {
+ this.toolbar.destroy();
+ this.toolbar = null;
+ }
+};