Adornments

Walter,

2 questions :

  1. By default, when you select a selectable and resizable part - both adornments are displayed. Is it possible to configure it so that the first click “selects” and then a subsequent click on the same part then activates the “resize”? ie. first click on a part activates the “select” and the second click activates the “resize”.

  2. I’ve create my own Layout and ResizeTool. The layout is essentially a GridLayout. When I drag parts over a Group+MyLayout - I would like to provide feedback that shows where the insertion point will be within the GridLayout. I can calculate the insertion point, but what I can’t seem to get working is the ability to display an Adornment (at least I think I need an adornment) - to indicate the position within the layout that the items will be dropped.

Can you please help?

OK, here’s a solution for your first question.

First we need to modify the ResizingTool so that it doesn’t display its resize Adornment whenever a Node is selected, but only when it is both selected and some flag has been set on it to indicate that the user has clicked on it after being selected. Let’s call this boolean property “isMultiClicked”.

function CustomResizingTool() { go.ResizingTool.call(this); } go.Diagram.inherit(CustomResizingTool, go.ResizingTool); CustomResizingTool.prototype.updateAdornments = function(part) { if (part === null || part instanceof Link) return; // can't resize links if (part.isMultiClicked) { go.ResizingTool.prototype.updateAdornments.call(this, part); } else { part.removeAdornment(this.name); } };
Second we need to change the click behavior so that when a click happens on a Node and that Node.isSelected, it sets the “isMultiClicked” property to true.

function CustomClickSelectingTool() { go.ClickSelectingTool.call(this); } go.Diagram.inherit(CustomClickSelectingTool, go.ClickSelectingTool); CustomClickSelectingTool.prototype.doMouseUp = function() { if (this.isActive) { var diagram = this.diagram; var e = diagram.lastInput; var node = this.diagram.findPartAt(e.documentPoint, true); if (node instanceof Node && node.isSelected) { node.isMultiClicked = true; node.updateAdornments(); } } go.ClickSelectingTool.prototype.doMouseUp.call(this); };
So now there is code that only shows the resize Adornment when Node.isMultiClicked is true, and there is code to set isMultiClicked to true.

But we also need to set isMultiClicked to false sometime. You didn’t say when, so I will assume when the Node is no longer selected. The easiest way to do this is to implement a Part.selectionChanged function:

myDiagram.nodeTemplate = $(go.Node, go.Panel.Auto, { selectionChanged: function(n) { n.isMultiClicked = false; } }, . . .
Finally we need to install the custom tools, replacing the standard ones:

myDiagram.toolManager.resizingTool = new CustomResizingTool(); myDiagram.toolManager.clickSelectingTool = new CustomClickSelectingTool();

Tools are a very flexible and powerful mechanism, yet they are fairly easy to implement.
(But I suppose customizing existing tools does require learning more about how they work.)I hope this demonstration of tool customization has the behavior that you want.

For your second question, here is a modification of an as-yet-unpublished sample that demonstrates adding nodes to groups and membership validation. To demonstrate that a drop could succeed in a group, the code had originally changed the fill of the group’s shape. I have changed that to add an Adornment that is centered in the group.

[code]<!doctype html>

  
[/code]

Perfect. Thank you.