// If no current snap action, set it to the action. // Otherwise, if set, we're possibly undoing the last snap action (these are always opposite attach/detach actions), // if re-attaching or re-detaching from the connection point. // Lastly, if attaching to a different connection point, buffer the last snap action (which would always be a detach) // and set the current snap action to what will always be the attach to another connection point. protected void SetCurrentAction(SnapAction action) { if (currentSnapAction == null) { currentSnapAction = action; } else { // Connecting to a different shape? if (action.TargetShape != currentSnapAction.TargetShape // connecting to a different endpoint on the connector? || action.GripType != currentSnapAction.GripType // connecting to a different connection point on the shape? || action.ShapeConnectionPoint != currentSnapAction.ShapeConnectionPoint) { snapActions.Add(currentSnapAction); currentSnapAction = action; } else { // User is undoing the last action by re-connecting or disconnecting from the shape to which we just connected / disconnected. currentSnapAction = null; } } }
public void Reset() { snapActions.Clear(); nearElements.Clear(); currentlyNear.Clear(); runningDelta = new Point(); currentSnapAction = null; }
public bool SnapCheck(GripType gripType, Point delta, Action <Point> update, bool isByKeyPress = false) { SnapAction action = Snap(gripType, delta, isByKeyPress); if (action != null) { if (action.SnapType == SnapAction.Action.Attach) { runningDelta = action.Delta; update(action.Delta); // Controller.DragSelectedElements(action.Delta); // Don't attach at this point, as this will be handled by the mouse-up action. SetCurrentAction(action); } else if (action.SnapType == SnapAction.Action.Detach) { runningDelta = action.Delta; update(action.Delta); // Controller.DragSelectedElements(action.Delta); // Don't detach at this point, as this will be handled by the mouse-up action. SetCurrentAction(action); } else // Attached { // The mouse move had no affect in detaching because it didn't have sufficient velocity. // The problem here is that the mouse moves, affecting the total delta, but the shape doesn't move. // This affects the computation in the MouseUp handler: // Point delta = CurrentMousePosition.Delta(startedDraggingShapesAt); // =================== // We could set the mouse cursor position, which isn't a bad idea, as it keeps the mouse with the shape: //Controller.Canvas.MouseMove -= HandleMouseMoveEvent; //Cursor.Position = Controller.Canvas.PointToScreen(LastMousePosition); //Application.DoEvents(); // sigh - we need the event to trigger, even though it's unwired. //Controller.Canvas.MouseMove += HandleMouseMoveEvent; // The above really doesn't work well because I think we can get multiple move events, and this only handles the first event. // =================== // =================== // Or we could add a "compensation" accumulator for dealing with the deltas that don't move the shape. // This works better, except the attached compensation has to be stored for each detach. // attachedCompensation = attachedCompensation.Add(delta); // That doesn't work either, as the attachedCompensation is treated as a move even though there is no actual movement of the connector! // =================== // Final implementation is to use the runningDelta instead of the CurrentMouseMosition - startDraggingShapesAt difference. // startedDraggingShapesAt = CurrentMousePosition; } } return(action != null); }
public SnapAction Clone() { SnapAction ret = new SnapAction(); ret.SnapType = SnapType; ret.connector = connector; ret.gripType = gripType; ret.targetShape = targetShape; ret.lineConnectionPoint = lineConnectionPoint; ret.shapeConnectionPoint = shapeConnectionPoint; ret.Delta = Delta; return(ret); }
protected void DoUndoSnapAction(UndoStack undoStack, SnapAction action) { SnapAction closureAction = action.Clone(); // Do/undo/redo as part of of the move group. if (closureAction.SnapType == SnapAction.Action.Attach) { undoStack.UndoRedo("Attach", () => closureAction.Attach(), () => closureAction.Detach(), false); } else { undoStack.UndoRedo("Detach", () => closureAction.Detach(), () => closureAction.Attach(), false); } }