Merge pull request #269 from mono/forms-changes

Making the Forms views more extendable
Merging this which contains most of the bits by @gentledepp in #260.
This commit is contained in:
Matthew Leibowitz 2017-04-23 20:04:31 +02:00 коммит произвёл GitHub
Родитель 2cdbe0558d 1c30427fd1
Коммит 055ef8c910
18 изменённых файлов: 372 добавлений и 535 удалений

Просмотреть файл

@ -1,8 +1,4 @@
using System;
using System.ComponentModel;
using Android.Content;
using Xamarin.Forms;
using Xamarin.Forms.Platform.Android;
using Xamarin.Forms;
using SKFormsView = SkiaSharp.Views.Forms.SKCanvasView;
using SKNativeView = SkiaSharp.Views.Android.SKCanvasView;
@ -11,90 +7,7 @@ using SKNativeView = SkiaSharp.Views.Android.SKCanvasView;
namespace SkiaSharp.Views.Forms
{
public class SKCanvasViewRenderer : ViewRenderer<SKFormsView, SKNativeView>
public class SKCanvasViewRenderer : SKCanvasViewRendererBase<SKFormsView, SKNativeView>
{
protected override void OnElementChanged(ElementChangedEventArgs<SKFormsView> e)
{
if (e.OldElement != null)
{
var oldController = (ISKCanvasViewController)e.OldElement;
// unsubscribe from events
oldController.SurfaceInvalidated -= OnSurfaceInvalidated;
oldController.GetCanvasSize -= OnGetCanvasSize;
}
if (e.NewElement != null)
{
var newController = (ISKCanvasViewController)e.NewElement;
// create the native view
var view = new InternalView(Context, newController);
view.IgnorePixelScaling = e.NewElement.IgnorePixelScaling;
SetNativeControl(view);
// subscribe to events from the user
newController.SurfaceInvalidated += OnSurfaceInvalidated;
newController.GetCanvasSize += OnGetCanvasSize;
// paint for the first time
Control.Invalidate();
}
base.OnElementChanged(e);
}
protected override void OnElementPropertyChanged(object sender, PropertyChangedEventArgs e)
{
base.OnElementPropertyChanged(sender, e);
if (e.PropertyName == nameof(SKFormsView.IgnorePixelScaling))
{
Control.IgnorePixelScaling = Element.IgnorePixelScaling;
}
}
protected override void Dispose(bool disposing)
{
// detach all events before disposing
var controller = (ISKCanvasViewController)Element;
if (controller != null)
{
controller.SurfaceInvalidated -= OnSurfaceInvalidated;
}
base.Dispose(disposing);
}
private void OnSurfaceInvalidated(object sender, EventArgs eventArgs)
{
// repaint the native control
Control.Invalidate();
}
// the user asked for the size
private void OnGetCanvasSize(object sender, GetCanvasSizeEventArgs e)
{
e.CanvasSize = Control?.CanvasSize ?? SKSize.Empty;
}
private class InternalView : SKNativeView
{
private readonly ISKCanvasViewController controller;
public InternalView(Context context, ISKCanvasViewController controller)
: base(context)
{
this.controller = controller;
}
protected override void OnDraw(SKSurface surface, SKImageInfo info)
{
base.OnDraw(surface, info);
// the control is being repainted, let the user know
controller.OnPaintSurface(new SKPaintSurfaceEventArgs(surface, info));
}
}
}
}

Просмотреть файл

@ -1,10 +1,5 @@
using System;
using System.ComponentModel;
using Android.Content;
using Android.Opengl;
using Javax.Microedition.Khronos.Opengles;
using Android.Opengl;
using Xamarin.Forms;
using Xamarin.Forms.Platform.Android;
using SKFormsView = SkiaSharp.Views.Forms.SKGLView;
using SKNativeView = SkiaSharp.Views.Android.SKGLSurfaceView;
@ -13,98 +8,18 @@ using SKNativeView = SkiaSharp.Views.Android.SKGLSurfaceView;
namespace SkiaSharp.Views.Forms
{
public class SKGLViewRenderer : ViewRenderer<SKFormsView, SKNativeView>
public class SKGLViewRenderer : SKGLViewRendererBase<SKFormsView, SKNativeView>
{
protected override void OnElementChanged(ElementChangedEventArgs<SKFormsView> e)
protected override void SetupRenderLoop(bool oneShot)
{
if (e.OldElement != null)
{
var oldController = (ISKGLViewController)e.OldElement;
// unsubscribe from events
oldController.SurfaceInvalidated -= OnSurfaceInvalidated;
oldController.GetCanvasSize -= OnGetCanvasSize;
}
if (e.NewElement != null)
{
var newController = (ISKGLViewController)e.NewElement;
// create the native view
var view = new SKNativeView(Context);
view.SetRenderer(new Renderer(newController));
SetNativeControl(view);
// subscribe to events from the user
newController.SurfaceInvalidated += OnSurfaceInvalidated;
newController.GetCanvasSize += OnGetCanvasSize;
// start the rendering
SetRenderMode();
}
base.OnElementChanged(e);
}
protected override void OnElementPropertyChanged(object sender, PropertyChangedEventArgs e)
{
base.OnElementPropertyChanged(sender, e);
// refresh the render loop
if (e.PropertyName == SKFormsView.HasRenderLoopProperty.PropertyName)
{
SetRenderMode();
}
}
protected override void Dispose(bool disposing)
{
// detach all events before disposing
var controller = (ISKGLViewController)Element;
if (controller != null)
{
controller.SurfaceInvalidated -= OnSurfaceInvalidated;
}
base.Dispose(disposing);
}
// the user asked to repaint
private void OnSurfaceInvalidated(object sender, EventArgs eventArgs)
{
// if we aren't in a loop, then refresh once
if (!Element.HasRenderLoop)
if (oneShot)
{
Control.RequestRender();
}
}
// the user asked for the size
private void OnGetCanvasSize(object sender, GetCanvasSizeEventArgs e)
{
e.CanvasSize = Control?.CanvasSize ?? SKSize.Empty;
}
private void SetRenderMode()
{
Control.RenderMode = Element.HasRenderLoop
? Rendermode.Continuously
: Rendermode.WhenDirty;
}
private class Renderer : SKNativeView.ISKRenderer
{
private readonly ISKGLViewController controller;
public Renderer(ISKGLViewController controller)
{
this.controller = controller;
}
public void OnDrawFrame(SKSurface surface, GRBackendRenderTargetDesc renderTarget)
{
controller.OnPaintSurface(new SKPaintGLSurfaceEventArgs(surface, renderTarget));
}
}
}
}

