From ba515619ba66f6cddb64d18f8370c06d2fc03758 Mon Sep 17 00:00:00 2001 From: Florian Hoelzl <hoelzl@fortiss.org> Date: Tue, 19 Jul 2011 10:02:04 +0000 Subject: [PATCH] refactored edit policies and commands, some clean up --- .../ChangeBoundsRequestCommandBase.java | 42 +--- .../base/ui/command/MoveConnectorCommand.java | 73 +++++++ .../MoveWithinDiagramCommand.java} | 46 ++++- .../ConnectorConnectionCompositorBase.java | 6 +- .../ui/editpart/ConnectorEditPartBase.java | 2 +- .../base/ui/editpart/DiagramEditPartBase.java | 48 ++++- .../base/ui/editpart/ElementEditPartBase.java | 34 ++- ...rt.java => FreeConnectorEditPartBase.java} | 29 ++- ....java => StickyConnectorEditPartBase.java} | 40 +++- .../policy/ConnectionBendpointEditPolicy.java | 97 +++++++++ .../ConnectionGraphicalNodeEditPolicy.java | 18 +- .../ConstrainedNonResizableEditPolicy.java | 112 ++++++++++ .../policy/DiagramLayoutEditPolicy.java | 70 +++++++ .../policy/ElementLayoutEditPolicy.java | 71 +++++++ .../policy/FreeResizableEditPolicy.java | 67 ++++++ .../editpart/policy/LayoutEditPolicyBase.java | 24 +-- .../ui/editpart/policy/RemoveEditPolicy.java | 2 +- .../ui/layout/util/EllipseLayoutUtils.java | 161 +++++++++++++++ .../base/ui/layout/util/LayoutDataUtils.java | 111 +++++----- ...utUtils.java => RectangleLayoutUtils.java} | 193 ++++-------------- .../base/ui/layout/util/SnapToGridUtils.java | 69 +++++++ 21 files changed, 984 insertions(+), 331 deletions(-) create mode 100644 org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/command/MoveConnectorCommand.java rename org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/{editpart/IStickyConnectorEditPart.java => command/MoveWithinDiagramCommand.java} (51%) rename org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/{SnapToGridSupport.java => FreeConnectorEditPartBase.java} (65%) rename org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/{IFreeConnectorEditPart.java => StickyConnectorEditPartBase.java} (50%) create mode 100644 org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/ConnectionBendpointEditPolicy.java create mode 100644 org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/ConstrainedNonResizableEditPolicy.java create mode 100644 org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/DiagramLayoutEditPolicy.java create mode 100644 org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/ElementLayoutEditPolicy.java create mode 100644 org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/FreeResizableEditPolicy.java create mode 100644 org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/layout/util/EllipseLayoutUtils.java rename org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/layout/util/{EditPartLayoutUtils.java => RectangleLayoutUtils.java} (54%) create mode 100644 org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/layout/util/SnapToGridUtils.java diff --git a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/command/ChangeBoundsRequestCommandBase.java b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/command/ChangeBoundsRequestCommandBase.java index bdb134007..49cee17b5 100644 --- a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/command/ChangeBoundsRequestCommandBase.java +++ b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/command/ChangeBoundsRequestCommandBase.java @@ -22,9 +22,7 @@ import java.util.List; import org.eclipse.gef.EditPart; import org.eclipse.gef.commands.Command; import org.eclipse.gef.requests.ChangeBoundsRequest; -import org.fortiss.tooling.base.model.layout.Dimension; import org.fortiss.tooling.base.model.layout.ILayoutedModelElement; -import org.fortiss.tooling.base.model.layout.Point; import org.fortiss.tooling.base.ui.editpart.ConnectorEditPartBase; import org.fortiss.tooling.base.ui.editpart.LayoutedConnectionEditPartBase; import org.fortiss.tooling.base.ui.layout.util.LayoutDataUtils; @@ -36,7 +34,7 @@ import org.fortiss.tooling.base.ui.layout.util.LayoutDataUtils; * @author hoelzl * @author $Author$ * @version $Rev$ - * @ConQAT.Rating RED Hash: + * @ConQAT.Rating YELLOW Hash: 97E72763FD3655AAF658FF43EAA8C3CF */ public abstract class ChangeBoundsRequestCommandBase extends Command { @@ -61,49 +59,21 @@ public abstract class ChangeBoundsRequestCommandBase extends Command { } /** Moves the given node using info from {@link #getRequest()}. */ - // TODO: move this computation to LayoutDataUtil protected void moveNode(ILayoutedModelElement layouted) { - Point p = LayoutDataUtils.getNodePosition(layouted); int dx = getRequest().getMoveDelta().x; int dy = getRequest().getMoveDelta().y; - LayoutDataUtils.setNodePosition(layouted, - LayoutDataUtils.translate(p, dx, dy)); + LayoutDataUtils.moveNode(layouted, dx, dy); } - /** - * Moves and resizes the given node using info from {@link #getRequest()}. - * The final size is returned. - */ - // TODO: move this computation to LayoutDataUtil - protected Dimension moveAndResizeNode(ILayoutedModelElement layouted, + /** Moves and resizes the given node using info from {@link #getRequest()}. */ + protected void moveAndResizeNode(ILayoutedModelElement layouted, int minWidth, int minHeight) { int dx = getRequest().getMoveDelta().x; int dy = getRequest().getMoveDelta().y; - Point pos = LayoutDataUtils.translate( - LayoutDataUtils.getNodePosition(layouted), dx, dy); - int dw = getRequest().getSizeDelta().width; int dh = getRequest().getSizeDelta().height; - Dimension dim = LayoutDataUtils.expand( - LayoutDataUtils.getNodeSize(layouted), dw, dh); - - if (dim.getWidth() < minWidth) { - if (getRequest().getMoveDelta().x > 0) { - pos.setX(pos.getX() - minWidth - dim.getWidth()); - } - dim.setWidth(minWidth); - } - - if (dim.getHeight() < minHeight) { - if (getRequest().getMoveDelta().y > 0) { - pos.setY(pos.getY() - minHeight - dim.getHeight()); - } - dim.setHeight(minHeight); - } - - LayoutDataUtils.setNodePosition(layouted, pos); - LayoutDataUtils.setNodeSize(layouted, dim); - return dim; + LayoutDataUtils.moveAndResizeNode(layouted, dx, dy, dw, dh, minWidth, + minHeight); } /** Move bend points along with a group of selected elements */ diff --git a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/command/MoveConnectorCommand.java b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/command/MoveConnectorCommand.java new file mode 100644 index 000000000..9356ea1e4 --- /dev/null +++ b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/command/MoveConnectorCommand.java @@ -0,0 +1,73 @@ +/*--------------------------------------------------------------------------+ +$Id$ +| | +| Copyright 2011 ForTISS GmbH | +| | +| Licensed under the Apache License, Version 2.0 (the "License"); | +| you may not use this file except in compliance with the License. | +| You may obtain a copy of the License at | +| | +| http://www.apache.org/licenses/LICENSE-2.0 | +| | +| Unless required by applicable law or agreed to in writing, software | +| distributed under the License is distributed on an "AS IS" BASIS, | +| WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | +| See the License for the specific language governing permissions and | +| limitations under the License. | ++--------------------------------------------------------------------------*/ +package org.fortiss.tooling.base.ui.command; + +import java.util.List; + +import org.eclipse.gef.EditPart; +import org.eclipse.gef.requests.ChangeBoundsRequest; +import org.fortiss.tooling.base.model.layout.ILayoutedModelElement; +import org.fortiss.tooling.base.model.layout.OffsetOrientation; +import org.fortiss.tooling.base.ui.editpart.FreeConnectorEditPartBase; +import org.fortiss.tooling.base.ui.editpart.StickyConnectorEditPartBase; +import org.fortiss.tooling.base.ui.layout.constants.LayoutKeyConstants; +import org.fortiss.tooling.base.ui.layout.util.LayoutDataUtils; + +/** + * A command to move connectors. The operation is performed differently for + * sticky and free connector edit parts. + * + * @author wandinger + * @author hoelzlf + * @author $Author$ + * @version $Rev$ + * @ConQAT.Rating YELLOW Hash: 44F8907016E9D390775ACCF4FC5FA5E8 + */ +public class MoveConnectorCommand extends ChangeBoundsRequestCommandBase { + + /** Constructor. */ + public MoveConnectorCommand(ChangeBoundsRequest request) { + super(request); + } + + /** {@inheritDoc} */ + @SuppressWarnings("unchecked") + @Override + public void execute() { + super.execute(); + for (EditPart editpart : (List<EditPart>) getRequest().getEditParts()) { + performMove(editpart, getRequest()); + } + } + + /** Performs the move of an edit part. */ + protected void performMove(EditPart editpart, ChangeBoundsRequest request) { + if (editpart instanceof StickyConnectorEditPartBase) { + // The orientation was already calculated for the sourceFeedback + OffsetOrientation offsetOrientation = (OffsetOrientation) request + .getExtendedData().get( + LayoutKeyConstants.CONNECTOR_OFFSET_ORIENTATION); + LayoutDataUtils.setConnectorOffsetOrientation( + (ILayoutedModelElement) editpart.getModel(), + offsetOrientation); + + } else if (editpart instanceof FreeConnectorEditPartBase) { + moveNode((ILayoutedModelElement) editpart.getModel()); + } + } +} diff --git a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/IStickyConnectorEditPart.java b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/command/MoveWithinDiagramCommand.java similarity index 51% rename from org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/IStickyConnectorEditPart.java rename to org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/command/MoveWithinDiagramCommand.java index e47aaa6a3..e41d77c5a 100644 --- a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/IStickyConnectorEditPart.java +++ b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/command/MoveWithinDiagramCommand.java @@ -15,22 +15,46 @@ $Id$ | See the License for the specific language governing permissions and | | limitations under the License. | +--------------------------------------------------------------------------*/ -package org.fortiss.tooling.base.ui.editpart; +package org.fortiss.tooling.base.ui.command; + +import java.util.List; + +import org.eclipse.gef.EditPart; +import org.eclipse.gef.requests.ChangeBoundsRequest; +import org.fortiss.tooling.base.model.layout.ILayoutedModelElement; +import org.fortiss.tooling.base.ui.editpart.ElementEditPartBase; +import org.fortiss.tooling.base.ui.layout.constants.DefaultLayoutConstants; /** - * This is a marker interface for edit parts, which resemble a sticky behavior - * like some connector moving only on the border of its parent element when - * viewed externally. - * - * <p> - * Edit parts implementing this marker must not implement - * {@link IFreeConnectorEditPart}. + * A command to move the elements within a diagram. * + * @author wandinger * @author hoelzl * @author $Author$ * @version $Rev$ - * @ConQAT.Rating RED Hash: + * @ConQAT.Rating YELLOW Hash: 4ECC57F8884FDDF3C622F30A50353585 */ -public interface IStickyConnectorEditPart { - // marker interface +public class MoveWithinDiagramCommand extends ChangeBoundsRequestCommandBase { + + /** Constructor. */ + public MoveWithinDiagramCommand(ChangeBoundsRequest request) { + super(request); + } + + /** {@inheritDoc} */ + @SuppressWarnings("unchecked") + @Override + public void execute() { + super.execute(); + + for (EditPart editpart : (List<EditPart>) getRequest().getEditParts()) { + if (editpart instanceof ElementEditPartBase) { + moveAndResizeNode((ILayoutedModelElement) editpart.getModel(), + DefaultLayoutConstants.DEFAULT_SHAPE_MINIMUM_WIDTH, + DefaultLayoutConstants.DEFAULT_SHAPE_MINIMUM_HEIGHT); + } else { + moveNode((ILayoutedModelElement) editpart.getModel()); + } + } + } } diff --git a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/compose/ConnectorConnectionCompositorBase.java b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/compose/ConnectorConnectionCompositorBase.java index 84922416a..005400cff 100644 --- a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/compose/ConnectorConnectionCompositorBase.java +++ b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/compose/ConnectorConnectionCompositorBase.java @@ -26,7 +26,7 @@ import org.fortiss.tooling.base.model.base.HierarchicElementBase; import org.fortiss.tooling.base.model.element.IConnector; import org.fortiss.tooling.base.model.element.IHierarchicElement; import org.fortiss.tooling.base.ui.dnd.DragContext; -import org.fortiss.tooling.base.ui.editpart.IFreeConnectorEditPart; +import org.fortiss.tooling.base.ui.editpart.FreeConnectorEditPartBase; import org.fortiss.tooling.kernel.extension.IConnectionCompositor; import org.fortiss.tooling.kernel.extension.data.IConnectionCompositionContext; import org.fortiss.tooling.kernel.extension.data.ITopLevelElement; @@ -51,8 +51,8 @@ public abstract class ConnectorConnectionCompositorBase<HE extends IHierarchicEl if (!allowInternalFeedback() && context instanceof DragContext) { DragContext dc = (DragContext) context; // - if (dc.getSource() instanceof IFreeConnectorEditPart - && dc.getTarget() instanceof IFreeConnectorEditPart) { + if (dc.getSource() instanceof FreeConnectorEditPartBase + && dc.getTarget() instanceof FreeConnectorEditPartBase) { return false; } } diff --git a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/ConnectorEditPartBase.java b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/ConnectorEditPartBase.java index 387ca9bfc..62c87aef3 100644 --- a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/ConnectorEditPartBase.java +++ b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/ConnectorEditPartBase.java @@ -86,7 +86,7 @@ public abstract class ConnectorEditPartBase<T extends ILayoutedModelElement & IC /** {@inheritDoc} */ @Override protected Rectangle determineBaseFigureBounds() { - Point connectorPos = LayoutDataUtils.getConnectorPosition(modelElement); + Point connectorPos = LayoutDataUtils.getNodePosition(modelElement); return new Rectangle(connectorPos.getX(), connectorPos.getY(), DefaultLayoutConstants.DEFAULT_CONNECTOR_SIZE, DefaultLayoutConstants.DEFAULT_CONNECTOR_SIZE); diff --git a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/DiagramEditPartBase.java b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/DiagramEditPartBase.java index b6c9b06d2..a538603f1 100644 --- a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/DiagramEditPartBase.java +++ b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/DiagramEditPartBase.java @@ -25,12 +25,18 @@ import org.eclipse.draw2d.ColorConstants; import org.eclipse.draw2d.ConnectionLayer; import org.eclipse.draw2d.ConnectionRouter; import org.eclipse.draw2d.FreeformLayer; -import org.eclipse.draw2d.Graphics; import org.eclipse.draw2d.IFigure; import org.eclipse.draw2d.XYLayout; import org.eclipse.emf.ecore.EObject; +import org.eclipse.gef.EditPolicy; import org.eclipse.gef.LayerConstants; +import org.eclipse.gef.SnapToHelper; +import org.eclipse.gef.editpolicies.RootComponentEditPolicy; +import org.eclipse.gef.editpolicies.SnapFeedbackPolicy; import org.eclipse.swt.SWT; +import org.fortiss.tooling.base.ui.editpart.policy.ConnectionGraphicalNodeEditPolicy; +import org.fortiss.tooling.base.ui.editpart.policy.DiagramLayoutEditPolicy; +import org.fortiss.tooling.base.ui.layout.util.SnapToGridUtils; /** * The base class for graphical diagrams. @@ -66,13 +72,7 @@ public abstract class DiagramEditPartBase<T extends EObject> extends protected IFigure createFigure() { setConnectionRouter(); - FreeformLayer f = new FreeformLayer() { - /** {@inheritDoc} */ - @Override - public void paint(Graphics graphics) { - super.paint(graphics); - } - }; + FreeformLayer f = new FreeformLayer(); f.setOpaque(false); f.setLayoutManager(new XYLayout()); f.setBackgroundColor(ColorConstants.white); @@ -80,6 +80,38 @@ public abstract class DiagramEditPartBase<T extends EObject> extends return f; } + /** {@inheritDoc} */ + @Override + protected void createEditPolicies() { + installEditPolicy(EditPolicy.COMPONENT_ROLE, + new RootComponentEditPolicy()); + installEditPolicy(EditPolicy.LAYOUT_ROLE, new DiagramLayoutEditPolicy()); + // snap to invisible grid policy + if (enableSnapToGrid()) { + installEditPolicy("SnapToGridFeedback", new SnapFeedbackPolicy()); + } + installEditPolicy(EditPolicy.GRAPHICAL_NODE_ROLE, + new ConnectionGraphicalNodeEditPolicy()); + } + + /** + * Returns whether snap-to-grid should be enabled. The default is + * <code>true</code>. + */ + protected boolean enableSnapToGrid() { + return true; + } + + /** {@inheritDoc} */ + @SuppressWarnings("rawtypes") + @Override + public Object getAdapter(Class adapter) { + if (adapter == SnapToHelper.class && enableSnapToGrid()) { + return SnapToGridUtils.snapToGridAdapter(this); + } + return super.getAdapter(adapter); + } + /** {@inheritDoc} */ @Override public IFigure getContentPane() { diff --git a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/ElementEditPartBase.java b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/ElementEditPartBase.java index f244eb09d..a4a961467 100644 --- a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/ElementEditPartBase.java +++ b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/ElementEditPartBase.java @@ -26,10 +26,14 @@ import org.eclipse.draw2d.geometry.Rectangle; import org.eclipse.gef.EditPolicy; import org.eclipse.gef.Request; import org.eclipse.gef.RequestConstants; +import org.eclipse.gef.SnapToHelper; import org.fortiss.tooling.base.model.layout.ILayoutedModelElement; +import org.fortiss.tooling.base.ui.editpart.policy.ConnectionGraphicalNodeEditPolicy; +import org.fortiss.tooling.base.ui.editpart.policy.ElementLayoutEditPolicy; import org.fortiss.tooling.base.ui.editpart.policy.RemoveEditPolicy; import org.fortiss.tooling.base.ui.layout.constants.DefaultLayoutConstants; import org.fortiss.tooling.base.ui.layout.util.LayoutDataUtils; +import org.fortiss.tooling.base.ui.layout.util.SnapToGridUtils; import org.fortiss.tooling.kernel.model.INamedCommentedElement; import org.fortiss.tooling.kernel.ui.service.IModelEditorBindingService; import org.fortiss.tooling.kernel.ui.service.IModelElementHandlerService; @@ -86,14 +90,14 @@ public abstract class ElementEditPartBase<T extends ILayoutedModelElement & INam return LayoutDataUtils.getNodeBounds(modelElement); } - /** - * {@inheritDoc} - * <p> - * Implements the component role for deletion. - */ + /** {@inheritDoc} */ @Override protected void createEditPolicies() { installEditPolicy(EditPolicy.COMPONENT_ROLE, new RemoveEditPolicy()); + installEditPolicy(EditPolicy.LAYOUT_ROLE, + new ElementLayoutEditPolicy<T>(this)); + installEditPolicy(EditPolicy.GRAPHICAL_NODE_ROLE, + new ConnectionGraphicalNodeEditPolicy()); } /** {@inheritDoc} */ @@ -124,4 +128,24 @@ public abstract class ElementEditPartBase<T extends ILayoutedModelElement & INam labelBounds.height = textBounds.height; labelFigure.setBounds(labelBounds); } + + /** + * {@inheritDoc} + */ + @SuppressWarnings({ "rawtypes" }) + @Override + public Object getAdapter(Class adapter) { + if (adapter == SnapToHelper.class && enableSnapToGrid()) { + return SnapToGridUtils.snapToGridAdapter(this); + } + return super.getAdapter(adapter); + } + + /** + * Returns whether snap-to-grid should be enabled. The default is + * <code>true</code>. + */ + protected boolean enableSnapToGrid() { + return true; + } } diff --git a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/SnapToGridSupport.java b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/FreeConnectorEditPartBase.java similarity index 65% rename from org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/SnapToGridSupport.java rename to org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/FreeConnectorEditPartBase.java index b2f59d7e8..aa67cfbb7 100644 --- a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/SnapToGridSupport.java +++ b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/FreeConnectorEditPartBase.java @@ -17,28 +17,25 @@ $Id$ +--------------------------------------------------------------------------*/ package org.fortiss.tooling.base.ui.editpart; -import org.eclipse.gef.GraphicalEditPart; -import org.eclipse.gef.SnapToGrid; +import org.fortiss.tooling.base.model.element.IConnector; +import org.fortiss.tooling.base.model.layout.ILayoutedModelElement; +import org.fortiss.tooling.kernel.model.INamedCommentedElement; /** - * Adapter support for snap to grid edit policies. + * Abstract base implementation of free connector edit parts. Usually, the + * connector can be moved freely in the diagram, e.g., a connector moving freely + * on the background area of its parent element when the internal structure of + * the parent is displayed. * - * @author hoelzlf * @author $Author$ * @version $Rev$ * @ConQAT.Rating RED Hash: */ -// TODO: rename suport -> adapter? -public final class SnapToGridSupport { - /** - * Adapter code for snap to grid feature. - */ - public static Object snapToGridAdapter(GraphicalEditPart editPart) { - final Boolean val = (Boolean) editPart.getViewer().getProperty( - SnapToGrid.PROPERTY_GRID_ENABLED); - if (val != null && val.booleanValue()) { - return new SnapToGrid(editPart); - } - return null; +public abstract class FreeConnectorEditPartBase<T extends ILayoutedModelElement & IConnector & INamedCommentedElement> + extends ConnectorEditPartBase<T> { + + /** Constructor. */ + protected FreeConnectorEditPartBase(T modelElement) { + super(modelElement); } } diff --git a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/IFreeConnectorEditPart.java b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/StickyConnectorEditPartBase.java similarity index 50% rename from org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/IFreeConnectorEditPart.java rename to org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/StickyConnectorEditPartBase.java index 0d4a8a24a..6d9dc13cb 100644 --- a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/IFreeConnectorEditPart.java +++ b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/StickyConnectorEditPartBase.java @@ -17,19 +17,41 @@ $Id$ +--------------------------------------------------------------------------*/ package org.fortiss.tooling.base.ui.editpart; +import org.eclipse.draw2d.geometry.Rectangle; +import org.fortiss.tooling.base.model.element.IConnector; +import org.fortiss.tooling.base.model.layout.ILayoutedModelElement; +import org.fortiss.tooling.base.ui.layout.constants.DefaultLayoutConstants; +import org.fortiss.tooling.base.ui.layout.util.RectangleLayoutUtils; +import org.fortiss.tooling.kernel.model.INamedCommentedElement; + /** - * This is a marker interface for edit parts, which resemble a free behavior - * like some connector moving freely on the background area of its parent - * element when viewed internally. - * - * <p> - * Edit parts implementing this marker must not implement - * {@link IStickyConnectorEditPart}. + * Abstract implementation for sticky connector edit parts. Usually, the + * connector sticks to some parent edit part, e.g., a connector moving only on + * the border of its parent element when the parent is viewed externally. * + * @author hoelzl * @author $Author$ * @version $Rev$ * @ConQAT.Rating RED Hash: */ -public interface IFreeConnectorEditPart { - // marker interface +public abstract class StickyConnectorEditPartBase<T extends ILayoutedModelElement & IConnector & INamedCommentedElement> + extends ConnectorEditPartBase<T> { + + /** Constructor. */ + protected StickyConnectorEditPartBase(T modelElement) { + super(modelElement); + } + + /** {@inheritDoc} */ + @Override + protected Rectangle determineBaseFigureBounds() { + if (modelElement.eContainer() instanceof ILayoutedModelElement) { + return RectangleLayoutUtils.getAbsoluteConnectorBounds( + modelElement, + (ILayoutedModelElement) modelElement.eContainer()); + } + return new Rectangle(0, 0, + DefaultLayoutConstants.DEFAULT_CONNECTOR_SIZE, + DefaultLayoutConstants.DEFAULT_CONNECTOR_SIZE); + } } diff --git a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/ConnectionBendpointEditPolicy.java b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/ConnectionBendpointEditPolicy.java new file mode 100644 index 000000000..1ecd9c490 --- /dev/null +++ b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/ConnectionBendpointEditPolicy.java @@ -0,0 +1,97 @@ +/*--------------------------------------------------------------------------+ +$Id$ +| | +| Copyright 2011 ForTISS GmbH | +| | +| Licensed under the Apache License, Version 2.0 (the "License"); | +| you may not use this file except in compliance with the License. | +| You may obtain a copy of the License at | +| | +| http://www.apache.org/licenses/LICENSE-2.0 | +| | +| Unless required by applicable law or agreed to in writing, software | +| distributed under the License is distributed on an "AS IS" BASIS, | +| WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | +| See the License for the specific language governing permissions and | +| limitations under the License. | ++--------------------------------------------------------------------------*/ +package org.fortiss.tooling.base.ui.editpart.policy; + +import org.eclipse.draw2d.geometry.Point; +import org.eclipse.gef.commands.Command; +import org.eclipse.gef.editpolicies.BendpointEditPolicy; +import org.eclipse.gef.requests.BendpointRequest; +import org.fortiss.tooling.base.model.element.IConnection; +import org.fortiss.tooling.base.model.layout.ILayoutedModelElement; +import org.fortiss.tooling.base.ui.command.CreateBendpointCommand; +import org.fortiss.tooling.base.ui.command.DeleteBendpointCommand; +import org.fortiss.tooling.base.ui.command.MoveBendpointCommand; +import org.fortiss.tooling.base.ui.editpart.ConnectionEditPartBase; +import org.fortiss.tooling.base.ui.layout.IPointLayouter; +import org.fortiss.tooling.base.ui.layout.util.SnapToGridUtils; + +/** + * An edit policy for bend points of connections. + * + * @author hoelzl + * @author $Author$ + * @version $Rev$ + * @ConQAT.Rating YELLOW Hash: 798A66B49EB8A53551DAFDE6BB690C3E + */ +public class ConnectionBendpointEditPolicy<T extends ILayoutedModelElement & IConnection> + extends BendpointEditPolicy implements IPointLayouter { + /** The channel of the bend point. */ + private final ConnectionEditPartBase<T> part; + + /** Constructor. */ + public ConnectionBendpointEditPolicy(ConnectionEditPartBase<T> part) { + this.part = part; + } + + /** {@inheritDoc} */ + @Override + protected Command getCreateBendpointCommand(BendpointRequest request) { + Point location = request.getLocation(); + part.getFigure().translateToRelative(location); + return new CreateBendpointCommand(part.getModelElement(), + request.getIndex(), location, this); + } + + /** {@inheritDoc} */ + @Override + protected Command getDeleteBendpointCommand(BendpointRequest request) { + return new DeleteBendpointCommand(part.getModelElement(), + request.getIndex()); + } + + /** {@inheritDoc} */ + @Override + protected Command getMoveBendpointCommand(BendpointRequest request) { + Point location = request.getLocation(); + part.getFigure().translateToRelative(location); + + return new MoveBendpointCommand(part.getModelElement(), + request.getIndex(), location, this); + } + + /** {@inheritDoc} */ + @Override + protected void showCreateBendpointFeedback(BendpointRequest request) { + doLayout(request.getLocation()); + super.showCreateBendpointFeedback(request); + } + + /** {@inheritDoc} */ + @Override + protected void showMoveBendpointFeedback(BendpointRequest request) { + doLayout(request.getLocation()); + super.showMoveBendpointFeedback(request); + } + + /** {@inheritDoc} */ + @Override + public void doLayout(Point p) { + p.x = SnapToGridUtils.snapToGrid(p.x); + p.y = SnapToGridUtils.snapToGrid(p.y); + } +} diff --git a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/ConnectionGraphicalNodeEditPolicy.java b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/ConnectionGraphicalNodeEditPolicy.java index 04a0a90d2..7daa36560 100644 --- a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/ConnectionGraphicalNodeEditPolicy.java +++ b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/ConnectionGraphicalNodeEditPolicy.java @@ -78,13 +78,11 @@ import org.fortiss.tooling.base.ui.dnd.DragContext; * @author hoelzl * @author $Author$ * @version $Rev$ - * @ConQAT.Rating YELLOW Hash: E6CB0FB2155238F0DDCB91D3BF2C0654 + * @ConQAT.Rating YELLOW Hash: 8FF043FB7B5273EEE1829448DB3F2EA8 */ public class ConnectionGraphicalNodeEditPolicy extends GraphicalNodeEditPolicy { - /** - * {@inheritDoc} - */ + /** {@inheritDoc} */ @Override protected Command getConnectionCompleteCommand( CreateConnectionRequest request) { @@ -97,9 +95,7 @@ public class ConnectionGraphicalNodeEditPolicy extends GraphicalNodeEditPolicy { return UnexecutableCommand.INSTANCE; } - /** - * {@inheritDoc} - */ + /** {@inheritDoc} */ @Override protected Command getConnectionCreateCommand(CreateConnectionRequest request) { DragContext context = new DragContext(getHost(), request.getLocation()); @@ -109,9 +105,7 @@ public class ConnectionGraphicalNodeEditPolicy extends GraphicalNodeEditPolicy { return cmd; } - /** - * {@inheritDoc} - */ + /** {@inheritDoc} */ @Override protected Command getReconnectSourceCommand(ReconnectRequest request) { if (request.getConnectionEditPart().getModel() instanceof EObject) { @@ -124,9 +118,7 @@ public class ConnectionGraphicalNodeEditPolicy extends GraphicalNodeEditPolicy { return UnexecutableCommand.INSTANCE; } - /** - * {@inheritDoc} - */ + /** {@inheritDoc} */ @Override protected Command getReconnectTargetCommand(ReconnectRequest request) { if (request.getConnectionEditPart().getModel() instanceof EObject) { diff --git a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/ConstrainedNonResizableEditPolicy.java b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/ConstrainedNonResizableEditPolicy.java new file mode 100644 index 000000000..e2563ded2 --- /dev/null +++ b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/ConstrainedNonResizableEditPolicy.java @@ -0,0 +1,112 @@ +/*--------------------------------------------------------------------------+ +$Id$ +| | +| Copyright 2011 ForTISS GmbH | +| | +| Licensed under the Apache License, Version 2.0 (the "License"); | +| you may not use this file except in compliance with the License. | +| You may obtain a copy of the License at | +| | +| http://www.apache.org/licenses/LICENSE-2.0 | +| | +| Unless required by applicable law or agreed to in writing, software | +| distributed under the License is distributed on an "AS IS" BASIS, | +| WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | +| See the License for the specific language governing permissions and | +| limitations under the License. | ++--------------------------------------------------------------------------*/ +package org.fortiss.tooling.base.ui.editpart.policy; + +import org.eclipse.draw2d.Viewport; +import org.eclipse.draw2d.geometry.Point; +import org.eclipse.draw2d.geometry.Rectangle; +import org.eclipse.gef.Request; +import org.eclipse.gef.editparts.ScalableRootEditPart; +import org.eclipse.gef.editpolicies.NonResizableEditPolicy; +import org.eclipse.gef.requests.ChangeBoundsRequest; +import org.fortiss.tooling.base.model.layout.Dimension; +import org.fortiss.tooling.base.model.layout.ILayoutedModelElement; +import org.fortiss.tooling.base.model.layout.OffsetOrientation; +import org.fortiss.tooling.base.ui.editpart.ElementEditPartBase; +import org.fortiss.tooling.base.ui.layout.constants.DefaultLayoutConstants; +import org.fortiss.tooling.base.ui.layout.constants.LayoutKeyConstants; +import org.fortiss.tooling.base.ui.layout.util.LayoutDataUtils; +import org.fortiss.tooling.base.ui.layout.util.RectangleLayoutUtils; +import org.fortiss.tooling.base.ui.layout.util.SnapToGridUtils; +import org.fortiss.tooling.kernel.model.INamedCommentedElement; + +/** + * EditPolicy for keeping a connector sticking to the border of it's parent + * element. + * <p> + * This EditPolicy is responsible for limiting connector placement to the border + * of a model element. It's clear, that this is only valid for sticky + * connectors, all others are not affected by this policy. + * + * @author wandinger + * @author hoelzl + * @author $Author$ + * @version $Rev$ + * @ConQAT.Rating YELLOW Hash: D8173BE506F1A36E8BF28B17E1BD9C1E + */ +public class ConstrainedNonResizableEditPolicy<T extends ILayoutedModelElement & INamedCommentedElement> + extends NonResizableEditPolicy { + + /** Stores the edit part. */ + private final ElementEditPartBase<T> part; + + /** Constructor. */ + public ConstrainedNonResizableEditPolicy(ElementEditPartBase<T> part) { + this.part = part; + } + + /** {@inheritDoc} */ + @SuppressWarnings("unchecked") + @Override + public void showSourceFeedback(Request request) { + if (REQ_MOVE.equals(request.getType())) { + // get the bounds of the parent + Rectangle containerBounds = LayoutDataUtils + .getNodeBounds((ILayoutedModelElement) part.getModel()); + // get the child position relative to the parent + Point childPos = getHostFigure().getBounds().getLocation() + .getTranslated(containerBounds.getLocation().getNegated()); + // get the current mouse position + Point mousePos = ((ChangeBoundsRequest) request).getLocation(); + // fix offset in mouse position because of possibly scrolled editing + // window + Point clientAreaOffset = new Point( + ((Viewport) ((ScalableRootEditPart) part.getRoot()) + .getFigure()).getClientArea().getLocation()); + mousePos.translate(clientAreaOffset); + // get the mouse position relative to the parent + Point relativePos = mousePos.getTranslated(containerBounds + .getLocation().getNegated()); + + // do border clamping + OffsetOrientation orient = RectangleLayoutUtils + .calculateRectangleBorderOrientation(relativePos, + containerBounds.getSize(), + DefaultLayoutConstants.DEFAULT_SHAPE_INSETS); + // snap to grid + orient.setOffset(SnapToGridUtils.snapToGrid(orient.getOffset())); + // use the calculated value for positioning + Dimension d = LayoutDataUtils + .getNodeSize((ILayoutedModelElement) part.getModel()); + org.fortiss.tooling.base.model.layout.Point p = LayoutDataUtils + .getAbsolute(orient, d, + DefaultLayoutConstants.DEFAULT_SHAPE_INSETS); + relativePos.setLocation(p.getX(), p.getY()); + + // store the orientation in the request so that the command can use + // it + request.getExtendedData().put( + LayoutKeyConstants.CONNECTOR_OFFSET_ORIENTATION, orient); + // MoveDelta needs positions relative to the child + relativePos.translate(childPos.getNegated()); + + ((ChangeBoundsRequest) request).setMoveDelta(relativePos); + } + super.showSourceFeedback(request); + } +} diff --git a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/DiagramLayoutEditPolicy.java b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/DiagramLayoutEditPolicy.java new file mode 100644 index 000000000..77211b126 --- /dev/null +++ b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/DiagramLayoutEditPolicy.java @@ -0,0 +1,70 @@ +/*--------------------------------------------------------------------------+ +$Id$ +| | +| Copyright 2011 ForTISS GmbH | +| | +| Licensed under the Apache License, Version 2.0 (the "License"); | +| you may not use this file except in compliance with the License. | +| You may obtain a copy of the License at | +| | +| http://www.apache.org/licenses/LICENSE-2.0 | +| | +| Unless required by applicable law or agreed to in writing, software | +| distributed under the License is distributed on an "AS IS" BASIS, | +| WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | +| See the License for the specific language governing permissions and | +| limitations under the License. | ++--------------------------------------------------------------------------*/ +package org.fortiss.tooling.base.ui.editpart.policy; + +import org.eclipse.gef.EditPart; +import org.eclipse.gef.EditPolicy; +import org.eclipse.gef.Request; +import org.eclipse.gef.RequestConstants; +import org.eclipse.gef.commands.Command; +import org.eclipse.gef.editpolicies.NonResizableEditPolicy; +import org.eclipse.gef.requests.ChangeBoundsRequest; +import org.fortiss.tooling.base.ui.command.MoveWithinDiagramCommand; +import org.fortiss.tooling.base.ui.editpart.ElementEditPartBase; +import org.fortiss.tooling.base.ui.layout.util.ZoomUtils; + +/** + * The layout policy for diagrams. + * + * @author wandinger + * @author hoelzl + * @author $Author$ + * @version $Rev$ + * @ConQAT.Rating YELLOW Hash: FBC121B49FD0AD95808132A6B4477132 + */ +public class DiagramLayoutEditPolicy extends LayoutEditPolicyBase { + + /** {@inheritDoc} */ + @Override + protected EditPolicy createChildEditPolicy(EditPart child) { + if (child instanceof ElementEditPartBase) { + return new FreeResizableEditPolicy(); + } + return new NonResizableEditPolicy(); + } + + /** {@inheritDoc} */ + @Override + public Command getCommand(Request request) { + if (RequestConstants.REQ_RESIZE_CHILDREN.equals(request.getType())) { + return getMoveChildrenCommand(request); + } + return super.getCommand(request); + } + + /** {@inheritDoc} */ + @Override + protected Command getMoveChildrenCommand(final Request request) { + if (request instanceof ChangeBoundsRequest) { + ZoomUtils.fixChangeBoundRequest((ChangeBoundsRequest) request, + ZoomUtils.determineZoom(getHost().getRoot())); + return new MoveWithinDiagramCommand((ChangeBoundsRequest) request); + } + return null; + } +} diff --git a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/ElementLayoutEditPolicy.java b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/ElementLayoutEditPolicy.java new file mode 100644 index 000000000..febafaced --- /dev/null +++ b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/ElementLayoutEditPolicy.java @@ -0,0 +1,71 @@ +/*--------------------------------------------------------------------------+ +$Id$ +| | +| Copyright 2011 ForTISS GmbH | +| | +| Licensed under the Apache License, Version 2.0 (the "License"); | +| you may not use this file except in compliance with the License. | +| You may obtain a copy of the License at | +| | +| http://www.apache.org/licenses/LICENSE-2.0 | +| | +| Unless required by applicable law or agreed to in writing, software | +| distributed under the License is distributed on an "AS IS" BASIS, | +| WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | +| See the License for the specific language governing permissions and | +| limitations under the License. | ++--------------------------------------------------------------------------*/ +package org.fortiss.tooling.base.ui.editpart.policy; + +import org.eclipse.gef.EditPart; +import org.eclipse.gef.EditPolicy; +import org.eclipse.gef.Request; +import org.eclipse.gef.commands.Command; +import org.eclipse.gef.editpolicies.NonResizableEditPolicy; +import org.eclipse.gef.requests.ChangeBoundsRequest; +import org.fortiss.tooling.base.model.layout.ILayoutedModelElement; +import org.fortiss.tooling.base.ui.command.MoveConnectorCommand; +import org.fortiss.tooling.base.ui.editpart.ElementEditPartBase; +import org.fortiss.tooling.base.ui.editpart.StickyConnectorEditPartBase; +import org.fortiss.tooling.base.ui.layout.util.ZoomUtils; +import org.fortiss.tooling.kernel.model.INamedCommentedElement; + +/** + * Layout policy for model elements, e.g. diagram nodes. + * + * @author hoelzl + * @author $Author$ + * @version $Rev$ + * @ConQAT.Rating YELLOW Hash: DA1558F01B70802D5D0DD9A6E2411E65 + */ +public class ElementLayoutEditPolicy<T extends ILayoutedModelElement & INamedCommentedElement> + extends LayoutEditPolicyBase { + + /** The edit part. */ + private final ElementEditPartBase<T> part; + + /** Constructor */ + public ElementLayoutEditPolicy(ElementEditPartBase<T> part) { + this.part = part; + } + + /** {@inheritDoc} */ + @Override + protected EditPolicy createChildEditPolicy(EditPart child) { + if (child instanceof StickyConnectorEditPartBase) { + return new ConstrainedNonResizableEditPolicy<T>(part); + } + return new NonResizableEditPolicy(); + } + + /** {@inheritDoc} */ + @Override + protected Command getMoveChildrenCommand(Request request) { + if (request instanceof ChangeBoundsRequest) { + ZoomUtils.fixChangeBoundRequest((ChangeBoundsRequest) request, + ZoomUtils.determineZoom(getHost().getRoot())); + return new MoveConnectorCommand((ChangeBoundsRequest) request); + } + return null; + } +} diff --git a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/FreeResizableEditPolicy.java b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/FreeResizableEditPolicy.java new file mode 100644 index 000000000..d3a55ba9f --- /dev/null +++ b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/FreeResizableEditPolicy.java @@ -0,0 +1,67 @@ +/*--------------------------------------------------------------------------+ +$Id$ +| | +| Copyright 2011 ForTISS GmbH | +| | +| Licensed under the Apache License, Version 2.0 (the "License"); | +| you may not use this file except in compliance with the License. | +| You may obtain a copy of the License at | +| | +| http://www.apache.org/licenses/LICENSE-2.0 | +| | +| Unless required by applicable law or agreed to in writing, software | +| distributed under the License is distributed on an "AS IS" BASIS, | +| WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | +| See the License for the specific language governing permissions and | +| limitations under the License. | ++--------------------------------------------------------------------------*/ +package org.fortiss.tooling.base.ui.editpart.policy; + +import org.eclipse.draw2d.PositionConstants; +import org.eclipse.draw2d.geometry.Dimension; +import org.eclipse.gef.Request; +import org.eclipse.gef.editpolicies.ResizableEditPolicy; +import org.eclipse.gef.requests.ChangeBoundsRequest; +import org.fortiss.tooling.base.ui.layout.util.RectangleLayoutUtils; + +/** + * EditPolicy for child resizing without a fixed aspect ratio. + * <p> + * This EditPolicy is responsible for resizing child parts. A minimal size is + * ensured. Resizing is restricted to the east, south-east and south handles. + * All other handles are used for moves only. + * </p> + * + * @author wandinger + * @author hoelzl + * @author $Author$ + * @version $Rev$ + * @ConQAT.Rating YELLOW Hash: DD495DD52938CABD033D98072C8EF8DF + */ +public class FreeResizableEditPolicy extends ResizableEditPolicy { + /** Constructor. */ + public FreeResizableEditPolicy() { + // enable resizing on east, south-east and south handles. + setResizeDirections(PositionConstants.SOUTH_EAST); + } + + /** {@inheritDoc} */ + @Override + public void showSourceFeedback(Request request) { + if (REQ_RESIZE.equals(request.getType())) { + Dimension oldSizeDelta = ((ChangeBoundsRequest) request) + .getSizeDelta(); + Dimension oldSize = new Dimension(getHostFigure().getBounds().width + + oldSizeDelta.width, getHostFigure().getBounds().height + + oldSizeDelta.height); + Dimension newSize = RectangleLayoutUtils + .clampRectangularShapeSize(oldSize); + Dimension newSizeDelta = new Dimension(newSize.width + - getHostFigure().getBounds().width, newSize.height + - getHostFigure().getBounds().height); + + ((ChangeBoundsRequest) request).setSizeDelta(newSizeDelta); + } + super.showSourceFeedback(request); + } +} diff --git a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/LayoutEditPolicyBase.java b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/LayoutEditPolicyBase.java index 2fda5601f..91be8ac1e 100644 --- a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/LayoutEditPolicyBase.java +++ b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/LayoutEditPolicyBase.java @@ -29,14 +29,14 @@ import org.fortiss.tooling.kernel.service.IElementCompositorService; import org.fortiss.tooling.kernel.ui.util.DragAndDropUtils; /** - * Base class for layout edit policies relaying create commands to the - * compositor service. + * Base class for layout edit policies relaying create commands to + * {@link IElementCompositorService}. * * @author hummel * @author hoelzl * @author $Author$ * @version $Rev$ - * @ConQAT.Rating YELLOW Hash: FF4755C1E99126698517CDCB5522F868 + * @ConQAT.Rating YELLOW Hash: 1123D10EB725BCC9D76B7F7322DAF5CA */ public abstract class LayoutEditPolicyBase extends LayoutEditPolicy { @@ -54,30 +54,30 @@ public abstract class LayoutEditPolicyBase extends LayoutEditPolicy { if (request.getSize() != null) { return null; } + if (!(getHost().getModel() instanceof EObject)) { + return null; + } Point location = request.getLocation(); ((GraphicalEditPart) getHost()).getFigure().translateToRelative( location); - if (!(getHost().getModel() instanceof EObject)) { - return null; - } final EObject model = (EObject) getHost().getModel(); - - final IElementCompositionContext context = new DropContext(getHost(), location); - final EObject dropped = DragAndDropUtils.extractDroppedEObject(request .getNewObject()); + final IElementCompositionContext context = new DropContext(getHost(), + location); return new Command() { @Override public boolean canExecute() { - return IElementCompositorService.INSTANCE.canCompose(model, dropped, - context); + return IElementCompositorService.INSTANCE.canCompose(model, + dropped, context); } @Override public void execute() { - IElementCompositorService.INSTANCE.compose(model, dropped, context); + IElementCompositorService.INSTANCE.compose(model, dropped, + context); } }; } diff --git a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/RemoveEditPolicy.java b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/RemoveEditPolicy.java index 940f2a872..648c717f9 100644 --- a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/RemoveEditPolicy.java +++ b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/editpart/policy/RemoveEditPolicy.java @@ -35,7 +35,7 @@ import org.fortiss.tooling.kernel.service.IElementCompositorService; * @author hoelzl * @author $Author$ * @version $Rev$ - * @ConQAT.Rating YELLOW Hash: 2B5B416E8F269FF00EC78D0226A479BA + * @ConQAT.Rating YELLOW Hash: 64EDE1E67D8B6F94C5B141D37A3B1B1F */ public final class RemoveEditPolicy extends ComponentEditPolicy { diff --git a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/layout/util/EllipseLayoutUtils.java b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/layout/util/EllipseLayoutUtils.java new file mode 100644 index 000000000..421808929 --- /dev/null +++ b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/layout/util/EllipseLayoutUtils.java @@ -0,0 +1,161 @@ +/*--------------------------------------------------------------------------+ +$Id$ +| | +| Copyright 2011 ForTISS GmbH | +| | +| Licensed under the Apache License, Version 2.0 (the "License"); | +| you may not use this file except in compliance with the License. | +| You may obtain a copy of the License at | +| | +| http://www.apache.org/licenses/LICENSE-2.0 | +| | +| Unless required by applicable law or agreed to in writing, software | +| distributed under the License is distributed on an "AS IS" BASIS, | +| WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | +| See the License for the specific language governing permissions and | +| limitations under the License. | ++--------------------------------------------------------------------------*/ +package org.fortiss.tooling.base.ui.layout.util; + +import org.eclipse.draw2d.PositionConstants; +import org.eclipse.draw2d.geometry.Dimension; +import org.eclipse.draw2d.geometry.Point; +import org.fortiss.tooling.base.model.layout.ILayoutedModelElement; +import org.fortiss.tooling.base.ui.layout.constants.DefaultLayoutConstants; + +/** + * Utility methods for ellipse-shaped edit part layout. + * + * @author hoelzl + * @author $Author$ + * @version $Rev$ + * @ConQAT.Rating RED Hash: 29FAC994522C13BC65F8538F36B6CFDA + */ +public final class EllipseLayoutUtils { + /** + * Returns polar coordinates of the point on the ellipse border having the + * given angle. + */ + public static Polar calculateEllipseBorderPolar(double angle, + Dimension ellipseSize, int inset) { + double a = ellipseSize.width / 2 - inset; + double b = ellipseSize.height / 2 - inset; + double epsilon = Math.sqrt(a * a - b * b) / a; + double r = b + / Math.sqrt(1 - epsilon * epsilon * Math.cos(angle) + * Math.cos(angle)); + return new Polar(angle, r); + } + + /** + * Returns Cartesian coordinates of the point on the ellipse border having + * the given angle. + */ + public static Point calculateEllipseBorderPoint(double angle, + Dimension ellipseSize, int inset) { + Polar p = calculateEllipseBorderPolar(angle, ellipseSize, inset); + return p.toCartesian().translate(ellipseSize.getScaled(.5)); + } + + /** Layouts the given connector within the surrounding ellipse. */ + public static void layoutConnectorInEllipse(ILayoutedModelElement layouted, + ILayoutedModelElement container, Point location) { + Point position = location.getCopy(); + org.fortiss.tooling.base.model.layout.Point np = LayoutDataUtils + .getNodePosition(container); + position.translate(-np.getX(), -np.getY()); + + org.fortiss.tooling.base.model.layout.Dimension nd = LayoutDataUtils + .getNodeSize(container); + Dimension d = new Dimension(nd.getWidth(), nd.getHeight()); + position.translate(d.scale(-.5)); + + // store the value in the model + LayoutDataUtils.setConnectorAngle(layouted, new Polar(position).angle); + } + + /** + * Ensure that the minimum size and aspect ratio of a oval shape are + * redeemed. + */ + public static Dimension clampEllipseShapeSize(Dimension oldSize, + int direction) { + return clampEllipseShapeSize(oldSize, direction, + DefaultLayoutConstants.DEFAULT_SHAPE_MINIMUM_WIDTH, + DefaultLayoutConstants.DEFAULT_SHAPE_MINIMUM_HEIGHT, + DefaultLayoutConstants.DEFAULT_SHAPE_ASPECT_RATIO); + } + + /** + * Ensure that the minimum size and aspect ratio of a oval shape are + * redeemed. + */ + public static Dimension clampEllipseShapeSize(Dimension oldSize, + int direction, int minimumWidth, int minimumHeight, + double aspectRatio) { + Dimension newSize; + + // check for minimum size + newSize = new Dimension(oldSize.width < minimumWidth ? minimumWidth + : oldSize.width, oldSize.height < minimumHeight ? minimumHeight + : oldSize.height); + + // ensure that the aspect ratio is redeemed + switch (direction) { + case PositionConstants.SOUTH_EAST: + int aspectHeight = (int) (newSize.width / aspectRatio); + int aspectWidth = (int) (newSize.height * aspectRatio); + newSize.setSize(new Dimension( + newSize.width > aspectWidth ? aspectWidth : newSize.width, + newSize.height > aspectHeight ? aspectHeight + : newSize.height)); + break; + case PositionConstants.SOUTH: + newSize.setSize(new Dimension((int) (newSize.height * aspectRatio), + newSize.height)); + break; + case PositionConstants.EAST: + newSize.setSize(new Dimension(newSize.width, + (int) (newSize.width / aspectRatio))); + break; + } + + return newSize; + } + + /** + * Class for storing polar coordinates. + * + * @author wandinger + * @author hummel + * @author $Author$ + * @version $Rev$ + * @levd.rating YELLOW Rev: 519 + */ + public static class Polar { + + /** The angle */ + public double angle; + + /** The distance */ + public double distance; + + /** The constructor */ + public Polar(double angle, double distance) { + this.angle = angle; + this.distance = distance; + } + + /** Create new polar values from cartesian ones. */ + public Polar(Point pos) { + angle = Math.atan2(pos.y, pos.x); + distance = Math.sqrt(pos.x * pos.x + pos.y * pos.y); + } + + /** Returns a cartesian representation. */ + public Point toCartesian() { + return new Point(distance * Math.cos(angle), distance + * Math.sin(angle)); + } + } +} diff --git a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/layout/util/LayoutDataUtils.java b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/layout/util/LayoutDataUtils.java index 600924f99..08e6da97d 100644 --- a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/layout/util/LayoutDataUtils.java +++ b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/layout/util/LayoutDataUtils.java @@ -45,21 +45,10 @@ import org.fortiss.tooling.base.ui.layout.constants.LayoutKeyConstants; * @author hummel * @author $Author$ * @version $Rev$ - * @ConQAT.Rating YELLOW Hash: F7FBEB4FD3CE4087069F5CEF38C76851 + * @ConQAT.Rating YELLOW Hash: 4B5CA7ECC0803744F20556EE5113D44A */ public class LayoutDataUtils { - /** Translates the given point by moving it accordingly. */ - public static Point translate(Point p, int dx, int dy) { - return PointUtil.createPoint(p.getX() + dx, p.getY() + dy); - } - - /** Expands the given dimension by resizing it accordingly. */ - public static Dimension expand(Dimension d, int dw, int dh) { - return DimensionUtil.createDimension(d.getWidth() + dw, d.getHeight() - + dh); - } - /** Returns the bounds rectangle of the given layouted element. */ public static Rectangle getNodeBounds(ILayoutedModelElement layouted) { Rectangle result = new Rectangle(); @@ -83,13 +72,6 @@ public class LayoutDataUtils { .getPosition(layouted, LayoutKeyConstants.NODE_POSITION); } - /** Sets the layouted node's position. */ - // TODO: clean up should remove this - public static void setNodePosition(ILayoutedModelElement layouted, - Point position) { - setNodePosition(layouted, position.getX(), position.getY()); - } - /** Sets the layouted node's position. */ public static void setNodePosition(ILayoutedModelElement layouted, int x, int y) { @@ -114,19 +96,47 @@ public class LayoutDataUtils { return EcoreUtil.copy(size); } - /** Sets the layouted node's size. */ - // TODO: cleanup should remove this method - public static void setNodeSize(ILayoutedModelElement layouted, - Dimension size) { - setNodeSize(layouted, size.getWidth(), size.getHeight()); - } - /** Sets the layouted node's size. */ public static void setNodeSize(ILayoutedModelElement layouted, int w, int h) { DimensionUtil.setDimension(layouted, LayoutKeyConstants.NODE_DIMENSION, w, h); } + /** Moves the given node. */ + public static void moveNode(ILayoutedModelElement layouted, int dx, int dy) { + Point p = LayoutDataUtils.getNodePosition(layouted); + LayoutDataUtils.setNodePosition(layouted, p.getX() + dx, p.getY() + dy); + } + + /** Moves and resizes the given node. */ + public static void moveAndResizeNode(ILayoutedModelElement layouted, + int dx, int dy, int dw, int dh, int minWidth, int minHeight) { + Point pos = LayoutDataUtils.getNodePosition(layouted); + int posX = pos.getX() + dx; + int posY = pos.getY() + dy; + + Dimension dim = LayoutDataUtils.getNodeSize(layouted); + int dimW = dim.getWidth() + dw; + int dimH = dim.getHeight() + dh; + + if (dimW < minWidth) { + if (dx > 0) { + posX = posX - minWidth - dimW; + } + dimW = minWidth; + } + + if (dimH < minHeight) { + if (dy > 0) { + posY = posY - minHeight - dimH; + } + dimH = minHeight; + } + + LayoutDataUtils.setNodePosition(layouted, posX, posY); + LayoutDataUtils.setNodeSize(layouted, dimW, dimH); + } + /** Returns the layouted connector's position. */ public static Point getConnectorPosition(ILayoutedModelElement layouted) { return PointUtil.getPosition(layouted, @@ -178,7 +188,6 @@ public class LayoutDataUtils { } /** Returns the layouted connector's angle. */ - // TODO: used? public static Angle getConnectorAngle(ILayoutedModelElement layouted) { Angle angle = AngleUtil.getAngle(layouted, LayoutKeyConstants.CONNECTOR_ANGLE); @@ -189,13 +198,11 @@ public class LayoutDataUtils { } /** Returns the angle as double value (0 if not existing). */ - // TODO: used? public static double getConnectorAngleAsDouble(ILayoutedModelElement lobject) { return getConnectorAngle(lobject).getAngle(); } /** Creates a new connection layout. */ - // TODO: used? public static void createConnectionLayout(ILayoutedModelElement lo) { Points points = PointsUtil.createPoints(); points.setKey(LayoutKeyConstants.CONNECTION_POINTS); @@ -204,7 +211,9 @@ public class LayoutDataUtils { /** Creates a new connector layout. */ public static void createConnectorLayout(ILayoutedModelElement lo) { - createNodeLayout(lo); + setNodePosition(lo, 0, 0); + setNodeSize(lo, DefaultLayoutConstants.DEFAULT_SHAPE_MINIMUM_WIDTH, + DefaultLayoutConstants.DEFAULT_SHAPE_MINIMUM_HEIGHT); Point cpos = LayoutFactory.eINSTANCE.createPoint(); cpos.setKey(LayoutKeyConstants.CONNECTOR_POSITION); @@ -216,26 +225,7 @@ public class LayoutDataUtils { lo.getLayoutDataList().add(cdim); } - /** Creates a new node layout. */ - // TODO: public? - public static void createNodeLayout(ILayoutedModelElement lobject) { - PointUtil.setPoint(lobject, LayoutKeyConstants.NODE_POSITION, 0, 0); - DimensionUtil.setDimension(lobject, LayoutKeyConstants.NODE_DIMENSION, - DefaultLayoutConstants.DEFAULT_SHAPE_MINIMUM_WIDTH, - DefaultLayoutConstants.DEFAULT_SHAPE_MINIMUM_HEIGHT); - } - - /** - * Return the absolute position for the given orientation using default - * insets. - */ - public static Point getAbsolute(OffsetOrientation oo, Dimension parentSize) { - return getAbsolute(oo, parentSize, - DefaultLayoutConstants.DEFAULT_SHAPE_INSETS); - } - - /** Return the absolute position for a given offset and orientation. */ - // TODO: public? + /** Return the absolute position for a given offset, orientation and insets. */ public static Point getAbsolute(OffsetOrientation oo, Dimension parentSize, int parentInsets) { Point pos = PointUtil.createPoint(0, 0); @@ -258,7 +248,6 @@ public class LayoutDataUtils { pos.setY(offsetValue); break; } - return pos; } @@ -268,20 +257,14 @@ public class LayoutDataUtils { LayoutKeyConstants.CONNECTION_POINTS); } - /** Sets the points layout data of the given connection. */ - private static void setConnectionPoints(ILayoutedModelElement lobject, - Points points) { - PointsUtil.setPoints(lobject, LayoutKeyConstants.CONNECTION_POINTS, - points); - } - /** Adds the given x/y point to the layout data of the given element. */ public static void addConnectionPoint(ILayoutedModelElement lobject, int x, int y) { Points pts = getConnectionPoints(lobject); Point np = PointUtil.createPoint(x, y); pts.getPointsList().add(np); - setConnectionPoints(lobject, pts); + PointsUtil + .setPoints(lobject, LayoutKeyConstants.CONNECTION_POINTS, pts); } /** Changes the point of the layout data at the given index. */ @@ -290,7 +273,8 @@ public class LayoutDataUtils { Points pts = getConnectionPoints(lobject); Point np = PointUtil.createPoint(x, y); pts.getPointsList().set(index, np); - setConnectionPoints(lobject, pts); + PointsUtil + .setPoints(lobject, LayoutKeyConstants.CONNECTION_POINTS, pts); } /** Changes all the point layout data of the given element. */ @@ -302,7 +286,8 @@ public class LayoutDataUtils { Point np = PointUtil.createPoint(p.getX() + dx, p.getY() + dy); npts.getPointsList().add(np); } - setConnectionPoints(lobject, npts); + PointsUtil + .setPoints(lobject, LayoutKeyConstants.CONNECTION_POINTS, pts); } /** @@ -313,6 +298,8 @@ public class LayoutDataUtils { int index) { Points pts = getConnectionPoints(lobject); pts.getPointsList().remove(index); - setConnectionPoints(lobject, pts); + PointsUtil + .setPoints(lobject, LayoutKeyConstants.CONNECTION_POINTS, pts); + } } diff --git a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/layout/util/EditPartLayoutUtils.java b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/layout/util/RectangleLayoutUtils.java similarity index 54% rename from org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/layout/util/EditPartLayoutUtils.java rename to org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/layout/util/RectangleLayoutUtils.java index d82257e01..71375aabd 100644 --- a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/layout/util/EditPartLayoutUtils.java +++ b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/layout/util/RectangleLayoutUtils.java @@ -19,7 +19,6 @@ package org.fortiss.tooling.base.ui.layout.util; import java.awt.Polygon; -import org.eclipse.draw2d.PositionConstants; import org.eclipse.draw2d.geometry.Dimension; import org.eclipse.draw2d.geometry.Point; import org.eclipse.draw2d.geometry.Rectangle; @@ -30,66 +29,15 @@ import org.fortiss.tooling.base.ui.dnd.DropContext; import org.fortiss.tooling.base.ui.layout.constants.DefaultLayoutConstants; /** - * Utility class for EditPart layout methods. + * Utility class for rectangle-shaped edit part layout. * * @author wandinger * @author hummel * @author $Author$ * @version $Rev$ - * @ConQAT.Rating YELLOW Hash: C35B3098DFF4E3BD3F5B0AB20DC39B30 + * @ConQAT.Rating YELLOW Hash: 3DAA7FF0B916B47CC06441E6AC6808BC */ -// TODO: split class into sTg, rectangular and oval? -public class EditPartLayoutUtils { - - /** Returns the given value aligned to the given grid size. */ - public static int snapToGrid(double d, int gridSize) { - return gridSize * (int) Math.round(d / gridSize); - } - - /** Returns the given value aligned to the recommended grid size. */ - public static int snapToGrid(double d) { - return snapToGrid(d, DefaultLayoutConstants.DEFAULT_GRID_SIZE); - } - - /** - * Modifies the x and y coordinates of the given point to be on the grid of - * the given size. - */ - public static void snapToGrid(Point p, int gridSize) { - p.x = snapToGrid(p.x, gridSize); - p.y = snapToGrid(p.y, gridSize); - } - - /** Modifies the x and y coordinates of the given point to be on the grid. */ - public static void snapToGrid(Point p) { - p.x = snapToGrid(p.x, DefaultLayoutConstants.DEFAULT_GRID_SIZE); - p.y = snapToGrid(p.y, DefaultLayoutConstants.DEFAULT_GRID_SIZE); - } - - /** - * Returns polar coordinates of the point on the ellipse border having the - * given angle. - */ - public static Polar calculateEllipseBorderPolar(double angle, - Dimension ellipseSize, int inset) { - double a = ellipseSize.width / 2 - inset; - double b = ellipseSize.height / 2 - inset; - double epsilon = Math.sqrt(a * a - b * b) / a; - double r = b - / Math.sqrt(1 - epsilon * epsilon * Math.cos(angle) - * Math.cos(angle)); - return new Polar(angle, r); - } - - /** - * Returns Cartesian coordinates of the point on the ellipse border having - * the given angle. - */ - public static Point calculateEllipseBorderPoint(double angle, - Dimension ellipseSize, int inset) { - Polar p = calculateEllipseBorderPolar(angle, ellipseSize, inset); - return p.toCartesian().translate(ellipseSize.getScaled(.5)); - } +public class RectangleLayoutUtils { /** * Returns the {@link OffsetOrientation} of the point on the rectangle @@ -141,54 +89,6 @@ public class EditPartLayoutUtils { orientation); } - /** - * Ensure that the minimum size and aspect ratio of a oval shape are - * redeemed. - */ - public static Dimension clampOvalShapeSize(Dimension oldSize, int direction) { - return clampOvalShapeSize(oldSize, direction, - DefaultLayoutConstants.DEFAULT_SHAPE_MINIMUM_WIDTH, - DefaultLayoutConstants.DEFAULT_SHAPE_MINIMUM_HEIGHT, - DefaultLayoutConstants.DEFAULT_SHAPE_ASPECT_RATIO); - } - - /** - * Ensure that the minimum size and aspect ratio of a oval shape are - * redeemed. - */ - public static Dimension clampOvalShapeSize(Dimension oldSize, - int direction, int minimumWidth, int minimumHeight, - double aspectRatio) { - Dimension newSize; - - // check for minimum size - newSize = new Dimension(oldSize.width < minimumWidth ? minimumWidth - : oldSize.width, oldSize.height < minimumHeight ? minimumHeight - : oldSize.height); - - // ensure that the aspect ratio is redeemed - switch (direction) { - case PositionConstants.SOUTH_EAST: - int aspectHeight = (int) (newSize.width / aspectRatio); - int aspectWidth = (int) (newSize.height * aspectRatio); - newSize.setSize(new Dimension( - newSize.width > aspectWidth ? aspectWidth : newSize.width, - newSize.height > aspectHeight ? aspectHeight - : newSize.height)); - break; - case PositionConstants.SOUTH: - newSize.setSize(new Dimension((int) (newSize.height * aspectRatio), - newSize.height)); - break; - case PositionConstants.EAST: - newSize.setSize(new Dimension(newSize.width, - (int) (newSize.width / aspectRatio))); - break; - } - - return newSize; - } - /** Ensure that the minimum size of a rectangular shape is redeemed. */ public static Dimension clampRectangularShapeSize(Dimension oldSize, int minimumWidth, int minimumHeight) { @@ -206,23 +106,6 @@ public class EditPartLayoutUtils { DefaultLayoutConstants.DEFAULT_SHAPE_MINIMUM_HEIGHT); } - /** Layouts the given connector within the surrounding ellipse. */ - public static void layoutConnectorInEllipse(ILayoutedModelElement layouted, - ILayoutedModelElement container, Point location) { - Point position = location.getCopy(); - org.fortiss.tooling.base.model.layout.Point np = LayoutDataUtils - .getNodePosition(container); - position.translate(-np.getX(), -np.getY()); - - org.fortiss.tooling.base.model.layout.Dimension nd = LayoutDataUtils - .getNodeSize(container); - Dimension d = new Dimension(nd.getWidth(), nd.getHeight()); - position.translate(d.scale(-.5)); - - // store the value in the model - LayoutDataUtils.setConnectorAngle(layouted, new Polar(position).angle); - } - /** Layouts the given connector within the surrounding rectangle. */ public static void layoutConnectorInRectangle( ILayoutedModelElement layouted, ILayoutedModelElement container, @@ -235,11 +118,11 @@ public class EditPartLayoutUtils { org.fortiss.tooling.base.model.layout.Dimension nd = LayoutDataUtils .getNodeSize(container); Dimension d = new Dimension(nd.getWidth(), nd.getHeight()); - OffsetOrientation orient = EditPartLayoutUtils + OffsetOrientation orient = RectangleLayoutUtils .calculateRectangleBorderOrientation(position, d, DefaultLayoutConstants.DEFAULT_SHAPE_INSETS); // snap to grid and store the value in the model - orient.setOffset(EditPartLayoutUtils.snapToGrid(orient.getOffset())); + orient.setOffset(SnapToGridUtils.snapToGrid(orient.getOffset())); LayoutDataUtils.setConnectorOffsetOrientation(layouted, orient); } @@ -256,44 +139,46 @@ public class EditPartLayoutUtils { Point position = location.getCopy(); position.translate(-positionOffset, -positionOffset); if (snapToGrid) { - EditPartLayoutUtils.snapToGrid(position); + SnapToGridUtils.snapToGrid(position); } LayoutDataUtils.setNodePosition(layouted, position.x, position.y); } - /** - * Class for storing polar coordinates. - * - * @author wandinger - * @author hummel - * @author $Author$ - * @version $Rev$ - * @levd.rating YELLOW Rev: 519 - */ - public static class Polar { - - /** The angle */ - public double angle; - - /** The distance */ - public double distance; - - /** The constructor */ - public Polar(double angle, double distance) { - this.angle = angle; - this.distance = distance; + /** Returns the bounds rectangle of the connector given its parent bounds. */ + public static Rectangle getAbsoluteConnectorBounds( + ILayoutedModelElement connector, ILayoutedModelElement parent) { + Rectangle result = new Rectangle(0, 0, + DefaultLayoutConstants.DEFAULT_CONNECTOR_SIZE, + DefaultLayoutConstants.DEFAULT_CONNECTOR_SIZE); + + // get orientation + OffsetOrientation orient = LayoutDataUtils + .getConnectorOffsetOrientation(connector); + // get parent size + org.fortiss.tooling.base.model.layout.Dimension parentSize = LayoutDataUtils + .getNodeSize(parent); + org.fortiss.tooling.base.model.layout.Point pos = LayoutDataUtils + .getAbsolute(orient, parentSize, + DefaultLayoutConstants.DEFAULT_SHAPE_INSETS); + int relX = pos.getX(); + int relY = pos.getY(); + org.fortiss.tooling.base.model.layout.Point parentPos = LayoutDataUtils + .getNodePosition(parent); + // fix X coordinate + if (relX > parentSize.getWidth() + - DefaultLayoutConstants.DEFAULT_CONNECTOR_SIZE) { + relX = parentSize.getWidth() + - DefaultLayoutConstants.DEFAULT_CONNECTOR_SIZE; } - - /** Create new polar values from cartesian ones. */ - public Polar(Point pos) { - angle = Math.atan2(pos.y, pos.x); - distance = Math.sqrt(pos.x * pos.x + pos.y * pos.y); + // fix Y coordinate + if (relY > parentSize.getHeight() + - DefaultLayoutConstants.DEFAULT_CONNECTOR_SIZE) { + relY = parentSize.getHeight() + - DefaultLayoutConstants.DEFAULT_CONNECTOR_SIZE; } - /** Returns a cartesian representation. */ - public Point toCartesian() { - return new Point(distance * Math.cos(angle), distance - * Math.sin(angle)); - } + result.x = parentPos.getX() + relX; + result.y = parentPos.getY() + relY; + return result; } } diff --git a/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/layout/util/SnapToGridUtils.java b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/layout/util/SnapToGridUtils.java new file mode 100644 index 000000000..0278a35e9 --- /dev/null +++ b/org.fortiss.tooling.base.ui/trunk/src/org/fortiss/tooling/base/ui/layout/util/SnapToGridUtils.java @@ -0,0 +1,69 @@ +/*--------------------------------------------------------------------------+ +$Id$ +| | +| Copyright 2011 ForTISS GmbH | +| | +| Licensed under the Apache License, Version 2.0 (the "License"); | +| you may not use this file except in compliance with the License. | +| You may obtain a copy of the License at | +| | +| http://www.apache.org/licenses/LICENSE-2.0 | +| | +| Unless required by applicable law or agreed to in writing, software | +| distributed under the License is distributed on an "AS IS" BASIS, | +| WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | +| See the License for the specific language governing permissions and | +| limitations under the License. | ++--------------------------------------------------------------------------*/ +package org.fortiss.tooling.base.ui.layout.util; + +import org.eclipse.draw2d.geometry.Point; +import org.eclipse.gef.GraphicalEditPart; +import org.eclipse.gef.SnapToGrid; +import org.fortiss.tooling.base.ui.layout.constants.DefaultLayoutConstants; + +/** + * Utility methods for snap-to-grid support. + * + * @author hoelzl + * @author $Author$ + * @version $Rev$ + * @ConQAT.Rating YELLOW Hash: 864E908FB1B86BFCA206640785FAB8D0 + */ +public final class SnapToGridUtils { + + /** Returns the given value aligned to the given grid size. */ + public static int snapToGrid(double d, int gridSize) { + return gridSize * (int) Math.round(d / gridSize); + } + + /** Returns the given value aligned to the recommended grid size. */ + public static int snapToGrid(double d) { + return snapToGrid(d, DefaultLayoutConstants.DEFAULT_GRID_SIZE); + } + + /** + * Modifies the x and y coordinates of the given point to be on the grid of + * the given size. + */ + public static void snapToGrid(Point p, int gridSize) { + p.x = snapToGrid(p.x, gridSize); + p.y = snapToGrid(p.y, gridSize); + } + + /** Modifies the x and y coordinates of the given point to be on the grid. */ + public static void snapToGrid(Point p) { + p.x = snapToGrid(p.x, DefaultLayoutConstants.DEFAULT_GRID_SIZE); + p.y = snapToGrid(p.y, DefaultLayoutConstants.DEFAULT_GRID_SIZE); + } + + /** Adapter code for snap to grid feature. */ + public static Object snapToGridAdapter(GraphicalEditPart editPart) { + final Boolean val = (Boolean) editPart.getViewer().getProperty( + SnapToGrid.PROPERTY_GRID_ENABLED); + if (val != null && val.booleanValue()) { + return new SnapToGrid(editPart); + } + return null; + } +} -- GitLab