public static void SelectCompartmentItem(DiagramDocView docView, ModelElement compartmentOwner, string compartmentListName, ModelElement compartmentItem) { var shapeElement = DiagramUtil.GetModelElementFirstShape(compartmentOwner); ElementListCompartment compartment = null; foreach (ShapeElement shape in shapeElement.NestedChildShapes) { if (shape is ElementListCompartment) { if ((shape as ElementListCompartment).Name == compartmentListName) { compartment = (ElementListCompartment)shape; } } } if (compartment != null) { var listField = compartment.ListField; var child = listField.FindFirstChild(compartment, true); while (child != null && !child.RepresentedElements.OfType <ModelElement>().Any(element => element == compartmentItem)) { child = listField.FindNextChild(child, true); } var selectedShapesCollection = docView.CurrentDesigner.Selection; selectedShapesCollection.Clear(); selectedShapesCollection.Set(child); } }
/// <summary> /// Sets the selection state of a shape element that represents the modelElement parameter on the given DiagramView /// </summary> /// <param name="diagramView">Object containing the shape element to select</param> /// <param name="modelElement">Model element the shape represents</param> /// <returns>True if the shape is present, visible and now selected, false otherwise</returns> public static bool SelectModelElement(this DiagramView diagramView, ModelElement modelElement) { // Get the shape element that corresponds to the model element ShapeElement shapeElement = modelElement.GetFirstShapeElement(); if (shapeElement != null) { // Make sure the shape element is visible (because connectors can be hidden) if (!shapeElement.IsVisible) { shapeElement.Show(); } // Create a diagram item for this shape element and select it diagramView.Selection.Set(new DiagramItem(shapeElement)); return(true); } // If the model element does not have a shape, try to cast it IModelElementCompartmented if (modelElement is IModelElementInCompartment compartmentedModelElement && compartmentedModelElement.ParentModelElement is ModelElement parentModelElement) { // Get the compartment that stores the model element ElementListCompartment compartment = parentModelElement.GetCompartment(compartmentedModelElement.CompartmentName); if (compartment == null) { throw new InvalidOperationException($"Can't find compartment {compartmentedModelElement.CompartmentName}"); } // Expand the compartment if (!compartment.IsExpanded) { using (Transaction trans = modelElement.Store.TransactionManager.BeginTransaction("IsExpanded")) { compartment.IsExpanded = true; trans.Commit(); } } // Find the model element in the compartment int index = compartment.Items.IndexOf(modelElement); if (index >= 0) { // Create a diagram item and select it diagramView.Selection.Set(new DiagramItem(compartment, compartment.ListField, new ListItemSubField(index))); return(true); } } return(false); }
public void ShapeInserted <T>(T shape) where T : CompartmentShape, ICompartmentMouseActionTrackable { Debug.Assert(!eventsRegisterd, "The events should only register once."); if (eventsRegisterd) { return; } // register events to the shape shape.MouseMove += Shape_MouseMove; shape.MouseDown += Shape_MouseDown; foreach (DiagramItem x in shape.Children()) { if (x.Shape is ElementListCompartment) { // and events to the compartment lists ElementListCompartment elc = (ElementListCompartment)x.Shape; elc.MouseMove += ElementListCompartment_MouseMove; } } eventsRegisterd = true; }
public static bool SelectModelElement(this DiagramView diagramView, ModelElement modelElement, bool ensureVisible) { // Get the shape element that corresponds to the model element ShapeElement shapeElement = PresentationViewsSubject.GetPresentation(modelElement) .OfType <ShapeElement>() .FirstOrDefault(s => s.Diagram == diagramView.Diagram); if (shapeElement != null) { // Make sure the shape element is visible (because connectors can be hidden) if (!shapeElement.IsVisible) { shapeElement.Show(); } // Create a diagram item for this shape element and select it diagramView.Selection.Set(new DiagramItem(shapeElement)); if (ensureVisible) { diagramView.Selection.EnsureVisible(DiagramClientView.EnsureVisiblePreferences.ScrollIntoViewCenter); diagramView.ZoomAtViewCenter(1); } shapeElement.Invalidate(); return(true); } // If the model element does not have a shape, try to cast it IModelElementCompartment if (modelElement is IModelElementInCompartment compartmentedModelElement) { // Get the parent IModelElementWithCompartments parentModelElement = compartmentedModelElement.ParentModelElement; if (parentModelElement != null) { // Get the compartment that stores the model element CompartmentShape parentShapeElement = PresentationViewsSubject.GetPresentation((ModelElement)parentModelElement) .OfType <CompartmentShape>() .FirstOrDefault(s => s.Diagram == diagramView.Diagram); ElementListCompartment compartment = parentShapeElement?.GetCompartment(compartmentedModelElement.CompartmentName); if (compartment != null) { if (!compartment.IsExpanded) { using (Transaction trans = modelElement.Store.TransactionManager.BeginTransaction("IsExpanded")) { compartment.IsExpanded = true; trans.Commit(); } } // Find the model element in the compartment int index = compartment.Items.IndexOf(modelElement); if (index >= 0) { // Create a diagram item and select it diagramView.Selection.Set(new DiagramItem(compartment, compartment.ListField, new ListItemSubField(index))); if (ensureVisible) { diagramView.Selection.EnsureVisible(DiagramClientView.EnsureVisiblePreferences.ScrollIntoViewCenter); diagramView.ZoomAtViewCenter(1); } compartment.Invalidate(); return(true); } } } } return(false); }
private static void MoveSubFieldSelectionOnOrderChange(ShapeElement parentShape, ElementListCompartment compartment, int oldIndex, int newIndex) { Diagram diagram; DiagramView view; SelectedShapesCollection selection; if (null != (diagram = parentShape.Diagram) && null != (view = diagram.ActiveDiagramView) && null != (selection = view.Selection)) { ShapeField testField = compartment.ListField; foreach (DiagramItem selectedItem in selection) { ListItemSubField testSubField; if (selectedItem.Shape == compartment && selectedItem.Field == testField && null != (testSubField = selectedItem.SubField as ListItemSubField)) { int testRow = testSubField.Row; if (testRow == oldIndex) { testSubField.Row = newIndex; } else { int adjustRow = testRow; if (testRow > oldIndex) { --adjustRow; } if (adjustRow >= newIndex) { ++adjustRow; } if (adjustRow != testRow) { testSubField.Row = adjustRow; } } } } } }
/// <summary> /// Determinates the vertical offset by searching the compartment entries connected by the given connection /// </summary> /// <typeparam name="T">The type of the compartment entry</typeparam> /// <param name="shape">the CompartmentShape</param> /// <param name="connection">the Connection</param> /// <param name="equaler">a delegate to the method to compare compartment entry with the connection</param> /// <returns></returns> protected virtual double GetVerticalOffset <T>(CompartmentShape shape, CONNECTION connection, IsEntryConnectionSourceTarget <T> equaler) where T : class { // the easy case: the header is meant or the shape is not expanded. so no entry must be searched if (!shape.IsExpanded || equaler(null, connection)) { return(shape.DefaultSize.Height / 2); //the half of the height (the height of a CompartmentShape means only the height of the header) } int elementListCompartmentCount = 0; bool entryFound = false; int entryPositionInListCompartment = -1; ElementListCompartment entryParent = null; // take a look at all children of the compartment shape foreach (DiagramItem item in shape.Children()) { // some of the children are ElementListCompartments if (item.Shape is ElementListCompartment) { // we have to count the ElementListCompartments elementListCompartmentCount++; // if we already found the entry and know the count of elementListCompartmentCount we can exit the foreach loop // I only need the information elementListCompartmentCount is == 1 or > 1, the exact count is irrelevant if (entryFound && elementListCompartmentCount > 1) { break; } ElementListCompartment compartmentList = (ElementListCompartment)item.Shape; int entryInList = 0; if (compartmentList.Items != null) { // now, take a look at the compartment entries of the compartment list foreach (object compartmentEntry in compartmentList.Items) { // is this entry of our type? if (compartmentEntry is T) { // finally check if this entry is targeted by the given connection if (equaler((T)compartmentEntry, connection)) { // hey found... :-) entryFound = true; entryParent = compartmentList; entryPositionInListCompartment = entryInList; break; // there is no need to search in this compartmentList any longer (breaks only the inner foreach loop) } // not found: count and next entryInList++; } } } } } if (entryFound) { // from msdn: IsSingleCompartmentHeaderVisible: Gets the compartment shape and checks to see whether the its header is visible (if there is only one header in the compartment). // to determinate if the compartment header is realy visible we need the IsSingleCompartmentHeaderVisible property and the number of compartment headers in this shape bool elementListCompartmentHeaderVisible = elementListCompartmentCount == 1 ? shape.IsSingleCompartmentHeaderVisible : true; int compartmentHeaderOffset = elementListCompartmentHeaderVisible ? 1 : 0; if (entryParent.IsExpanded) { // the entry is visible double singelElementRowHeight = entryParent.BoundingBox.Height / (entryParent.Items.Count + compartmentHeaderOffset); return(entryParent.BoundingBox.Top + singelElementRowHeight * (entryPositionInListCompartment + 0.6 + compartmentHeaderOffset)); } else { // the entry is not visible // so we target the middel of the compartment header return(entryParent.BoundingBox.Top + entryParent.BoundingBox.Height * 0.5); } } // if we come to this point, we cannot find the entry. just return null. :-/ return(0); }