Просмотреть файл

@ -104,6 +104,7 @@
</ProjectReference>
</ItemGroup>
<Import Project="..\SkiaSharp.Views.Forms.Shared\SkiaSharp.Views.Forms.Shared.projitems" Label="Shared" Condition="Exists('..\SkiaSharp.Views.Forms.Shared\SkiaSharp.Views.Forms.Shared.projitems')" />
<Import Project="..\SkiaSharp.Views.Forms.Native.Shared\SkiaSharp.Views.Forms.Native.Shared.projitems" Label="Shared" />
<Import Project="$(MSBuildExtensionsPath)\Xamarin\Android\Xamarin.Android.CSharp.targets" />
<Import Project="..\..\packages\Xamarin.Android.Support.Vector.Drawable.23.3.0\build\Xamarin.Android.Support.Vector.Drawable.targets" Condition="Exists('..\..\packages\Xamarin.Android.Support.Vector.Drawable.23.3.0\build\Xamarin.Android.Support.Vector.Drawable.targets')" />
<Import Project="..\..\packages\Xamarin.Forms.2.3.3.193\build\portable-win+net45+wp80+win81+wpa81+MonoAndroid10+MonoTouch10+Xamarin.iOS10\Xamarin.Forms.targets" Condition="Exists('..\..\packages\Xamarin.Forms.2.3.3.193\build\portable-win+net45+wp80+win81+wpa81+MonoAndroid10+MonoTouch10+Xamarin.iOS10\Xamarin.Forms.targets')" />

Просмотреть файл

@ -0,0 +1,129 @@
using System;
using System.ComponentModel;
using SKFormsView = SkiaSharp.Views.Forms.SKCanvasView;
#if __ANDROID__
using Xamarin.Forms.Platform.Android;
using SKNativeView = SkiaSharp.Views.Android.SKCanvasView;
using SKNativePaintSurfaceEventArgs = SkiaSharp.Views.Android.SKPaintSurfaceEventArgs;
#elif __IOS__
using Xamarin.Forms.Platform.iOS;
using SKNativeView = SkiaSharp.Views.iOS.SKCanvasView;
using SKNativePaintSurfaceEventArgs = SkiaSharp.Views.iOS.SKPaintSurfaceEventArgs;
#elif WINDOWS_UWP
using Xamarin.Forms.Platform.UWP;
using SKNativeView = SkiaSharp.Views.UWP.SKXamlCanvas;
using SKNativePaintSurfaceEventArgs = SkiaSharp.Views.UWP.SKPaintSurfaceEventArgs;
#endif
namespace SkiaSharp.Views.Forms
{
public abstract class SKCanvasViewRendererBase<TFormsView, TNativeView> : ViewRenderer<TFormsView, TNativeView>
where TFormsView : SKFormsView
where TNativeView : SKNativeView
{
protected override void OnElementChanged(ElementChangedEventArgs<TFormsView> e)
{
if (e.OldElement != null)
{
var oldController = (ISKCanvasViewController)e.OldElement;
// unsubscribe from events
oldController.SurfaceInvalidated -= OnSurfaceInvalidated;
oldController.GetCanvasSize -= OnGetCanvasSize;
}
if (Control != null)
{
var control = Control;
control.PaintSurface -= OnPaintSurface;
}
if (e.NewElement != null)
{
var newController = (ISKCanvasViewController)e.NewElement;
// create the native view
var view = CreateNativeControl();
view.IgnorePixelScaling = e.NewElement.IgnorePixelScaling;
view.PaintSurface += OnPaintSurface;
SetNativeControl(view);
// subscribe to events from the user
newController.SurfaceInvalidated += OnSurfaceInvalidated;
newController.GetCanvasSize += OnGetCanvasSize;
// paint for the first time
OnSurfaceInvalidated(newController, EventArgs.Empty);
}
base.OnElementChanged(e);
}
#if __ANDROID__
protected override TNativeView CreateNativeControl()
{
return (TNativeView)Activator.CreateInstance(typeof(TNativeView), new[] { Context });
}
#else
protected virtual TNativeView CreateNativeControl()
{
return (TNativeView)Activator.CreateInstance(typeof(TNativeView));
}
#endif
protected override void OnElementPropertyChanged(object sender, PropertyChangedEventArgs e)
{
base.OnElementPropertyChanged(sender, e);
if (e.PropertyName == nameof(SKFormsView.IgnorePixelScaling))
{
Control.IgnorePixelScaling = Element.IgnorePixelScaling;
}
}
protected override void Dispose(bool disposing)
{
// detach all events before disposing
var controller = (ISKCanvasViewController)Element;
if (controller != null)
{
controller.SurfaceInvalidated -= OnSurfaceInvalidated;
controller.GetCanvasSize -= OnGetCanvasSize;
}
var control = Control;
if (control != null)
{
control.PaintSurface -= OnPaintSurface;
}
base.Dispose(disposing);
}
private void OnPaintSurface(object sender, SKNativePaintSurfaceEventArgs e)
{
var controller = Element as ISKCanvasViewController;
// the control is being repainted, let the user know
controller?.OnPaintSurface(new SKPaintSurfaceEventArgs(e.Surface, e.Info));
}
private void OnSurfaceInvalidated(object sender, EventArgs eventArgs)
{
// repaint the native control
#if __IOS__
Control.SetNeedsDisplay();
#else
Control.Invalidate();
#endif
}
// the user asked for the size
private void OnGetCanvasSize(object sender, GetCanvasSizeEventArgs e)
{
e.CanvasSize = Control?.CanvasSize ?? SKSize.Empty;
}
}
}

Просмотреть файл

