summaryrefslogtreecommitdiff
path: root/Xamarin.Forms.Platform.iOS
diff options
context:
space:
mode:
authorRui Marinho <me@ruimarinho.net>2017-01-26 15:33:15 +0000
committerGitHub <noreply@github.com>2017-01-26 15:33:15 +0000
commit52fc04724fc163c68c54cf33a5931871f8c1ee8e (patch)
tree28a56527e0886e616735d5334f7b10688c255074 /Xamarin.Forms.Platform.iOS
parent6b2a69d930d42657aff2b9ad769503b4939568ab (diff)
downloadxamarin-forms-52fc04724fc163c68c54cf33a5931871f8c1ee8e.tar.gz
xamarin-forms-52fc04724fc163c68c54cf33a5931871f8c1ee8e.tar.bz2
xamarin-forms-52fc04724fc163c68c54cf33a5931871f8c1ee8e.zip
MacOS (#650)
* [MacOS] Add SwitchRenderer * [MacOS] Add TimePickerRenderer * [MacOS] Cleanup TimePcikerRender * [MacOS] Add WebViewRenderer * [MacOS] Add Javascript evaluate to webview * [MacOS] Fix build error on WebViewRenderer * [MacOS] Add Base and TextCell renderers * [MacOS] Start on ListViewRenderer * [MacOS] Cleanup * [MacOS] Vertical center text on default NSTextField * [MacOS] Center NSTextField vertically * [MacOS] Add ImageCellRenderer * [MacOS] Add SwitchCellRenderer * [MacOS] Add SwitchCellRenderer * [iOS] Allow to set background color on other CellRenderers * [MacOS] Fix selection mode on ListView * [MacOS] Set background on Entry of entry cell * [MacOS] Fix casting bug on CellRenderer * [MacOS] Other fix on CellRenderer background * [MacOS] Add ViewCellRenderer * [MacOS] Fixes and cleanup on cells * [MacOS] Add NSScrollView so NSTableView can scroll * [MacOS] Add HeaderView to ListView * [MacOS] Cleanup * [Controls] Add Header support to ListView * [MacOS] NSView reuse on NSTableView * [MacOS] Some fix on layour order * [MacOS] Add CarouselPageRenderer * [MacOS] Implement EventTracker on PageRenderer * [MacOS] Cleanup CarouselPageRenderer * [MacOS] Add MasterDetailPage renderer * [MacOS] MDP renderer don't allow drag of splitter * [MacOS] Add TabbedPage renderer * [MacOS] Initial sketch of NavigationPageRenderer * [MacOS] Send disappearing of CurrentPage on Dispose on NavigationPageRenderer * [MacOS] Add Gallery page for Mac * [MacOS] Add MacOSExpressionSearch * [MacOS] Fix ColorExtension * [MacOS] Fix MDP renderer layout * [MacOS] Implement native selection on ListViewRenderer * [MacOS] Deselect a item on NSTableView * [MacOS] Remove previous SplitViewItems * [MacOS] Fix navigationpage height * [MacOS] Add toolbar for NavigationPageRenderer * [MacOS] Don't remove selection for now (crashing) * [MacOS] Refactor page and back button title on NavigationPageRenderer * [MacOS] Fix bug when native navigate back * [MacOS] Hide layer when transition * [MacOS] ListviewRenderer fix BbackgroundColor * [MacOS] Fix background on ScrollViewRenderer * [MacOS] Fix header measure on ListViewRenderer * [MacOS] Add Mac twitter demo * [Controls] Spaces for easy reading * [MacOS] More xaml cleanup * [Core] Add Mac as aTargetPlatform * [MacOS] Add alerts and actionsheets * [MacOS] Add GestureRecognizers * [MacOS] Fix Layout issues when adding children, enable transformations * [MacOS] Fix title on tab item, move to tabbed navigation based on segmented control * [MacOS] Hide toolbar when not needed, this allows to work with tabbed page, cleanup * [MacOS] Add NativeBindings and NativeViewWrapper * [MacOS] Fix AssemblyInfo * [MacOS] FIX NRE on SetBackgroundColor BoxView * [MacOS] Fix NavigationPageRenderer * [MacOS] Fix build * [MacOS] Also update page when it resizes * [MacOS] Add LayoutRenderer for handle items position when the bounds change. * [MacOS] Refactor/Cleanup * [MacOS] Add toolbar items support to NavigationPage * [MacOS] Resize images for TabViewITems * [MacOS] Fix TabbedPage resize issues , allow users to override some features when creating TVI * [MacOS] Fix hide/show Navigation toolbar * [MacOS] Redo CarouselPageRenderer with NSPageController * [MacOS] Add support for Modal pages * [MacOS] Refactor navigation from platform * [Nuget] Add nuget for MacOS * [Nuget]Fix nuspec * [Nuget] Add variables for CI * [Controls] Remove MainMenu from MacOS * [MacOS] Add TableView renderer (no headers yet) * [MacOS] Refactoring, marking extensions as internal * [MacOS] Add group headers for TableViewRenderer * [MacOS] Workaround for updates on listview collection * [MacOS] Handle updates of rows in the ListViewRenderer properly * [MacOS] Fix navigation animation * Fix navigation header issues with modal pages * [MacOS] Fix MDP issues with resizing * [MacOS] Fix general dispose * [MacOS] Add a ViewControllerWrapper for NSSplitView * [MacOS] MDP renderer fix animation * [MacOS] Fix ListView selection bug * [MacOS] Fix rendering MDP Layout inside wrappers * [MacOS] Re write the MainToolbar handler * [MacOS] Don't use Sierra new extensions so we can run in stable channel * [MacOS] Another way to hide the toolbar (smarter i think) * [MacOS] Fix MDP bug and remove debug color * [Controls] Add HanselForms sample * [MacOS] Fix NRE WebviewRenderer * [MacOS] Fix uneven rows on ListView renderer * [MacOS] Fix NRE on load (can+t find the reason this happens) * [MacOS] Fix uneven rows * [MacOS] Fix header sizing on ListViewRenderer * [Controls] More stuff on HanselForms * [MacOS] Remove warning from ListViewRenderer * [MacOS] Fix PageRenderer bug double init * [MacOS] Don't calculate height if RowHeight is provided * [Controls] More Hanselforms stuff * [MacOS] Once again a new implementation for the NavigationBar, this time using a custom view to support BackgroundColor * [MacOS] Fix build * [MacOS] Refactoring AwesomeBar related controls * Fix build * [MacOS] NavigationBar update background and t test colors * [MacOS] Fix when we remove navigation so it works when the NavigationRenderer wasn't removed from the parent controller like in a TabbedPage * [MacOS] Add support for ListView grouping * [MacOS] Fix image extension method. * [MacOS] Add base Maps project * [MacOS] Export MapRenderer * [MacOS] Add pin click and geocoderbacked for Maps * [MacOS] Add extra binding project for API not in stable. * [MacOS] Add MacOS Maps lib * [MacOS]Fix build on alpha * [MacOS] Remove MacOS Maps extra binding * [UITest] Basic macOS setup * [UITest] Add MacOSApp wrapper implementation * [MacOS] Set AutomationID * [UITests] Add ActionSheetUITests to MacOS UITest * [MacOS] Fix bug on Picker * [UITests] Link basic uitest basefixture and related files * [MacOS] Fix pickers reuse * [UItests] Fix MacOS app path * [UITest] Ignore UItest for appearing on macOS for now * [UITest] Update macOS for 2.0.3 * [UITest] Refactor EnterText MacOS app * [UITest]Fix ViewQuery on MacOS * [UITest]Fix IsEnabled UItest on macOS * [UITest] Implement Enter, mark some tests inconclusive fix others * [MacOS] Implement Entry Completed event * [UITests] Fix UITest for IsVisible, ignore ToolbarItem test for now * [UITests] Fix ISVisible again add extra category * [Controls] Cleanup macOS gallery * [MacOS] Fix Assembly info * [Docs] Fix docs * Fix build * [Nuget] Fix nuspec * [Controls] Link files on MacOS * [Core] Update Forms stack before firing a event saying page was removed, possible breaking change * [MacOS] Implement RemovePage on NavigationPAgeRenderer * [UItest] Ignore some , implement back on MacOS UITest app * [MacOS] Add default back button name (needs to be translated) * [MacOS] Fix dispose * [UITest] Make 29257 work on MacOS * [MacOS] Rename stuff * [MacOS] More renaming and cleanup * [MacOS] Share implementations for iOS * [MacOS] Reuse more IOS extensions * [MacOS] Reuse FontExtensions * [MacOS] Share NativeViewWrapper related stuff * [MAcOS] Share event args and ExportRenderer * [MacOS] Share platform effect * [MacOS] Fix build * [Docs]Fixing docs * [MacOS] Fix ViewCell reuse * [Core] Support ListView CachingStrategy on MacOS * [MacOS] Fix issues with TextCell and ImageCell (we can’t set null to a NSControl value) * [MacOS] Fix MDP child sizing bug [UITest] Query marked by id and text * [MacOS] Comment test related with context actions * [MacOS] Implement missing stuff on ticker * [MacOS] Make sure VisualElemenTracker calls the ticker update * [UITests]Ignore context actions and not possible to test * [MacOS] Fix Grouping bug on Listview * [MacOS] Fix selection on Listview when using grouping * [MacOS] Update navbar when page is popped * [MacOS] Cleanup NavigationBar * [Controls] More info on exceptions * [MacOS] Fix bug animation pop modal * [MacOS] Bring back BackgroundColor of NavigationBar * [MacOS] Fix UITest animation delay * [MacOS] Treat warnings as errors * [MacOS] Center title on toolbar * [Core] Add Platform configuration specific for MacOS * [MacOS] Implement TabbedPage platform specific to handle TabItems on NavigationPage bar * [MacOS] Fix warning * [MacOS] Fix bug on SearchBar color * [MacOS]Fix build * [MacOS] remove extra dll from maps * [Docs] Update docs * [MacOS]Cleanup and refactoring * Revert "[MacOS] remove extra dll from maps" This reverts commit 73b948937001fea3f28449a963d0b94943e07aa0. * [MacOS] Fix wrong refactoring * [MacOS] Remove gallery and uitest project * [MacOS] dix formatting * [MacOS] Remove extra stuff * Merge branch 'master' into macOS-gallery * [MacOS] Fix rebase * [MacOS] Fix TargetPlatform * fix docs * [MacOS] Fix bug on TabbedPageRenderer no title * [MacOS] Remove FormsNSView * [MacOS] Cleanup on dispose on MDP renderer * [MacOS] Update current page when source changes * [MacOS] More cleanup * [MacOS] Make sure we show the previous page when popping a Modal * [MacOS] Fix issue with sizing the Header and visibility, remove for now header renderer reuse * [MacOS] Clean CustomNSTableView * [MacOS] Share LabelRenderer with iOS * [MacOS] Share ResourcesProvider with iOS * [MAcoS] Share VisualElementPackager with iOS * [MacOS] Share ViewRenderer with iOS * [MacOS] Merge with VisualElementTracker from iOS * [MacOS] Merge with EventTracker from iOS * [MacOS] Merge with VisualElementRenderer of iOS * [MacOS] Make sure we always have a layer * [MacOS] Fix Tracker merge with iOS version * [MacOS] Fix bug with tabbed page on modal without navigation * [Core] Rever change on core * [MacOS] Clear renderers before setting them MDP * [MacOS] Update tabbedPage ContainerArea * [MacOS] Fix ListViewRenderer * [MacOS] Make sure we don’t pass null to TextField string value * [MacOS] Support for multiple clicks in same selected item on NSTableView * [MacOS] Support Focus on EntryRenderer * [MacOS] Fix index bug on TablevIewDataSource * [MacOS] Fix SelectedItem TableViewDataSource * [Nuget] Add Mac to Maps nuspec * [Nuget]Fix path * [macOS] Fixed Tab NSImage crash in TabbedPageRenderer (#705) * [macOS] Fixed Tab NSImage crash in TabbedPageRenderer * Coding Style * Coding Style * [MacOS] Fix previous merge with master * [MacOS] Possible simple fix for click on views overlapping * [MacOS] Rename to IsOnViewCell * [MacOS] Cleanup, Address feedback from Samantha’s review
Diffstat (limited to 'Xamarin.Forms.Platform.iOS')
-rw-r--r--Xamarin.Forms.Platform.iOS/Deserializer.cs5
-rw-r--r--Xamarin.Forms.Platform.iOS/EffectUtilities.cs6
-rw-r--r--Xamarin.Forms.Platform.iOS/ElementChangedEventArgs.cs8
-rw-r--r--Xamarin.Forms.Platform.iOS/EventTracker.cs110
-rw-r--r--Xamarin.Forms.Platform.iOS/ExportRendererAttribute.cs12
-rw-r--r--Xamarin.Forms.Platform.iOS/Extensions/ColorExtensions.cs47
-rw-r--r--Xamarin.Forms.Platform.iOS/Extensions/DateExtensions.cs5
-rw-r--r--Xamarin.Forms.Platform.iOS/Extensions/LayoutExtensions.cs21
-rw-r--r--Xamarin.Forms.Platform.iOS/Extensions/PlatformConfigurationExtensions.cs11
-rw-r--r--Xamarin.Forms.Platform.iOS/Extensions/UIViewExtensions.cs45
-rw-r--r--Xamarin.Forms.Platform.iOS/Forms.cs57
-rw-r--r--Xamarin.Forms.Platform.iOS/IVisualElementRenderer.cs13
-rw-r--r--Xamarin.Forms.Platform.iOS/NativeValueConverterService.cs13
-rw-r--r--Xamarin.Forms.Platform.iOS/NativeViewPropertyListener.cs7
-rw-r--r--Xamarin.Forms.Platform.iOS/NativeViewWrapper.cs12
-rw-r--r--Xamarin.Forms.Platform.iOS/NativeViewWrapperRenderer.cs30
-rw-r--r--Xamarin.Forms.Platform.iOS/PlatformEffect.cs9
-rw-r--r--Xamarin.Forms.Platform.iOS/RendererPool.cs8
-rw-r--r--Xamarin.Forms.Platform.iOS/Renderers/FontExtensions.cs108
-rw-r--r--Xamarin.Forms.Platform.iOS/Renderers/FormattedStringExtensions.cs35
-rw-r--r--Xamarin.Forms.Platform.iOS/Renderers/LabelRenderer.cs97
-rw-r--r--Xamarin.Forms.Platform.iOS/ResourcesProvider.cs16
-rw-r--r--Xamarin.Forms.Platform.iOS/ViewInitializedEventArgs.cs9
-rw-r--r--Xamarin.Forms.Platform.iOS/ViewRenderer.cs52
-rw-r--r--Xamarin.Forms.Platform.iOS/VisualElementPackager.cs10
-rw-r--r--Xamarin.Forms.Platform.iOS/VisualElementRenderer.cs94
-rw-r--r--Xamarin.Forms.Platform.iOS/VisualElementTracker.cs61
27 files changed, 767 insertions, 134 deletions
diff --git a/Xamarin.Forms.Platform.iOS/Deserializer.cs b/Xamarin.Forms.Platform.iOS/Deserializer.cs
index 86657578..dcef049c 100644
--- a/Xamarin.Forms.Platform.iOS/Deserializer.cs
+++ b/Xamarin.Forms.Platform.iOS/Deserializer.cs
@@ -6,7 +6,12 @@ using System.Runtime.Serialization;
using System.Threading.Tasks;
using System.Xml;
+#if __MOBILE__
namespace Xamarin.Forms.Platform.iOS
+#else
+
+namespace Xamarin.Forms.Platform.MacOS
+#endif
{
internal class Deserializer : IDeserializer
{
diff --git a/Xamarin.Forms.Platform.iOS/EffectUtilities.cs b/Xamarin.Forms.Platform.iOS/EffectUtilities.cs
index c9523479..6b053787 100644
--- a/Xamarin.Forms.Platform.iOS/EffectUtilities.cs
+++ b/Xamarin.Forms.Platform.iOS/EffectUtilities.cs
@@ -1,4 +1,10 @@
+
+#if __MOBILE__
namespace Xamarin.Forms.Platform.iOS
+#else
+
+namespace Xamarin.Forms.Platform.MacOS
+#endif
{
internal static class EffectUtilities
{
diff --git a/Xamarin.Forms.Platform.iOS/ElementChangedEventArgs.cs b/Xamarin.Forms.Platform.iOS/ElementChangedEventArgs.cs
index 560cfd1c..49cf85d9 100644
--- a/Xamarin.Forms.Platform.iOS/ElementChangedEventArgs.cs
+++ b/Xamarin.Forms.Platform.iOS/ElementChangedEventArgs.cs
@@ -1,10 +1,16 @@
using System;
+#if __MOBILE__
namespace Xamarin.Forms.Platform.iOS
+#else
+
+namespace Xamarin.Forms.Platform.MacOS
+#endif
{
public class VisualElementChangedEventArgs : ElementChangedEventArgs<VisualElement>
{
- public VisualElementChangedEventArgs(VisualElement oldElement, VisualElement newElement) : base(oldElement, newElement)
+ public VisualElementChangedEventArgs(VisualElement oldElement, VisualElement newElement)
+ : base(oldElement, newElement)
{
}
}
diff --git a/Xamarin.Forms.Platform.iOS/EventTracker.cs b/Xamarin.Forms.Platform.iOS/EventTracker.cs
index 9c6c90e9..596506a5 100644
--- a/Xamarin.Forms.Platform.iOS/EventTracker.cs
+++ b/Xamarin.Forms.Platform.iOS/EventTracker.cs
@@ -3,27 +3,42 @@ using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Collections.Specialized;
using System.Linq;
+
+#if __MOBILE__
using UIKit;
+using NativeView = UIKit.UIView;
+using NativeGestureRecognizer = UIKit.UIGestureRecognizer;
+using NativeGestureRecognizerState = UIKit.UIGestureRecognizerState;
namespace Xamarin.Forms.Platform.iOS
+#else
+using AppKit;
+using NativeView = AppKit.NSView;
+using NativeGestureRecognizer = AppKit.NSGestureRecognizer;
+using NativeGestureRecognizerState = AppKit.NSGestureRecognizerState;
+
+namespace Xamarin.Forms.Platform.MacOS
+#endif
{
public class EventTracker : IDisposable
{
readonly NotifyCollectionChangedEventHandler _collectionChangedHandler;
- readonly Dictionary<IGestureRecognizer, UIGestureRecognizer> _gestureRecognizers = new Dictionary<IGestureRecognizer, UIGestureRecognizer>();
+ readonly Dictionary<IGestureRecognizer, NativeGestureRecognizer> _gestureRecognizers = new Dictionary<IGestureRecognizer, NativeGestureRecognizer>();
readonly IVisualElementRenderer _renderer;
bool _disposed;
- UIView _handler;
+ NativeView _handler;
double _previousScale = 1.0;
+#if __MOBILE__
UITouchEventArgs _shouldReceive;
+#endif
public EventTracker(IVisualElementRenderer renderer)
{
if (renderer == null)
- throw new ArgumentNullException("renderer");
+ throw new ArgumentNullException(nameof(renderer));
_collectionChangedHandler = ModelGestureRecognizersOnCollectionChanged;
@@ -62,18 +77,18 @@ namespace Xamarin.Forms.Platform.iOS
_handler = null;
}
- public void LoadEvents(UIView handler)
+ public void LoadEvents(NativeView handler)
{
if (_disposed)
throw new ObjectDisposedException(null);
-
+#if __MOBILE__
_shouldReceive = (r, t) => t.View is IVisualElementRenderer;
-
+#endif
_handler = handler;
OnElementChanged(this, new VisualElementChangedEventArgs(null, _renderer.Element));
}
- protected virtual UIGestureRecognizer GetNativeRecognizer(IGestureRecognizer recognizer)
+ protected virtual NativeGestureRecognizer GetNativeRecognizer(IGestureRecognizer recognizer)
{
if (recognizer == null)
return null;
@@ -84,7 +99,7 @@ namespace Xamarin.Forms.Platform.iOS
var tapRecognizer = recognizer as TapGestureRecognizer;
if (tapRecognizer != null)
{
- var uiRecognizer = CreateTapRecognizer(1, tapRecognizer.NumberOfTapsRequired, r =>
+ var returnAction = new Action(() =>
{
var tapGestureRecognizer = weakRecognizer.Target as TapGestureRecognizer;
var eventTracker = weakEventTracker.Target as EventTracker;
@@ -93,6 +108,7 @@ namespace Xamarin.Forms.Platform.iOS
if (tapGestureRecognizer != null && view != null)
tapGestureRecognizer.SendTapped(view);
});
+ var uiRecognizer = CreateTapRecognizer(tapRecognizer.NumberOfTapsRequired, returnAction);
return uiRecognizer;
}
@@ -110,41 +126,51 @@ namespace Xamarin.Forms.Platform.iOS
{
var oldScale = eventTracker._previousScale;
var originPoint = r.LocationInView(null);
+#if __MOBILE__
originPoint = UIApplication.SharedApplication.KeyWindow.ConvertPointToView(originPoint, eventTracker._renderer.NativeView);
+#else
+ originPoint = NSApplication.SharedApplication.KeyWindow.ContentView.ConvertPointToView(originPoint, eventTracker._renderer.NativeView);
+#endif
var scaledPoint = new Point(originPoint.X / view.Width, originPoint.Y / view.Height);
switch (r.State)
{
- case UIGestureRecognizerState.Began:
+ case NativeGestureRecognizerState.Began:
+#if __MOBILE__
if (r.NumberOfTouches < 2)
return;
+#endif
pinchGestureRecognizer.SendPinchStarted(view, scaledPoint);
startingScale = view.Scale;
break;
- case UIGestureRecognizerState.Changed:
+ case NativeGestureRecognizerState.Changed:
+#if __MOBILE__
if (r.NumberOfTouches < 2 && pinchGestureRecognizer.IsPinching)
{
- r.State = UIGestureRecognizerState.Ended;
+ r.State = NativeGestureRecognizerState.Ended;
pinchGestureRecognizer.SendPinchEnded(view);
return;
}
-
+ var scale = r.Scale;
+#else
+ var scale = r.Magnification;
+#endif
var delta = 1.0;
- var dif = Math.Abs(r.Scale - oldScale) * startingScale;
- if (oldScale < r.Scale)
+ var dif = Math.Abs(scale - oldScale) * startingScale;
+ if (oldScale < scale)
delta = 1 + dif;
- if (oldScale > r.Scale)
+ if (oldScale > scale)
delta = 1 - dif;
pinchGestureRecognizer.SendPinch(view, delta, scaledPoint);
- eventTracker._previousScale = r.Scale;
+ eventTracker._previousScale = scale;
break;
- case UIGestureRecognizerState.Cancelled:
- case UIGestureRecognizerState.Failed:
+ case NativeGestureRecognizerState.Cancelled:
+ case NativeGestureRecognizerState.Failed:
if (pinchGestureRecognizer.IsPinching)
pinchGestureRecognizer.SendPinchCanceled(view);
break;
- case UIGestureRecognizerState.Ended:
+ case NativeGestureRecognizerState.Ended:
if (pinchGestureRecognizer.IsPinching)
pinchGestureRecognizer.SendPinchEnded(view);
eventTracker._previousScale = 1;
@@ -168,33 +194,42 @@ namespace Xamarin.Forms.Platform.iOS
{
switch (r.State)
{
- case UIGestureRecognizerState.Began:
+ case NativeGestureRecognizerState.Began:
+#if __MOBILE__
if (r.NumberOfTouches != panRecognizer.TouchPoints)
return;
+#endif
panGestureRecognizer.SendPanStarted(view, Application.Current.PanGestureId);
break;
- case UIGestureRecognizerState.Changed:
+ case NativeGestureRecognizerState.Changed:
+#if __MOBILE__
if (r.NumberOfTouches != panRecognizer.TouchPoints)
{
- r.State = UIGestureRecognizerState.Ended;
+ r.State = NativeGestureRecognizerState.Ended;
panGestureRecognizer.SendPanCompleted(view, Application.Current.PanGestureId);
Application.Current.PanGestureId++;
return;
}
+#endif
var translationInView = r.TranslationInView(_handler);
panGestureRecognizer.SendPan(view, translationInView.X, translationInView.Y, Application.Current.PanGestureId);
break;
- case UIGestureRecognizerState.Cancelled:
- case UIGestureRecognizerState.Failed:
+ case NativeGestureRecognizerState.Cancelled:
+ case NativeGestureRecognizerState.Failed:
panGestureRecognizer.SendPanCanceled(view, Application.Current.PanGestureId);
Application.Current.PanGestureId++;
break;
- case UIGestureRecognizerState.Ended:
+ case NativeGestureRecognizerState.Ended:
+#if __MOBILE__
if (r.NumberOfTouches != panRecognizer.TouchPoints)
{
panGestureRecognizer.SendPanCompleted(view, Application.Current.PanGestureId);
Application.Current.PanGestureId++;
}
+#else
+ panGestureRecognizer.SendPanCompleted(view, Application.Current.PanGestureId);
+ Application.Current.PanGestureId++;
+#endif
break;
}
}
@@ -204,7 +239,7 @@ namespace Xamarin.Forms.Platform.iOS
return null;
}
-
+#if __MOBILE__
UIPanGestureRecognizer CreatePanRecognizer(int numTouches, Action<UIPanGestureRecognizer> action)
{
var result = new UIPanGestureRecognizer(action);
@@ -218,14 +253,33 @@ namespace Xamarin.Forms.Platform.iOS
return result;
}
- UITapGestureRecognizer CreateTapRecognizer(int numFingers, int numTaps, Action<UITapGestureRecognizer> action)
+ UITapGestureRecognizer CreateTapRecognizer(int numTaps, Action action, int numFingers = 1)
{
var result = new UITapGestureRecognizer(action);
result.NumberOfTouchesRequired = (uint)numFingers;
result.NumberOfTapsRequired = (uint)numTaps;
return result;
}
+#else
+ NSPanGestureRecognizer CreatePanRecognizer(int numTouches, Action<NSPanGestureRecognizer> action)
+ {
+ var result = new NSPanGestureRecognizer(action);
+ return result;
+ }
+
+ NSMagnificationGestureRecognizer CreatePinchRecognizer(Action<NSMagnificationGestureRecognizer> action)
+ {
+ var result = new NSMagnificationGestureRecognizer(action);
+ return result;
+ }
+ NSClickGestureRecognizer CreateTapRecognizer(int numTaps, Action action)
+ {
+ var result = new NSClickGestureRecognizer(action);
+ result.NumberOfClicksRequired = numTaps;
+ return result;
+ }
+#endif
void LoadRecognizers()
{
if (ElementGestureRecognizers == null)
@@ -239,7 +293,9 @@ namespace Xamarin.Forms.Platform.iOS
var nativeRecognizer = GetNativeRecognizer(recognizer);
if (nativeRecognizer != null)
{
+#if __MOBILE__
nativeRecognizer.ShouldReceiveTouch = _shouldReceive;
+#endif
_handler.AddGestureRecognizer(nativeRecognizer);
_gestureRecognizers[recognizer] = nativeRecognizer;
diff --git a/Xamarin.Forms.Platform.iOS/ExportRendererAttribute.cs b/Xamarin.Forms.Platform.iOS/ExportRendererAttribute.cs
index 50bba17f..3b3ef91b 100644
--- a/Xamarin.Forms.Platform.iOS/ExportRendererAttribute.cs
+++ b/Xamarin.Forms.Platform.iOS/ExportRendererAttribute.cs
@@ -1,29 +1,37 @@
using System;
+
+#if __MOBILE__
using UIKit;
+#endif
namespace Xamarin.Forms
{
[AttributeUsage(AttributeTargets.Assembly, AllowMultiple = true)]
public sealed class ExportRendererAttribute : HandlerAttribute
{
+#if __MOBILE__
public ExportRendererAttribute(Type handler, Type target, UIUserInterfaceIdiom idiom) : base(handler, target)
{
Idiomatic = true;
Idiom = idiom;
}
+ internal UIUserInterfaceIdiom Idiom { get; }
+#endif
public ExportRendererAttribute(Type handler, Type target) : base(handler, target)
{
Idiomatic = false;
}
- internal UIUserInterfaceIdiom Idiom { get; }
-
internal bool Idiomatic { get; }
public override bool ShouldRegister()
{
+#if __MOBILE__
return !Idiomatic || Idiom == UIDevice.CurrentDevice.UserInterfaceIdiom;
+#else
+ return !Idiomatic;
+#endif
}
}
} \ No newline at end of file
diff --git a/Xamarin.Forms.Platform.iOS/Extensions/ColorExtensions.cs b/Xamarin.Forms.Platform.iOS/Extensions/ColorExtensions.cs
index bb4342ab..2b8b9101 100644
--- a/Xamarin.Forms.Platform.iOS/Extensions/ColorExtensions.cs
+++ b/Xamarin.Forms.Platform.iOS/Extensions/ColorExtensions.cs
@@ -1,16 +1,27 @@
using System;
using CoreGraphics;
-using UIKit;
using PointF = CoreGraphics.CGPoint;
using RectangleF = CoreGraphics.CGRect;
using SizeF = CoreGraphics.CGSize;
-
+#if __MOBILE__
+using UIKit;
namespace Xamarin.Forms.Platform.iOS
+#else
+using AppKit;
+using UIColor = AppKit.NSColor;
+
+namespace Xamarin.Forms.Platform.MacOS
+#endif
{
public static class ColorExtensions
{
+#if __MOBILE__
internal static readonly UIColor Black = UIColor.Black;
internal static readonly UIColor SeventyPercentGrey = new UIColor(0.7f, 0.7f, 0.7f, 1);
+#else
+ internal static readonly NSColor Black = NSColor.Black;
+ internal static readonly NSColor SeventyPercentGrey = NSColor.FromRgba(0.7f, 0.7f, 0.7f, 1);
+#endif
public static CGColor ToCGColor(this Color color)
{
@@ -23,10 +34,15 @@ namespace Xamarin.Forms.Platform.iOS
nfloat green;
nfloat blue;
nfloat alpha;
+#if __MOBILE__
color.GetRGBA(out red, out green, out blue, out alpha);
+#else
+ color.GetRgba(out red, out green, out blue, out alpha);
+#endif
return new Color(red, green, blue, alpha);
}
+#if __MOBILE__
public static UIColor ToUIColor(this Color color)
{
return new UIColor((float)color.R, (float)color.G, (float)color.B, (float)color.A);
@@ -47,6 +63,28 @@ namespace Xamarin.Forms.Platform.iOS
return color.ToUIColor();
}
+#else
+ public static NSColor ToNSColor(this Color color)
+ {
+ return NSColor.FromRgba((float)color.R, (float)color.G, (float)color.B, (float)color.A);
+ }
+
+ public static NSColor ToNSColor(this Color color, Color defaultColor)
+ {
+ if (color.IsDefault)
+ return defaultColor.ToNSColor();
+
+ return color.ToNSColor();
+ }
+
+ public static NSColor ToNSColor(this Color color, NSColor defaultColor)
+ {
+ if (color.IsDefault)
+ return defaultColor;
+
+ return color.ToNSColor();
+ }
+#endif
}
public static class PointExtensions
@@ -55,6 +93,11 @@ namespace Xamarin.Forms.Platform.iOS
{
return new Point(point.X, point.Y);
}
+
+ public static PointF ToPointF(this Point point)
+ {
+ return new PointF(point.X, point.Y);
+ }
}
public static class SizeExtensions
diff --git a/Xamarin.Forms.Platform.iOS/Extensions/DateExtensions.cs b/Xamarin.Forms.Platform.iOS/Extensions/DateExtensions.cs
index bb0dfff9..73ca347c 100644
--- a/Xamarin.Forms.Platform.iOS/Extensions/DateExtensions.cs
+++ b/Xamarin.Forms.Platform.iOS/Extensions/DateExtensions.cs
@@ -1,7 +1,12 @@
using System;
using Foundation;
+#if __MOBILE__
namespace Xamarin.Forms.Platform.iOS
+#else
+
+namespace Xamarin.Forms.Platform.MacOS
+#endif
{
public static class DateExtensions
{
diff --git a/Xamarin.Forms.Platform.iOS/Extensions/LayoutExtensions.cs b/Xamarin.Forms.Platform.iOS/Extensions/LayoutExtensions.cs
index 823c3f30..d65caf12 100644
--- a/Xamarin.Forms.Platform.iOS/Extensions/LayoutExtensions.cs
+++ b/Xamarin.Forms.Platform.iOS/Extensions/LayoutExtensions.cs
@@ -1,10 +1,19 @@
using System.Collections.Generic;
using CoreGraphics;
+#if __MOBILE__
using UIKit;
-
+using Xamarin.Forms.Platform.iOS;
namespace Xamarin.Forms.Platform.iOS
+#else
+using AppKit;
+using UIView = AppKit.NSView;
+using Xamarin.Forms.Platform.MacOS;
+
+namespace Xamarin.Forms.Platform.MacOS
+#endif
{
- public delegate SizeRequest? GetDesiredSizeDelegate(NativeViewWrapperRenderer renderer, double widthConstraint, double heightConstraint);
+ public delegate SizeRequest? GetDesiredSizeDelegate(
+ NativeViewWrapperRenderer renderer, double widthConstraint, double heightConstraint);
public delegate CGSize? SizeThatFitsDelegate(CGSize size);
@@ -12,13 +21,15 @@ namespace Xamarin.Forms.Platform.iOS
public static class LayoutExtensions
{
- public static void Add(this IList<View> children, UIView view, GetDesiredSizeDelegate getDesiredSizeDelegate = null, SizeThatFitsDelegate sizeThatFitsDelegate = null,
- LayoutSubviewsDelegate layoutSubViews = null)
+ public static void Add(this IList<View> children, UIView view, GetDesiredSizeDelegate getDesiredSizeDelegate = null,
+ SizeThatFitsDelegate sizeThatFitsDelegate = null,
+ LayoutSubviewsDelegate layoutSubViews = null)
{
children.Add(view.ToView(getDesiredSizeDelegate, sizeThatFitsDelegate, layoutSubViews));
}
- public static View ToView(this UIView view, GetDesiredSizeDelegate getDesiredSizeDelegate = null, SizeThatFitsDelegate sizeThatFitsDelegate = null, LayoutSubviewsDelegate layoutSubViews = null)
+ public static View ToView(this UIView view, GetDesiredSizeDelegate getDesiredSizeDelegate = null,
+ SizeThatFitsDelegate sizeThatFitsDelegate = null, LayoutSubviewsDelegate layoutSubViews = null)
{
return new NativeViewWrapper(view, getDesiredSizeDelegate, sizeThatFitsDelegate, layoutSubViews);
}
diff --git a/Xamarin.Forms.Platform.iOS/Extensions/PlatformConfigurationExtensions.cs b/Xamarin.Forms.Platform.iOS/Extensions/PlatformConfigurationExtensions.cs
index f61837f2..f2932e3a 100644
--- a/Xamarin.Forms.Platform.iOS/Extensions/PlatformConfigurationExtensions.cs
+++ b/Xamarin.Forms.Platform.iOS/Extensions/PlatformConfigurationExtensions.cs
@@ -1,11 +1,18 @@
+#if __MOBILE__
+using CurrentPlatform = Xamarin.Forms.PlatformConfiguration.iOS;
namespace Xamarin.Forms.Platform.iOS
+#else
+using CurrentPlatform = Xamarin.Forms.PlatformConfiguration.macOS;
+
+namespace Xamarin.Forms.Platform.MacOS
+#endif
{
public static class PlatformConfigurationExtensions
{
- public static IPlatformElementConfiguration<PlatformConfiguration.iOS, T> OnThisPlatform<T>(this T element)
+ public static IPlatformElementConfiguration<CurrentPlatform, T> OnThisPlatform<T>(this T element)
where T : Element, IElementConfiguration<T>
{
- return (element).On<PlatformConfiguration.iOS>();
+ return (element).On<CurrentPlatform>();
}
}
} \ No newline at end of file
diff --git a/Xamarin.Forms.Platform.iOS/Extensions/UIViewExtensions.cs b/Xamarin.Forms.Platform.iOS/Extensions/UIViewExtensions.cs
index 4c3eed98..8248af11 100644
--- a/Xamarin.Forms.Platform.iOS/Extensions/UIViewExtensions.cs
+++ b/Xamarin.Forms.Platform.iOS/Extensions/UIViewExtensions.cs
@@ -2,10 +2,15 @@ using System;
using System.Collections.Generic;
using System.Drawing;
using System.Linq;
-using UIKit;
using static System.String;
-
+#if __MOBILE__
+using UIKit;
namespace Xamarin.Forms.Platform.iOS
+#else
+using UIView = AppKit.NSView;
+
+namespace Xamarin.Forms.Platform.MacOS
+#endif
{
public static class UIViewExtensions
{
@@ -16,15 +21,28 @@ namespace Xamarin.Forms.Platform.iOS
return self.Subviews.Concat(self.Subviews.SelectMany(s => s.Descendants()));
}
- public static SizeRequest GetSizeRequest(this UIView self, double widthConstraint, double heightConstraint, double minimumWidth = -1, double minimumHeight = -1)
+ public static SizeRequest GetSizeRequest(this UIView self, double widthConstraint, double heightConstraint,
+ double minimumWidth = -1, double minimumHeight = -1)
{
- var s = self.SizeThatFits(new SizeF((float)widthConstraint, (float)heightConstraint));
- var request = new Size(s.Width == float.PositiveInfinity ? double.PositiveInfinity : s.Width, s.Height == float.PositiveInfinity ? double.PositiveInfinity : s.Height);
- var minimum = new Size(minimumWidth < 0 ? request.Width : minimumWidth, minimumHeight < 0 ? request.Height : minimumHeight);
+ CoreGraphics.CGSize s;
+#if __MOBILE__
+ s = self.SizeThatFits(new SizeF((float)widthConstraint, (float)heightConstraint));
+#else
+ var control = self as AppKit.NSControl;
+ if (control != null)
+ s = control.SizeThatFits(new CoreGraphics.CGSize(widthConstraint, heightConstraint));
+ else
+ s = self.FittingSize;
+#endif
+ var request = new Size(s.Width == float.PositiveInfinity ? double.PositiveInfinity : s.Width,
+ s.Height == float.PositiveInfinity ? double.PositiveInfinity : s.Height);
+ var minimum = new Size(minimumWidth < 0 ? request.Width : minimumWidth,
+ minimumHeight < 0 ? request.Height : minimumHeight);
return new SizeRequest(request, minimum);
}
- public static void SetBinding(this UIView view, string propertyName, BindingBase bindingBase, string updateSourceEventName = null)
+ public static void SetBinding(this UIView view, string propertyName, BindingBase bindingBase,
+ string updateSourceEventName = null)
{
var binding = bindingBase as Binding;
//This will allow setting bindings from Xaml by reusing the MarkupExtension
@@ -51,6 +69,7 @@ namespace Xamarin.Forms.Platform.iOS
view.AddObserver(nativePropertyListener, key, Foundation.NSKeyValueObservingOptions.New, IntPtr.Zero);
}
}
+#if __MOBILE__
catch (Foundation.MonoTouchException ex)
{
nativePropertyListener = null;
@@ -61,7 +80,12 @@ namespace Xamarin.Forms.Platform.iOS
}
throw ex;
}
-
+#else
+ catch (Exception ex)
+ {
+ throw ex;
+ }
+#endif
}
NativeBindingHelpers.SetBinding(view, propertyName, bindingBase, nativePropertyListener);
@@ -77,7 +101,8 @@ namespace Xamarin.Forms.Platform.iOS
NativeBindingHelpers.SetValue(target, targetProperty, value);
}
- public static void SetBindingContext(this UIView target, object bindingContext, Func<UIView, IEnumerable<UIView>> getChildren = null)
+ public static void SetBindingContext(this UIView target, object bindingContext,
+ Func<UIView, IEnumerable<UIView>> getChildren = null)
{
NativeBindingHelpers.SetBindingContext(target, bindingContext, getChildren);
}
@@ -107,6 +132,7 @@ namespace Xamarin.Forms.Platform.iOS
return null;
}
+#if __MOBILE__
internal static UIView FindFirstResponder(this UIView view)
{
if (view.IsFirstResponder)
@@ -121,5 +147,6 @@ namespace Xamarin.Forms.Platform.iOS
return null;
}
+#endif
}
} \ No newline at end of file
diff --git a/Xamarin.Forms.Platform.iOS/Forms.cs b/Xamarin.Forms.Platform.iOS/Forms.cs
index 2c8fc6f7..d6e7e07f 100644
--- a/Xamarin.Forms.Platform.iOS/Forms.cs
+++ b/Xamarin.Forms.Platform.iOS/Forms.cs
@@ -11,11 +11,18 @@ using System.Security.Cryptography;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
-using CoreFoundation;
+using Xamarin.Forms.Internals;
using Foundation;
+#if __MOBILE__
using UIKit;
-using Xamarin.Forms.Internals;
using Xamarin.Forms.Platform.iOS;
+using TNativeView = UIKit.UIView;
+#else
+using AppKit;
+using Xamarin.Forms.Platform.MacOS;
+using TNativeView = AppKit.NSView;
+
+#endif
namespace Xamarin.Forms
{
@@ -24,7 +31,11 @@ namespace Xamarin.Forms
//Preserve GetCallingAssembly
static readonly bool nevertrue = false;
+ public static bool IsInitialized { get; private set; }
+
+#if __MOBILE__
static bool? s_isiOS9OrNewer;
+#endif
static Forms()
{
@@ -32,8 +43,7 @@ namespace Xamarin.Forms
Assembly.GetCallingAssembly();
}
- public static bool IsInitialized { get; private set; }
-
+#if __MOBILE__
internal static bool IsiOS9OrNewer
{
get
@@ -43,6 +53,7 @@ namespace Xamarin.Forms
return s_isiOS9OrNewer.Value;
}
}
+#endif
public static void Init()
{
@@ -53,19 +64,22 @@ namespace Xamarin.Forms
Log.Listeners.Add(new DelegateLogListener((c, m) => Trace.WriteLine(m, c)));
+#if __MOBILE__
+ Device.Idiom = UIDevice.CurrentDevice.UserInterfaceIdiom == UIUserInterfaceIdiom.Pad ? TargetIdiom.Tablet : TargetIdiom.Phone;
+#else
+ Device.Idiom = TargetIdiom.Desktop;
+#endif
Device.PlatformServices = new IOSPlatformServices();
Device.Info = new IOSDeviceInfo();
- Registrar.RegisterAll(new[] { typeof(ExportRendererAttribute), typeof(ExportCellAttribute), typeof(ExportImageSourceHandlerAttribute) });
-
- Device.Idiom = UIDevice.CurrentDevice.UserInterfaceIdiom == UIUserInterfaceIdiom.Pad ? TargetIdiom.Tablet : TargetIdiom.Phone;
-
+ Registrar.RegisterAll(new[]
+ { typeof(ExportRendererAttribute), typeof(ExportCellAttribute), typeof(ExportImageSourceHandlerAttribute) });
ExpressionSearch.Default = new iOSExpressionSearch();
}
public static event EventHandler<ViewInitializedEventArgs> ViewInitialized;
- internal static void SendViewInitialized(this VisualElement self, UIView nativeView)
+ internal static void SendViewInitialized(this VisualElement self, TNativeView nativeView)
{
ViewInitialized?.Invoke(self, new ViewInitializedEventArgs { View = self, NativeView = nativeView });
}
@@ -99,16 +113,22 @@ namespace Xamarin.Forms
internal class IOSDeviceInfo : DeviceInfo
{
+#if __MOBILE__
readonly NSObject _notification;
+#endif
readonly Size _scaledScreenSize;
readonly double _scalingFactor;
public IOSDeviceInfo()
{
+#if __MOBILE__
_notification = UIDevice.Notifications.ObserveOrientationDidChange((sender, args) => CurrentOrientation = UIDevice.CurrentDevice.Orientation.ToDeviceOrientation());
-
_scalingFactor = UIScreen.MainScreen.Scale;
_scaledScreenSize = new Size(UIScreen.MainScreen.Bounds.Width, UIScreen.MainScreen.Bounds.Height);
+#else
+ _scalingFactor = NSScreen.MainScreen.BackingScaleFactor;
+ _scaledScreenSize = new Size(NSScreen.MainScreen.Frame.Width, NSScreen.MainScreen.Frame.Height);
+#endif
PixelScreenSize = new Size(_scaledScreenSize.Width * _scalingFactor, _scaledScreenSize.Height * _scalingFactor);
}
@@ -120,7 +140,9 @@ namespace Xamarin.Forms
protected override void Dispose(bool disposing)
{
+#if __MOBILE__
_notification.Dispose();
+#endif
base.Dispose(disposing);
}
}
@@ -198,11 +220,19 @@ namespace Xamarin.Forms
public bool IsInvokeRequired => !NSThread.IsMain;
+#if __MOBILE__
public string RuntimePlatform => Device.iOS;
+#else
+ public string RuntimePlatform => Device.macOS;
+#endif
public void OpenUriAction(Uri uri)
{
+#if __MOBILE__
UIApplication.SharedApplication.OpenUrl(new NSUrl(uri.AbsoluteUri));
+#else
+ NSWorkspace.SharedWorkspace.OpenUrl(new NSUrl(uri.AbsoluteUri));
+#endif
}
public void StartTimer(TimeSpan interval, Func<bool> callback)
@@ -217,11 +247,11 @@ namespace Xamarin.Forms
HttpClient GetHttpClient()
{
- var proxy = CFNetwork.GetSystemProxySettings();
+ var proxy = CoreFoundation.CFNetwork.GetSystemProxySettings();
var handler = new HttpClientHandler();
if (!string.IsNullOrEmpty(proxy.HTTPProxy))
{
- handler.Proxy = CFNetwork.GetDefaultProxy();
+ handler.Proxy = CoreFoundation.CFNetwork.GetDefaultProxy();
handler.UseProxy = true;
}
return new HttpClient(handler);
@@ -272,7 +302,8 @@ namespace Xamarin.Forms
public Task<Stream> OpenFileAsync(string path, FileMode mode, FileAccess access, FileShare share)
{
- Stream stream = _isolatedStorageFile.OpenFile(path, (System.IO.FileMode)mode, (System.IO.FileAccess)access, (System.IO.FileShare)share);
+ Stream stream = _isolatedStorageFile.OpenFile(path, (System.IO.FileMode)mode, (System.IO.FileAccess)access,
+ (System.IO.FileShare)share);
return Task.FromResult(stream);
}
}
diff --git a/Xamarin.Forms.Platform.iOS/IVisualElementRenderer.cs b/Xamarin.Forms.Platform.iOS/IVisualElementRenderer.cs
index 9a2bf580..ffb2de29 100644
--- a/Xamarin.Forms.Platform.iOS/IVisualElementRenderer.cs
+++ b/Xamarin.Forms.Platform.iOS/IVisualElementRenderer.cs
@@ -1,15 +1,24 @@
using System;
+#if __MOBILE__
using UIKit;
+using NativeView = UIKit.UIView;
+using NativeViewController = UIKit.UIViewController;
namespace Xamarin.Forms.Platform.iOS
+#else
+using NativeView = AppKit.NSView;
+using NativeViewController = AppKit.NSViewController;
+
+namespace Xamarin.Forms.Platform.MacOS
+#endif
{
public interface IVisualElementRenderer : IDisposable, IRegisterable
{
VisualElement Element { get; }
- UIView NativeView { get; }
+ NativeView NativeView { get; }
- UIViewController ViewController { get; }
+ NativeViewController ViewController { get; }
event EventHandler<VisualElementChangedEventArgs> ElementChanged;
diff --git a/Xamarin.Forms.Platform.iOS/NativeValueConverterService.cs b/Xamarin.Forms.Platform.iOS/NativeValueConverterService.cs
index 9e20e045..acdd6523 100644
--- a/Xamarin.Forms.Platform.iOS/NativeValueConverterService.cs
+++ b/Xamarin.Forms.Platform.iOS/NativeValueConverterService.cs
@@ -1,16 +1,23 @@
using System;
+#if __MOBILE__
using UIKit;
-
[assembly: Xamarin.Forms.Dependency(typeof(Xamarin.Forms.Platform.iOS.NativeValueConverterService))]
-
namespace Xamarin.Forms.Platform.iOS
+#else
+using UIView = AppKit.NSView;
+
+[assembly: Xamarin.Forms.Dependency(typeof(Xamarin.Forms.Platform.MacOS.NativeValueConverterService))]
+
+namespace Xamarin.Forms.Platform.MacOS
+#endif
{
class NativeValueConverterService : Xaml.INativeValueConverterService
{
public bool ConvertTo(object value, Type toType, out object nativeValue)
{
nativeValue = null;
- if (typeof(UIView).IsInstanceOfType(value) && toType.IsAssignableFrom(typeof(View))) {
+ if (typeof(UIView).IsInstanceOfType(value) && toType.IsAssignableFrom(typeof(View)))
+ {
nativeValue = ((UIView)value).ToView();
return true;
}
diff --git a/Xamarin.Forms.Platform.iOS/NativeViewPropertyListener.cs b/Xamarin.Forms.Platform.iOS/NativeViewPropertyListener.cs
index 4e6601ef..e819519a 100644
--- a/Xamarin.Forms.Platform.iOS/NativeViewPropertyListener.cs
+++ b/Xamarin.Forms.Platform.iOS/NativeViewPropertyListener.cs
@@ -2,7 +2,12 @@ using System;
using System.ComponentModel;
using Foundation;
+#if __MOBILE__
namespace Xamarin.Forms.Platform.iOS
+#else
+
+namespace Xamarin.Forms.Platform.MacOS
+#endif
{
class NativeViewPropertyListener : NSObject, INotifyPropertyChanged
{
@@ -23,4 +28,4 @@ namespace Xamarin.Forms.Platform.iOS
base.ObserveValue(keyPath, ofObject, change, context);
}
}
-}
+} \ No newline at end of file
diff --git a/Xamarin.Forms.Platform.iOS/NativeViewWrapper.cs b/Xamarin.Forms.Platform.iOS/NativeViewWrapper.cs
index 31cb186d..165bc0f9 100644
--- a/Xamarin.Forms.Platform.iOS/NativeViewWrapper.cs
+++ b/Xamarin.Forms.Platform.iOS/NativeViewWrapper.cs
@@ -1,10 +1,16 @@
-using UIKit;
-
+#if __MOBILE__
+using UIKit;
namespace Xamarin.Forms.Platform.iOS
+#else
+using UIView = AppKit.NSView;
+
+namespace Xamarin.Forms.Platform.MacOS
+#endif
{
public class NativeViewWrapper : View
{
- public NativeViewWrapper(UIView nativeView, GetDesiredSizeDelegate getDesiredSizeDelegate = null, SizeThatFitsDelegate sizeThatFitsDelegate = null, LayoutSubviewsDelegate layoutSubViews = null)
+ public NativeViewWrapper(UIView nativeView, GetDesiredSizeDelegate getDesiredSizeDelegate = null,
+ SizeThatFitsDelegate sizeThatFitsDelegate = null, LayoutSubviewsDelegate layoutSubViews = null)
{
GetDesiredSizeDelegate = getDesiredSizeDelegate;
SizeThatFitsDelegate = sizeThatFitsDelegate;
diff --git a/Xamarin.Forms.Platform.iOS/NativeViewWrapperRenderer.cs b/Xamarin.Forms.Platform.iOS/NativeViewWrapperRenderer.cs
index 4d1252ee..cde9fe81 100644
--- a/Xamarin.Forms.Platform.iOS/NativeViewWrapperRenderer.cs
+++ b/Xamarin.Forms.Platform.iOS/NativeViewWrapperRenderer.cs
@@ -1,8 +1,13 @@
using CoreGraphics;
-using UIKit;
using Xamarin.Forms.Internals;
-
+#if __MOBILE__
+using UIKit;
namespace Xamarin.Forms.Platform.iOS
+#else
+using UIView = AppKit.NSView;
+
+namespace Xamarin.Forms.Platform.MacOS
+#endif
{
public class NativeViewWrapperRenderer : ViewRenderer<NativeViewWrapper, UIView>
{
@@ -19,6 +24,7 @@ namespace Xamarin.Forms.Platform.iOS
return result ?? base.GetDesiredSize(widthConstraint, heightConstraint);
}
+#if __MOBILE__
public override void LayoutSubviews()
{
if (Element?.LayoutSubViews == null)
@@ -50,6 +56,26 @@ namespace Xamarin.Forms.Platform.iOS
// if it returns null, fall back to the default implementation
return result ?? base.SizeThatFits(size);
}
+#else
+ public override void Layout()
+ {
+ if (Element?.LayoutSubViews == null)
+ {
+ ((IVisualElementController)Element)?.InvalidateMeasure(InvalidationTrigger.MeasureChanged);
+ base.Layout();
+ return;
+ }
+
+ // The user has specified a different implementation of LayoutSubviews
+ var handled = Element.LayoutSubViews();
+
+ if (!handled)
+ {
+ // If the delegate wasn't able to handle the request, fall back to the default implementation
+ base.Layout();
+ }
+ }
+#endif
protected override void OnElementChanged(ElementChangedEventArgs<NativeViewWrapper> e)
{
diff --git a/Xamarin.Forms.Platform.iOS/PlatformEffect.cs b/Xamarin.Forms.Platform.iOS/PlatformEffect.cs
index 8fb4f975..6a1ca494 100644
--- a/Xamarin.Forms.Platform.iOS/PlatformEffect.cs
+++ b/Xamarin.Forms.Platform.iOS/PlatformEffect.cs
@@ -1,6 +1,11 @@
-using UIKit;
-
+#if __MOBILE__
+using UIKit;
namespace Xamarin.Forms.Platform.iOS
+#else
+using UIView = AppKit.NSView;
+
+namespace Xamarin.Forms.Platform.MacOS
+#endif
{
public abstract class PlatformEffect : PlatformEffect<UIView, UIView>
{
diff --git a/Xamarin.Forms.Platform.iOS/RendererPool.cs b/Xamarin.Forms.Platform.iOS/RendererPool.cs
index babfa7bc..38fe3c02 100644
--- a/Xamarin.Forms.Platform.iOS/RendererPool.cs
+++ b/Xamarin.Forms.Platform.iOS/RendererPool.cs
@@ -1,11 +1,17 @@
using System;
using System.Collections.Generic;
+#if __MOBILE__
namespace Xamarin.Forms.Platform.iOS
+#else
+
+namespace Xamarin.Forms.Platform.MacOS
+#endif
{
public sealed class RendererPool
{
- readonly Dictionary<Type, Stack<IVisualElementRenderer>> _freeRenderers = new Dictionary<Type, Stack<IVisualElementRenderer>>();
+ readonly Dictionary<Type, Stack<IVisualElementRenderer>> _freeRenderers =
+ new Dictionary<Type, Stack<IVisualElementRenderer>>();
readonly VisualElement _oldElement;
diff --git a/Xamarin.Forms.Platform.iOS/Renderers/FontExtensions.cs b/Xamarin.Forms.Platform.iOS/Renderers/FontExtensions.cs
index cbc2e625..ba8acbe5 100644
--- a/Xamarin.Forms.Platform.iOS/Renderers/FontExtensions.cs
+++ b/Xamarin.Forms.Platform.iOS/Renderers/FontExtensions.cs
@@ -1,15 +1,26 @@
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
+using Xamarin.Forms;
+#if __MOBILE__
using UIKit;
-
namespace Xamarin.Forms.Platform.iOS
+#else
+using AppKit;
+using UIFont = AppKit.NSFont;
+
+namespace Xamarin.Forms.Platform.MacOS
+#endif
{
public static class FontExtensions
{
static readonly Dictionary<ToUIFontKey, UIFont> ToUiFont = new Dictionary<ToUIFontKey, UIFont>();
-
+#if __MOBILE__
public static UIFont ToUIFont(this Font self)
+
+#else
+ public static UIFont ToNSFont(this Font self)
+#endif
{
var size = (float)self.FontSize;
if (self.UseNamedSize)
@@ -41,6 +52,7 @@ namespace Xamarin.Forms.Platform.iOS
{
try
{
+#if __MOBILE__
if (UIFont.FamilyNames.Contains(self.FontFamily))
{
var descriptor = new UIFontDescriptor().CreateWithFamily(self.FontFamily);
@@ -59,6 +71,25 @@ namespace Xamarin.Forms.Platform.iOS
}
return UIFont.FromName(self.FontFamily, size);
+
+#else
+
+ var descriptor = new NSFontDescriptor().FontDescriptorWithFamily(self.FontFamily);
+
+ if (bold || italic)
+ {
+ var traits = (NSFontSymbolicTraits)0;
+ if (bold)
+ traits = traits | NSFontSymbolicTraits.BoldTrait;
+ if (italic)
+ traits = traits | NSFontSymbolicTraits.ItalicTrait;
+
+ descriptor = descriptor.FontDescriptorWithSymbolicTraits(traits);
+ return NSFont.FromDescription(descriptor, size);
+ }
+
+ return NSFont.FromFontName(self.FontFamily, size);
+#endif
}
catch
{
@@ -68,28 +99,54 @@ namespace Xamarin.Forms.Platform.iOS
if (bold && italic)
{
var defaultFont = UIFont.SystemFontOfSize(size);
+#if __MOBILE__
var descriptor = defaultFont.FontDescriptor.CreateWithTraits(UIFontDescriptorSymbolicTraits.Bold | UIFontDescriptorSymbolicTraits.Italic);
return UIFont.FromDescriptor(descriptor, 0);
}
- if (bold)
- return UIFont.BoldSystemFontOfSize(size);
if (italic)
return UIFont.ItalicSystemFontOfSize(size);
+#else
+ var descriptor = defaultFont.FontDescriptor.FontDescriptorWithSymbolicTraits(
+ NSFontSymbolicTraits.BoldTrait |
+ NSFontSymbolicTraits.ItalicTrait);
+
+ return NSFont.FromDescription(descriptor, 0);
+ }
+ if (italic)
+ {
+ Debug.WriteLine("Italic font requested, passing regular one");
+ return NSFont.UserFontOfSize(size);
+ }
+#endif
+
+ if (bold)
+ return UIFont.BoldSystemFontOfSize(size);
+
return UIFont.SystemFontOfSize(size);
}
internal static bool IsDefault(this Span self)
{
- return self.FontFamily == null && self.FontSize == Device.GetNamedSize(NamedSize.Default, typeof(Label), true) && self.FontAttributes == FontAttributes.None;
+ return self.FontFamily == null && self.FontSize == Device.GetNamedSize(NamedSize.Default, typeof(Label), true) &&
+ self.FontAttributes == FontAttributes.None;
}
+#if __MOBILE__
internal static UIFont ToUIFont(this Label label)
+#else
+ internal static UIFont ToNSFont(this Label label)
+#endif
{
var values = label.GetValues(Label.FontFamilyProperty, Label.FontSizeProperty, Label.FontAttributesProperty);
- return ToUIFont((string)values[0], (float)(double)values[1], (FontAttributes)values[2]) ?? UIFont.SystemFontOfSize(UIFont.LabelFontSize);
+ return ToUIFont((string)values[0], (float)(double)values[1], (FontAttributes)values[2]) ??
+ UIFont.SystemFontOfSize(UIFont.LabelFontSize);
}
+#if __MOBILE__
internal static UIFont ToUIFont(this IFontElement element)
+#else
+ internal static NSFont ToNSFont(this IFontElement element)
+#endif
{
return ToUIFont(element.FontFamily, (float)element.FontSize, element.FontAttributes);
}
@@ -104,6 +161,7 @@ namespace Xamarin.Forms.Platform.iOS
try
{
UIFont result;
+#if __MOBILE__
if (UIFont.FamilyNames.Contains(family))
{
var descriptor = new UIFontDescriptor().CreateWithFamily(family);
@@ -124,6 +182,26 @@ namespace Xamarin.Forms.Platform.iOS
}
result = UIFont.FromName(family, size);
+#else
+
+ var descriptor = new NSFontDescriptor().FontDescriptorWithFamily(family);
+
+ if (bold || italic)
+ {
+ var traits = (NSFontSymbolicTraits)0;
+ if (bold)
+ traits = traits | NSFontSymbolicTraits.BoldTrait;
+ if (italic)
+ traits = traits | NSFontSymbolicTraits.ItalicTrait;
+
+ descriptor = descriptor.FontDescriptorWithSymbolicTraits(traits);
+ result = NSFont.FromDescription(descriptor, size);
+ if (result != null)
+ return result;
+ }
+
+ result = NSFont.FromFontName(family, size);
+#endif
if (result != null)
return result;
}
@@ -137,13 +215,27 @@ namespace Xamarin.Forms.Platform.iOS
{
var defaultFont = UIFont.SystemFontOfSize(size);
+#if __MOBILE__
var descriptor = defaultFont.FontDescriptor.CreateWithTraits(UIFontDescriptorSymbolicTraits.Bold | UIFontDescriptorSymbolicTraits.Italic);
return UIFont.FromDescriptor(descriptor, 0);
}
- if (bold)
- return UIFont.BoldSystemFontOfSize(size);
if (italic)
return UIFont.ItalicSystemFontOfSize(size);
+#else
+ var descriptor = defaultFont.FontDescriptor.FontDescriptorWithSymbolicTraits(
+ NSFontSymbolicTraits.BoldTrait |
+ NSFontSymbolicTraits.ItalicTrait);
+
+ return NSFont.FromDescription(descriptor, 0);
+ }
+ if (italic)
+ {
+ Debug.WriteLine("Italic font requested, passing regular one");
+ return NSFont.UserFontOfSize(size);
+ }
+#endif
+ if (bold)
+ return UIFont.BoldSystemFontOfSize(size);
return UIFont.SystemFontOfSize(size);
}
diff --git a/Xamarin.Forms.Platform.iOS/Renderers/FormattedStringExtensions.cs b/Xamarin.Forms.Platform.iOS/Renderers/FormattedStringExtensions.cs
index dce86b98..825a20bd 100644
--- a/Xamarin.Forms.Platform.iOS/Renderers/FormattedStringExtensions.cs
+++ b/Xamarin.Forms.Platform.iOS/Renderers/FormattedStringExtensions.cs
@@ -1,7 +1,13 @@
using Foundation;
+#if __MOBILE__
using UIKit;
-
namespace Xamarin.Forms.Platform.iOS
+#else
+using AppKit;
+using UIColor = AppKit.NSColor;
+
+namespace Xamarin.Forms.Platform.MacOS
+#endif
{
public static class FormattedStringExtensions
{
@@ -19,10 +25,16 @@ namespace Xamarin.Forms.Platform.iOS
if (fgcolor.IsDefault)
fgcolor = Color.Black; // as defined by apple docs
+#if __MOBILE__
return new NSAttributedString(span.Text, font == Font.Default ? null : font.ToUIFont(), fgcolor.ToUIColor(), span.BackgroundColor.ToUIColor());
+#else
+ return new NSAttributedString(span.Text, font == Font.Default ? null : font.ToNSFont(), fgcolor.ToNSColor(),
+ span.BackgroundColor.ToNSColor());
+#endif
}
- public static NSAttributedString ToAttributed(this FormattedString formattedString, Font defaultFont, Color defaultForegroundColor)
+ public static NSAttributedString ToAttributed(this FormattedString formattedString, Font defaultFont,
+ Color defaultForegroundColor)
{
if (formattedString == null)
return null;
@@ -43,6 +55,7 @@ namespace Xamarin.Forms.Platform.iOS
if (span == null)
return null;
+#if __MOBILE__
UIFont targetFont;
if (span.IsDefault())
targetFont = ((IFontElement)owner).ToUIFont();
@@ -56,9 +69,25 @@ namespace Xamarin.Forms.Platform.iOS
fgcolor = Color.Black; // as defined by apple docs
return new NSAttributedString(span.Text, targetFont, fgcolor.ToUIColor(), span.BackgroundColor.ToUIColor());
+#else
+ NSFont targetFont;
+ if (span.IsDefault())
+ targetFont = ((IFontElement)owner).ToNSFont();
+ else
+ targetFont = span.ToNSFont();
+
+ var fgcolor = span.ForegroundColor;
+ if (fgcolor.IsDefault)
+ fgcolor = defaultForegroundColor;
+ if (fgcolor.IsDefault)
+ fgcolor = Color.Black; // as defined by apple docs
+
+ return new NSAttributedString(span.Text, targetFont, fgcolor.ToNSColor(), span.BackgroundColor.ToNSColor());
+#endif
}
- internal static NSAttributedString ToAttributed(this FormattedString formattedString, Element owner, Color defaultForegroundColor)
+ internal static NSAttributedString ToAttributed(this FormattedString formattedString, Element owner,
+ Color defaultForegroundColor)
{
if (formattedString == null)
return null;
diff --git a/Xamarin.Forms.Platform.iOS/Renderers/LabelRenderer.cs b/Xamarin.Forms.Platform.iOS/Renderers/LabelRenderer.cs
index 58312f8a..5fde3519 100644
--- a/Xamarin.Forms.Platform.iOS/Renderers/LabelRenderer.cs
+++ b/Xamarin.Forms.Platform.iOS/Renderers/LabelRenderer.cs
@@ -1,12 +1,21 @@
using System;
using System.ComponentModel;
-using UIKit;
using RectangleF = CoreGraphics.CGRect;
using SizeF = CoreGraphics.CGSize;
+#if __MOBILE__
+using UIKit;
+using NativeLabel = UIKit.UILabel;
+
namespace Xamarin.Forms.Platform.iOS
+#else
+using AppKit;
+using NativeLabel = AppKit.NSTextField;
+
+namespace Xamarin.Forms.Platform.MacOS
+#endif
{
- public class LabelRenderer : ViewRenderer<Label, UILabel>
+ public class LabelRenderer : ViewRenderer<Label, NativeLabel>
{
SizeRequest _perfectSize;
@@ -35,9 +44,16 @@ namespace Xamarin.Forms.Platform.iOS
return result;
}
+#if __MOBILE__
public override void LayoutSubviews()
{
base.LayoutSubviews();
+#else
+ public override void Layout()
+ {
+ base.Layout();
+#endif
+
if (Control == null)
return;
@@ -69,7 +85,12 @@ namespace Xamarin.Forms.Platform.iOS
{
if (Control == null)
{
- SetNativeControl(new UILabel(RectangleF.Empty) { BackgroundColor = UIColor.Clear });
+ SetNativeControl(new NativeLabel(RectangleF.Empty));
+#if !__MOBILE__
+ Control.Editable = false;
+ Control.Bezeled = false;
+ Control.DrawsBackground = false;
+#endif
}
UpdateText();
@@ -87,7 +108,7 @@ namespace Xamarin.Forms.Platform.iOS
if (e.PropertyName == Label.HorizontalTextAlignmentProperty.PropertyName)
UpdateAlignment();
else if (e.PropertyName == Label.VerticalTextAlignmentProperty.PropertyName)
- LayoutSubviews();
+ UpdateLayout();
else if (e.PropertyName == Label.TextColorProperty.PropertyName)
UpdateText();
else if (e.PropertyName == Label.FontProperty.PropertyName)
@@ -102,21 +123,33 @@ namespace Xamarin.Forms.Platform.iOS
protected override void SetBackgroundColor(Color color)
{
+#if __MOBILE__
if (color == Color.Default)
BackgroundColor = UIColor.Clear;
else
BackgroundColor = color.ToUIColor();
+#else
+ if (color == Color.Default)
+ Layer.BackgroundColor = NSColor.Clear.CGColor;
+ else
+ Layer.BackgroundColor = color.ToCGColor();
+#endif
+
}
void UpdateAlignment()
{
+#if __MOBILE__
Control.TextAlignment = Element.HorizontalTextAlignment.ToNativeTextAlignment();
+#else
+ Control.Alignment = Element.HorizontalTextAlignment.ToNativeTextAlignment();
+#endif
}
void UpdateLineBreakMode()
{
_perfectSizeValid = false;
-
+#if __MOBILE__
switch (Element.LineBreakMode)
{
case LineBreakMode.NoWrap:
@@ -144,6 +177,35 @@ namespace Xamarin.Forms.Platform.iOS
Control.Lines = 1;
break;
}
+#else
+ switch (Element.LineBreakMode)
+ {
+ case LineBreakMode.NoWrap:
+ Control.LineBreakMode = NSLineBreakMode.Clipping;
+ Control.MaximumNumberOfLines = 1;
+ break;
+ case LineBreakMode.WordWrap:
+ Control.LineBreakMode = NSLineBreakMode.ByWordWrapping;
+ Control.MaximumNumberOfLines = 0;
+ break;
+ case LineBreakMode.CharacterWrap:
+ Control.LineBreakMode = NSLineBreakMode.CharWrapping;
+ Control.MaximumNumberOfLines = 0;
+ break;
+ case LineBreakMode.HeadTruncation:
+ Control.LineBreakMode = NSLineBreakMode.TruncatingHead;
+ Control.MaximumNumberOfLines = 1;
+ break;
+ case LineBreakMode.MiddleTruncation:
+ Control.LineBreakMode = NSLineBreakMode.TruncatingMiddle;
+ Control.MaximumNumberOfLines = 1;
+ break;
+ case LineBreakMode.TailTruncation:
+ Control.LineBreakMode = NSLineBreakMode.TruncatingTail;
+ Control.MaximumNumberOfLines = 1;
+ break;
+ }
+#endif
}
void UpdateText()
@@ -151,9 +213,12 @@ namespace Xamarin.Forms.Platform.iOS
_perfectSizeValid = false;
var values = Element.GetValues(Label.FormattedTextProperty, Label.TextProperty, Label.TextColorProperty);
- var formatted = (FormattedString)values[0];
+ var formatted = values[0] as FormattedString;
if (formatted != null)
+ {
+#if __MOBILE__
Control.AttributedText = formatted.ToAttributed(Element, (Color)values[2]);
+ }
else
{
Control.Text = (string)values[1];
@@ -161,8 +226,28 @@ namespace Xamarin.Forms.Platform.iOS
Control.Font = Element.ToUIFont();
Control.TextColor = ((Color)values[2]).ToUIColor(ColorExtensions.Black);
}
+#else
+ Control.AttributedStringValue = formatted.ToAttributed(Element, (Color)values[2]);
+ }
+ else
+ {
+ Control.StringValue = (string)values[1] ?? "";
+ // default value of color documented to be black in iOS docs
+ Control.Font = Element.ToNSFont();
+ Control.TextColor = ((Color)values[2]).ToNSColor(ColorExtensions.Black);
+ }
+#endif
+
+ UpdateLayout();
+ }
+ void UpdateLayout()
+ {
+#if __MOBILE__
LayoutSubviews();
+#else
+ Layout();
+#endif
}
}
} \ No newline at end of file
diff --git a/Xamarin.Forms.Platform.iOS/ResourcesProvider.cs b/Xamarin.Forms.Platform.iOS/ResourcesProvider.cs
index 3e5655c9..f02655a0 100644
--- a/Xamarin.Forms.Platform.iOS/ResourcesProvider.cs
+++ b/Xamarin.Forms.Platform.iOS/ResourcesProvider.cs
@@ -1,6 +1,11 @@
+#if __MOBILE__
using UIKit;
namespace Xamarin.Forms.Platform.iOS
+#else
+
+namespace Xamarin.Forms.Platform.MacOS
+#endif
{
internal class ResourcesProvider : ISystemResourcesProvider
{
@@ -8,7 +13,9 @@ namespace Xamarin.Forms.Platform.iOS
public ResourcesProvider()
{
+#if __MOBILE__
UIApplication.Notifications.ObserveContentSizeCategoryChanged((sender, args) => UpdateStyles());
+#endif
}
public IResourceDictionary GetSystemResources()
@@ -19,6 +26,7 @@ namespace Xamarin.Forms.Platform.iOS
return _dictionary;
}
+#if __MOBILE__
Style GenerateListItemDetailTextStyle()
{
var font = new UITableViewCell(UITableViewCellStyle.Subtitle, "Foobar").DetailTextLabel.Font;
@@ -44,7 +52,7 @@ namespace Xamarin.Forms.Platform.iOS
void UpdateStyles()
{
-
+
_dictionary[Device.Styles.TitleStyleKey] = GenerateStyle(UIFont.PreferredHeadline);
_dictionary[Device.Styles.SubtitleStyleKey] = GenerateStyle(UIFont.PreferredSubheadline);
_dictionary[Device.Styles.BodyStyleKey] = GenerateStyle(UIFont.PreferredBody);
@@ -53,5 +61,11 @@ namespace Xamarin.Forms.Platform.iOS
_dictionary[Device.Styles.ListItemTextStyleKey] = GenerateListItemTextStyle();
_dictionary[Device.Styles.ListItemDetailTextStyleKey] = GenerateListItemDetailTextStyle();
}
+#else
+ void UpdateStyles()
+ {
+ }
+#endif
+
}
} \ No newline at end of file
diff --git a/Xamarin.Forms.Platform.iOS/ViewInitializedEventArgs.cs b/Xamarin.Forms.Platform.iOS/ViewInitializedEventArgs.cs
index 73041163..9ee0da88 100644
--- a/Xamarin.Forms.Platform.iOS/ViewInitializedEventArgs.cs
+++ b/Xamarin.Forms.Platform.iOS/ViewInitializedEventArgs.cs
@@ -1,11 +1,16 @@
using System;
-using UIKit;
+#if __MOBILE__
+using TNativeView = UIKit.UIView;
+#else
+using TNativeView = AppKit.NSView;
+
+#endif
namespace Xamarin.Forms
{
public class ViewInitializedEventArgs : EventArgs
{
- public UIView NativeView { get; internal set; }
+ public TNativeView NativeView { get; internal set; }
public VisualElement View { get; internal set; }
}
diff --git a/Xamarin.Forms.Platform.iOS/ViewRenderer.cs b/Xamarin.Forms.Platform.iOS/ViewRenderer.cs
index 6ecc307b..01f8e06a 100644
--- a/Xamarin.Forms.Platform.iOS/ViewRenderer.cs
+++ b/Xamarin.Forms.Platform.iOS/ViewRenderer.cs
@@ -1,21 +1,34 @@
using System;
using System.ComponentModel;
-using UIKit;
+
using RectangleF = CoreGraphics.CGRect;
using SizeF = CoreGraphics.CGSize;
+#if __MOBILE__
+using UIKit;
+using NativeView = UIKit.UIView;
+using NativeColor = UIKit.UIColor;
+using NativeControl = UIKit.UIControl;
+
namespace Xamarin.Forms.Platform.iOS
+#else
+using NativeView = AppKit.NSView;
+using NativeColor = CoreGraphics.CGColor;
+using NativeControl = AppKit.NSControl;
+
+namespace Xamarin.Forms.Platform.MacOS
+#endif
{
- public abstract class ViewRenderer : ViewRenderer<View, UIView>
+ public abstract class ViewRenderer : ViewRenderer<View, NativeView>
{
}
- public abstract class ViewRenderer<TView, TNativeView> : VisualElementRenderer<TView> where TView : View where TNativeView : UIView
+ public abstract class ViewRenderer<TView, TNativeView> : VisualElementRenderer<TView> where TView : View where TNativeView : NativeView
{
- UIColor _defaultColor;
+ NativeColor _defaultColor;
public TNativeView Control { get; private set; }
-
+#if __MOBILE__
public override void LayoutSubviews()
{
base.LayoutSubviews();
@@ -30,6 +43,19 @@ namespace Xamarin.Forms.Platform.iOS
return Control.SizeThatFits(size);
}
+#else
+ public override SizeRequest GetDesiredSize(double widthConstraint, double heightConstraint)
+ {
+ return (Control ?? NativeView).GetSizeRequest(widthConstraint, heightConstraint);
+ }
+
+ public override void Layout()
+ {
+ if (Control != null)
+ Control.Frame = new RectangleF(0, 0, (nfloat)Element.Width, (nfloat)Element.Height);
+ base.Layout();
+ }
+#endif
/// <summary>
/// Determines whether the native control is disposed of when this renderer is disposed
@@ -100,16 +126,24 @@ namespace Xamarin.Forms.Platform.iOS
{
if (Control == null)
return;
-
+#if __MOBILE__
if (color == Color.Default)
Control.BackgroundColor = _defaultColor;
else
Control.BackgroundColor = color.ToUIColor();
+#else
+ Control.Layer.BackgroundColor = color == Color.Default ? _defaultColor : color.ToCGColor();
+#endif
}
protected void SetNativeControl(TNativeView uiview)
{
+#if __MOBILE__
_defaultColor = uiview.BackgroundColor;
+#else
+ uiview.WantsLayer = true;
+ _defaultColor = uiview.Layer.BackgroundColor;
+#endif
Control = uiview;
if (Element.BackgroundColor != Color.Default)
@@ -120,17 +154,19 @@ namespace Xamarin.Forms.Platform.iOS
AddSubview(uiview);
}
- internal override void SendVisualElementInitialized(VisualElement element, UIView nativeView)
+#if __MOBILE__
+ internal override void SendVisualElementInitialized(VisualElement element, NativeView nativeView)
{
base.SendVisualElementInitialized(element, Control);
}
+#endif
void UpdateIsEnabled()
{
if (Element == null || Control == null)
return;
- var uiControl = Control as UIControl;
+ var uiControl = Control as NativeControl;
if (uiControl == null)
return;
uiControl.Enabled = Element.IsEnabled;
diff --git a/Xamarin.Forms.Platform.iOS/VisualElementPackager.cs b/Xamarin.Forms.Platform.iOS/VisualElementPackager.cs
index 1670176d..fa91cf6a 100644
--- a/Xamarin.Forms.Platform.iOS/VisualElementPackager.cs
+++ b/Xamarin.Forms.Platform.iOS/VisualElementPackager.cs
@@ -1,6 +1,11 @@
using System;
+#if __MOBILE__
namespace Xamarin.Forms.Platform.iOS
+#else
+
+namespace Xamarin.Forms.Platform.MacOS
+#endif
{
public class VisualElementPackager : IDisposable
{
@@ -13,7 +18,7 @@ namespace Xamarin.Forms.Platform.iOS
public VisualElementPackager(IVisualElementRenderer renderer)
{
if (renderer == null)
- throw new ArgumentNullException("renderer");
+ throw new ArgumentNullException(nameof(renderer));
Renderer = renderer;
renderer.ElementChanged += OnRendererElementChanged;
@@ -100,8 +105,9 @@ namespace Xamarin.Forms.Platform.iOS
continue;
var nativeControl = childRenderer.NativeView;
-
+#if __MOBILE__
Renderer.NativeView.BringSubviewToFront(nativeControl);
+#endif
nativeControl.Layer.ZPosition = z * 1000;
}
}
diff --git a/Xamarin.Forms.Platform.iOS/VisualElementRenderer.cs b/Xamarin.Forms.Platform.iOS/VisualElementRenderer.cs
index 155f8b60..0e7af2a5 100644
--- a/Xamarin.Forms.Platform.iOS/VisualElementRenderer.cs
+++ b/Xamarin.Forms.Platform.iOS/VisualElementRenderer.cs
@@ -1,13 +1,25 @@
using System;
using System.Collections.Generic;
using System.ComponentModel;
-using UIKit;
-using Xamarin.Forms.PlatformConfiguration.iOSSpecific;
using RectangleF = CoreGraphics.CGRect;
using SizeF = CoreGraphics.CGSize;
+#if __MOBILE__
+using Xamarin.Forms.PlatformConfiguration.iOSSpecific;
+using UIKit;
+using NativeView = UIKit.UIView;
+using NativeViewController = UIKit.UIViewController;
+using NativeColor = UIKit.UIColor;
namespace Xamarin.Forms.Platform.iOS
+#else
+using AppKit;
+using NativeView = AppKit.NSView;
+using NativeViewController = AppKit.NSViewController;
+using NativeColor = AppKit.NSColor;
+
+namespace Xamarin.Forms.Platform.MacOS
+#endif
{
[Flags]
public enum VisualElementRendererFlags
@@ -17,9 +29,9 @@ namespace Xamarin.Forms.Platform.iOS
AutoPackage = 1 << 2
}
- public class VisualElementRenderer<TElement> : UIView, IVisualElementRenderer, IEffectControlProvider where TElement : VisualElement
+ public class VisualElementRenderer<TElement> : NativeView, IVisualElementRenderer, IEffectControlProvider where TElement : VisualElement
{
- readonly UIColor _defaultColor = UIColor.Clear;
+ readonly NativeColor _defaultColor = NativeColor.Clear;
readonly List<EventHandler<VisualElementChangedEventArgs>> _elementChangedHandlers = new List<EventHandler<VisualElementChangedEventArgs>>();
@@ -31,21 +43,30 @@ namespace Xamarin.Forms.Platform.iOS
VisualElementPackager _packager;
VisualElementTracker _tracker;
+#if __MOBILE__
UIVisualEffectView _blur;
BlurEffectStyle _previousBlur;
+#endif
protected VisualElementRenderer() : base(RectangleF.Empty)
{
_propertyChangedHandler = OnElementPropertyChanged;
- BackgroundColor = UIColor.Clear;
+#if __MOBILE__
+ BackgroundColor = _defaultColor;
+#else
+ WantsLayer = true;
+ Layer.BackgroundColor = _defaultColor.CGColor;
+#endif
}
+#if __MOBILE__
// prevent possible crashes in overrides
- public sealed override UIColor BackgroundColor
+ public sealed override NativeColor BackgroundColor
{
get { return base.BackgroundColor; }
set { base.BackgroundColor = value; }
}
+#endif
public TElement Element { get; private set; }
@@ -73,7 +94,7 @@ namespace Xamarin.Forms.Platform.iOS
}
}
- public static void RegisterEffect(Effect effect, UIView container, UIView control = null)
+ public static void RegisterEffect(Effect effect, NativeView container, NativeView control = null)
{
var platformEffect = effect as PlatformEffect;
if (platformEffect == null)
@@ -106,10 +127,7 @@ namespace Xamarin.Forms.Platform.iOS
return NativeView.GetSizeRequest(widthConstraint, heightConstraint);
}
- public UIView NativeView
- {
- get { return this; }
- }
+ public NativeView NativeView => this;
void IVisualElementRenderer.SetElement(VisualElement element)
{
@@ -118,13 +136,10 @@ namespace Xamarin.Forms.Platform.iOS
public void SetElementSize(Size size)
{
- Layout.LayoutChildIntoBoundingRegion(Element, new Rectangle(Element.X, Element.Y, size.Width, size.Height));
+ Xamarin.Forms.Layout.LayoutChildIntoBoundingRegion(Element, new Rectangle(Element.X, Element.Y, size.Width, size.Height));
}
- public virtual UIViewController ViewController
- {
- get { return null; }
- }
+ public virtual NativeViewController ViewController => null;
public event EventHandler<ElementChangedEventArgs<TElement>> ElementChanged;
@@ -175,6 +190,7 @@ namespace Xamarin.Forms.Platform.iOS
SetAutomationId(Element.AutomationId);
}
+#if __MOBILE__
public override SizeF SizeThatFits(SizeF size)
{
return new SizeF(0, 0);
@@ -190,6 +206,16 @@ namespace Xamarin.Forms.Platform.iOS
Superview.Add(_blur);
}
}
+#else
+ public override void MouseDown(NSEvent theEvent)
+ {
+ bool inViewCell = IsOnViewCell(Element);
+
+ if (Element.InputTransparent || inViewCell)
+ base.MouseDown(theEvent);
+ }
+#endif
+
protected override void Dispose(bool disposing)
{
if ((_flags & VisualElementRendererFlags.Disposed) != 0)
@@ -227,22 +253,23 @@ namespace Xamarin.Forms.Platform.iOS
for (var i = 0; i < _elementChangedHandlers.Count; i++)
_elementChangedHandlers[i](this, args);
- var changed = ElementChanged;
- if (changed != null)
- changed(this, e);
-
+ ElementChanged?.Invoke(this, e);
+#if __MOBILE__
if (e.NewElement != null)
SetBlur((BlurEffectStyle)e.NewElement.GetValue(PlatformConfiguration.iOSSpecific.VisualElement.BlurEffectProperty));
+#endif
}
protected virtual void OnElementPropertyChanged(object sender, PropertyChangedEventArgs e)
{
if (e.PropertyName == VisualElement.BackgroundColorProperty.PropertyName)
SetBackgroundColor(Element.BackgroundColor);
- else if (e.PropertyName == Layout.IsClippedToBoundsProperty.PropertyName)
+ else if (e.PropertyName == Xamarin.Forms.Layout.IsClippedToBoundsProperty.PropertyName)
UpdateClipToBounds();
+#if __MOBILE__
else if (e.PropertyName == PlatformConfiguration.iOSSpecific.VisualElement.BlurEffectProperty.PropertyName)
SetBlur((BlurEffectStyle)Element.GetValue(PlatformConfiguration.iOSSpecific.VisualElement.BlurEffectProperty));
+#endif
}
protected virtual void OnRegisterEffect(PlatformEffect effect)
@@ -258,11 +285,20 @@ namespace Xamarin.Forms.Platform.iOS
protected virtual void SetBackgroundColor(Color color)
{
if (color == Color.Default)
+#if __MOBILE__
+
BackgroundColor = _defaultColor;
else
BackgroundColor = color.ToUIColor();
+
+#else
+ Layer.BackgroundColor = _defaultColor.CGColor;
+ else
+ Layer.BackgroundColor = color.ToCGColor();
+#endif
}
+#if __MOBILE__
protected virtual void SetBlur(BlurEffectStyle blur)
{
if (_previousBlur == blur)
@@ -300,21 +336,35 @@ namespace Xamarin.Forms.Platform.iOS
_blur = new UIVisualEffectView(blurEffect);
LayoutSubviews();
}
+#endif
protected virtual void UpdateNativeWidget()
{
}
- internal virtual void SendVisualElementInitialized(VisualElement element, UIView nativeView)
+ internal virtual void SendVisualElementInitialized(VisualElement element, NativeView nativeView)
{
element.SendViewInitialized(nativeView);
}
void UpdateClipToBounds()
{
+#if __MOBILE__
var clippableLayout = Element as Layout;
if (clippableLayout != null)
ClipsToBounds = clippableLayout.IsClippedToBounds;
+#endif
+ }
+
+ static bool IsOnViewCell(Element element)
+ {
+
+ if (element.Parent == null)
+ return false;
+ else if (element.Parent is ViewCell)
+ return true;
+ else
+ return IsOnViewCell(element.Parent);
}
}
} \ No newline at end of file
diff --git a/Xamarin.Forms.Platform.iOS/VisualElementTracker.cs b/Xamarin.Forms.Platform.iOS/VisualElementTracker.cs
index 5b41ca84..29840e2d 100644
--- a/Xamarin.Forms.Platform.iOS/VisualElementTracker.cs
+++ b/Xamarin.Forms.Platform.iOS/VisualElementTracker.cs
@@ -3,8 +3,13 @@ using System.ComponentModel;
using System.Drawing;
using System.Threading;
using CoreAnimation;
+#if __MOBILE__
namespace Xamarin.Forms.Platform.iOS
+#else
+
+namespace Xamarin.Forms.Platform.MacOS
+#endif
{
public class VisualElementTracker : IDisposable
{
@@ -18,7 +23,9 @@ namespace Xamarin.Forms.Platform.iOS
// Track these by hand because the calls down into iOS are too expensive
bool _isInteractive;
Rectangle _lastBounds;
-
+#if !__MOBILE__
+ Rectangle _lastParentBounds;
+#endif
CALayer _layer;
int _updateCount;
@@ -107,12 +114,17 @@ namespace Xamarin.Forms.Platform.iOS
var shouldInteract = !view.InputTransparent && view.IsEnabled;
if (_isInteractive != shouldInteract)
{
+#if __MOBILE__
uiview.UserInteractionEnabled = shouldInteract;
+#endif
_isInteractive = shouldInteract;
}
var boundsChanged = _lastBounds != view.Bounds;
-
+#if !__MOBILE__
+ var viewParent = view.RealParent as VisualElement;
+ var parentBoundsChanged = _lastParentBounds != (viewParent == null ? Rectangle.Zero : viewParent.Bounds);
+#endif
var thread = !boundsChanged && !caLayer.Frame.IsEmpty;
var anchorX = (float)view.AnchorX;
@@ -136,13 +148,17 @@ namespace Xamarin.Forms.Platform.iOS
{
if (updateTarget != _updateCount)
return;
-
+#if __MOBILE__
var visualElement = view;
+#endif
var parent = view.RealParent;
var shouldRelayoutSublayers = false;
if (isVisible && caLayer.Hidden)
{
+#if !__MOBILE__
+ uiview.Hidden = false;
+#endif
caLayer.Hidden = false;
if (!caLayer.Frame.IsEmpty)
shouldRelayoutSublayers = true;
@@ -150,6 +166,9 @@ namespace Xamarin.Forms.Platform.iOS
if (!isVisible && !caLayer.Hidden)
{
+#if !__MOBILE__
+ uiview.Hidden = true;
+#endif
caLayer.Hidden = true;
shouldRelayoutSublayers = true;
}
@@ -157,11 +176,26 @@ namespace Xamarin.Forms.Platform.iOS
// ripe for optimization
var transform = CATransform3D.Identity;
+#if __MOBILE__
+ bool shouldUpdate = (!(visualElement is Page) || visualElement is ContentPage) && width > 0 && height > 0 && parent != null && boundsChanged;
+#else
+ // We don't care if it's a page or not since bounds of the window can change
+ // TODO: Find why it doesn't work to check if the parentsBounds changed and remove true;
+ parentBoundsChanged = true;
+ bool shouldUpdate = width > 0 && height > 0 && parent != null && (boundsChanged || parentBoundsChanged);
+#endif
// Dont ever attempt to actually change the layout of a Page unless it is a ContentPage
// iOS is a really big fan of you not actually modifying the View's of the UIViewControllers
- if ((!(visualElement is Page) || visualElement is ContentPage) && width > 0 && height > 0 && parent != null && boundsChanged)
+ if (shouldUpdate)
{
+#if __MOBILE__
var target = new RectangleF(x, y, width, height);
+#else
+ var visualParent = parent as VisualElement;
+ float newY = visualParent == null ? y : Math.Max(0, (float)(visualParent.Height - y - view.Height));
+ var target = new RectangleF(x, newY, width, height);
+#endif
+
// must reset transform prior to setting frame...
caLayer.Transform = transform;
uiview.Frame = target;
@@ -170,11 +204,17 @@ namespace Xamarin.Forms.Platform.iOS
}
else if (width <= 0 || height <= 0)
{
+ //TODO: FInd why it doesn't work
+#if __MOBILE__
caLayer.Hidden = true;
+#endif
return;
}
-
+#if __MOBILE__
caLayer.AnchorPoint = new PointF(anchorX, anchorY);
+#else
+ caLayer.AnchorPoint = new PointF(anchorX - 0.5f, anchorY - 0.5f);
+#endif
caLayer.Opacity = opacity;
const double epsilon = 0.001;
@@ -209,6 +249,9 @@ namespace Xamarin.Forms.Platform.iOS
update();
_lastBounds = view.Bounds;
+#if !__MOBILE__
+ _lastParentBounds = viewParent?.Bounds ?? Rectangle.Zero;
+#endif
}
void SetElement(VisualElement oldElement, VisualElement newElement)
@@ -239,14 +282,18 @@ namespace Xamarin.Forms.Platform.iOS
if (_layer == null)
{
+#if !__MOBILE__
+ Renderer.NativeView.WantsLayer = true;
+#endif
_layer = Renderer.NativeView.Layer;
+#if __MOBILE__
_isInteractive = Renderer.NativeView.UserInteractionEnabled;
+#endif
}
OnUpdateNativeControl(_layer);
- if (NativeControlUpdated != null)
- NativeControlUpdated(this, EventArgs.Empty);
+ NativeControlUpdated?.Invoke(this, EventArgs.Empty);
}
}
} \ No newline at end of file