Implement scene delegate for iOS (#20454)
* Implement scene delegate for iOS * Move OS check to its own method to make analyzer happy
This commit is contained in:
committed by
GitHub
parent
a2a1663f4b
commit
ac37bd6353
@@ -1,4 +1,5 @@
|
||||
using System;
|
||||
using System.Runtime.Versioning;
|
||||
using Foundation;
|
||||
using Avalonia.Controls.ApplicationLifetimes;
|
||||
using UIKit;
|
||||
@@ -27,6 +28,7 @@ namespace Avalonia.iOS
|
||||
add { _onActivated += value; }
|
||||
remove { _onActivated -= value; }
|
||||
}
|
||||
|
||||
event EventHandler<ActivatedEventArgs> IAvaloniaAppDelegate.Deactivated
|
||||
{
|
||||
add { _onDeactivated += value; }
|
||||
@@ -39,6 +41,17 @@ namespace Avalonia.iOS
|
||||
[Export("window")]
|
||||
public UIWindow? Window { get; set; }
|
||||
|
||||
[Export("application:configurationForConnectingSceneSession:options:")]
|
||||
[SupportedOSPlatform("ios13.0")]
|
||||
[SupportedOSPlatform("tvos13.0")]
|
||||
[SupportedOSPlatform("maccatalyst")]
|
||||
public UISceneConfiguration GetConfiguration(UIApplication application, UISceneSession connectingSceneSession, UISceneConnectionOptions options)
|
||||
{
|
||||
var config = new UISceneConfiguration(null, connectingSceneSession.Role);
|
||||
config.DelegateType = typeof(AvaloniaSceneDelegate);
|
||||
return config;
|
||||
}
|
||||
|
||||
[Export("application:didFinishLaunchingWithOptions:")]
|
||||
public bool FinishedLaunching(UIApplication application, NSDictionary? launchOptions)
|
||||
{
|
||||
@@ -46,28 +59,27 @@ namespace Avalonia.iOS
|
||||
builder = CustomizeAppBuilder(builder);
|
||||
|
||||
var lifetime = new SingleViewLifetime();
|
||||
|
||||
builder.AfterApplicationSetup(_ =>
|
||||
{
|
||||
Window = new UIWindow();
|
||||
|
||||
var view = new AvaloniaView();
|
||||
lifetime.View = view;
|
||||
var controller = new DefaultAvaloniaViewController
|
||||
{
|
||||
View = view
|
||||
};
|
||||
Window.RootViewController = controller;
|
||||
view.InitWithController(controller);
|
||||
});
|
||||
|
||||
builder.AfterApplicationSetup(_ => CreateAndInitWindow(lifetime));
|
||||
builder.SetupWithLifetime(lifetime);
|
||||
|
||||
Window!.MakeKeyAndVisible();
|
||||
Window?.MakeKeyAndVisible();
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
private void CreateAndInitWindow(SingleViewLifetime lifetime)
|
||||
{
|
||||
if (OperatingSystem.IsIOSVersionAtLeast(13) ||
|
||||
OperatingSystem.IsTvOSVersionAtLeast(13) ||
|
||||
OperatingSystem.IsMacCatalyst())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
Window = new UIWindow();
|
||||
AvaloniaSceneDelegate.InitWindow(Window, lifetime);
|
||||
}
|
||||
|
||||
[Export("application:openURL:options:")]
|
||||
public bool OpenUrl(UIApplication app, NSUrl url, NSDictionary options)
|
||||
{
|
||||
|
||||
@@ -0,0 +1,36 @@
|
||||
using Foundation;
|
||||
using UIKit;
|
||||
|
||||
namespace Avalonia.iOS;
|
||||
|
||||
internal sealed class AvaloniaSceneDelegate : UIResponder, IUIWindowSceneDelegate
|
||||
{
|
||||
[Export("window")]
|
||||
public UIWindow? Window { get; set; }
|
||||
|
||||
[Export("scene:willConnectToSession:options:")]
|
||||
public void WillConnect(UIScene scene, UISceneSession session, UISceneConnectionOptions connectionOptions)
|
||||
{
|
||||
if (session.Configuration.Name is not null ||
|
||||
scene is not UIWindowScene windowScene ||
|
||||
Application.Current?.ApplicationLifetime is not SingleViewLifetime lifetime)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
Window = new UIWindow(windowScene);
|
||||
InitWindow(Window, lifetime);
|
||||
|
||||
Window.MakeKeyAndVisible();
|
||||
}
|
||||
|
||||
internal static void InitWindow(UIWindow window, SingleViewLifetime lifetime)
|
||||
{
|
||||
var view = new AvaloniaView();
|
||||
lifetime.View = view;
|
||||
|
||||
var controller = new DefaultAvaloniaViewController { View = view };
|
||||
window.RootViewController = controller;
|
||||
view.InitWithController(controller);
|
||||
}
|
||||
}
|
||||
@@ -1,6 +1,4 @@
|
||||
using System;
|
||||
using System.Diagnostics.CodeAnalysis;
|
||||
using Avalonia.Controls;
|
||||
using Avalonia.Controls;
|
||||
using Avalonia.Controls.ApplicationLifetimes;
|
||||
|
||||
namespace Avalonia.iOS;
|
||||
@@ -10,9 +8,9 @@ internal class SingleViewLifetime : ISingleViewApplicationLifetime, ISingleTopLe
|
||||
private Control? _mainView;
|
||||
private AvaloniaView? _view;
|
||||
|
||||
public AvaloniaView View
|
||||
public AvaloniaView? View
|
||||
{
|
||||
[return: MaybeNull] get => _view!;
|
||||
get => _view;
|
||||
internal set
|
||||
{
|
||||
if (_view != null)
|
||||
@@ -21,7 +19,7 @@ internal class SingleViewLifetime : ISingleViewApplicationLifetime, ISingleTopLe
|
||||
_view.Dispose();
|
||||
}
|
||||
_view = value;
|
||||
_view.Content = _mainView;
|
||||
_view?.Content = _mainView;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -33,10 +31,7 @@ internal class SingleViewLifetime : ISingleViewApplicationLifetime, ISingleTopLe
|
||||
if (_mainView != value)
|
||||
{
|
||||
_mainView = value;
|
||||
if (_view != null)
|
||||
{
|
||||
_view.Content = _mainView;
|
||||
}
|
||||
_view?.Content = _mainView;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user