@ -0,0 +1,160 @@
using System;
using System.ComponentModel;
using Xamarin.Forms;
using SKFormsView = SkiaSharp.Views.Forms.SKGLView;
#if __ANDROID__
using Xamarin.Forms.Platform.Android;
using SKNativeView = SkiaSharp.Views.Android.SKGLSurfaceView;
using SKNativePaintGLSurfaceEventArgs = SkiaSharp.Views.Android.SKPaintGLSurfaceEventArgs;
#elif __IOS__
using Xamarin.Forms.Platform.iOS;
using SKNativeView = SkiaSharp.Views.iOS.SKGLView;
using SKNativePaintGLSurfaceEventArgs = SkiaSharp.Views.iOS.SKPaintGLSurfaceEventArgs;
#elif WINDOWS_UWP
using Xamarin.Forms.Platform.UWP;
using SKNativeView = SkiaSharp.Views.UWP.SKSwapChainPanel;
using SKNativePaintGLSurfaceEventArgs = SkiaSharp.Views.UWP.SKPaintGLSurfaceEventArgs;
#endif
namespace SkiaSharp.Views.Forms
{
public abstract class SKGLViewRendererBase<TFormsView, TNativeView> : ViewRenderer<TFormsView, TNativeView>
where TFormsView : SKFormsView
where TNativeView : SKNativeView
{
protected override void OnElementChanged(ElementChangedEventArgs<TFormsView> e)
{
if (e.OldElement != null)
{
var oldController = (ISKGLViewController)e.OldElement;
// unsubscribe from events
oldController.SurfaceInvalidated -= OnSurfaceInvalidated;
oldController.GetCanvasSize -= OnGetCanvasSize;
}
if (Control != null)
{
var control = Control;
#if __ANDROID__
control.SetRenderer(null);
#else
control.PaintSurface -= OnPaintSurface;
#endif
}
if (e.NewElement != null)
{
var newController = (ISKGLViewController)e.NewElement;
// create the native view
var view = CreateNativeControl();
#if __ANDROID__
view.SetRenderer(new Renderer(newController));
#else
view.PaintSurface += OnPaintSurface;
#endif
SetNativeControl(view);
// subscribe to events from the user
newController.SurfaceInvalidated += OnSurfaceInvalidated;
newController.GetCanvasSize += OnGetCanvasSize;
// start the rendering
SetupRenderLoop(false);
}
base.OnElementChanged(e);
}
#if __ANDROID__
protected override TNativeView CreateNativeControl()
{
return (TNativeView)Activator.CreateInstance(typeof(TNativeView), new[] { Context });
}
#else
protected virtual TNativeView CreateNativeControl()
{
return (TNativeView)Activator.CreateInstance(typeof(TNativeView));
}
#endif
protected override void OnElementPropertyChanged(object sender, PropertyChangedEventArgs e)
{
base.OnElementPropertyChanged(sender, e);
// refresh the render loop
if (e.PropertyName == SKFormsView.HasRenderLoopProperty.PropertyName)
{
SetupRenderLoop(false);
}
}
protected override void Dispose(bool disposing)
{
// detach all events before disposing
var controller = (ISKGLViewController)Element;
if (controller != null)
{
controller.SurfaceInvalidated -= OnSurfaceInvalidated;
}
var control = Control;
if (control != null)
{
#if __ANDROID__
control.SetRenderer(null);
#else
control.PaintSurface -= OnPaintSurface;
#endif
}
base.Dispose(disposing);
}
protected abstract void SetupRenderLoop(bool oneShot);
// the user asked to repaint
private void OnSurfaceInvalidated(object sender, EventArgs eventArgs)
{
// if we aren't in a loop, then refresh once
if (!Element.HasRenderLoop)
{
SetupRenderLoop(true);
}
}
// the user asked for the size
private void OnGetCanvasSize(object sender, GetCanvasSizeEventArgs e)
{
e.CanvasSize = Control?.CanvasSize ?? SKSize.Empty;
}
private void OnPaintSurface(object sender, SKNativePaintGLSurfaceEventArgs e)
{
var controller = Element as ISKGLViewController;
// the control is being repainted, let the user know
controller?.OnPaintSurface(new SKPaintGLSurfaceEventArgs(e.Surface, e.RenderTarget));
}
#if __ANDROID__
private class Renderer : SKNativeView.ISKRenderer
{
private readonly ISKGLViewController controller;
public Renderer(ISKGLViewController controller)
{
this.controller = controller;
}
public void OnDrawFrame(SKSurface surface, GRBackendRenderTargetDesc renderTarget)
{
controller.OnPaintSurface(new SKPaintGLSurfaceEventArgs(surface, renderTarget));
}
}
#endif
}
}

Просмотреть файл

@ -0,0 +1,15 @@
<?xml version="1.0" encoding="utf-8"?>
<Project xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<PropertyGroup>
<MSBuildAllProjects>$(MSBuildAllProjects);$(MSBuildThisFileFullPath)</MSBuildAllProjects>
<HasSharedItems>true</HasSharedItems>
<SharedGUID>cebd25fd-dd4f-4d5f-b809-d50d02176f41</SharedGUID>
</PropertyGroup>
<PropertyGroup Label="Configuration">
<Import_RootNamespace>SkiaSharp.Views.Forms.Native.Shared</Import_RootNamespace>
</PropertyGroup>
<ItemGroup>
<Compile Include="$(MSBuildThisFileDirectory)SKCanvasViewRendererBase.cs" />
<Compile Include="$(MSBuildThisFileDirectory)SKGLViewRendererBase.cs" />
</ItemGroup>
</Project>

Просмотреть файл

@ -0,0 +1,13 @@
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="14.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<PropertyGroup Label="Globals">
<ProjectGuid>cebd25fd-dd4f-4d5f-b809-d50d02176f41</ProjectGuid>
<MinimumVisualStudioVersion>14.0</MinimumVisualStudioVersion>
</PropertyGroup>
<Import Project="$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props" Condition="Exists('$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props')" />
<Import Project="$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion)\CodeSharing\Microsoft.CodeSharing.Common.Default.props" Condition="Exists('$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion)\CodeSharing\Microsoft.CodeSharing.Common.Default.props')" />
<Import Project="$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion)\CodeSharing\Microsoft.CodeSharing.Common.props" Condition="Exists('$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion)\CodeSharing\Microsoft.CodeSharing.Common.props')" />
<PropertyGroup />
<Import Project="SkiaSharp.Views.Forms.Native.Shared.projitems" Label="Shared" />
<Import Project="$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion)\CodeSharing\Microsoft.CodeSharing.CSharp.targets" Condition="Exists('$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion)\CodeSharing\Microsoft.CodeSharing.CSharp.targets')" />
</Project>

