summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJayant Gupta2012-07-22 20:40:07 (EDT)
committer Jayant Gupta2012-08-20 14:49:22 (EDT)
commit9c4538525d003463a4cf00c8e32f6d9d324ce047 (patch)
treefa81eb2d1d139f3fa618bafc7bc83e13f81cd2de
parentaab0e7dbfa4dc0c0c071673686a94b5cc279ab63 (diff)
downloadorg.eclipse.etrice-9c4538525d003463a4cf00c8e32f6d9d324ce047.zip
org.eclipse.etrice-9c4538525d003463a4cf00c8e32f6d9d324ce047.tar.gz
org.eclipse.etrice-9c4538525d003463a4cf00c8e32f6d9d324ce047.tar.bz2
Rebuild on Juno and solved some layout issuesrefs/changes/12/6912/2
1. Port labels corrected. 2. Heuristic for node sizes developed. 3. Context sensitive layout provided. 4. Internal Port Layout improved. 5. Default Layout options set. Change-Id: I1c2eb4bbc39f79d81c39c65c220ac2bc2015cd8d
-rw-r--r--plugins/org.eclipse.etrice.ui.layout/plugin.xml23
-rw-r--r--plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/BehaviorDiagramLayoutManager.java70
-rw-r--r--plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/BehaviorLayoutCommand.java128
-rw-r--r--plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/ETriceDiagramLayoutManager.java181
-rw-r--r--plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/ETriceLayoutCommand.java55
-rw-r--r--plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/StructureDiagramLayoutmanager.java107
-rw-r--r--plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/StructureLayoutCommand.java150
7 files changed, 617 insertions, 97 deletions
diff --git a/plugins/org.eclipse.etrice.ui.layout/plugin.xml b/plugins/org.eclipse.etrice.ui.layout/plugin.xml
index 58435d8..8528c91 100644
--- a/plugins/org.eclipse.etrice.ui.layout/plugin.xml
+++ b/plugins/org.eclipse.etrice.ui.layout/plugin.xml
@@ -12,5 +12,28 @@
priority="1">
</manager>
</extension>
+ <extension
+ point="de.cau.cs.kieler.kiml.layoutInfo">
+ <option
+ class="org.eclipse.etrice.core.room.ActorClass"
+ option="de.cau.cs.kieler.borderSpacing"
+ value="50">
+ </option>
+ <option
+ class="org.eclipse.etrice.core.room.ActorClass"
+ option="de.cau.cs.kieler.spacing"
+ value="50">
+ </option>
+ <option
+ class="org.eclipse.etrice.core.room.StateGraph"
+ option="de.cau.cs.kieler.borderSpacing"
+ value="30">
+ </option>
+ <option
+ class="org.eclipse.etrice.core.room.StateGraph"
+ option="de.cau.cs.kieler.spacing"
+ value="50">
+ </option>
+ </extension>
</plugin>
diff --git a/plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/BehaviorDiagramLayoutManager.java b/plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/BehaviorDiagramLayoutManager.java
index 63329e1..1bb0d29 100644
--- a/plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/BehaviorDiagramLayoutManager.java
+++ b/plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/BehaviorDiagramLayoutManager.java
@@ -23,10 +23,7 @@ import org.eclipse.graphiti.mm.pictograms.Shape;
import org.eclipse.graphiti.ui.internal.parts.IPictogramElementEditPart;
import de.cau.cs.kieler.core.kgraph.KNode;
-import de.cau.cs.kieler.kiml.LayoutContext;
-import de.cau.cs.kieler.kiml.config.VolatileLayoutConfig;
import de.cau.cs.kieler.kiml.graphiti.KimlGraphitiUtil;
-import de.cau.cs.kieler.kiml.options.LayoutOptions;
import de.cau.cs.kieler.kiml.ui.diagram.LayoutMapping;
import de.cau.cs.kieler.kiml.util.KimlUtil;
@@ -79,16 +76,42 @@ public class BehaviorDiagramLayoutManager extends ETriceDiagramLayoutManager {
}
- /** the fixed minimal height of nodes. */
- public static final float MIN_HEIGHT = StateSupport.DEFAULT_SIZE_Y;
- /** the fixed minimal width of shapes. */
- public static final float MIN_WIDHT = StateSupport.DEFAULT_SIZE_X;
+ @Override
+ protected Size getDefaultSize(Shape shape) {
+ Size defaultSize = new Size();
+
+ // This code sets same minimal default size for both State Graph and
+ // State
+ defaultSize.setHeight(StateSupport.MIN_SIZE_Y);
+ defaultSize.setWidth(StateSupport.MIN_SIZE_X);
+
+ /*
+ * This code sets default size differently for Actor Class and Actor Container
+ * Refs. This keeps the top-level container quite large on layout, which
+ * might not seem so pleasant, but is more closer to the model.
+ */
+ /*
+ EObject modelObject = shape.getLink().getBusinessObjects().get(0);
+ if (modelObject instanceof StateGraph) {
+ defaultSize.setHeight(StateGraphSupport.DEFAULT_SIZE_Y);
+ defaultSize.setWidth(StateGraphSupport.DEFAULT_SIZE_X);
+ } else if (modelObject instanceof State) {
+ defaultSize.setHeight(StateSupport.MIN_SIZE_Y);
+ defaultSize.setWidth(StateSupport.MIN_SIZE_X);
+ } else {
+ defaultSize.setHeight(MIN_HEIGHT);
+ defaultSize.setWidth(MIN_WIDHT);
+ }*/
+
+ return defaultSize;
+ }
/**
* {@inheritDoc}
*
* @author jayant
*/
+ @Override
protected KNode createNode(final LayoutMapping<PictogramElement> mapping,
final KNode parentNode, final Shape shape) {
KNode node = KimlUtil.createInitializedNode();
@@ -96,15 +119,6 @@ public class BehaviorDiagramLayoutManager extends ETriceDiagramLayoutManager {
setCurrentPositionAndSize(mapping, parentNode, node, shape);
- VolatileLayoutConfig staticConfig = mapping
- .getProperty(KimlGraphitiUtil.STATIC_CONFIG);
- // FIXME find a way to specify the minimal size dynamically
-
- staticConfig.setValue(LayoutOptions.MIN_WIDTH, node,
- LayoutContext.GRAPH_ELEM, MIN_WIDHT);
- staticConfig.setValue(LayoutOptions.MIN_HEIGHT, node,
- LayoutContext.GRAPH_ELEM, MIN_HEIGHT);
-
mapping.getGraphMap().put(node, shape);
// gather all connections directly connected to the Node (not the
@@ -118,33 +132,45 @@ public class BehaviorDiagramLayoutManager extends ETriceDiagramLayoutManager {
return node;
}
-
-
/**
* {@inheritDoc}
*
* @author jayant
*/
@Override
- protected boolean isPort(Shape shape) {
+ public boolean isBoundaryPort(Shape shape) {
EObject modelObject = shape.getLink().getBusinessObjects().get(0);
if (modelObject instanceof TrPoint)
return true;
-
+
return false;
}
+
/**
* {@inheritDoc}
*
* @author jayant
*/
@Override
- protected boolean isTopLevelBoundingBox(Shape shape) {
+ public boolean isInternalPort(Shape shape) {
+ //No shape is an internal port (i.e. All ports are external only)
+ return false;
+ }
+
+ /**
+ * {@inheritDoc}
+ *
+ * @author jayant
+ */
+ @Override
+ public boolean isTopLevelBoundingBox(Shape shape) {
EObject modelObject = shape.getLink().getBusinessObjects().get(0);
if (modelObject instanceof StateGraph)
return true;
-
+
return false;
}
+
+
}
diff --git a/plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/BehaviorLayoutCommand.java b/plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/BehaviorLayoutCommand.java
new file mode 100644
index 0000000..26ee581
--- /dev/null
+++ b/plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/BehaviorLayoutCommand.java
@@ -0,0 +1,128 @@
+package org.eclipse.etrice.ui.layout;
+
+import org.eclipse.emf.ecore.EObject;
+import org.eclipse.emf.transaction.TransactionalEditingDomain;
+import org.eclipse.etrice.core.room.State;
+import org.eclipse.etrice.ui.behavior.support.TrPointSupport;
+import org.eclipse.graphiti.features.IFeatureProvider;
+import org.eclipse.graphiti.features.context.impl.LayoutContext;
+import org.eclipse.graphiti.mm.algorithms.GraphicsAlgorithm;
+import org.eclipse.graphiti.mm.algorithms.Text;
+import org.eclipse.graphiti.mm.algorithms.styles.Orientation;
+import org.eclipse.graphiti.mm.pictograms.Anchor;
+import org.eclipse.graphiti.mm.pictograms.ContainerShape;
+import org.eclipse.graphiti.mm.pictograms.PictogramElement;
+import org.eclipse.graphiti.services.Graphiti;
+import org.eclipse.graphiti.services.IGaService;
+
+import de.cau.cs.kieler.core.kgraph.KNode;
+import de.cau.cs.kieler.core.kgraph.KPort;
+
+public class BehaviorLayoutCommand extends ETriceLayoutCommand {
+
+ public BehaviorLayoutCommand(TransactionalEditingDomain domain,
+ IFeatureProvider thefeatureProvider) {
+ super(domain, thefeatureProvider);
+ // TODO Auto-generated constructor stub
+ }
+
+ /**
+ * {@inheritDoc}
+ *
+ * @author jayant
+ */
+ @Override
+ protected void applyNodeLayout(KNode knode, PictogramElement pelem) {
+ setCalculatedPositionAndSize(knode, knode.getParent(),
+ (ContainerShape) pelem);
+
+ getFeatureProvider().layoutIfPossible(new LayoutContext(pelem));
+
+ };
+
+ /**
+ * {@inheritDoc}
+ *
+ * @author jayant
+ */
+ @Override
+ protected void applyPortLayout(KPort kport, PictogramElement pelem) {
+
+ ContainerShape shape = (ContainerShape) ((Anchor) pelem).getParent();
+
+ setCalculatedPositionAndSize(kport, kport.getNode(), shape);
+
+ GraphicsAlgorithm ga = shape.getGraphicsAlgorithm();
+ EObject bo = shape.getContainer().getLink().getBusinessObjects().get(0);
+
+ // margin and size for bounding box (State Graph)
+ int margin = TrPointSupport.MARGIN;
+ int size = TrPointSupport.ITEM_SIZE;
+
+ if (bo instanceof State) {
+ // margin and size for a State
+ margin = TrPointSupport.MARGIN_SMALL;
+ size = TrPointSupport.ITEM_SIZE_SMALL;
+ }
+
+ Text label = (Text) (shape.getChildren().get(0).getGraphicsAlgorithm());
+
+ adjustLabel(label, ga.getX(), ga.getY(), ga.getWidth(), margin, size);
+
+ getFeatureProvider().layoutIfPossible(new LayoutContext(shape));
+
+ }
+
+ /**
+ * Sets correct port label position depending on the corresponding port
+ * position.
+ *
+ * @param label
+ * Text Graphics Algorithm to be placed
+ * @param x
+ * The x coordinate of the containing shape
+ * @param y
+ * The y coordinate of the containing shape
+ * @param width
+ * The width of the containing shape
+ * @param margin
+ * The margin of the containing shape
+ * @param size
+ * The size(length/width) of the port's visible graphics
+ * algorithm
+ *
+ */
+ /*
+ * This method has been copied from TrPointSuppot.FeatureProvider class
+ * since its visibility is not public there
+ */
+ private static void adjustLabel(Text label, int x, int y, int width,
+ int margin, int size) {
+ Orientation halign = Orientation.ALIGNMENT_CENTER;
+ Orientation valign = Orientation.ALIGNMENT_CENTER;
+
+ int pos = 0;
+
+ if (x <= margin)
+ halign = Orientation.ALIGNMENT_LEFT;
+ else if ((width - margin) <= x)
+ halign = Orientation.ALIGNMENT_RIGHT;
+ if (y <= margin) {
+ pos = 0;
+ valign = Orientation.ALIGNMENT_BOTTOM;
+ } else {
+ pos = 5 * margin / 4;
+ valign = Orientation.ALIGNMENT_TOP;
+ }
+
+ label.setHorizontalAlignment(halign);
+ label.setVerticalAlignment(valign);
+
+ if (pos != label.getY()) {
+ IGaService gaService = Graphiti.getGaService();
+ gaService.setLocationAndSize(label, 0, pos, 2 * margin,
+ 3 * margin / 4);
+ }
+ }
+
+}
diff --git a/plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/ETriceDiagramLayoutManager.java b/plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/ETriceDiagramLayoutManager.java
index a5a83b7..9cf2a5f 100644
--- a/plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/ETriceDiagramLayoutManager.java
+++ b/plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/ETriceDiagramLayoutManager.java
@@ -18,6 +18,7 @@ import java.util.Map.Entry;
import org.eclipse.core.runtime.IAdaptable;
import org.eclipse.emf.ecore.EObject;
import org.eclipse.emf.transaction.TransactionalEditingDomain;
+import org.eclipse.etrice.ui.behavior.editor.BehaviorEditor;
import org.eclipse.etrice.ui.common.editor.RoomDiagramEditor;
import org.eclipse.gef.EditPart;
import org.eclipse.graphiti.mm.algorithms.AbstractText;
@@ -50,6 +51,7 @@ import de.cau.cs.kieler.kiml.graphiti.KimlGraphitiUtil;
import de.cau.cs.kieler.kiml.klayoutdata.KInsets;
import de.cau.cs.kieler.kiml.klayoutdata.KShapeLayout;
import de.cau.cs.kieler.kiml.klayoutdata.impl.KShapeLayoutImpl;
+import de.cau.cs.kieler.kiml.options.LayoutOptions;
import de.cau.cs.kieler.kiml.ui.diagram.LayoutMapping;
import de.cau.cs.kieler.kiml.util.KimlUtil;
@@ -153,9 +155,19 @@ public abstract class ETriceDiagramLayoutManager extends
protected void transferLayout(final LayoutMapping<PictogramElement> mapping) {
DiagramEditor diagramEditor = mapping
.getProperty(KimlGraphitiUtil.DIAGRAM_EDITOR);
- ETriceLayoutCommand command = new ETriceLayoutCommand(
- diagramEditor.getEditingDomain(), diagramEditor
- .getDiagramTypeProvider().getFeatureProvider());
+
+ ETriceLayoutCommand command = null;
+
+ if (diagramEditor instanceof BehaviorEditor) {
+ command = new BehaviorLayoutCommand(
+ diagramEditor.getEditingDomain(), diagramEditor
+ .getDiagramTypeProvider().getFeatureProvider());
+ } else {
+ command = new StructureLayoutCommand(
+ diagramEditor.getEditingDomain(), diagramEditor
+ .getDiagramTypeProvider().getFeatureProvider());
+ }
+
for (Entry<KGraphElement, PictogramElement> entry : mapping
.getGraphMap().entrySet()) {
command.add(entry.getKey(), entry.getValue());
@@ -231,15 +243,17 @@ public abstract class ETriceDiagramLayoutManager extends
} else if (element instanceof Shape) {
- if ( isTopLevelBoundingBox( (Shape)element) ) {
+ if (isTopLevelBoundingBox((Shape) element)) {
// The selected Element is the Top Level Top Level Bounding Box
mapping.setLayoutGraph((KNode) buildAllLevels(mapping,
(Shape) element, null));
} else {
+
KGraphElement internalKGraphElement = createKGaphElementFromShape(
mapping, null, (Shape) element);
- if (internalKGraphElement instanceof KNode) {
+ if (internalKGraphElement instanceof KNode
+ && !isInternalPort((Shape) element)) {
// The selected Element is a Node.
for (Shape childShape : ((ContainerShape) element)
.getChildren()) {
@@ -247,15 +261,16 @@ public abstract class ETriceDiagramLayoutManager extends
createKGaphElementFromShape(mapping,
internalKGraphElement, childShape);
}
-
+
mapping.setLayoutGraph((KNode) internalKGraphElement);
-
+
} else {
- // The selected Element is a Port or an Edge Label.
+ // The selected Element is a Port(Boundary or Internal) or an Edge Label.
// Giving the user a SWT dialog indicating that this Shape
// cannot be lay-outed.
- Shell shell = PlatformUI.getWorkbench().getActiveWorkbenchWindow().getShell();
+ Shell shell = PlatformUI.getWorkbench()
+ .getActiveWorkbenchWindow().getShell();
MessageBox dialog = new MessageBox(shell, SWT.ICON_ERROR
| SWT.OK | SWT.CANCEL);
dialog.setText("Invalid Layout Call");
@@ -266,7 +281,8 @@ public abstract class ETriceDiagramLayoutManager extends
}
} else if (element instanceof FreeFormConnection) {
- // This gives the user a SWT dialog indicating this is a connection and
+ // This gives the user a SWT dialog indicating this is a connection
+ // and
// cannot be lay-outed.
Shell shell = PlatformUI.getWorkbench().getActiveWorkbenchWindow()
.getShell();
@@ -340,9 +356,19 @@ public abstract class ETriceDiagramLayoutManager extends
createKGaphElementFromShape(mapping,
secondLevelKGraphElement, thirdLevelShape);
}
+
+ if (!isInternalPort(secondtLevelShape)) {
+ // For KNodes which are not internal ports.
+ setNodeLayoutOptions(mapping,
+ (KNode) secondLevelKGraphElement, secondtLevelShape);
+ }
+
}
}
+ setNodeLayoutOptions(mapping, topLevelBoundingBoxNode,
+ topLevelBoundingBox);
+
return topLevelBoundingBoxNode;
}
@@ -382,12 +408,13 @@ public abstract class ETriceDiagramLayoutManager extends
else if (shape instanceof ContainerShape) {
- // Checking whether this shape is a Port
- if (isPort(shape))
+ // Checking whether this shape is a boundary port
+ if (isBoundaryPort(shape))
return createPort(mapping, (KNode) parent, shape);
else
- // This shape is a node
+ // This shape is considered to be a node (includes internal
+ // Ports)
return createNode(mapping, (KNode) parent, shape);
} else
@@ -395,9 +422,15 @@ public abstract class ETriceDiagramLayoutManager extends
}
/**
- * {@inheritDoc}
+ * Create a node for the layout graph.
*
- * @author jayant
+ * @param mapping
+ * the mapping of pictogram elements to graph elements
+ * @param parentNode
+ * the parent node
+ * @param shape
+ * the shape for a new node
+ * @return a new layout node
*/
protected abstract KNode createNode(
final LayoutMapping<PictogramElement> mapping,
@@ -504,23 +537,131 @@ public abstract class ETriceDiagramLayoutManager extends
}
/**
- * Determines whether the given shape is a port.
+ * Sets the heuristic layout options for nodes (like minimal width and
+ * minimal height)
+ *
+ * @param mapping
+ * the mapping of pictogram elements to graph elements
+ * @param node
+ * the node for which layout options need to be set
+ * @param shape
+ * TODO
+ * @author jayant
+ */
+ /* This is fairly general for both the eTrice editors */
+ protected void setNodeLayoutOptions(
+ final LayoutMapping<PictogramElement> mapping, final KNode node,
+ Shape shape) {
+
+ // get label width and height for the node
+ float labelWidth = 0.0f;
+ float labelHeight = 0.0f;
+
+ if (!node.getLabels().isEmpty()) {
+ KShapeLayout labelLayout = node.getLabels().get(0)
+ .getData(KShapeLayout.class);
+ labelWidth = labelLayout.getWidth();
+ labelHeight = labelLayout.getHeight();
+ }
+
+ VolatileLayoutConfig staticConfig = mapping
+ .getProperty(KimlGraphitiUtil.STATIC_CONFIG);
+
+ Size defaultSize = getDefaultSize(shape);
+ staticConfig.setValue(LayoutOptions.MIN_WIDTH, node,
+ LayoutContext.GRAPH_ELEM, defaultSize.getWidth() + labelWidth);
+ staticConfig
+ .setValue(LayoutOptions.MIN_HEIGHT, node,
+ LayoutContext.GRAPH_ELEM, defaultSize.getHeight()
+ + labelHeight);
+ }
+
+ public static class Size {
+ private float width = 0;
+ private float height = 0;
+
+ /**
+ * Getter for width
+ *
+ * @return the width
+ */
+ public float getWidth() {
+ return width;
+ }
+
+ /**
+ * Setter for width
+ *
+ * @param width
+ * the width to set
+ */
+ public void setWidth(float width) {
+ this.width = width;
+ }
+
+ /**
+ * Getter for height
+ *
+ * @return the height
+ */
+ public float getHeight() {
+ return height;
+ }
+
+ /**
+ * Setter for height
+ *
+ * @param height
+ * the height to set
+ */
+ public void setHeight(float height) {
+ this.height = height;
+ }
+ }
+
+ /**
+ * Determines whether the given shape is a boundary port or not.
*
- * @param shape the shape to be investigated
+ * @param shape
+ * the shape to be investigated
* @return true if the {@code shape} is a port else false
*
* @author jayant
*/
- protected abstract boolean isPort(Shape shape);
+ public abstract boolean isBoundaryPort(Shape shape);
+
+ /**
+ * Determines whether the given shape is an internal port or not.
+ *
+ * @param shape
+ * the shape to be investigated
+ * @return true if the {@code shape} is a port else false
+ *
+ * @author jayant
+ */
+ public abstract boolean isInternalPort(Shape shape);
/**
* Determines whether the given shape is a Top Level Bounding Box or not.
*
- * @param shape the shape to be investigated
+ * @param shape
+ * the shape to be investigated
* @return true if the {@code shape} is the Top Level Bounding Box
*
* @author jayant
*/
- protected abstract boolean isTopLevelBoundingBox(Shape shape);
+ public abstract boolean isTopLevelBoundingBox(Shape shape);
+
+ /**
+ * Gets the Default Minimal Width for a node
+ *
+ * @param shape
+ * TODO
+ *
+ * @return the defaults minimal width a node
+ *
+ * @author jayant
+ */
+ protected abstract Size getDefaultSize(Shape shape);
}
diff --git a/plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/ETriceLayoutCommand.java b/plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/ETriceLayoutCommand.java
index c09dabf..5d33d8a 100644
--- a/plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/ETriceLayoutCommand.java
+++ b/plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/ETriceLayoutCommand.java
@@ -15,14 +15,13 @@ import java.util.List;
import org.eclipse.emf.transaction.TransactionalEditingDomain;
import org.eclipse.graphiti.features.IFeatureProvider;
-import org.eclipse.graphiti.features.context.impl.LayoutContext;
import org.eclipse.graphiti.mm.algorithms.GraphicsAlgorithm;
import org.eclipse.graphiti.mm.algorithms.styles.Point;
-import org.eclipse.graphiti.mm.pictograms.Anchor;
import org.eclipse.graphiti.mm.pictograms.ContainerShape;
import org.eclipse.graphiti.mm.pictograms.FreeFormConnection;
import org.eclipse.graphiti.mm.pictograms.PictogramElement;
import org.eclipse.graphiti.services.Graphiti;
+import org.eclipse.graphiti.services.IGaService;
import de.cau.cs.kieler.core.kgraph.KEdge;
import de.cau.cs.kieler.core.kgraph.KGraphElement;
@@ -40,7 +39,7 @@ import de.cau.cs.kieler.kiml.klayoutdata.KShapeLayout;
*
* @author jayant
*/
-public class ETriceLayoutCommand extends GraphitiLayoutCommand {
+public abstract class ETriceLayoutCommand extends GraphitiLayoutCommand {
public ETriceLayoutCommand(TransactionalEditingDomain domain,
IFeatureProvider thefeatureProvider) {
@@ -48,30 +47,21 @@ public class ETriceLayoutCommand extends GraphitiLayoutCommand {
}
/**
- * {@inheritDoc}
+ * {@inheritDoc} Also responsible for the layout of internal ports in eTrice
+ * (which are considered as KNodes)
*
* @author jayant
*/
@Override
- protected void applyPortLayout(KPort kport, PictogramElement pelem) {
-
- ContainerShape shape = (ContainerShape) ((Anchor) pelem).getParent();
-
- setCalculatedPositionAndSize(kport, kport.getNode(), shape);
- };
+ protected abstract void applyNodeLayout(KNode knode, PictogramElement pelem);
/**
- * {@inheritDoc}
+ * {@inheritDoc} Only Boundary Ports are lay-outed by this method
*
* @author jayant
*/
@Override
- protected void applyNodeLayout(KNode knode, PictogramElement pelem) {
-
- setCalculatedPositionAndSize(knode, knode.getParent(),
- (ContainerShape) pelem);
-
- };
+ protected abstract void applyPortLayout(KPort kport, PictogramElement pelem);
/**
* {@inheritDoc}
@@ -112,8 +102,8 @@ public class ETriceLayoutCommand extends GraphitiLayoutCommand {
}
/**
- * Sets the calculated position and size from a KGraph Model-Element (Node or
- * Port) back to the corresponding diagram shape.
+ * Sets the calculated position and size from a KGraph Model-Element (Node
+ * or Port) back to the corresponding diagram shape.
*
* @param kelem
* the KGraph Model Element (Node/Port)
@@ -124,11 +114,7 @@ public class ETriceLayoutCommand extends GraphitiLayoutCommand {
*
* @author jayant
*/
- /*
- * This function derives its code majorly from
- * GraphitilayoutCommand.applyNodeLayout() method
- */
- private void setCalculatedPositionAndSize(final KGraphElement kelem,
+ public static void setCalculatedPositionAndSize(final KGraphElement kelem,
KNode parentNode, final ContainerShape shape) {
KShapeLayout shapeLayout = kelem.getData(KShapeLayout.class);
@@ -147,21 +133,20 @@ public class ETriceLayoutCommand extends GraphitiLayoutCommand {
float width = shapeLayout.getWidth();
float height = shapeLayout.getHeight();
- KInsets nodeInsets = shapeLayout.getProperty(INVIS_INSETS);
- if (nodeInsets != null) {
- xpos -= nodeInsets.getLeft();
- ypos -= nodeInsets.getTop();
- width += nodeInsets.getLeft() + nodeInsets.getRight();
- height += nodeInsets.getTop() + nodeInsets.getBottom();
+ KInsets shapeInsets = shapeLayout.getProperty(INVIS_INSETS);
+ if (shapeInsets != null) {
+ xpos -= shapeInsets.getLeft();
+ ypos -= shapeInsets.getTop();
+ width += shapeInsets.getLeft() + shapeInsets.getRight();
+ height += shapeInsets.getTop() + shapeInsets.getBottom();
}
GraphicsAlgorithm ga = shape.getGraphicsAlgorithm();
- ga.setX(Math.round(xpos));
- ga.setY(Math.round(ypos));
- ga.setWidth(Math.round(width));
- ga.setHeight(Math.round(height));
+ IGaService gaService = Graphiti.getGaService();
+ gaService.setLocationAndSize(ga, Math.round(xpos), Math.round(ypos),
+ Math.round(width), Math.round(height));
- featureProvider.layoutIfPossible(new LayoutContext(shape));
}
+
}
diff --git a/plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/StructureDiagramLayoutmanager.java b/plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/StructureDiagramLayoutmanager.java
index 5dd544f..63a1976 100644
--- a/plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/StructureDiagramLayoutmanager.java
+++ b/plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/StructureDiagramLayoutmanager.java
@@ -12,21 +12,22 @@ package org.eclipse.etrice.ui.layout;
import org.eclipse.emf.ecore.EObject;
import org.eclipse.etrice.core.room.ActorClass;
+import org.eclipse.etrice.core.room.ActorContainerClass;
import org.eclipse.etrice.core.room.InterfaceItem;
+import org.eclipse.etrice.core.room.Port;
import org.eclipse.etrice.core.room.SAPoint;
+import org.eclipse.etrice.core.room.SPPRef;
import org.eclipse.etrice.core.room.SPPoint;
import org.eclipse.etrice.ui.structure.editor.StructureEditor;
import org.eclipse.etrice.ui.structure.support.ActorContainerRefSupport;
+import org.eclipse.graphiti.mm.pictograms.Anchor;
import org.eclipse.graphiti.mm.pictograms.Diagram;
import org.eclipse.graphiti.mm.pictograms.PictogramElement;
import org.eclipse.graphiti.mm.pictograms.Shape;
import org.eclipse.graphiti.ui.internal.parts.IPictogramElementEditPart;
import de.cau.cs.kieler.core.kgraph.KNode;
-import de.cau.cs.kieler.kiml.LayoutContext;
-import de.cau.cs.kieler.kiml.config.VolatileLayoutConfig;
import de.cau.cs.kieler.kiml.graphiti.KimlGraphitiUtil;
-import de.cau.cs.kieler.kiml.options.LayoutOptions;
import de.cau.cs.kieler.kiml.ui.diagram.LayoutMapping;
import de.cau.cs.kieler.kiml.util.KimlUtil;
@@ -70,16 +71,43 @@ public class StructureDiagramLayoutmanager extends ETriceDiagramLayoutManager {
}
}
- /** the fixed minimal height of nodes. */
- public static final float MIN_HEIGHT = ActorContainerRefSupport.DEFAULT_SIZE_Y;
- /** the fixed minimal width of shapes. */
- public static final float MIN_WIDHT = ActorContainerRefSupport.DEFAULT_SIZE_X;
+ @Override
+ protected Size getDefaultSize(Shape shape) {
+ Size defaultSize = new Size();
+
+ // This code sets same minimal default size for both Actor Class and
+ // Actor Container Ref
+ defaultSize.setHeight(ActorContainerRefSupport.MIN_SIZE_Y);
+ defaultSize.setWidth(ActorContainerRefSupport.MIN_SIZE_X);
+
+
+ /*
+ * This code sets default size differently for Actor Class and Actor Container
+ * Refs. This keeps the top-level container quite large on layout, which
+ * might not seem so pleasant, but is more closer to the model.
+ */
+ /*
+ EObject modelObject = shape.getLink().getBusinessObjects().get(0);
+ if (modelObject instanceof ActorClass) {
+ defaultSize.setHeight(StructureClassSupport.DEFAULT_SIZE_Y);
+ defaultSize.setWidth(StructureClassSupport.DEFAULT_SIZE_X);
+ } else if (modelObject instanceof ActorContainerRef) {
+ defaultSize.setHeight(ActorContainerRefSupport.MIN_SIZE_Y);
+ defaultSize.setWidth(ActorContainerRefSupport.MIN_SIZE_X);
+ } else {
+ defaultSize.setHeight(MIN_HEIGHT);
+ defaultSize.setWidth(MIN_WIDHT);
+ }*/
+
+ return defaultSize;
+ }
/**
* {@inheritDoc}
*
* @author jayant
*/
+ @Override
protected KNode createNode(final LayoutMapping<PictogramElement> mapping,
final KNode parentNode, final Shape shape) {
KNode node = KimlUtil.createInitializedNode();
@@ -87,17 +115,16 @@ public class StructureDiagramLayoutmanager extends ETriceDiagramLayoutManager {
setCurrentPositionAndSize(mapping, parentNode, node, shape);
- VolatileLayoutConfig staticConfig = mapping
- .getProperty(KimlGraphitiUtil.STATIC_CONFIG);
- // FIXME find a way to specify the minimal size dynamically
-
- staticConfig.setValue(LayoutOptions.MIN_WIDTH, node,
- LayoutContext.GRAPH_ELEM, MIN_WIDHT);
- staticConfig.setValue(LayoutOptions.MIN_HEIGHT, node,
- LayoutContext.GRAPH_ELEM, MIN_HEIGHT);
-
mapping.getGraphMap().put(node, shape);
+ // gather all connections connected to Internal ports in the diagram.
+ // It is of no use to ActorRefs as they do-not possess direct
+ // connection(They have all connections via port).
+ for (Anchor anchor : shape.getAnchors()) {
+ mapping.getProperty(KimlGraphitiUtil.CONNECTIONS).addAll(
+ anchor.getOutgoingConnections());
+ }
+
return node;
}
@@ -107,11 +134,11 @@ public class StructureDiagramLayoutmanager extends ETriceDiagramLayoutManager {
* @author jayant
*/
@Override
- protected boolean isPort(Shape shape) {
+ public boolean isBoundaryPort(Shape shape) {
EObject modelObject = shape.getLink().getBusinessObjects().get(0);
- if (modelObject instanceof InterfaceItem
+ if ((modelObject instanceof InterfaceItem && !isInternal((InterfaceItem) modelObject))
|| modelObject instanceof SPPoint
- || modelObject instanceof SAPoint)
+ || modelObject instanceof SAPoint)
return true;
return false;
@@ -123,7 +150,47 @@ public class StructureDiagramLayoutmanager extends ETriceDiagramLayoutManager {
* @author jayant
*/
@Override
- protected boolean isTopLevelBoundingBox(Shape shape) {
+ public boolean isInternalPort(Shape shape) {
+ EObject modelObject = shape.getLink().getBusinessObjects().get(0);
+
+ if ((modelObject instanceof InterfaceItem && isInternal((InterfaceItem) modelObject)))
+ return true;
+
+ return false;
+ }
+
+ /*
+ * This method has been derived from
+ * org.eclipse.eTrice.ui.structure.InterfaceItem.FeatureProvider
+ */
+ private static boolean isInternal(InterfaceItem item) {
+ if (item instanceof Port) {
+ Port port = (Port) item;
+
+ // NB: the port's container might be a base class of the depicted
+ // actor class
+ ActorContainerClass acc = (ActorContainerClass) port.eContainer();
+ if (acc instanceof ActorClass) {
+ ActorClass ac = (ActorClass) acc;
+ if (ac.getIntPorts().contains(port))
+ return true;
+ }
+ } else if (item instanceof SPPRef) {
+ return false;
+ } else {
+ assert (false) : "unexpected sub type";
+ }
+
+ return false;
+ }
+
+ /**
+ * {@inheritDoc}
+ *
+ * @author jayant
+ */
+ @Override
+ public boolean isTopLevelBoundingBox(Shape shape) {
EObject modelObject = shape.getLink().getBusinessObjects().get(0);
if (modelObject instanceof ActorClass)
return true;
diff --git a/plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/StructureLayoutCommand.java b/plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/StructureLayoutCommand.java
new file mode 100644
index 0000000..f3f4dde
--- /dev/null
+++ b/plugins/org.eclipse.etrice.ui.layout/src/org/eclipse/etrice/ui/layout/StructureLayoutCommand.java
@@ -0,0 +1,150 @@
+package org.eclipse.etrice.ui.layout;
+
+import org.eclipse.emf.ecore.EObject;
+import org.eclipse.emf.transaction.TransactionalEditingDomain;
+import org.eclipse.etrice.core.room.ActorContainerRef;
+import org.eclipse.etrice.core.room.InterfaceItem;
+import org.eclipse.etrice.ui.structure.support.InterfaceItemSupport;
+import org.eclipse.graphiti.features.IFeatureProvider;
+import org.eclipse.graphiti.features.context.impl.LayoutContext;
+import org.eclipse.graphiti.mm.algorithms.GraphicsAlgorithm;
+import org.eclipse.graphiti.mm.algorithms.Text;
+import org.eclipse.graphiti.mm.algorithms.styles.Orientation;
+import org.eclipse.graphiti.mm.pictograms.Anchor;
+import org.eclipse.graphiti.mm.pictograms.ContainerShape;
+import org.eclipse.graphiti.mm.pictograms.PictogramElement;
+import org.eclipse.graphiti.services.Graphiti;
+import org.eclipse.graphiti.services.IGaService;
+
+import de.cau.cs.kieler.core.kgraph.KNode;
+import de.cau.cs.kieler.core.kgraph.KPort;
+
+public class StructureLayoutCommand extends ETriceLayoutCommand {
+
+ public StructureLayoutCommand(TransactionalEditingDomain domain,
+ IFeatureProvider thefeatureProvider) {
+ super(domain, thefeatureProvider);
+ }
+
+ /**
+ * {@inheritDoc}
+ *
+ * @author jayant
+ */
+ @Override
+ protected void applyNodeLayout(KNode knode, PictogramElement pelem) {
+
+ setCalculatedPositionAndSize(knode, knode.getParent(),
+ (ContainerShape) pelem);
+
+ // Checking whether this node corresponds to an internal port or
+ // ActorContainerRef
+ EObject modelObject = pelem.getLink().getBusinessObjects().get(0);
+ if (modelObject instanceof InterfaceItem) {
+ // adjust label for internal port
+ adjustLabelForPort((ContainerShape) pelem);
+ }
+
+ getFeatureProvider().layoutIfPossible(new LayoutContext(pelem));
+
+ };
+
+ /**
+ * {@inheritDoc}
+ *
+ * @author jayant
+ */
+ @Override
+ protected void applyPortLayout(KPort kport, PictogramElement pelem) {
+
+ ContainerShape shape = (ContainerShape) ((Anchor) pelem).getParent();
+
+ setCalculatedPositionAndSize(kport, kport.getNode(), shape);
+
+ // adjust label for this (boundary)port
+ adjustLabelForPort(shape);
+
+ getFeatureProvider().layoutIfPossible(new LayoutContext(shape));
+ }
+
+ /**
+ * Extracts relevant information and delegates it to
+ * {@link #adjustLabel(Text, int, int, int, int, int)} for proper adjustment
+ * of port label
+ *
+ * @param shape
+ * the Shape for the port
+ *
+ * @author jayant
+ */
+ private static void adjustLabelForPort(ContainerShape shape) {
+ GraphicsAlgorithm ga = shape.getGraphicsAlgorithm();
+ EObject boContainer = shape.getContainer().getLink().getBusinessObjects().get(0);
+
+ // First make sure that the shape corresponds to a Port
+ EObject bo = shape.getLink().getBusinessObjects().get(0);
+ if ( bo instanceof InterfaceItem) {
+ // margin and size for bounding box (ActorClass )
+ int margin = InterfaceItemSupport.MARGIN;
+ int size = InterfaceItemSupport.ITEM_SIZE;
+
+ if (boContainer instanceof ActorContainerRef) {
+ // margin and size for ActorContainerRef
+ margin = InterfaceItemSupport.MARGIN_SMALL;
+ size = InterfaceItemSupport.ITEM_SIZE_SMALL;
+ }
+
+ Text label = (Text) (shape.getChildren().get(0)
+ .getGraphicsAlgorithm());
+
+ adjustLabel(label, ga.getX(), ga.getY(), ga.getWidth(), margin,
+ size);
+ }
+ };
+
+ /**
+ * Sets correct port label position depending on the corresponding port
+ * position.
+ *
+ * @param label
+ * Text Graphics Algorithm to be placed
+ * @param x
+ * The x coordinate of the containing shape
+ * @param y
+ * The y coordinate of the containing shape
+ * @param width
+ * The width of the containing shape
+ * @param margin
+ * The margin of the containing shape
+ * @param size
+ * The size(length/width) of the port's visible graphics
+ * algorithm
+ *
+ */
+ /*
+ * This method has been copied from InterfaceItemSuppot.FeatureProvider
+ * class since its visibility is not public there
+ */
+ private static void adjustLabel(Text label, int x, int y, int width,
+ int margin, int size) {
+ Orientation align = Orientation.ALIGNMENT_CENTER;
+ label.setHorizontalAlignment(align);
+
+ int pos = margin + size / 2;
+
+ if (x <= margin)
+ align = Orientation.ALIGNMENT_LEFT;
+ else if ((width - margin) <= x)
+ align = Orientation.ALIGNMENT_RIGHT;
+ if (y <= margin)
+ pos = (margin - size) / 2;
+
+ if (align != label.getHorizontalAlignment()) {
+ label.setHorizontalAlignment(align);
+ }
+ if (pos != label.getY()) {
+ IGaService gaService = Graphiti.getGaService();
+ gaService.setLocationAndSize(label, 0, pos, 2 * margin, margin / 2);
+ }
+ }
+}