From 17fdde66d94155fc62a034fa6658995bef6fd6e5 Mon Sep 17 00:00:00 2001 From: Jason Smith Date: Tue, 22 Mar 2016 13:02:25 -0700 Subject: Initial import --- .../TabbedPageRenderer.cs | 284 +++++++++++++++++++++ 1 file changed, 284 insertions(+) create mode 100644 Xamarin.Forms.Platform.WinRT.Phone/TabbedPageRenderer.cs (limited to 'Xamarin.Forms.Platform.WinRT.Phone/TabbedPageRenderer.cs') diff --git a/Xamarin.Forms.Platform.WinRT.Phone/TabbedPageRenderer.cs b/Xamarin.Forms.Platform.WinRT.Phone/TabbedPageRenderer.cs new file mode 100644 index 00000000..9de3a623 --- /dev/null +++ b/Xamarin.Forms.Platform.WinRT.Phone/TabbedPageRenderer.cs @@ -0,0 +1,284 @@ +using System; +using System.Collections.Specialized; +using System.ComponentModel; +using Windows.UI.Xaml; +using Windows.UI.Xaml.Automation; +using Windows.UI.Xaml.Controls; +using Windows.UI.Xaml.Media; + +namespace Xamarin.Forms.Platform.WinRT +{ + internal class TabbedPagePresenter : Windows.UI.Xaml.Controls.ContentPresenter + { + public TabbedPagePresenter () + { + SizeChanged += (s, e) => { + if (ActualWidth > 0 && ActualHeight > 0) { + var tab = ((Page) DataContext); + ((TabbedPage) tab.RealParent).ContainerArea = new Rectangle (0, 0, ActualWidth, ActualHeight); + } + }; + } + } + + public class TabbedPageRenderer + : IVisualElementRenderer, ITitleProvider + { + public event EventHandler ElementChanged; + + public FrameworkElement ContainerElement + { + get { return Control; } + } + + VisualElement IVisualElementRenderer.Element + { + get { return Element; } + } + + public Pivot Control + { + get; + private set; + } + + public TabbedPage Element + { + get; + private set; + } + + public void SetElement (VisualElement element) + { + if (element != null && !(element is TabbedPage)) + throw new ArgumentException ("Element must be a TabbedPage", "element"); + + TabbedPage oldElement = Element; + Element = (TabbedPage) element; + + if (oldElement != null) { + oldElement.PropertyChanged -= OnElementPropertyChanged; + ((INotifyCollectionChanged) oldElement.Children).CollectionChanged -= OnPagesChanged; + } + + if (element != null) { + if (Control == null) { + Control = new FormsPivot { + Style = (Windows.UI.Xaml.Style) Windows.UI.Xaml.Application.Current.Resources["TabbedPageStyle"] + }; + Control.HeaderTemplate = (Windows.UI.Xaml.DataTemplate)Windows.UI.Xaml.Application.Current.Resources["TabbedPageHeader"]; + Control.ItemTemplate = (Windows.UI.Xaml.DataTemplate)Windows.UI.Xaml.Application.Current.Resources["TabbedPage"]; + + Control.SelectionChanged += OnSelectionChanged; + + Tracker = new BackgroundTracker (Windows.UI.Xaml.Controls.Control.BackgroundProperty) { + Element = (Page) element, + Control = Control, + Container = Control + }; + + Control.Loaded += OnLoaded; + Control.Unloaded += OnUnloaded; + } + + Control.DataContext = Element; + OnPagesChanged (Element.Children, new NotifyCollectionChangedEventArgs (NotifyCollectionChangedAction.Reset)); + UpdateCurrentPage (); + + ((INotifyCollectionChanged) Element.Children).CollectionChanged += OnPagesChanged; + element.PropertyChanged += OnElementPropertyChanged; + + if (!string.IsNullOrEmpty (element.AutomationId)) + Control.SetValue (AutomationProperties.AutomationIdProperty, element.AutomationId); + } + + OnElementChanged (new VisualElementChangedEventArgs (oldElement, element)); + } + + public SizeRequest GetDesiredSize (double widthConstraint, double heightConstraint) + { + var constraint = new Windows.Foundation.Size (widthConstraint, heightConstraint); + + var oldWidth = Control.Width; + var oldHeight = Control.Height; + + Control.Height = double.NaN; + Control.Width = double.NaN; + + Control.Measure (constraint); + var result = new Size (Math.Ceiling (Control.DesiredSize.Width), Math.Ceiling (Control.DesiredSize.Height)); + + Control.Width = oldWidth; + Control.Height = oldHeight; + + return new SizeRequest (result); + } + + public void Dispose () + { + Dispose (true); + } + + protected virtual void Dispose (bool disposing) + { + if (!disposing || _disposed) + return; + + _disposed = true; + SetElement (null); + Tracker = null; + } + + protected VisualElementTracker Tracker + { + get + { + return _tracker; + } + set + { + if (_tracker == value) + return; + + if (_tracker != null) { + _tracker.Dispose (); + /*this.tracker.Updated -= OnTrackerUpdated;*/ + } + + _tracker = value; + + /*if (this.tracker != null) + this.tracker.Updated += OnTrackerUpdated;*/ + } + } + + bool ITitleProvider.ShowTitle + { + get + { + return _showTitle; + } + + set + { + if (_showTitle == value) + return; + _showTitle = value; + + (Control as FormsPivot).ToolbarVisibility = _showTitle ? Visibility.Visible : Visibility.Collapsed; + } + } + + string ITitleProvider.Title + { + get + { + return (string)Control?.Title; + } + + set + { + if (Control != null) + Control.Title = value; + } + } + + Brush ITitleProvider.BarBackgroundBrush + { + set + { + (Control as FormsPivot).ToolbarBackground = value; + } + } + + Brush ITitleProvider.BarForegroundBrush + { + set + { + (Control as FormsPivot).ToolbarForeground = value; + } + } + + protected virtual void OnElementChanged (VisualElementChangedEventArgs e) + { + var changed = ElementChanged; + if (changed != null) + changed (this, e); + } + + bool _disposed; + VisualElementTracker _tracker; + bool _showTitle; + + void OnPagesChanged (object sender, NotifyCollectionChangedEventArgs e) + { + e.Apply (Element.Children, Control.Items); + + // Potential performance issue, UpdateLayout () is called for every page change + Control.UpdateLayout (); + } + + void OnSelectionChanged (object sender, SelectionChangedEventArgs e) + { + if (Element == null) + return; + + Page page = (e.AddedItems.Count > 0) ? (Page) e.AddedItems[0] : null; + Element.CurrentPage = page; + } + + void OnElementPropertyChanged (object sender, PropertyChangedEventArgs e) + { + if (e.PropertyName == "CurrentPage") + UpdateCurrentPage (); + } + + void UpdateCurrentPage () + { + Page page = Element.CurrentPage; + UpdateTitle (page); + + if (page == null) + return; + Control.SelectedItem = page; + } + + void OnLoaded (object sender, RoutedEventArgs args) + { + if (Element == null) + return; + + Element.SendAppearing (); + } + + void OnUnloaded (object sender, RoutedEventArgs args) + { + if (Element == null) + return; + + Element.SendDisappearing (); + } + + void OnTrackerUpdated (object sender, EventArgs e) + { + + } + + void UpdateTitle (Page child) + { + Control.ClearValue (Pivot.TitleProperty); + + if (child == null) + return; + var renderer = Platform.GetRenderer (child); + var navigationRenderer = renderer as NavigationPageRenderer; + if (navigationRenderer != null) { + Control.Title = navigationRenderer.Title; + } else { + ((ITitleProvider) this).ShowTitle = false; + } + + } + + } +} \ No newline at end of file -- cgit v1.2.3