Просмотреть файл

@ -1,7 +1,4 @@
using System;
using System.ComponentModel;
using Xamarin.Forms;
using Xamarin.Forms.Platform.UWP;
using Xamarin.Forms.Platform.UWP;
using SKFormsView = SkiaSharp.Views.Forms.SKCanvasView;
using SKNativeView = SkiaSharp.Views.UWP.SKXamlCanvas;
@ -10,90 +7,7 @@ using SKNativeView = SkiaSharp.Views.UWP.SKXamlCanvas;
namespace SkiaSharp.Views.Forms
{
public class SKCanvasViewRenderer : ViewRenderer<SKFormsView, SKNativeView>
public class SKCanvasViewRenderer : SKCanvasViewRendererBase<SKFormsView, SKNativeView>
{
protected override void OnElementChanged(ElementChangedEventArgs<SKFormsView> e)
{
if (e.OldElement != null)
{
var oldController = (ISKCanvasViewController)e.OldElement;
// unsubscribe from events
oldController.SurfaceInvalidated -= OnSurfaceInvalidated;
oldController.GetCanvasSize -= OnGetCanvasSize;
}
if (e.NewElement != null)
{
var newController = (ISKCanvasViewController)e.NewElement;
// create the native view
var view = new InternalView(newController);
view.IgnorePixelScaling = e.NewElement.IgnorePixelScaling;
SetNativeControl(view);
// subscribe to events from the user
newController.SurfaceInvalidated += OnSurfaceInvalidated;
newController.GetCanvasSize += OnGetCanvasSize;
// paint for the first time
Control.Invalidate();
}
base.OnElementChanged(e);
}
protected override void OnElementPropertyChanged(object sender, PropertyChangedEventArgs e)
{
base.OnElementPropertyChanged(sender, e);
if (e.PropertyName == nameof(SKFormsView.IgnorePixelScaling))
{
Control.IgnorePixelScaling = Element.IgnorePixelScaling;
}
}
protected override void Dispose(bool disposing)
{
// detach all events before disposing
var controller = (ISKCanvasViewController)Element;
if (controller != null)
{
controller.SurfaceInvalidated -= OnSurfaceInvalidated;
controller.GetCanvasSize -= OnGetCanvasSize;
}
base.Dispose(disposing);
}
private void OnSurfaceInvalidated(object sender, EventArgs eventArgs)
{
// repaint the native control
Control.Invalidate();
}
// the user asked for the size
private void OnGetCanvasSize(object sender, GetCanvasSizeEventArgs e)
{
e.CanvasSize = Control?.CanvasSize ?? SKSize.Empty;
}
private class InternalView : SKNativeView
{
private readonly ISKCanvasViewController controller;
public InternalView(ISKCanvasViewController controller)
{
this.controller = controller;
}
protected override void OnPaintSurface(SkiaSharp.Views.UWP.SKPaintSurfaceEventArgs e)
{
base.OnPaintSurface(e);
// the control is being repainted, let the user know
controller.OnPaintSurface(new SKPaintSurfaceEventArgs(e.Surface, e.Info));
}
}
}
}

Просмотреть файл

@ -1,6 +1,4 @@
using System;
using System.ComponentModel;
using Xamarin.Forms.Platform.UWP;
using Xamarin.Forms.Platform.UWP;
using SKFormsView = SkiaSharp.Views.Forms.SKGLView;
using SKNativeView = SkiaSharp.Views.UWP.SKSwapChainPanel;
@ -9,98 +7,16 @@ using SKNativeView = SkiaSharp.Views.UWP.SKSwapChainPanel;
namespace SkiaSharp.Views.Forms
{
public class SKGLViewRenderer : ViewRenderer<SKFormsView, SKNativeView>
public class SKGLViewRenderer : SKGLViewRendererBase<SKFormsView, SKNativeView>
{
protected override void OnElementChanged(ElementChangedEventArgs<SKFormsView> e)
protected override void SetupRenderLoop(bool oneShot)
{
if (e.OldElement != null)
{
var oldController = (ISKGLViewController)e.OldElement;
// unsubscribe from events
oldController.SurfaceInvalidated -= OnSurfaceInvalidated;
oldController.GetCanvasSize -= OnGetCanvasSize;
}
if (e.NewElement != null)
{
var newController = (ISKGLViewController)e.NewElement;
// create the native view
var view = new InternalView(newController);
SetNativeControl(view);
// subscribe to events from the user
newController.SurfaceInvalidated += OnSurfaceInvalidated;
newController.GetCanvasSize += OnGetCanvasSize;
// start the rendering
SetRenderMode();
}
base.OnElementChanged(e);
}
protected override void OnElementPropertyChanged(object sender, PropertyChangedEventArgs e)
{
base.OnElementPropertyChanged(sender, e);
// refresh the render loop
if (e.PropertyName == SKFormsView.HasRenderLoopProperty.PropertyName)
{
SetRenderMode();
}
}
protected override void Dispose(bool disposing)
{
// detach all events before disposing
var controller = (ISKGLViewController)Element;
if (controller != null)
{
controller.SurfaceInvalidated -= OnSurfaceInvalidated;
controller.GetCanvasSize -= OnGetCanvasSize;
}
base.Dispose(disposing);
}
// the user asked to repaint
private void OnSurfaceInvalidated(object sender, EventArgs eventArgs)
{
// if we aren't in a loop, then refresh once
if (!Element.HasRenderLoop)
if (oneShot)
{
Control.Invalidate();
}
}
// the user asked for the size
private void OnGetCanvasSize(object sender, GetCanvasSizeEventArgs e)
{
e.CanvasSize = Control?.CanvasSize ?? SKSize.Empty;
}
private void SetRenderMode()
{
Control.EnableRenderLoop = Element.HasRenderLoop;
}
private class InternalView : SKNativeView
{
private readonly ISKGLViewController controller;
public InternalView(ISKGLViewController controller)
{
this.controller = controller;
}
protected override void OnPaintSurface(SkiaSharp.Views.UWP.SKPaintGLSurfaceEventArgs e)
{
base.OnPaintSurface(e);
controller.OnPaintSurface(new SKPaintGLSurfaceEventArgs(e.Surface, e.RenderTarget));
}
}
}
}

