1 //----------------------------------------------------------------
2 // Copyright (c) Microsoft Corporation. All rights reserved.
3 //----------------------------------------------------------------
4 namespace System.Activities.Core.Presentation
7 using System.Activities.Presentation;
8 using System.Activities.Presentation.FreeFormEditing;
9 using System.Activities.Presentation.Internal.PropertyEditing;
10 using System.Activities.Presentation.Model;
11 using System.Activities.Presentation.View;
12 using System.Activities.Statements;
15 using System.Windows.Controls;
16 using System.Windows.Input;
17 using System.Windows.Media;
19 //This class is visual representation of ResizeGrip like control, which is used in a Grid to allow resizing.
20 class StateContainerResizeGrip : Control
22 public static readonly DependencyProperty IconProperty =
23 DependencyProperty.Register("Icon", typeof(DrawingBrush), typeof(StateContainerResizeGrip));
25 public static readonly DependencyProperty ParentStateContainerEditorProperty =
26 DependencyProperty.Register("ParentStateContainerEditor", typeof(StateContainerEditor), typeof(StateContainerResizeGrip));
28 public static readonly DependencyProperty DisabledProperty =
29 DependencyProperty.Register("Disabled", typeof(bool), typeof(StateContainerResizeGrip), new UIPropertyMetadata(false));
33 // The scope is used for capturing the current size of all the StateContainer instances that contain the target ResizeGrip.
34 // As the user resizes the target StateContainer, its Visual ancestors would get resized.
35 // The purpose of the scope is to store their sizes before the resizing to facilitate Undo.
38 public DrawingBrush Icon
40 get { return (DrawingBrush)GetValue(IconProperty); }
41 set { SetValue(IconProperty, value); }
44 public StateContainerEditor ParentStateContainerEditor
46 get { return (StateContainerEditor)GetValue(ParentStateContainerEditorProperty); }
47 set { SetValue(ParentStateContainerEditorProperty, value); }
52 get { return (bool)GetValue(DisabledProperty); }
53 set { SetValue(DisabledProperty, value); }
56 protected override void OnInitialized(EventArgs e)
58 base.OnInitialized(e);
59 this.Cursor = Cursors.SizeNWSE;
62 protected override void OnGotMouseCapture(MouseEventArgs e)
64 ModelItem stateContainerModelItem = this.ParentStateContainerEditor.ModelItem;
65 string undoItemName = string.Empty;
66 if (stateContainerModelItem.ItemType == typeof(StateMachine))
68 undoItemName = SR.StateMachineResize;
70 else if (stateContainerModelItem.ItemType == typeof(State))
72 undoItemName = SR.StateResize;
76 Fx.Assert(false, "The model item type is invalid");
78 this.scope = (EditingScope)this.ParentStateContainerEditor.ModelItem.BeginEdit(undoItemName);
79 base.OnGotMouseCapture(e);
82 protected override void OnLostMouseCapture(MouseEventArgs e)
84 if (this.scope != null)
86 this.scope.Complete();
90 base.OnLostMouseCapture(e);
93 protected override void OnPreviewMouseLeftButtonDown(MouseButtonEventArgs e)
95 if (e != null && !this.Disabled)
97 this.offset = e.GetPosition(this);
99 if (this.scope != null)
101 this.ParentStateContainerEditor.StoreShapeSizeWithUndoRecursively(this.ParentStateContainerEditor.ModelItem);
103 // Select the designer when it is being resized
104 WorkflowViewElement designer = this.ParentStateContainerEditor.ModelItem.View as WorkflowViewElement;
106 if (!designer.IsKeyboardFocusWithin)
108 // Fix 185562 - if the designer has the keyboard focus (i.e. DisplayName being edited)
109 // then there is no need to refocus on the designer again. That prevents the
110 // DisplayName editing to be group into the same EditingScope as resizing, and
111 // also the defaultDisplayNameReadOnlyControl from being Visible but not modified.
112 Keyboard.Focus(designer);
115 StateMachineDesigner stateMachineDesigner = VisualTreeUtils.FindVisualAncestor<StateMachineDesigner>(this.ParentStateContainerEditor);
116 stateMachineDesigner.IsResizing = true;
120 base.OnPreviewMouseLeftButtonDown(e);
123 protected override void OnMouseMove(MouseEventArgs args)
125 base.OnMouseMove(args);
126 if (args != null && !this.Disabled)
128 if (args.LeftButton == MouseButtonState.Pressed && this.IsMouseCaptured && this.scope != null)
130 StateContainerEditor stateContainerEditor = this.ParentStateContainerEditor;
131 FreeFormPanel panel = stateContainerEditor.Panel;
132 Grid stateContainerGrid = stateContainerEditor.stateContainerGrid;
133 Point currentPosition = Mouse.GetPosition(stateContainerGrid);
134 currentPosition.Offset(this.offset.X, this.offset.Y);
135 stateContainerEditor.StateContainerWidth = Math.Min(Math.Max(panel.RequiredWidth, currentPosition.X), stateContainerGrid.MaxWidth);
136 stateContainerEditor.StateContainerHeight = Math.Min(Math.Max(panel.RequiredHeight, currentPosition.Y), stateContainerGrid.MaxHeight);
142 protected override void OnPreviewMouseLeftButtonUp(MouseButtonEventArgs e)
144 if (e != null && !this.Disabled && this.scope != null)
146 ModelItem stateContainerModelItem = this.ParentStateContainerEditor.ModelItem;
147 ViewStateService viewStateService = this.ParentStateContainerEditor.Context.Services.GetService<ViewStateService>();
148 viewStateService.StoreViewStateWithUndo(stateContainerModelItem, StateContainerEditor.StateContainerWidthViewStateKey, this.ParentStateContainerEditor.StateContainerWidth);
149 viewStateService.StoreViewStateWithUndo(stateContainerModelItem, StateContainerEditor.StateContainerHeightViewStateKey, this.ParentStateContainerEditor.StateContainerHeight);
150 Mouse.OverrideCursor = null;
152 StateMachineDesigner stateMachineDesigner = VisualTreeUtils.FindVisualAncestor<StateMachineDesigner>(this.ParentStateContainerEditor);
153 stateMachineDesigner.IsResizing = false;
156 base.OnPreviewMouseLeftButtonUp(e);