//Calls the Line routing algorithm and populates the points collection of the connector. void RoutePolyLine(Connector connector) { Point[] pts = ConnectorRouter.Route(this, FreeFormPanel.GetSourceConnectionPoint(connector), FreeFormPanel.GetDestinationConnectionPoint(connector)); List<Point> points = new List<Point>(pts); if (pts != null) { UpdateConnectorPoints(connector, points); } }
internal ConnectorCreationResult CreateConnectorGesture(ConnectionPoint sourceConnectionPoint, UIElement dest, Connector referenceConnector, bool isConnectorStartMoved) { ConnectionPoint destConnectionPoint = GetClosestDestConnectionPoint(sourceConnectionPoint, dest); if (destConnectionPoint != null) { return CreateConnectorGesture(sourceConnectionPoint, destConnectionPoint, referenceConnector, isConnectorStartMoved); } return ConnectorCreationResult.OtherFailure; }
public void UpdateConnectorPoints(Connector connector, List<Point> points) { PointCollection pointCollection = new PointCollection(); foreach (Point point in points) { pointCollection.Add(new Point(point.X < 0 ? 0 : point.X, point.Y < 0 ? 0 : point.Y)); } connector.Points = pointCollection; OnLocationChanged(connector, null); }
// referenceConnector is used when we are re-linking the connector. internal ConnectorCreationResult CreateConnectorGesture(ConnectionPoint sourceConnectionPoint, ConnectionPoint destConnectionPoint, Connector referenceConnector, bool isConnectorStartMoved) { Debug.Assert(this.IsOutmostStateContainerEditor(), "Should only be called by the outmost editor."); Debug.Assert(sourceConnectionPoint != null, "sourceConnectionPoint is null."); Debug.Assert(destConnectionPoint != null, "destConnectionPoint is null."); ConnectorCreationResult result = ConnectorCreationResult.OtherFailure; if (destConnectionPoint.PointType != ConnectionPointType.Outgoing && sourceConnectionPoint.PointType != ConnectionPointType.Incoming) { if (sourceConnectionPoint.ParentDesigner is StateDesigner) { bool sameDestination = false; ModelItem refTransitionModelItem = null; if(referenceConnector != null) { refTransitionModelItem = StateContainerEditor.GetConnectorModelItem(referenceConnector); ModelItem destStateModelItem = ((StateDesigner)destConnectionPoint.ParentDesigner).ModelItem; if (refTransitionModelItem != null && refTransitionModelItem.Properties[TransitionDesigner.ToPropertyName].Value == destStateModelItem) { sameDestination = true; } } // We do not allow transitions to composite states unless we don't change the transition destination // (e.g., we are moving the start of a connector). if (!sameDestination && !((StateDesigner)destConnectionPoint.ParentDesigner).IsSimpleState()) { result = ConnectorCreationResult.CannotCreateTransitionToCompositeState; } // We do not allow transitions from an ancestor to its descendant else if (StateContainerEditor.IsDescendantStateOf(((StateDesigner)destConnectionPoint.ParentDesigner).ModelItem, ((StateDesigner)sourceConnectionPoint.ParentDesigner).ModelItem)) { result = ConnectorCreationResult.CannotCreateTransitionFromAncestorToDescendant; } else { using (EditingScope es = (EditingScope)this.ModelItem.BeginEdit(SR.CreateTransition)) { if (refTransitionModelItem != null) { this.CreateTransition(sourceConnectionPoint, destConnectionPoint, refTransitionModelItem, isConnectorStartMoved); } else { this.CreateTransition(sourceConnectionPoint, destConnectionPoint, null, false); } result = ConnectorCreationResult.Success; es.Complete(); } } } else if (sourceConnectionPoint.ParentDesigner is InitialNode) { StateDesigner destDesigner = (StateDesigner)destConnectionPoint.ParentDesigner; // We only allow simple states to be set as the initial state if (!destDesigner.IsSimpleState()) { result = ConnectorCreationResult.CannotSetCompositeStateAsInitialState; } else if (destDesigner.IsFinalState()) { result = ConnectorCreationResult.CannotSetFinalStateAsInitialState; } else { ModelItem destModelItem = destDesigner.ModelItem; using (EditingScope es = (EditingScope)this.ModelItem.BeginEdit(SR.SetInitialState)) { this.StateMachineModelItem.Properties[StateMachineDesigner.InitialStatePropertyName].SetValue(destModelItem); PointCollection connectorViewState = new PointCollection(ConnectorRouter.Route(this.panel, sourceConnectionPoint, destConnectionPoint)); this.StoreConnectorLocationViewState(this.StateMachineModelItem, connectorViewState, true); result = ConnectorCreationResult.Success; es.Complete(); } } } } return result; }
void StoreConnectorLocationViewState(Connector connector, bool isUndoableViewState) { //This method will be called whenever the FreeFormPanel raises a location changed event on a connector. //Such location changed events are a result of changes already committed in the UI. Hence we do not want to react to such view state changes. //Using internalViewStateChange flag for that purpose. this.internalViewStateChange = true; this.StoreConnectorLocationViewState(StateContainerEditor.GetConnectorModelItem(connector), connector.Points, isUndoableViewState); this.internalViewStateChange = false; }
void OnConnectorMouseDown(object sender, MouseButtonEventArgs e) { Connector connector = (Connector)sender; if (this.panel.Children.Contains(connector)) { this.selectedConnector = connector; } // In order to not let WorkflowViewElement handle the event, which would cause the // ConnectorEditor to be removed. e.Handled = true; }
internal void DeleteConnectorModelItem(Connector connector) { ModelItem connectorModelItem = StateContainerEditor.GetConnectorModelItem(connector); if (connectorModelItem.ItemType == typeof(Transition)) { StateContainerEditor.GetParentStateModelItemForTransition(connectorModelItem).Properties[StateDesigner.TransitionsPropertyName].Collection.Remove(connectorModelItem); } // Connector from initial node else if (connectorModelItem.ItemType == typeof(StateMachine)) { using (EditingScope es = (EditingScope)this.ModelItem.BeginEdit(SR.ClearInitialState)) { connectorModelItem.Properties[StateMachineDesigner.InitialStatePropertyName].SetValue(null); es.Complete(); } } }
Connector CreateConnector(ConnectionPoint srcConnPoint, ConnectionPoint destConnPoint, PointCollection points, ModelItem connectorModelItem) { Debug.Assert(this.IsOutmostStateContainerEditor(), "Should only be called by the outmost editor."); Connector connector = new Connector(); connector.FocusVisualStyle = null; connector.Focusable = true; DesignerView.SetCommandMenuMode(connector, CommandMenuMode.NoCommandMenu); if (connectorModelItem != null && connectorModelItem.ItemType == typeof(Transition)) { SetConnectorLabel(connector, connectorModelItem); SetConnectorStartDotToolTip(connector.startDotGrid, connectorModelItem); connector.IsTransition = true; connector.ToolTip = SR.EditTransitionTooltip; connector.startDotGrid.MouseDown += new MouseButtonEventHandler(OnConnectorStartDotMouseDown); connector.startDotGrid.MouseUp += new MouseButtonEventHandler(OnConnectorStartDotMouseUp); } connector.GotKeyboardFocus += new KeyboardFocusChangedEventHandler(OnConnectorGotKeyboardFocus); connector.RequestBringIntoView += new RequestBringIntoViewEventHandler(OnConnectorRequestBringIntoView); connector.GotFocus += new RoutedEventHandler(OnConnectorGotFocus); connector.LostFocus += new RoutedEventHandler(OnConnectorLostFocus); connector.MouseDoubleClick += new MouseButtonEventHandler(OnConnectorMouseDoubleClick); connector.MouseDown += new MouseButtonEventHandler(OnConnectorMouseDown); connector.KeyDown += new KeyEventHandler(OnConnectorKeyDown); connector.ContextMenuOpening += new ContextMenuEventHandler(OnConnectorContextMenuOpening); SetConnectorSrcDestConnectionPoints(connector, srcConnPoint, destConnPoint); StateContainerEditor.SetConnectorModelItem(connector, connectorModelItem); connector.Unloaded += new RoutedEventHandler(OnConnectorUnloaded); connector.Points = points; return connector; }
void OnConnectorGotFocus(object sender, RoutedEventArgs e) { Connector connector = e.Source as Connector; if (this.panel.connectorEditor == null || !connector.Equals(this.panel.connectorEditor.Connector)) { this.panel.RemoveConnectorEditor(); this.panel.connectorEditor = new ConnectorEditor(this.panel, connector); } if (this.panel.Children.Contains(connector)) { ModelItem connectorModelItem = StateContainerEditor.GetConnectorModelItem(connector); Selection newSelection = new Selection(); if (connectorModelItem != null && connectorModelItem.ItemType == typeof(Transition)) { newSelection = new Selection(connectorModelItem); } this.Context.Items.SetValue(newSelection); this.selectedConnector = connector; e.Handled = true; } }
void ClearSelectedConnector() { if (this.panel.connectorEditor != null && this.panel.connectorEditor.Connector == this.selectedConnector) { this.panel.RemoveConnectorEditor(); } this.selectedConnector = null; }
void UpdateStateMachineOnConnectorMoved(ConnectionPoint knownConnectionPoint, Point newPoint, Connector movedConnector, bool isConnectorStartMoved) { HitTestResult hitTestResult = VisualTreeHelper.HitTest(this.panel, newPoint); if (hitTestResult == null) { return; } UIElement newViewElement = null; ConnectionPoint newConnectionPoint = null; //The case where the Connector is dropped on a ConnectionPoint. if (this.lastConnectionPointMouseUpElement != null) { newConnectionPoint = StateContainerEditor.ConnectionPointHitTest(this.lastConnectionPointMouseUpElement, newPoint); if (newConnectionPoint != null) { newViewElement = this.lastConnectionPointMouseUpElement; } this.lastConnectionPointMouseUpElement = null; } //The case where the link is dropped on a shape. if (newViewElement == null) { newViewElement = StateContainerEditor.GetVisualAncestor<WorkflowViewElement>(hitTestResult.VisualHit); } if (newViewElement != null) { if (this.panel.IsAncestorOf(newViewElement)) { using (EditingScope es = (EditingScope)this.ModelItem.BeginEdit(SR.MoveLink)) { // Remove the old connector ModelItem this.DeleteConnectorModelItem(movedConnector); // Create new connector ConnectorCreationResult result = ConnectorCreationResult.OtherFailure; if (!isConnectorStartMoved) { if (newConnectionPoint == null) { result = CreateConnectorGesture(knownConnectionPoint, newViewElement, movedConnector, false); } else { result = CreateConnectorGesture(knownConnectionPoint, newConnectionPoint, movedConnector, false); } } else { // Don't allow moving the start of the initial node connector to a state if (!(newViewElement is StateDesigner && StateContainerEditor.IsConnectorFromInitialNode(movedConnector))) { if (newConnectionPoint == null) { result = CreateConnectorGesture(newViewElement, knownConnectionPoint, movedConnector, true); } else { result = CreateConnectorGesture(newConnectionPoint, knownConnectionPoint, movedConnector, true); } } } if (result == ConnectorCreationResult.Success) { es.Complete(); } else { StateContainerEditor.ReportConnectorCreationError(result); es.Revert(); } } } } }
void RemoveConnectorOnOutmostEditor(Connector connector) { ConnectionPoint srcConnectionPoint = FreeFormPanel.GetSourceConnectionPoint(connector); ConnectionPoint destConnectionPoint = FreeFormPanel.GetDestinationConnectionPoint(connector); // Update ConnectionPoints srcConnectionPoint.AttachedConnectors.Remove(connector); destConnectionPoint.AttachedConnectors.Remove(connector); StateContainerEditor outmostContainer = this.GetOutmostStateContainerEditor(); outmostContainer.panel.Children.Remove(connector); if (outmostContainer.selectedConnector == connector) { outmostContainer.ClearSelectedConnector(); } }
void OnStateContainerGridPreviewMouseDown(object sender, MouseButtonEventArgs e) { this.selectedConnector = null; }
private void MeasureChildren(out double height, out double width) { height = 0; width = 0; Point pt = new Point(0, 0); bool isOutmostPanel = this.IsOutmostPanel(); foreach (UIElement child in Children) { Connector connectorChild = child as Connector; if (connectorChild != null && isOutmostPanel) { pt = new Point(0, 0); if (measureConnectors) { Point srcPoint = FreeFormPanel.GetLocationRelativeToOutmostPanel(FreeFormPanel.GetSourceConnectionPoint(connectorChild)); Point destPoint = FreeFormPanel.GetLocationRelativeToOutmostPanel(FreeFormPanel.GetDestinationConnectionPoint(connectorChild)); if (connectorChild.Points.Count == 0 || (DesignerGeometryHelper.DistanceBetweenPoints(connectorChild.Points[0], srcPoint) > 1) || (DesignerGeometryHelper.DistanceBetweenPoints(connectorChild.Points[connectorChild.Points.Count - 1], destPoint) > 1)) { connectorChild.Points = new PointCollection(); RoutePolyLine(connectorChild); } connectorChild.Measure(new Size(Double.PositiveInfinity, Double.PositiveInfinity)); } else { continue; } } else //Measure non-connector elements. { child.Measure(new Size(Double.PositiveInfinity, Double.PositiveInfinity)); if (!child.DesiredSize.Equals(((Size)FreeFormPanel.GetChildSize(child)))) { FreeFormPanel.SetChildSize(child, child.DesiredSize); } pt = FreeFormPanel.GetLocation(child); if (pt.X == 0 && pt.Y == 0) { pt = new Point(LeftStackingMargin, lastYPosition); OnLocationChanged(child, new LocationChangedEventArgs(pt)); FreeFormPanel.SetLocation(child, pt); lastYPosition += child.DesiredSize.Height + VerticalStackingDistance; } } if (height < child.DesiredSize.Height + pt.Y) { height = child.DesiredSize.Height + pt.Y; } if (width < child.DesiredSize.Width + pt.X) { width = child.DesiredSize.Width + pt.X; } } width = (width < this.MinWidth) ? this.MinWidth : width; height = (height < this.MinHeight) ? this.MinHeight : height; }