Просмотреть файл

@ -57,6 +57,7 @@
</ProjectReference>
</ItemGroup>
<Import Project="..\SkiaSharp.Views.Forms.Shared\SkiaSharp.Views.Forms.Shared.projitems" Label="Shared" />
<Import Project="..\SkiaSharp.Views.Forms.Native.Shared\SkiaSharp.Views.Forms.Native.Shared.projitems" Label="Shared" />
<PropertyGroup Condition=" '$(VisualStudioVersion)' == '' or '$(VisualStudioVersion)' &lt; '14.0' ">
<VisualStudioVersion>14.0</VisualStudioVersion>
</PropertyGroup>

Просмотреть файл

@ -1,7 +1,4 @@
using System;
using System.ComponentModel;
using Xamarin.Forms;
using Xamarin.Forms.Platform.iOS;
using Xamarin.Forms;
using SKFormsView = SkiaSharp.Views.Forms.SKCanvasView;
using SKNativeView = SkiaSharp.Views.iOS.SKCanvasView;
@ -10,94 +7,17 @@ using SKNativeView = SkiaSharp.Views.iOS.SKCanvasView;
namespace SkiaSharp.Views.Forms
{
public class SKCanvasViewRenderer : ViewRenderer<SKFormsView, SKNativeView>
public class SKCanvasViewRenderer : SKCanvasViewRendererBase<SKFormsView, SKNativeView>
{
protected override void OnElementChanged(ElementChangedEventArgs<SKFormsView> e)
protected override SKNativeView CreateNativeControl()
{
if (e.OldElement != null)
{
var oldController = (ISKCanvasViewController)e.OldElement;
var view = base.CreateNativeControl();
// unsubscribe from events
oldController.SurfaceInvalidated -= OnSurfaceInvalidated;
oldController.GetCanvasSize -= OnGetCanvasSize;
}
view.UserInteractionEnabled = false;
// Force the opacity to false for consistency with the other platforms
view.Opaque = false;
if (e.NewElement != null)
{
var newController = (ISKCanvasViewController)e.NewElement;
// create the native view
var view = new InternalView(newController);
view.IgnorePixelScaling = e.NewElement.IgnorePixelScaling;
SetNativeControl(view);
// subscribe to events from the user
newController.SurfaceInvalidated += OnSurfaceInvalidated;
newController.GetCanvasSize += OnGetCanvasSize;
// paint for the first time
Control.SetNeedsDisplay();
}
base.OnElementChanged(e);
}
protected override void OnElementPropertyChanged(object sender, PropertyChangedEventArgs e)
{
base.OnElementPropertyChanged(sender, e);
if (e.PropertyName == nameof(SKFormsView.IgnorePixelScaling))
{
Control.IgnorePixelScaling = Element.IgnorePixelScaling;
}
}
protected override void Dispose(bool disposing)
{
// detach all events before disposing
var controller = (ISKCanvasViewController)Element;
if (controller != null)
{
controller.SurfaceInvalidated -= OnSurfaceInvalidated;
}
base.Dispose(disposing);
}
// the user asked for the size
private void OnGetCanvasSize(object sender, GetCanvasSizeEventArgs e)
{
e.CanvasSize = Control?.CanvasSize ?? SKSize.Empty;
}
private void OnSurfaceInvalidated(object sender, EventArgs eventArgs)
{
// repaint the native control
Control.SetNeedsDisplay();
}
private class InternalView : SKNativeView
{
private readonly ISKCanvasViewController controller;
public InternalView(ISKCanvasViewController controller)
{
UserInteractionEnabled = false;
this.controller = controller;
// Force the opacity to false for consistency with the other platforms
Opaque = false;
}
public override void DrawInSurface(SKSurface surface, SKImageInfo info)
{
base.DrawInSurface(surface, info);
// the control is being repainted, let the user know
controller.OnPaintSurface(new SKPaintSurfaceEventArgs(surface, info));
}
return view;
}
}
}

Просмотреть файл

