diff options
| author | Roy <roy.mail.net@gmail.com> | 2018-04-21 19:49:05 +0300 |
|---|---|---|
| committer | Roy <roy.mail.net@gmail.com> | 2018-04-21 19:49:05 +0300 |
| commit | 0dec8a74239cff769836cae577fbd84824070e83 (patch) | |
| tree | d6cc24ee53454b3f17f1580e90de38238555b6bd /Software/Visual_Studio/Tango.SharedUI | |
| parent | 4df1724226c0d0941b970dbe71b1476e3c3e9902 (diff) | |
| download | Tango-0dec8a74239cff769836cae577fbd84824070e83.tar.gz Tango-0dec8a74239cff769836cae577fbd84824070e83.zip | |
Implemented NavigationControl for better performance!!!
Redesign of machine studio module initialization.
Diffstat (limited to 'Software/Visual_Studio/Tango.SharedUI')
| -rw-r--r-- | Software/Visual_Studio/Tango.SharedUI/Controls/NavigationControl.cs | 458 | ||||
| -rw-r--r-- | Software/Visual_Studio/Tango.SharedUI/Tango.SharedUI.csproj | 1 |
2 files changed, 459 insertions, 0 deletions
diff --git a/Software/Visual_Studio/Tango.SharedUI/Controls/NavigationControl.cs b/Software/Visual_Studio/Tango.SharedUI/Controls/NavigationControl.cs new file mode 100644 index 000000000..5a39948b2 --- /dev/null +++ b/Software/Visual_Studio/Tango.SharedUI/Controls/NavigationControl.cs @@ -0,0 +1,458 @@ +using System; +using System.Collections.Generic; +using System.Collections.ObjectModel; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using System.Windows; +using System.Windows.Controls; +using System.Windows.Markup; +using System.Windows.Media; +using System.Windows.Media.Animation; +using Tango.SharedUI.Helpers; + +namespace Tango.SharedUI.Controls +{ + [ContentProperty(nameof(Elements))] + public class NavigationControl : UserControl + { + #region Transition Types + + public enum TransitionTypes + { + Fade, + Zoom, + Slide, + } + + #endregion + + #region Navigation Element + + private class NavigationElement : ContentControl + { + public FrameworkElement Element + { + get { return (FrameworkElement)GetValue(ElementProperty); } + set { SetValue(ElementProperty, value); } + } + public static readonly DependencyProperty ElementProperty = + DependencyProperty.Register("Element", typeof(FrameworkElement), typeof(NavigationControl), new PropertyMetadata(null)); + + public ScaleTransform Scale + { + get { return (ScaleTransform)GetValue(ScaleProperty); } + set { SetValue(ScaleProperty, value); } + } + public static readonly DependencyProperty ScaleProperty = + DependencyProperty.Register("Scale", typeof(ScaleTransform), typeof(NavigationControl), new PropertyMetadata(null)); + + public RotateTransform Rotate + { + get { return (RotateTransform)GetValue(RotateProperty); } + set { SetValue(RotateProperty, value); } + } + public static readonly DependencyProperty RotateProperty = + DependencyProperty.Register("Rotate", typeof(RotateTransform), typeof(NavigationControl), new PropertyMetadata(null)); + + public TranslateTransform Translate + { + get { return (TranslateTransform)GetValue(TranslateProperty); } + set { SetValue(TranslateProperty, value); } + } + public static readonly DependencyProperty TranslateProperty = + DependencyProperty.Register("Translate", typeof(TranslateTransform), typeof(NavigationControl), new PropertyMetadata(null)); + + public NavigationElement() + { + Visibility = Visibility.Hidden; + + Scale = new ScaleTransform(1, 1); + Rotate = new RotateTransform(0); + Translate = new TranslateTransform(0, 0); + + TransformGroup group = new TransformGroup(); + group.Children.Add(Scale); + group.Children.Add(Rotate); + group.Children.Add(Translate); + + RenderTransformOrigin = new Point(0.5, 0.5); + RenderTransform = group; + } + + public NavigationElement(FrameworkElement element) : this() + { + Element = element; + } + + public void AnimateScale(DoubleAnimation animation) + { + Scale.BeginAnimation(ScaleTransform.ScaleXProperty, animation); + Scale.BeginAnimation(ScaleTransform.ScaleYProperty, animation); + } + + public void AnimateTranslateX(DoubleAnimation animation) + { + Translate.BeginAnimation(TranslateTransform.XProperty, animation); + } + + public void AnimateOpacity(DoubleAnimation animation) + { + BeginAnimation(OpacityProperty, animation); + } + + public void Reset() + { + Scale.BeginAnimation(ScaleTransform.ScaleXProperty, null); + Scale.BeginAnimation(ScaleTransform.ScaleYProperty, null); + Rotate.BeginAnimation(RotateTransform.AngleProperty, null); + Translate.BeginAnimation(TranslateTransform.XProperty, null); + Translate.BeginAnimation(TranslateTransform.YProperty, null); + Opacity = 1; + } + + public void Activate() + { + if (Content != Element) + { + Content = Element; + } + + Visibility = Visibility.Visible; + } + + public void Deactivate(bool detach) + { + if (detach) + { + Content = null; + } + + Visibility = Visibility.Hidden; + } + } + + #endregion + + #region INavigationView + + public interface INavigationView + { + void OnNavigated(); + } + + #endregion + + private Grid _grid; + private bool _loaded; + + #region Properties + + public ObservableCollection<FrameworkElement> Elements + { + get { return (ObservableCollection<FrameworkElement>)GetValue(ElementsProperty); } + set { SetValue(ElementsProperty, value); } + } + public static readonly DependencyProperty ElementsProperty = + DependencyProperty.Register("Elements", typeof(ObservableCollection<FrameworkElement>), typeof(NavigationControl), new PropertyMetadata(null, (d, e) => (d as NavigationControl).OnElementsChanged())); + + public FrameworkElement SelectedElement + { + get { return (FrameworkElement)GetValue(SelectedElementProperty); } + set { SetValue(SelectedElementProperty, value); } + } + public static readonly DependencyProperty SelectedElementProperty = + DependencyProperty.Register("SelectedElement", typeof(FrameworkElement), typeof(NavigationControl), new PropertyMetadata(null, (d, e) => (d as NavigationControl).OnSelectedElementChanged(e.OldValue as FrameworkElement, e.NewValue as FrameworkElement))); + + public TransitionTypes TransitionType + { + get { return (TransitionTypes)GetValue(TransitionTypeProperty); } + set { SetValue(TransitionTypeProperty, value); } + } + public static readonly DependencyProperty TransitionTypeProperty = + DependencyProperty.Register("TransitionType", typeof(TransitionTypes), typeof(NavigationControl), new PropertyMetadata(TransitionTypes.Zoom)); + + public bool TransitionAlwaysFades + { + get { return (bool)GetValue(TransitionAlwaysFadesProperty); } + set { SetValue(TransitionAlwaysFadesProperty, value); } + } + public static readonly DependencyProperty TransitionAlwaysFadesProperty = + DependencyProperty.Register("TransitionAlwaysFades", typeof(bool), typeof(NavigationControl), new PropertyMetadata(false)); + + public Duration TransitionDuration + { + get { return (Duration)GetValue(TransitionDurationProperty); } + set { SetValue(TransitionDurationProperty, value); } + } + public static readonly DependencyProperty TransitionDurationProperty = + DependencyProperty.Register("TransitionDuration", typeof(Duration), typeof(NavigationControl), new PropertyMetadata(new Duration(TimeSpan.FromSeconds(0.5)))); + + public bool KeepElementsAttached + { + get { return (bool)GetValue(KeepElementsAttachedProperty); } + set { SetValue(KeepElementsAttachedProperty, value); } + } + public static readonly DependencyProperty KeepElementsAttachedProperty = + DependencyProperty.Register("KeepElementsAttached", typeof(bool), typeof(NavigationControl), new PropertyMetadata(false)); + + + #endregion + + #region Attached Properties + + #region Draggable + + /// <summary> + /// Determines the element navigation name. + /// </summary> + public static readonly DependencyProperty NavigationName = + DependencyProperty.RegisterAttached("NavigationName", + typeof(String), typeof(NavigationControl), + new FrameworkPropertyMetadata("")); + + /// <summary> + /// Sets the name of the navigation. + /// </summary> + /// <param name="element">The element.</param> + /// <param name="value">The value.</param> + public static void SetNavigationName(FrameworkElement element, String value) + { + element.SetValue(NavigationName, value); + } + + /// <summary> + /// Gets the name of the navigation. + /// </summary> + /// <param name="element">The element.</param> + /// <returns></returns> + public static String GetNavigationName(FrameworkElement element) + { + return element.GetValue(NavigationName).ToString(); + } + + #endregion + + #endregion + + #region Constructors + + public NavigationControl() + { + ClipToBounds = true; + _grid = new Grid(); + Content = _grid; + Elements = new ObservableCollection<FrameworkElement>(); + Loaded += NavigationControl_Loaded; + } + + #endregion + + #region Event Handlers + + private void NavigationControl_Loaded(object sender, RoutedEventArgs e) + { + if (!_loaded) + { + if (Elements != null) + { + SelectedElement = Elements.FirstOrDefault(); + } + + _loaded = true; + } + } + + private void Elements_CollectionChanged(object sender, System.Collections.Specialized.NotifyCollectionChangedEventArgs e) + { + SyncElements(); + } + + #endregion + + #region Private Methods + + private void OnElementsChanged() + { + if (Elements != null) + { + Elements.CollectionChanged -= Elements_CollectionChanged; + Elements.CollectionChanged += Elements_CollectionChanged; + } + + SyncElements(); + } + + private void SyncElements() + { + if (Elements == null) + { + _grid.Children.Clear(); + } + else + { + var toRemove = _grid.Children.OfType<NavigationElement>().ToList().Where(x => !Elements.Contains(x.Element)).ToList(); + var toAdd = Elements.Where(x => !_grid.Children.OfType<NavigationElement>().Select(y => y.Element).ToList().Contains(x)).ToList(); + + toRemove.ForEach(x => _grid.Children.Remove(x)); + toAdd.ForEach(x => _grid.Children.Add( + new NavigationElement() + { + RenderTransformOrigin = new Point(0.5, 0.5), + Element = x, + Content = KeepElementsAttached ? x : null, + })); + } + + if (!Elements.Contains(SelectedElement)) + { + SelectedElement = null; + } + } + + private NavigationElement GetElementContainer(FrameworkElement element) + { + return _grid.Children.OfType<NavigationElement>().ToList().SingleOrDefault(x => x.Element == element); + } + + private void Navigate(NavigationElement fromElement, NavigationElement toElement) + { + if (toElement == null) return; + if (toElement == fromElement) return; + + if (fromElement != null) + { + DoubleAnimation toAnimation = new DoubleAnimation(); + toAnimation.Duration = TransitionDuration; + + DoubleAnimation fromAnimation = new DoubleAnimation(); + fromAnimation.Duration = TransitionDuration; + + int fromIndex = Elements.IndexOf(fromElement.Element); + int toIndex = Elements.IndexOf(toElement.Element); + + fromElement.Reset(); + toElement.Reset(); + + fromAnimation.Completed += (_, __) => + { + fromElement.Deactivate(!KeepElementsAttached); + }; + + toAnimation.Completed += (_, __) => + { + INavigationView navigationView = toElement.Element as INavigationView; + if (navigationView != null) + { + navigationView.OnNavigated(); + } + }; + + switch (TransitionType) + { + case TransitionTypes.Fade: + fromAnimation.From = 1; + fromAnimation.To = 0; + + toAnimation.From = 0; + toAnimation.To = 1; + + fromElement.AnimateOpacity(fromAnimation); + toElement.AnimateOpacity(toAnimation); + + break; + case TransitionTypes.Zoom: + fromAnimation.From = 1; + fromAnimation.To = 0; + + toAnimation.From = 0; + toAnimation.To = 1; + + fromElement.AnimateScale(fromAnimation); + toElement.AnimateScale(toAnimation); + + break; + case TransitionTypes.Slide: + + if (toIndex > fromIndex) + { + fromAnimation.From = 0; + fromAnimation.To = -ActualWidth; + + toAnimation.From = ActualWidth; + toAnimation.To = 0; + } + else + { + fromAnimation.From = 0; + fromAnimation.To = ActualWidth; + + toAnimation.From = -ActualWidth; + toAnimation.To = 0; + } + + fromElement.AnimateTranslateX(fromAnimation); + toElement.AnimateTranslateX(toAnimation); + + break; + } + + if (TransitionAlwaysFades && TransitionType != TransitionTypes.Fade) + { + DoubleAnimation fromFadeAnimation = new DoubleAnimation(); + fromFadeAnimation.From = 1; + fromFadeAnimation.To = 0; + fromFadeAnimation.Duration = TransitionDuration; + + DoubleAnimation toFadeAnimation = new DoubleAnimation(); + toFadeAnimation.From = 0; + toFadeAnimation.To = 1; + toFadeAnimation.Duration = TransitionDuration; + + fromElement.AnimateOpacity(fromFadeAnimation); + toElement.AnimateOpacity(toFadeAnimation); + } + + fromElement.Activate(); + toElement.Activate(); + } + else + { + toElement.Activate(); + toElement.Reset(); + } + } + + #endregion + + #region Properties Changes + + protected virtual void OnSelectedElementChanged(FrameworkElement fromElement, FrameworkElement toElement) + { + Navigate(GetElementContainer(fromElement), GetElementContainer(toElement)); + } + + #endregion + + #region Public Methods + + public void NavigateTo(FrameworkElement element) + { + SelectedElement = element; + } + + public void NavigateTo(String navigationName) + { + SelectedElement = Elements.SingleOrDefault(x => GetNavigationName(x) == navigationName); + } + + public FrameworkElement GetAndDetach(String navigationName) + { + var element = Elements.SingleOrDefault(x => GetNavigationName(x) == navigationName); + GetElementContainer(element).Deactivate(!KeepElementsAttached); + return element; + } + + #endregion + } +} diff --git a/Software/Visual_Studio/Tango.SharedUI/Tango.SharedUI.csproj b/Software/Visual_Studio/Tango.SharedUI/Tango.SharedUI.csproj index 8ce56b6ff..af4084453 100644 --- a/Software/Visual_Studio/Tango.SharedUI/Tango.SharedUI.csproj +++ b/Software/Visual_Studio/Tango.SharedUI/Tango.SharedUI.csproj @@ -83,6 +83,7 @@ <Compile Include="Controls\MultiTransitionControl.xaml.cs"> <DependentUpon>MultiTransitionControl.xaml</DependentUpon> </Compile> + <Compile Include="Controls\NavigationControl.cs" /> <Compile Include="Controls\ScriptEditorControl.xaml.cs"> <DependentUpon>ScriptEditorControl.xaml</DependentUpon> </Compile> |