@ -1,9 +1,6 @@
using System;
using System.ComponentModel;
using CoreAnimation;
using CoreAnimation;
using Foundation;
using Xamarin.Forms;
using Xamarin.Forms.Platform.iOS;
using SKFormsView = SkiaSharp.Views.Forms.SKGLView;
using SKNativeView = SkiaSharp.Views.iOS.SKGLView;
@ -12,49 +9,19 @@ using SKNativeView = SkiaSharp.Views.iOS.SKGLView;
namespace SkiaSharp.Views.Forms
{
public class SKGLViewRenderer : ViewRenderer<SKFormsView, SKNativeView>
public class SKGLViewRenderer : SKGLViewRendererBase<SKFormsView, SKNativeView>
{
private CADisplayLink displayLink;
protected override void OnElementChanged(ElementChangedEventArgs<SKFormsView> e)
protected override SKNativeView CreateNativeControl()
{
if (e.OldElement != null)
{
var oldController = (ISKGLViewController)e.OldElement;
var view = base.CreateNativeControl();
// unsubscribe from events
oldController.SurfaceInvalidated -= OnSurfaceInvalidated;
oldController.GetCanvasSize -= OnGetCanvasSize;
}
view.UserInteractionEnabled = false;
// Force the opacity to false for consistency with the other platforms
view.Opaque = false;
if (e.NewElement != null)
{
var newController = (ISKGLViewController)e.NewElement;
// create the native view
var view = new InternalView(newController);
SetNativeControl(view);
// subscribe to events from the user
newController.SurfaceInvalidated += OnSurfaceInvalidated;
newController.GetCanvasSize += OnGetCanvasSize;
// start the rendering
SetupRenderLoop(false);
}
base.OnElementChanged(e);
}
protected override void OnElementPropertyChanged(object sender, PropertyChangedEventArgs e)
{
base.OnElementPropertyChanged(sender, e);
// refresh the render loop
if (e.PropertyName == SKFormsView.HasRenderLoopProperty.PropertyName)
{
SetupRenderLoop(false);
}
return view;
}
protected override void Dispose(bool disposing)
@ -66,18 +33,11 @@ namespace SkiaSharp.Views.Forms
displayLink.Dispose();
displayLink = null;
}
// detach all events before disposing
var controller = (ISKGLViewController)Element;
if (controller != null)
{
controller.SurfaceInvalidated -= OnSurfaceInvalidated;
}
base.Dispose(disposing);
}
private void SetupRenderLoop(bool oneShot)
protected override void SetupRenderLoop(bool oneShot)
{
// only start if we haven't already
if (displayLink != null)
@ -106,44 +66,5 @@ namespace SkiaSharp.Views.Forms
});
displayLink.AddToRunLoop(NSRunLoop.Current, NSRunLoop.NSDefaultRunLoopMode);
}
// the user asked to repaint
private void OnSurfaceInvalidated(object sender, EventArgs eventArgs)
{
// if we aren't in a loop, then refresh once
if (!Element.HasRenderLoop)
{
SetupRenderLoop(true);
}
}
// the user asked for the size
private void OnGetCanvasSize(object sender, GetCanvasSizeEventArgs e)
{
e.CanvasSize = Control?.CanvasSize ?? SKSize.Empty;
}
private class InternalView : SKNativeView
{
private readonly ISKGLViewController controller;
public InternalView(ISKGLViewController controller)
{
UserInteractionEnabled = false;
this.controller = controller;
// Force the opacity to false for consistency with the other platforms
Opaque = false;
}
public override void DrawInSurface(SKSurface surface, GRBackendRenderTargetDesc renderTarget)
{
base.DrawInSurface(surface, renderTarget);
// the control is being repainted, let the user know
controller.OnPaintSurface(new SKPaintGLSurfaceEventArgs(surface, renderTarget));
}
}
}
}

Просмотреть файл

@ -86,6 +86,7 @@
</ProjectReference>
</ItemGroup>
<Import Project="..\SkiaSharp.Views.Forms.Shared\SkiaSharp.Views.Forms.Shared.projitems" Label="Shared" Condition="Exists('..\SkiaSharp.Views.Forms.Shared\SkiaSharp.Views.Forms.Shared.projitems')" />
<Import Project="..\SkiaSharp.Views.Forms.Native.Shared\SkiaSharp.Views.Forms.Native.Shared.projitems" Label="Shared" />
<Import Project="$(MSBuildExtensionsPath)\Xamarin\iOS\Xamarin.iOS.CSharp.targets" />
<Import Project="..\..\packages\Xamarin.Forms.2.3.3.193\build\portable-win+net45+wp80+win81+wpa81+MonoAndroid10+MonoTouch10+Xamarin.iOS10\Xamarin.Forms.targets" Condition="Exists('..\..\packages\Xamarin.Forms.2.3.3.193\build\portable-win+net45+wp80+win81+wpa81+MonoAndroid10+MonoTouch10+Xamarin.iOS10\Xamarin.Forms.targets')" />
</Project>

Просмотреть файл

@ -3,4 +3,4 @@
internal class SKCanvasViewRenderer
{
}
}
}

Просмотреть файл

@ -3,4 +3,4 @@
internal class SKGLViewRenderer
{
}
}
}

Просмотреть файл

@ -1,7 +1,7 @@

Microsoft Visual Studio Solution File, Format Version 12.00
# Visual Studio 14
VisualStudioVersion = 14.0.25420.1
# Visual Studio 15
VisualStudioVersion = 15.0.26228.4
MinimumVisualStudioVersion = 10.0.40219.1
Project("{D954291E-2A0B-460D-934E-DC6B0785DB48}") = "SkiaSharp.Views.Forms.Shared", "SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Shared\SkiaSharp.Views.Forms.Shared.shproj", "{314FB505-9858-4E03-B799-91B0BA627D05}"
EndProject
@ -55,13 +55,17 @@ Project("{D954291E-2A0B-460D-934E-DC6B0785DB48}") = "SkiaSharp.Extended.Shared",
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "SkiaSharp.Extended", "SkiaSharp.Extended\SkiaSharp.Extended\SkiaSharp.Extended.csproj", "{FEA1FEC9-950C-46C0-9EB0-A515E0AB8F19}"
EndProject
Project("{D954291E-2A0B-460D-934E-DC6B0785DB48}") = "SkiaSharp.Views.Forms.Native.Shared", "SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Native.Shared\SkiaSharp.Views.Forms.Native.Shared.shproj", "{CEBD25FD-DD4F-4D5F-B809-D50D02176F41}"
EndProject
Global
GlobalSection(SharedMSBuildProjectFiles) = preSolution
SkiaSharp.Svg\SkiaSharp.Svg.Shared\SkiaSharp.Svg.Shared.projitems*{04c4399a-6740-4733-b6b7-f968232a76c8}*SharedItemsImports = 4
SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Shared\SkiaSharp.Views.Forms.Shared.projitems*{1555d119-8598-4e4d-91ac-d313f94a1673}*SharedItemsImports = 4
SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Native.Shared\SkiaSharp.Views.Forms.Native.Shared.projitems*{2f94f024-1841-47e8-b521-74aa4e3eba54}*SharedItemsImports = 4
SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Shared\SkiaSharp.Views.Forms.Shared.projitems*{2f94f024-1841-47e8-b521-74aa4e3eba54}*SharedItemsImports = 4
SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Shared\SkiaSharp.Views.Forms.Shared.projitems*{314fb505-9858-4e03-b799-91b0ba627d05}*SharedItemsImports = 13
..\Binding\Binding\Binding.projitems*{4588a759-3853-49b8-8a68-6c7917be9220}*SharedItemsImports = 4
SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Native.Shared\SkiaSharp.Views.Forms.Native.Shared.projitems*{4ac36d63-bf11-445f-81ee-107c0cef4fc9}*SharedItemsImports = 4
SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Shared\SkiaSharp.Views.Forms.Shared.projitems*{4ac36d63-bf11-445f-81ee-107c0cef4fc9}*SharedItemsImports = 4
..\Binding\Binding\Binding.projitems*{5180e370-a455-42bb-99f9-97bd269b8a52}*SharedItemsImports = 4
SkiaSharp.Views\SkiaSharp.Views.Shared\SkiaSharp.Views.Shared.projitems*{5a67972c-1c04-4913-9950-06a03bfe9533}*SharedItemsImports = 13
@ -76,6 +80,7 @@ Global
SkiaSharp.Svg\SkiaSharp.Svg.Shared\SkiaSharp.Svg.Shared.projitems*{b201e760-db91-485c-a99a-814bded90bdb}*SharedItemsImports = 13
..\Binding\Binding\Binding.projitems*{c737dc80-5b71-4b26-a2dc-da30421788b0}*SharedItemsImports = 4
SkiaSharp.Views\SkiaSharp.Views.Apple\SkiaSharp.Views.Apple.projitems*{cbca14e7-96c9-4697-909c-19b1ef7298f7}*SharedItemsImports = 13
SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Native.Shared\SkiaSharp.Views.Forms.Native.Shared.projitems*{cebd25fd-dd4f-4d5f-b809-d50d02176f41}*SharedItemsImports = 13
SkiaSharp.Extended\SkiaSharp.Extended.Shared\SkiaSharp.Extended.Shared.projitems*{e3290ce6-0ada-486b-9bab-8bcf07f9be45}*SharedItemsImports = 13
SkiaSharp.Views\SkiaSharp.Views.AppleiOS\SkiaSharp.Views.AppleiOS.projitems*{e5973829-6c8b-43e4-b81b-c8492df26c90}*SharedItemsImports = 4
SkiaSharp.Views\SkiaSharp.Views.Apple\SkiaSharp.Views.Apple.projitems*{e5973829-6c8b-43e4-b81b-c8492df26c90}*SharedItemsImports = 4
@ -170,5 +175,6 @@ Global
{B201E760-DB91-485C-A99A-814BDED90BDB} = {F9C7D51F-468C-4E58-BB75-2317DB99C8A7}
{E3290CE6-0ADA-486B-9BAB-8BCF07F9BE45} = {8570A43F-3AD6-4EC4-8CD1-92EF9AC23916}
{FEA1FEC9-950C-46C0-9EB0-A515E0AB8F19} = {8570A43F-3AD6-4EC4-8CD1-92EF9AC23916}
{CEBD25FD-DD4F-4D5F-B809-D50D02176F41} = {EB592D4C-48E1-498D-8A9F-3AEA0C7FAB30}
EndGlobalSection
EndGlobal

Просмотреть файл

@ -43,17 +43,21 @@ Project("{D954291E-2A0B-460D-934E-DC6B0785DB48}") = "SkiaSharp.Extended.Shared",
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "SkiaSharp.Extended", "SkiaSharp.Extended\SkiaSharp.Extended\SkiaSharp.Extended.csproj", "{FEA1FEC9-950C-46C0-9EB0-A515E0AB8F19}"
EndProject
Project("{D954291E-2A0B-460D-934E-DC6B0785DB48}") = "SkiaSharp.Views.Forms.Native.Shared", "SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Native.Shared\SkiaSharp.Views.Forms.Native.Shared.shproj", "{CEBD25FD-DD4F-4D5F-B809-D50D02176F41}"
EndProject
Global
GlobalSection(SharedMSBuildProjectFiles) = preSolution
SkiaSharp.Svg\SkiaSharp.Svg.Shared\SkiaSharp.Svg.Shared.projitems*{04c4399a-6740-4733-b6b7-f968232a76c8}*SharedItemsImports = 4
SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Shared\SkiaSharp.Views.Forms.Shared.projitems*{1555d119-8598-4e4d-91ac-d313f94a1673}*SharedItemsImports = 4
SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Shared\SkiaSharp.Views.Forms.Shared.projitems*{314fb505-9858-4e03-b799-91b0ba627d05}*SharedItemsImports = 13
SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Native.Shared\SkiaSharp.Views.Forms.Native.Shared.projitems*{3a1277b5-cfae-48cc-b64b-4dae1222a3eb}*SharedItemsImports = 4
SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Shared\SkiaSharp.Views.Forms.Shared.projitems*{3a1277b5-cfae-48cc-b64b-4dae1222a3eb}*SharedItemsImports = 4
SkiaSharp.Views\SkiaSharp.Views.Shared\SkiaSharp.Views.Shared.projitems*{5a67972c-1c04-4913-9950-06a03bfe9533}*SharedItemsImports = 13
SkiaSharp.Views\SkiaSharp.Views.Shared\SkiaSharp.Views.Shared.projitems*{8bb20362-91a2-4206-944d-634070eac6f3}*SharedItemsImports = 4
..\Binding\Binding\Binding.projitems*{9c502b9a-25d4-473f-89bd-5a13dde16354}*SharedItemsImports = 13
SkiaSharp.Svg\SkiaSharp.Svg.Shared\SkiaSharp.Svg.Shared.projitems*{b201e760-db91-485c-a99a-814bded90bdb}*SharedItemsImports = 13
..\Binding\Binding\Binding.projitems*{bab615aa-956e-4079-b260-dd7b1f52ec7d}*SharedItemsImports = 4
SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Native.Shared\SkiaSharp.Views.Forms.Native.Shared.projitems*{cebd25fd-dd4f-4d5f-b809-d50d02176f41}*SharedItemsImports = 13
SkiaSharp.Extended\SkiaSharp.Extended.Shared\SkiaSharp.Extended.Shared.projitems*{e3290ce6-0ada-486b-9bab-8bcf07f9be45}*SharedItemsImports = 13
SkiaSharp.Views\SkiaSharp.Views.Shared\SkiaSharp.Views.Shared.projitems*{e5a90865-c185-45ad-88d1-6da7d6004b03}*SharedItemsImports = 4
..\Binding\Binding\Binding.projitems*{eb1bbdcc-fb07-40d5-8b9e-0079e2c2f2df}*SharedItemsImports = 4
@ -124,5 +128,6 @@ Global
{B201E760-DB91-485C-A99A-814BDED90BDB} = {F9C7D51F-468C-4E58-BB75-2317DB99C8A7}
{E3290CE6-0ADA-486B-9BAB-8BCF07F9BE45} = {2F0684AA-463A-443A-AB75-A2DA9B15D975}
{FEA1FEC9-950C-46C0-9EB0-A515E0AB8F19} = {2F0684AA-463A-443A-AB75-A2DA9B15D975}
{CEBD25FD-DD4F-4D5F-B809-D50D02176F41} = {D40675E1-610D-4BBB-AA2A-BEF020717431}
EndGlobalSection
EndGlobal

Просмотреть файл

@ -73,15 +73,20 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "SkiaSharp.Extended", "SkiaS
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "SkiaSharp.Extended.NetStandard", "SkiaSharp.Extended\SkiaSharp.Extended.NetStandard\SkiaSharp.Extended.NetStandard.csproj", "{36456F7F-388A-49E1-B9C5-CC2DEC82D2C2}"
EndProject
Project("{D954291E-2A0B-460D-934E-DC6B0785DB48}") = "SkiaSharp.Views.Forms.Native.Shared", "SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Native.Shared\SkiaSharp.Views.Forms.Native.Shared.shproj", "{CEBD25FD-DD4F-4D5F-B809-D50D02176F41}"
EndProject
Global
GlobalSection(SharedMSBuildProjectFiles) = preSolution
SkiaSharp.Svg\SkiaSharp.Svg.Shared\SkiaSharp.Svg.Shared.projitems*{04c4399a-6740-4733-b6b7-f968232a76c8}*SharedItemsImports = 4
SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Shared\SkiaSharp.Views.Forms.Shared.projitems*{1555d119-8598-4e4d-91ac-d313f94a1673}*SharedItemsImports = 4
SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Native.Shared\SkiaSharp.Views.Forms.Native.Shared.projitems*{2f94f024-1841-47e8-b521-74aa4e3eba54}*SharedItemsImports = 4
SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Shared\SkiaSharp.Views.Forms.Shared.projitems*{2f94f024-1841-47e8-b521-74aa4e3eba54}*SharedItemsImports = 4
SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Shared\SkiaSharp.Views.Forms.Shared.projitems*{314fb505-9858-4e03-b799-91b0ba627d05}*SharedItemsImports = 13
SkiaSharp.Extended\SkiaSharp.Extended.Shared\SkiaSharp.Extended.Shared.projitems*{36456f7f-388a-49e1-b9c5-cc2dec82d2c2}*SharedItemsImports = 4
SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Native.Shared\SkiaSharp.Views.Forms.Native.Shared.projitems*{3a1277b5-cfae-48cc-b64b-4dae1222a3eb}*SharedItemsImports = 4
SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Shared\SkiaSharp.Views.Forms.Shared.projitems*{3a1277b5-cfae-48cc-b64b-4dae1222a3eb}*SharedItemsImports = 4
..\Binding\Binding\Binding.projitems*{4588a759-3853-49b8-8a68-6c7917be9220}*SharedItemsImports = 4
SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Native.Shared\SkiaSharp.Views.Forms.Native.Shared.projitems*{4ac36d63-bf11-445f-81ee-107c0cef4fc9}*SharedItemsImports = 4
SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Shared\SkiaSharp.Views.Forms.Shared.projitems*{4ac36d63-bf11-445f-81ee-107c0cef4fc9}*SharedItemsImports = 4
..\Binding\Binding\Binding.projitems*{4e0924f8-d546-4428-9412-4b9411fba5ff}*SharedItemsImports = 4
..\Binding\Binding\Binding.projitems*{5180e370-a455-42bb-99f9-97bd269b8a52}*SharedItemsImports = 4
@ -99,6 +104,7 @@ Global
..\Binding\Binding\Binding.projitems*{bab615aa-956e-4079-b260-dd7b1f52ec7d}*SharedItemsImports = 4
..\Binding\Binding\Binding.projitems*{c737dc80-5b71-4b26-a2dc-da30421788b0}*SharedItemsImports = 4
SkiaSharp.Views\SkiaSharp.Views.Apple\SkiaSharp.Views.Apple.projitems*{cbca14e7-96c9-4697-909c-19b1ef7298f7}*SharedItemsImports = 13
SkiaSharp.Views.Forms\SkiaSharp.Views.Forms.Native.Shared\SkiaSharp.Views.Forms.Native.Shared.projitems*{cebd25fd-dd4f-4d5f-b809-d50d02176f41}*SharedItemsImports = 13
SkiaSharp.Svg\SkiaSharp.Svg.Shared\SkiaSharp.Svg.Shared.projitems*{e19ffaf3-31a4-4a52-8460-de0c00221439}*SharedItemsImports = 4
SkiaSharp.Extended\SkiaSharp.Extended.Shared\SkiaSharp.Extended.Shared.projitems*{e3290ce6-0ada-486b-9bab-8bcf07f9be45}*SharedItemsImports = 13
SkiaSharp.Views\SkiaSharp.Views.AppleiOS\SkiaSharp.Views.AppleiOS.projitems*{e5973829-6c8b-43e4-b81b-c8492df26c90}*SharedItemsImports = 4
@ -241,5 +247,6 @@ Global
{E3290CE6-0ADA-486B-9BAB-8BCF07F9BE45} = {06F5DF49-E622-4A4C-8F01-0DB0E04721CE}
{FEA1FEC9-950C-46C0-9EB0-A515E0AB8F19} = {06F5DF49-E622-4A4C-8F01-0DB0E04721CE}
{36456F7F-388A-49E1-B9C5-CC2DEC82D2C2} = {06F5DF49-E622-4A4C-8F01-0DB0E04721CE}
{CEBD25FD-DD4F-4D5F-B809-D50D02176F41} = {DCADA8CC-D50A-4BD9-B2E6-86696A43D819}
EndGlobalSection
EndGlobal