From edd1e2e95c38d760531329dd022ae1f4be2e0500 Mon Sep 17 00:00:00 2001 From: Joseph Pender Date: Fri, 12 Jun 2026 15:10:55 -0500 Subject: [PATCH 01/15] Starting on adding UIScene support --- .../Capacitor/CAPNotifications.swift | 2 + .../Capacitor/CAPSceneDelegateProxy.swift | 85 +++++++++++++++++++ 2 files changed, 87 insertions(+) create mode 100644 ios/Capacitor/Capacitor/CAPSceneDelegateProxy.swift diff --git a/ios/Capacitor/Capacitor/CAPNotifications.swift b/ios/Capacitor/Capacitor/CAPNotifications.swift index 03d80aa87b..9421b32af3 100644 --- a/ios/Capacitor/Capacitor/CAPNotifications.swift +++ b/ios/Capacitor/Capacitor/CAPNotifications.swift @@ -18,6 +18,7 @@ extension Notification.Name { public static let capacitorStatusBarTapped = Notification.Name(rawValue: "CapacitorStatusBarTappedNotification") public static let capacitorViewDidAppear = Notification.Name(rawValue: "CapacitorViewDidAppear") public static let capacitorViewWillTransition = Notification.Name(rawValue: "CapacitorViewWillTransition") + public static let capacitorSceneWillConnect = Notification.Name(rawValue: "CapacitorSceneWillConnect") } @objc extension NSNotification { @@ -30,6 +31,7 @@ extension Notification.Name { public static let capacitorStatusBarTapped = Notification.Name.capacitorStatusBarTapped public static let capacitorViewDidAppear = Notification.Name.capacitorViewDidAppear public static let capacitorViewWillTransition = Notification.Name.capacitorViewWillTransition + public static let capacitorSceneWillConnect = Notification.Name.capacitorSceneWillConnect } /** diff --git a/ios/Capacitor/Capacitor/CAPSceneDelegateProxy.swift b/ios/Capacitor/Capacitor/CAPSceneDelegateProxy.swift new file mode 100644 index 0000000000..eb3a556741 --- /dev/null +++ b/ios/Capacitor/Capacitor/CAPSceneDelegateProxy.swift @@ -0,0 +1,85 @@ +// +// CAPSceneDelegateProxy.swift +// Capacitor +// +// Created by Joseph Orlando Pender on 6/10/26. +// Copyright © 2026 Drifty Co. All rights reserved. +// + +import Foundation + +@objc(CAPSceneDelegateProxy) +public class SceneDelegateProxy: NSObject, UISceneDelegate { + public static let shared = SceneDelegateProxy() + + public private(set) var lastURL: URL? + + public func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions) { + NotificationCenter.default.post(name: .capacitorSceneWillConnect, object: scene) + + if !connectionOptions.urlContexts.isEmpty { + self.scene(scene, openURLContexts: connectionOptions.urlContexts) + } + + for userActivity in connectionOptions.userActivities { + self.scene(scene, continue: userActivity) + } + } + + public func scene(_ scene: UIScene, openURLContexts URLContexts: Set) { + for context in URLContexts { + lastURL = context.url + NotificationCenter.default.post(name: .capacitorOpenURL, object: [ + "url": context.url, + "options": Self.openURLOptions(from: context.options) + ]) + } + } + + public func scene(_ scene: UIScene, continue userActivity: NSUserActivity) { + guard userActivity.activityType == NSUserActivityTypeBrowsingWeb, + let url = userActivity.webpageURL else { + return + } + lastURL = url + NotificationCenter.default.post(name: .capacitorOpenUniversalLink, object: [ + "url": url + ]) + } + + // Lifecycle hooks are intentionally stubbed until multi-window support lands. + // Until then, CapacitorBridge keeps observing the UIApplication.* equivalents, + // which still fire in scene-based apps for first-foreground / last-background. + + public func sceneDidDisconnect(_ scene: UIScene) { + // TODO: multi-window — tear down the bridge associated with this scene. + } + + public func sceneDidBecomeActive(_ scene: UIScene) { + // TODO: multi-window — forward per-scene active event to the bridge. + } + + public func sceneWillResignActive(_ scene: UIScene) { + // TODO: multi-window — forward per-scene resign-active event to the bridge. + } + + public func sceneWillEnterForeground(_ scene: UIScene) { + // TODO: multi-window — drive JS `resume` from this instead of UIApplication.willEnterForegroundNotification. + } + + public func sceneDidEnterBackground(_ scene: UIScene) { + // TODO: multi-window — drive JS `pause` from this instead of UIApplication.didEnterBackgroundNotification. + } + + private static func openURLOptions(from sceneOptions: UIScene.OpenURLOptions) -> [UIApplication.OpenURLOptionsKey: Any] { + var options: [UIApplication.OpenURLOptionsKey: Any] = [:] + if let sourceApplication = sceneOptions.sourceApplication { + options[.sourceApplication] = sourceApplication + } + if let annotation = sceneOptions.annotation { + options[.annotation] = annotation + } + options[.openInPlace] = sceneOptions.openInPlace + return options + } +} From 799226f8e99632e9b52e521002ec38b99d23c5c2 Mon Sep 17 00:00:00 2001 From: Joseph Pender Date: Fri, 12 Jun 2026 15:18:44 -0500 Subject: [PATCH 02/15] use UIScene lifecycle notifications --- ios/Capacitor/Capacitor.xcodeproj/project.pbxproj | 4 ++++ ios/Capacitor/Capacitor/CapacitorBridge.swift | 9 +++++++-- ios/Capacitor/Capacitor/WebViewDelegationHandler.swift | 4 ++-- 3 files changed, 13 insertions(+), 4 deletions(-) diff --git a/ios/Capacitor/Capacitor.xcodeproj/project.pbxproj b/ios/Capacitor/Capacitor.xcodeproj/project.pbxproj index b060d9f7d0..e4a9e93369 100644 --- a/ios/Capacitor/Capacitor.xcodeproj/project.pbxproj +++ b/ios/Capacitor/Capacitor.xcodeproj/project.pbxproj @@ -80,6 +80,7 @@ 62FABD1A25AE5C01007B3814 /* Array+Capacitor.swift in Sources */ = {isa = PBXBuildFile; fileRef = 62FABD1925AE5C01007B3814 /* Array+Capacitor.swift */; }; 62FABD2325AE60BA007B3814 /* BridgedTypesTests.m in Sources */ = {isa = PBXBuildFile; fileRef = 62FABD2225AE60BA007B3814 /* BridgedTypesTests.m */; }; 62FABD2B25AE6182007B3814 /* BridgedTypesHelper.swift in Sources */ = {isa = PBXBuildFile; fileRef = 62FABD2A25AE6182007B3814 /* BridgedTypesHelper.swift */; }; + 952707712FD9DD2D0079E5D3 /* CAPSceneDelegateProxy.swift in Sources */ = {isa = PBXBuildFile; fileRef = 9527076F2FD9DD260079E5D3 /* CAPSceneDelegateProxy.swift */; }; 957BD9402E78A4A50056874C /* SystemBars.swift in Sources */ = {isa = PBXBuildFile; fileRef = 957BD93E2E78A4A20056874C /* SystemBars.swift */; }; A327E6B628DB8B2900CA8B0A /* HttpRequestHandler.swift in Sources */ = {isa = PBXBuildFile; fileRef = A327E6B228DB8B2800CA8B0A /* HttpRequestHandler.swift */; }; A327E6B728DB8B2900CA8B0A /* CapacitorHttp.swift in Sources */ = {isa = PBXBuildFile; fileRef = A327E6B428DB8B2900CA8B0A /* CapacitorHttp.swift */; }; @@ -238,6 +239,7 @@ 62FABD1925AE5C01007B3814 /* Array+Capacitor.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "Array+Capacitor.swift"; sourceTree = ""; }; 62FABD2225AE60BA007B3814 /* BridgedTypesTests.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = BridgedTypesTests.m; sourceTree = ""; }; 62FABD2A25AE6182007B3814 /* BridgedTypesHelper.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = BridgedTypesHelper.swift; sourceTree = ""; }; + 9527076F2FD9DD260079E5D3 /* CAPSceneDelegateProxy.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CAPSceneDelegateProxy.swift; sourceTree = ""; }; 957BD93E2E78A4A20056874C /* SystemBars.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SystemBars.swift; sourceTree = ""; }; A327E6B228DB8B2800CA8B0A /* HttpRequestHandler.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = HttpRequestHandler.swift; sourceTree = ""; }; A327E6B428DB8B2900CA8B0A /* CapacitorHttp.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = CapacitorHttp.swift; sourceTree = ""; }; @@ -355,6 +357,7 @@ 62959AE12524DA7700A3D7F1 /* Capacitor */ = { isa = PBXGroup; children = ( + 9527076F2FD9DD260079E5D3 /* CAPSceneDelegateProxy.swift */, A7D9312C2B2370EF00FF59A2 /* Codable */, 0F8F33B127DA980A003F49D6 /* PluginConfig.swift */, A76739782B98E09700795F7B /* PrivacyInfo.xcprivacy */, @@ -724,6 +727,7 @@ A7F7EDD5292BE8520015B73B /* CAPInstancePlugin.swift in Sources */, A38C3D7B2848BE6F004B3680 /* CapacitorCookieManager.swift in Sources */, 62959B1B2524DA7800A3D7F1 /* CAPFile.swift in Sources */, + 952707712FD9DD2D0079E5D3 /* CAPSceneDelegateProxy.swift in Sources */, 62959B462524DA7800A3D7F1 /* CAPBridge.swift in Sources */, 62959B1D2524DA7800A3D7F1 /* UIColor.swift in Sources */, 62959B332524DA7800A3D7F1 /* CAPPlugin.m in Sources */, diff --git a/ios/Capacitor/Capacitor/CapacitorBridge.swift b/ios/Capacitor/Capacitor/CapacitorBridge.swift index 7b8b9b99dc..6e6f50228f 100644 --- a/ios/Capacitor/Capacitor/CapacitorBridge.swift +++ b/ios/Capacitor/Capacitor/CapacitorBridge.swift @@ -270,11 +270,16 @@ open class CapacitorBridge: NSObject, CAPBridgeProtocol { exportCordovaJS() registerCordovaPlugins() } else { - observers.append(NotificationCenter.default.addObserver(forName: UIApplication.willEnterForegroundNotification, object: nil, queue: OperationQueue.main) { [weak self] (_) in + observers.append(NotificationCenter.default.addObserver(forName: UIScene.willEnterForegroundNotification, object: nil, queue: OperationQueue.main) { [weak self] notification in + if let scene = notification.object as? UIWindowScene, scene === self?.viewController?.view.window?.windowScene { self?.triggerDocumentJSEvent(eventName: "resume") + } + }) - observers.append(NotificationCenter.default.addObserver(forName: UIApplication.didEnterBackgroundNotification, object: nil, queue: OperationQueue.main) { [weak self] (_) in + observers.append(NotificationCenter.default.addObserver(forName: UIScene.didEnterBackgroundNotification, object: nil, queue: OperationQueue.main) { [weak self] notification in + if let scene = notification.object as? UIWindowScene, scene === self?.viewController?.view.window?.windowScene { self?.triggerDocumentJSEvent(eventName: "pause") + } }) } } diff --git a/ios/Capacitor/Capacitor/WebViewDelegationHandler.swift b/ios/Capacitor/Capacitor/WebViewDelegationHandler.swift index 2b4a256d00..cab0279c4b 100644 --- a/ios/Capacitor/Capacitor/WebViewDelegationHandler.swift +++ b/ios/Capacitor/Capacitor/WebViewDelegationHandler.swift @@ -107,8 +107,8 @@ open class WebViewDelegationHandler: NSObject, WKNavigationDelegate, WKUIDelegat if !isApplicationNavigation, toplevelNavigation { // disallow and let the system handle it - if UIApplication.shared.applicationState == .active { - UIApplication.shared.open(navURL, options: [:], completionHandler: nil) + if webView.window?.windowScene?.activationState == .foregroundActive { + UIApplication.shared.open(navURL, options: [:], completionHandler: nil) } decisionHandler(.cancel) return From ca7ba2351a94cacdccc62b43adfa517db07a3d74 Mon Sep 17 00:00:00 2001 From: Joseph Pender Date: Mon, 15 Jun 2026 09:42:40 -0500 Subject: [PATCH 03/15] scene-aware openURL and universal link notifications --- .../Capacitor/CAPNotifications.swift | 5 +++++ .../Capacitor/CAPSceneDelegateProxy.swift | 20 +++++++++++++++---- 2 files changed, 21 insertions(+), 4 deletions(-) diff --git a/ios/Capacitor/Capacitor/CAPNotifications.swift b/ios/Capacitor/Capacitor/CAPNotifications.swift index 9421b32af3..9731f74e4d 100644 --- a/ios/Capacitor/Capacitor/CAPNotifications.swift +++ b/ios/Capacitor/Capacitor/CAPNotifications.swift @@ -19,6 +19,9 @@ extension Notification.Name { public static let capacitorViewDidAppear = Notification.Name(rawValue: "CapacitorViewDidAppear") public static let capacitorViewWillTransition = Notification.Name(rawValue: "CapacitorViewWillTransition") public static let capacitorSceneWillConnect = Notification.Name(rawValue: "CapacitorSceneWillConnect") + public static let capacitorSceneOpenURL = Notification.Name(rawValue: "CapacitorSceneOpenURLNotification") + public static let capacitorSceneOpenUniversalLink = + Notification.Name(rawValue: "CapacitorSceneOpenUniversalLinkNotification") } @objc extension NSNotification { @@ -32,6 +35,8 @@ extension Notification.Name { public static let capacitorViewDidAppear = Notification.Name.capacitorViewDidAppear public static let capacitorViewWillTransition = Notification.Name.capacitorViewWillTransition public static let capacitorSceneWillConnect = Notification.Name.capacitorSceneWillConnect + public static let capacitorSceneOpenURL = Notification.Name.capacitorSceneOpenURL + public static let capacitorSceneOpenUniversalLink = Notification.Name.capacitorSceneOpenUniversalLink } /** diff --git a/ios/Capacitor/Capacitor/CAPSceneDelegateProxy.swift b/ios/Capacitor/Capacitor/CAPSceneDelegateProxy.swift index eb3a556741..045ee7bad2 100644 --- a/ios/Capacitor/Capacitor/CAPSceneDelegateProxy.swift +++ b/ios/Capacitor/Capacitor/CAPSceneDelegateProxy.swift @@ -29,9 +29,17 @@ public class SceneDelegateProxy: NSObject, UISceneDelegate { public func scene(_ scene: UIScene, openURLContexts URLContexts: Set) { for context in URLContexts { lastURL = context.url + let options = Self.openURLOptions(from: context.options) + + // Capacitor 8 backwards compat NotificationCenter.default.post(name: .capacitorOpenURL, object: [ "url": context.url, - "options": Self.openURLOptions(from: context.options) + "options": options + ]) + + NotificationCenter.default.post(name: .capacitorSceneOpenURL, object: scene, userInfo: [ + "url": context.url, + "options": options ]) } } @@ -42,14 +50,18 @@ public class SceneDelegateProxy: NSObject, UISceneDelegate { return } lastURL = url + + // Capacitor 8 backwards compat NotificationCenter.default.post(name: .capacitorOpenUniversalLink, object: [ "url": url ]) + + NotificationCenter.default.post(name: .capacitorSceneOpenUniversalLink, object: scene, userInfo: [ + "url": url + ]) } - // Lifecycle hooks are intentionally stubbed until multi-window support lands. - // Until then, CapacitorBridge keeps observing the UIApplication.* equivalents, - // which still fire in scene-based apps for first-foreground / last-background. + // TODO: Not until Phase 2 of the UI modernization project public func sceneDidDisconnect(_ scene: UIScene) { // TODO: multi-window — tear down the bridge associated with this scene. From 8e219f121d0486638eb076fa23928e6b13b8ef39 Mon Sep 17 00:00:00 2001 From: Joseph Pender Date: Mon, 15 Jun 2026 09:56:41 -0500 Subject: [PATCH 04/15] remove TmpViewController --- ios/Capacitor/Capacitor.xcodeproj/project.pbxproj | 4 ---- ios/Capacitor/Capacitor/CapacitorBridge.swift | 7 ------- ios/Capacitor/Capacitor/TmpViewController.swift | 8 -------- 3 files changed, 19 deletions(-) delete mode 100644 ios/Capacitor/Capacitor/TmpViewController.swift diff --git a/ios/Capacitor/Capacitor.xcodeproj/project.pbxproj b/ios/Capacitor/Capacitor.xcodeproj/project.pbxproj index e4a9e93369..6cd33b6005 100644 --- a/ios/Capacitor/Capacitor.xcodeproj/project.pbxproj +++ b/ios/Capacitor/Capacitor.xcodeproj/project.pbxproj @@ -52,7 +52,6 @@ 62959B3A2524DA7800A3D7F1 /* CAPLog.swift in Sources */ = {isa = PBXBuildFile; fileRef = 62959B082524DA7700A3D7F1 /* CAPLog.swift */; }; 62959B3B2524DA7800A3D7F1 /* CAPPluginMethod.h in Headers */ = {isa = PBXBuildFile; fileRef = 62959B092524DA7700A3D7F1 /* CAPPluginMethod.h */; settings = {ATTRIBUTES = (Public, ); }; }; 62959B3C2524DA7800A3D7F1 /* CAPBridgeDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = 62959B0A2524DA7700A3D7F1 /* CAPBridgeDelegate.swift */; }; - 62959B402524DA7800A3D7F1 /* TmpViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 62959B0E2524DA7700A3D7F1 /* TmpViewController.swift */; }; 62959B412524DA7800A3D7F1 /* Capacitor.h in Headers */ = {isa = PBXBuildFile; fileRef = 62959B0F2524DA7700A3D7F1 /* Capacitor.h */; settings = {ATTRIBUTES = (Public, ); }; }; 62959B422524DA7800A3D7F1 /* DocLinks.swift in Sources */ = {isa = PBXBuildFile; fileRef = 62959B102524DA7700A3D7F1 /* DocLinks.swift */; }; 62959B432524DA7800A3D7F1 /* Data+Capacitor.swift in Sources */ = {isa = PBXBuildFile; fileRef = 62959B112524DA7700A3D7F1 /* Data+Capacitor.swift */; }; @@ -205,7 +204,6 @@ 62959B082524DA7700A3D7F1 /* CAPLog.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = CAPLog.swift; sourceTree = ""; }; 62959B092524DA7700A3D7F1 /* CAPPluginMethod.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = CAPPluginMethod.h; sourceTree = ""; }; 62959B0A2524DA7700A3D7F1 /* CAPBridgeDelegate.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = CAPBridgeDelegate.swift; sourceTree = ""; }; - 62959B0E2524DA7700A3D7F1 /* TmpViewController.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = TmpViewController.swift; sourceTree = ""; }; 62959B0F2524DA7700A3D7F1 /* Capacitor.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = Capacitor.h; sourceTree = ""; }; 62959B102524DA7700A3D7F1 /* DocLinks.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = DocLinks.swift; sourceTree = ""; }; 62959B112524DA7700A3D7F1 /* Data+Capacitor.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = "Data+Capacitor.swift"; sourceTree = ""; }; @@ -398,7 +396,6 @@ 6214934625509C3F006C36F9 /* CAPInstanceConfiguration.swift */, 62959B082524DA7700A3D7F1 /* CAPLog.swift */, 62959AE72524DA7700A3D7F1 /* CAPFile.swift */, - 62959B0E2524DA7700A3D7F1 /* TmpViewController.swift */, 62959B102524DA7700A3D7F1 /* DocLinks.swift */, 62959B152524DA7700A3D7F1 /* CAPNotifications.swift */, 62959B072524DA7700A3D7F1 /* CapacitorExtension.swift */, @@ -713,7 +710,6 @@ A7D9312F2B23710300FF59A2 /* JSValueDecoder.swift in Sources */, 62959B362524DA7800A3D7F1 /* CAPBridgeViewController.swift in Sources */, 621ECCB72542045900D3D615 /* CAPBridgedJSTypes.m in Sources */, - 62959B402524DA7800A3D7F1 /* TmpViewController.swift in Sources */, 621ECCD6254205BD00D3D615 /* CAPBridgeProtocol.swift in Sources */, 62D43AF02581817500673C24 /* WKWebView+Capacitor.swift in Sources */, 62959B432524DA7800A3D7F1 /* Data+Capacitor.swift in Sources */, diff --git a/ios/Capacitor/Capacitor/CapacitorBridge.swift b/ios/Capacitor/Capacitor/CapacitorBridge.swift index 6e6f50228f..58af7819ca 100644 --- a/ios/Capacitor/Capacitor/CapacitorBridge.swift +++ b/ios/Capacitor/Capacitor/CapacitorBridge.swift @@ -93,10 +93,6 @@ open class CapacitorBridge: NSObject, CAPBridgeProtocol { } } } - @available(*, deprecated, message: "obsolete") - var tmpWindow: UIWindow? - @available(*, deprecated, message: "obsolete") - static let tmpVCAppeared = Notification(name: Notification.Name(rawValue: "tmpViewControllerAppeared")) public static let capacitorSite = "https://capacitorjs.com/" public static let fileStartIdentifier = "/_capacitor_file_" public static let httpInterceptorStartIdentifier = "/_capacitor_http_interceptor_" @@ -223,9 +219,6 @@ open class CapacitorBridge: NSObject, CAPBridgeProtocol { setupCordovaCompatibility() exportMiscJS() canInjectJS = false - observers.append(NotificationCenter.default.addObserver(forName: type(of: self).tmpVCAppeared.name, object: .none, queue: .none) { [weak self] _ in - self?.tmpWindow = nil - }) self.setupWebDebugging(configuration: configuration) } diff --git a/ios/Capacitor/Capacitor/TmpViewController.swift b/ios/Capacitor/Capacitor/TmpViewController.swift deleted file mode 100644 index 3511d18aed..0000000000 --- a/ios/Capacitor/Capacitor/TmpViewController.swift +++ /dev/null @@ -1,8 +0,0 @@ -import UIKit - -internal class TmpViewController: UIViewController { - override func viewDidAppear(_ animated: Bool) { - super.viewDidAppear(animated) - NotificationCenter.default.post(CapacitorBridge.tmpVCAppeared) - } -} From 2f14984f23dfb879eec2ed433fb83a3ed181d23e Mon Sep 17 00:00:00 2001 From: Joseph Pender Date: Mon, 22 Jun 2026 11:19:17 -0500 Subject: [PATCH 05/15] updating templates for UIScene changes --- .../App/App.xcodeproj/project.pbxproj | 4 +++ ios-pods-template/App/App/AppDelegate.swift | 9 +++++++ ios-pods-template/App/App/Info.plist | 19 ++++++++++++++ ios-pods-template/App/App/SceneDelegate.swift | 26 +++++++++++++++++++ .../App/App.xcodeproj/project.pbxproj | 4 +++ ios-spm-template/App/App/AppDelegate.swift | 21 ++++++--------- ios-spm-template/App/App/Info.plist | 21 ++++++++++++++- ios-spm-template/App/App/SceneDelegate.swift | 20 ++++++++++++++ 8 files changed, 110 insertions(+), 14 deletions(-) create mode 100644 ios-pods-template/App/App/SceneDelegate.swift create mode 100644 ios-spm-template/App/App/SceneDelegate.swift diff --git a/ios-pods-template/App/App.xcodeproj/project.pbxproj b/ios-pods-template/App/App.xcodeproj/project.pbxproj index 092f574919..75dc9750fa 100644 --- a/ios-pods-template/App/App.xcodeproj/project.pbxproj +++ b/ios-pods-template/App/App.xcodeproj/project.pbxproj @@ -14,6 +14,7 @@ 504EC30F1FED79650016851F /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 504EC30E1FED79650016851F /* Assets.xcassets */; }; 504EC3121FED79650016851F /* LaunchScreen.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 504EC3101FED79650016851F /* LaunchScreen.storyboard */; }; 50B271D11FEDC1A000F3C39B /* public in Resources */ = {isa = PBXBuildFile; fileRef = 50B271D01FEDC1A000F3C39B /* public */; }; + 9582B6852FE996820072D4E8 /* SceneDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = 9582B6842FE996800072D4E8 /* SceneDelegate.swift */; }; A084ECDBA7D38E1E42DFC39D /* Pods_App.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = AF277DCFFFF123FFC6DF26C7 /* Pods_App.framework */; }; /* End PBXBuildFile section */ @@ -27,6 +28,7 @@ 504EC3111FED79650016851F /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/LaunchScreen.storyboard; sourceTree = ""; }; 504EC3131FED79650016851F /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; 50B271D01FEDC1A000F3C39B /* public */ = {isa = PBXFileReference; lastKnownFileType = folder; path = public; sourceTree = ""; }; + 9582B6842FE996800072D4E8 /* SceneDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SceneDelegate.swift; sourceTree = ""; }; AF277DCFFFF123FFC6DF26C7 /* Pods_App.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Pods_App.framework; sourceTree = BUILT_PRODUCTS_DIR; }; AF51FD2D460BCFE21FA515B2 /* Pods-App.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-App.release.xcconfig"; path = "Pods/Target Support Files/Pods-App/Pods-App.release.xcconfig"; sourceTree = ""; }; FC68EB0AF532CFC21C3344DD /* Pods-App.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-App.debug.xcconfig"; path = "Pods/Target Support Files/Pods-App/Pods-App.debug.xcconfig"; sourceTree = ""; }; @@ -73,6 +75,7 @@ 504EC3061FED79650016851F /* App */ = { isa = PBXGroup; children = ( + 9582B6842FE996800072D4E8 /* SceneDelegate.swift */, 50379B222058CBB4000EE86E /* capacitor.config.json */, 504EC3071FED79650016851F /* AppDelegate.swift */, 504EC30B1FED79650016851F /* Main.storyboard */, @@ -210,6 +213,7 @@ buildActionMask = 2147483647; files = ( 504EC3081FED79650016851F /* AppDelegate.swift in Sources */, + 9582B6852FE996820072D4E8 /* SceneDelegate.swift in Sources */, ); runOnlyForDeploymentPostprocessing = 0; }; diff --git a/ios-pods-template/App/App/AppDelegate.swift b/ios-pods-template/App/App/AppDelegate.swift index c3cd83b5c0..0198f78130 100644 --- a/ios-pods-template/App/App/AppDelegate.swift +++ b/ios-pods-template/App/App/AppDelegate.swift @@ -45,5 +45,14 @@ class AppDelegate: UIResponder, UIApplicationDelegate { // tracking app url opens, make sure to keep this call return ApplicationDelegateProxy.shared.application(application, continue: userActivity, restorationHandler: restorationHandler) } + + func application(_ application: UIApplication, + configurationForConnecting connectingSceneSession: UISceneSession, + options: UIScene.ConnectionOptions) -> UISceneConfiguration { + + let config = UISceneConfiguration(name: "Default Configuration", sessionRole: connectingSceneSession.role) + config.delegateClass = SceneDelegate.self + return config + } } diff --git a/ios-pods-template/App/App/Info.plist b/ios-pods-template/App/App/Info.plist index ed6ff0bd4d..f8c8a57659 100644 --- a/ios-pods-template/App/App/Info.plist +++ b/ios-pods-template/App/App/Info.plist @@ -22,6 +22,25 @@ $(CURRENT_PROJECT_VERSION) LSRequiresIPhoneOS + UIApplicationSceneManifest + + UIApplicationSupportsMultipleScenes + + UISceneConfigurations + + UIWindowSceneSessionRoleApplication + + + UISceneConfigurationName + Default Configuration + UISceneDelegateClassName + $(PRODUCT_MODULE_NAME).SceneDelegate + UISceneStoryboardFile + Main + + + + UILaunchStoryboardName LaunchScreen UIMainStoryboardFile diff --git a/ios-pods-template/App/App/SceneDelegate.swift b/ios-pods-template/App/App/SceneDelegate.swift new file mode 100644 index 0000000000..412fe45746 --- /dev/null +++ b/ios-pods-template/App/App/SceneDelegate.swift @@ -0,0 +1,26 @@ +import UIKit +import Capacitor + +class SceneDelegate: UIResponder, UIWindowSceneDelegate { + var window: UIWindow? + + func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions) { + guard let windowScene = scene as? UIWindowScene else { return } + + window = UIWindow(windowScene: windowScene) + window?.rootViewController = CAPBridgeViewController() + window?.makeKeyAndVisible() + + SceneDelegateProxy.shared.scene(scene, willConnectTo: session, options: connectionOptions) + } + + func scene(_ scene: UIScene, openURLContexts URLContexts: Set) { + SceneDelegateProxy.shared.scene(scene, openURLContexts: URLContexts) + } + + func scene(_ scene: UIScene, continue userActivity: NSUserActivity) { + SceneDelegateProxy.shared.scene(scene, continue: userActivity) + } +} + + diff --git a/ios-spm-template/App/App.xcodeproj/project.pbxproj b/ios-spm-template/App/App.xcodeproj/project.pbxproj index 46f934efd5..56a0b7d40f 100644 --- a/ios-spm-template/App/App.xcodeproj/project.pbxproj +++ b/ios-spm-template/App/App.xcodeproj/project.pbxproj @@ -15,6 +15,7 @@ 504EC30F1FED79650016851F /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 504EC30E1FED79650016851F /* Assets.xcassets */; }; 504EC3121FED79650016851F /* LaunchScreen.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 504EC3101FED79650016851F /* LaunchScreen.storyboard */; }; 50B271D11FEDC1A000F3C39B /* public in Resources */ = {isa = PBXBuildFile; fileRef = 50B271D01FEDC1A000F3C39B /* public */; }; + 9582B6832FE993A70072D4E8 /* SceneDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = 9582B6822FE993A50072D4E8 /* SceneDelegate.swift */; }; /* End PBXBuildFile section */ /* Begin PBXFileReference section */ @@ -27,6 +28,7 @@ 504EC3111FED79650016851F /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/LaunchScreen.storyboard; sourceTree = ""; }; 504EC3131FED79650016851F /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; 50B271D01FEDC1A000F3C39B /* public */ = {isa = PBXFileReference; lastKnownFileType = folder; path = public; sourceTree = ""; }; + 9582B6822FE993A50072D4E8 /* SceneDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SceneDelegate.swift; sourceTree = ""; }; 958DCC722DB07C7200EA8C5F /* debug.xcconfig */ = {isa = PBXFileReference; lastKnownFileType = text.xcconfig; name = debug.xcconfig; path = ../debug.xcconfig; sourceTree = SOURCE_ROOT; }; /* End PBXFileReference section */ @@ -62,6 +64,7 @@ 504EC3061FED79650016851F /* App */ = { isa = PBXGroup; children = ( + 9582B6822FE993A50072D4E8 /* SceneDelegate.swift */, 50379B222058CBB4000EE86E /* capacitor.config.json */, 504EC3071FED79650016851F /* AppDelegate.swift */, 504EC30B1FED79650016851F /* Main.storyboard */, @@ -156,6 +159,7 @@ buildActionMask = 2147483647; files = ( 504EC3081FED79650016851F /* AppDelegate.swift in Sources */, + 9582B6832FE993A70072D4E8 /* SceneDelegate.swift in Sources */, ); runOnlyForDeploymentPostprocessing = 0; }; diff --git a/ios-spm-template/App/App/AppDelegate.swift b/ios-spm-template/App/App/AppDelegate.swift index c3cd83b5c0..65256aaac9 100644 --- a/ios-spm-template/App/App/AppDelegate.swift +++ b/ios-spm-template/App/App/AppDelegate.swift @@ -32,18 +32,13 @@ class AppDelegate: UIResponder, UIApplicationDelegate { func applicationWillTerminate(_ application: UIApplication) { // Called when the application is about to terminate. Save data if appropriate. See also applicationDidEnterBackground:. } - - func application(_ app: UIApplication, open url: URL, options: [UIApplication.OpenURLOptionsKey: Any] = [:]) -> Bool { - // Called when the app was launched with a url. Feel free to add additional processing here, - // but if you want the App API to support tracking app url opens, make sure to keep this call - return ApplicationDelegateProxy.shared.application(app, open: url, options: options) - } - - func application(_ application: UIApplication, continue userActivity: NSUserActivity, restorationHandler: @escaping ([UIUserActivityRestoring]?) -> Void) -> Bool { - // Called when the app was launched with an activity, including Universal Links. - // Feel free to add additional processing here, but if you want the App API to support - // tracking app url opens, make sure to keep this call - return ApplicationDelegateProxy.shared.application(application, continue: userActivity, restorationHandler: restorationHandler) + + func application(_ application: UIApplication, + configurationForConnecting connectingSceneSession: UISceneSession, + options: UIScene.ConnectionOptions) -> UISceneConfiguration { + let config = UISceneConfiguration(name: "Default Configuration", + sessionRole: connectingSceneSession.role) + config.delegateClass = SceneDelegate.self + return config } - } diff --git a/ios-spm-template/App/App/Info.plist b/ios-spm-template/App/App/Info.plist index 42bcf67503..fc41ce69bc 100644 --- a/ios-spm-template/App/App/Info.plist +++ b/ios-spm-template/App/App/Info.plist @@ -2,7 +2,7 @@ - CAPACITOR_DEBUG + CAPACITOR_DEBUG $(CAPACITOR_DEBUG) CFBundleDevelopmentRegion en @@ -24,6 +24,25 @@ $(CURRENT_PROJECT_VERSION) LSRequiresIPhoneOS + UIApplicationSceneManifest + + UIApplicationSupportsMultipleScenes + + UISceneConfigurations + + UIWindowSceneSessionRoleApplication + + + UISceneConfigurationName + Default Configuration + UISceneDelegateClassName + $(PRODUCT_MODULE_NAME).SceneDelegate + UISceneStoryboardFile + Main + + + + UILaunchStoryboardName LaunchScreen UIMainStoryboardFile diff --git a/ios-spm-template/App/App/SceneDelegate.swift b/ios-spm-template/App/App/SceneDelegate.swift new file mode 100644 index 0000000000..c60c9a8ac3 --- /dev/null +++ b/ios-spm-template/App/App/SceneDelegate.swift @@ -0,0 +1,20 @@ +import UIKit +import Capacitor + +class SceneDelegate: UIResponder, UIWindowSceneDelegate { + var window: UIWindow? + + func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions) { + SceneDelegateProxy.shared.scene(scene, willConnectTo: session, options: connectionOptions) + } + + func scene(_ scene: UIScene, openURLContexts URLContexts: Set) { + SceneDelegateProxy.shared.scene(scene, openURLContexts: URLContexts) + } + + func scene(_ scene: UIScene, continue userActivity: NSUserActivity) { + SceneDelegateProxy.shared.scene(scene, continue: userActivity) + } +} + + From 8f43e0acf0a9d26cc52c792efe8835b76337f96c Mon Sep 17 00:00:00 2001 From: jcesarmobile Date: Mon, 15 Jun 2026 12:11:19 +0200 Subject: [PATCH 06/15] fix(cli): make SPM dependency patch work on prereleases (#8508) --- cli/src/ios/update.ts | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/cli/src/ios/update.ts b/cli/src/ios/update.ts index 1f4bc87d03..3ab793c250 100644 --- a/cli/src/ios/update.ts +++ b/cli/src/ios/update.ts @@ -1,6 +1,6 @@ import { copy, remove, pathExists, readFile, realpath, writeFile } from 'fs-extra'; import { basename, dirname, join, relative } from 'path'; -import { major } from 'semver'; +import { major, prerelease } from 'semver'; import c from '../colors'; import { checkPlatformVersions, getCapacitorPackageVersion, runTask } from '../common'; @@ -70,11 +70,13 @@ async function updatePluginFiles(config: Config, plugins: Plugin[], deployment: const version = content.match(regex)?.[1]; const majorCapVersion = major(iosPlatformVersion); if (version && major(version) != majorCapVersion) { + const preCapVersion = prerelease(iosPlatformVersion); + const forceVersion = preCapVersion ? iosPlatformVersion : `${majorCapVersion}.0.0`; content = setAllStringIn( content, `url: "https://github.com/ionic-team/capacitor-swift-pm.git",`, `)`, - ` from: "${majorCapVersion}.0.0"`, + ` from: "${forceVersion}"`, ); await writeFile(packageSwiftPath, content); logger.warn(`${plugin.id} is built for Capacitor ${major(version)}, it might cause issues`); From 3f0b63d20b572b8073ad82bc0f7e4b1bd9316687 Mon Sep 17 00:00:00 2001 From: "Github Workflow (on behalf of jcesarmobile)" Date: Fri, 19 Jun 2026 09:01:59 +0000 Subject: [PATCH 07/15] Release 8.4.1 --- CHANGELOG.md | 7 +++++++ android/CHANGELOG.md | 4 ++++ android/package.json | 2 +- cli/CHANGELOG.md | 7 +++++++ cli/package.json | 2 +- core/CHANGELOG.md | 4 ++++ core/package.json | 2 +- ios/CHANGELOG.md | 4 ++++ ios/package.json | 2 +- lerna.json | 2 +- 10 files changed, 31 insertions(+), 5 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index cd4fe5f5ad..db39545625 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -3,6 +3,13 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +## [8.4.1](https://github.com/ionic-team/capacitor/compare/8.4.0...8.4.1) (2026-06-19) + +### Bug Fixes + +- **cli:** make SPM dependency patch work on prereleases ([#8508](https://github.com/ionic-team/capacitor/issues/8508)) ([6048e90](https://github.com/ionic-team/capacitor/commit/6048e90171afa0229a3c25b52a23c377c6bb804c)) +- **cli:** patch Capacitor SPM dependency version in plugins ([#8492](https://github.com/ionic-team/capacitor/issues/8492)) ([28bb2c6](https://github.com/ionic-team/capacitor/commit/28bb2c687069dfdd6aa7abc866004a1c6388d103)) + # [8.4.0](https://github.com/ionic-team/capacitor/compare/8.3.4...8.4.0) (2026-06-02) ### Bug Fixes diff --git a/android/CHANGELOG.md b/android/CHANGELOG.md index df7ce545e4..5bc9de9f61 100644 --- a/android/CHANGELOG.md +++ b/android/CHANGELOG.md @@ -3,6 +3,10 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +## [8.4.1](https://github.com/ionic-team/capacitor/compare/8.4.0...8.4.1) (2026-06-19) + +**Note:** Version bump only for package @capacitor/android + # [8.4.0](https://github.com/ionic-team/capacitor/compare/8.3.4...8.4.0) (2026-06-02) ### Bug Fixes diff --git a/android/package.json b/android/package.json index af3f4f556f..7354f3b2c6 100644 --- a/android/package.json +++ b/android/package.json @@ -1,6 +1,6 @@ { "name": "@capacitor/android", - "version": "8.4.0", + "version": "8.4.1", "description": "Capacitor: Cross-platform apps with JavaScript and the web", "homepage": "https://capacitorjs.com", "author": "Ionic Team (https://ionic.io)", diff --git a/cli/CHANGELOG.md b/cli/CHANGELOG.md index ee48a8d5f4..df61fcbaaf 100644 --- a/cli/CHANGELOG.md +++ b/cli/CHANGELOG.md @@ -3,6 +3,13 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +## [8.4.1](https://github.com/ionic-team/capacitor/compare/8.4.0...8.4.1) (2026-06-19) + +### Bug Fixes + +- **cli:** make SPM dependency patch work on prereleases ([#8508](https://github.com/ionic-team/capacitor/issues/8508)) ([6048e90](https://github.com/ionic-team/capacitor/commit/6048e90171afa0229a3c25b52a23c377c6bb804c)) +- **cli:** patch Capacitor SPM dependency version in plugins ([#8492](https://github.com/ionic-team/capacitor/issues/8492)) ([28bb2c6](https://github.com/ionic-team/capacitor/commit/28bb2c687069dfdd6aa7abc866004a1c6388d103)) + # [8.4.0](https://github.com/ionic-team/capacitor/compare/8.3.4...8.4.0) (2026-06-02) ### Bug Fixes diff --git a/cli/package.json b/cli/package.json index 1f987d33ad..7a77d11e96 100644 --- a/cli/package.json +++ b/cli/package.json @@ -1,6 +1,6 @@ { "name": "@capacitor/cli", - "version": "8.4.0", + "version": "8.4.1", "description": "Capacitor: Cross-platform apps with JavaScript and the web", "homepage": "https://capacitorjs.com", "author": "Ionic Team (https://ionic.io)", diff --git a/core/CHANGELOG.md b/core/CHANGELOG.md index 1de9522ff4..1003c8ceb1 100644 --- a/core/CHANGELOG.md +++ b/core/CHANGELOG.md @@ -3,6 +3,10 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +## [8.4.1](https://github.com/ionic-team/capacitor/compare/8.4.0...8.4.1) (2026-06-19) + +**Note:** Version bump only for package @capacitor/core + # [8.4.0](https://github.com/ionic-team/capacitor/compare/8.3.4...8.4.0) (2026-06-02) **Note:** Version bump only for package @capacitor/core diff --git a/core/package.json b/core/package.json index b22aef174f..f821cfd9d9 100644 --- a/core/package.json +++ b/core/package.json @@ -1,6 +1,6 @@ { "name": "@capacitor/core", - "version": "8.4.0", + "version": "8.4.1", "description": "Capacitor: Cross-platform apps with JavaScript and the web", "homepage": "https://capacitorjs.com", "author": "Ionic Team (https://ionic.io)", diff --git a/ios/CHANGELOG.md b/ios/CHANGELOG.md index eac0a4a1ca..dfcf383ff8 100644 --- a/ios/CHANGELOG.md +++ b/ios/CHANGELOG.md @@ -3,6 +3,10 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. +## [8.4.1](https://github.com/ionic-team/capacitor/compare/8.4.0...8.4.1) (2026-06-19) + +**Note:** Version bump only for package @capacitor/ios + # [8.4.0](https://github.com/ionic-team/capacitor/compare/8.3.4...8.4.0) (2026-06-02) ### Features diff --git a/ios/package.json b/ios/package.json index a58c020903..a6a78c23df 100644 --- a/ios/package.json +++ b/ios/package.json @@ -1,6 +1,6 @@ { "name": "@capacitor/ios", - "version": "8.4.0", + "version": "8.4.1", "description": "Capacitor: Cross-platform apps with JavaScript and the web", "homepage": "https://capacitorjs.com", "author": "Ionic Team (https://ionic.io)", diff --git a/lerna.json b/lerna.json index b2efb400d4..be36669427 100644 --- a/lerna.json +++ b/lerna.json @@ -11,6 +11,6 @@ "tagVersionPrefix": "" } }, - "version": "8.4.0", + "version": "8.4.1", "$schema": "node_modules/lerna/schemas/lerna-schema.json" } From db0e074da71c1df08ed3dc9ab51406b4444a9e57 Mon Sep 17 00:00:00 2001 From: Chace Daniels Date: Mon, 29 Jun 2026 11:00:49 -0500 Subject: [PATCH 08/15] fix(ios): mirror deep-link URL to ApplicationDelegateProxy for getLaunchUrl --- ios/Capacitor/Capacitor/CAPApplicationDelegateProxy.swift | 2 +- ios/Capacitor/Capacitor/CAPSceneDelegateProxy.swift | 4 ++++ 2 files changed, 5 insertions(+), 1 deletion(-) diff --git a/ios/Capacitor/Capacitor/CAPApplicationDelegateProxy.swift b/ios/Capacitor/Capacitor/CAPApplicationDelegateProxy.swift index 7f510bc5ac..ef41457d2d 100644 --- a/ios/Capacitor/Capacitor/CAPApplicationDelegateProxy.swift +++ b/ios/Capacitor/Capacitor/CAPApplicationDelegateProxy.swift @@ -4,7 +4,7 @@ import Foundation public class ApplicationDelegateProxy: NSObject, UIApplicationDelegate { public static let shared = ApplicationDelegateProxy() - public private(set) var lastURL: URL? + public internal(set) var lastURL: URL? public func application(_ app: UIApplication, open url: URL, options: [UIApplication.OpenURLOptionsKey: Any] = [:]) -> Bool { NotificationCenter.default.post(name: .capacitorOpenURL, object: [ diff --git a/ios/Capacitor/Capacitor/CAPSceneDelegateProxy.swift b/ios/Capacitor/Capacitor/CAPSceneDelegateProxy.swift index 045ee7bad2..1ec16af7fd 100644 --- a/ios/Capacitor/Capacitor/CAPSceneDelegateProxy.swift +++ b/ios/Capacitor/Capacitor/CAPSceneDelegateProxy.swift @@ -29,6 +29,7 @@ public class SceneDelegateProxy: NSObject, UISceneDelegate { public func scene(_ scene: UIScene, openURLContexts URLContexts: Set) { for context in URLContexts { lastURL = context.url + ApplicationDelegateProxy.shared.lastURL = context.url let options = Self.openURLOptions(from: context.options) // Capacitor 8 backwards compat @@ -37,6 +38,8 @@ public class SceneDelegateProxy: NSObject, UISceneDelegate { "options": options ]) + NotificationCenter.default.post(name: NSNotification.Name.CDVPluginHandleOpenURL, object: context.url) + NotificationCenter.default.post(name: .capacitorSceneOpenURL, object: scene, userInfo: [ "url": context.url, "options": options @@ -50,6 +53,7 @@ public class SceneDelegateProxy: NSObject, UISceneDelegate { return } lastURL = url + ApplicationDelegateProxy.shared.lastURL = url // Capacitor 8 backwards compat NotificationCenter.default.post(name: .capacitorOpenUniversalLink, object: [ From 7d9b89218b35f0c7c9ddb2591648cd751c924616 Mon Sep 17 00:00:00 2001 From: Joseph Pender Date: Wed, 22 Jul 2026 10:19:59 -0500 Subject: [PATCH 09/15] fmt --- .../cordova/MockCordovaWebViewImpl.java | 14 ++++---- ios-pods-template/App/App/AppDelegate.swift | 4 +-- ios-pods-template/App/App/SceneDelegate.swift | 32 +++++++++---------- ios-spm-template/App/App/AppDelegate.swift | 4 +-- ios-spm-template/App/App/SceneDelegate.swift | 22 ++++++------- ios/Capacitor/Capacitor/CapacitorBridge.swift | 14 ++++---- .../Capacitor/WebViewDelegationHandler.swift | 2 +- 7 files changed, 45 insertions(+), 47 deletions(-) diff --git a/android/capacitor/src/main/java/com/getcapacitor/cordova/MockCordovaWebViewImpl.java b/android/capacitor/src/main/java/com/getcapacitor/cordova/MockCordovaWebViewImpl.java index 020c1457a1..1115429d7b 100644 --- a/android/capacitor/src/main/java/com/getcapacitor/cordova/MockCordovaWebViewImpl.java +++ b/android/capacitor/src/main/java/com/getcapacitor/cordova/MockCordovaWebViewImpl.java @@ -70,12 +70,14 @@ public CapacitorEvalBridgeMode(WebView webView, CordovaInterface cordova) { @Override public void onNativeToJsMessageAvailable(final NativeToJsMessageQueue queue) { - cordova.getActivity().runOnUiThread(() -> { - String js = queue.popAndEncodeAsJs(); - if (js != null) { - webView.evaluateJavascript(js, null); - } - }); + cordova + .getActivity() + .runOnUiThread(() -> { + String js = queue.popAndEncodeAsJs(); + if (js != null) { + webView.evaluateJavascript(js, null); + } + }); } } diff --git a/ios-pods-template/App/App/AppDelegate.swift b/ios-pods-template/App/App/AppDelegate.swift index 0198f78130..7ad11d83ed 100644 --- a/ios-pods-template/App/App/AppDelegate.swift +++ b/ios-pods-template/App/App/AppDelegate.swift @@ -45,11 +45,11 @@ class AppDelegate: UIResponder, UIApplicationDelegate { // tracking app url opens, make sure to keep this call return ApplicationDelegateProxy.shared.application(application, continue: userActivity, restorationHandler: restorationHandler) } - + func application(_ application: UIApplication, configurationForConnecting connectingSceneSession: UISceneSession, options: UIScene.ConnectionOptions) -> UISceneConfiguration { - + let config = UISceneConfiguration(name: "Default Configuration", sessionRole: connectingSceneSession.role) config.delegateClass = SceneDelegate.self return config diff --git a/ios-pods-template/App/App/SceneDelegate.swift b/ios-pods-template/App/App/SceneDelegate.swift index 412fe45746..f352e1e959 100644 --- a/ios-pods-template/App/App/SceneDelegate.swift +++ b/ios-pods-template/App/App/SceneDelegate.swift @@ -2,25 +2,23 @@ import UIKit import Capacitor class SceneDelegate: UIResponder, UIWindowSceneDelegate { - var window: UIWindow? + var window: UIWindow? - func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions) { - guard let windowScene = scene as? UIWindowScene else { return } - - window = UIWindow(windowScene: windowScene) - window?.rootViewController = CAPBridgeViewController() - window?.makeKeyAndVisible() - - SceneDelegateProxy.shared.scene(scene, willConnectTo: session, options: connectionOptions) - } + func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions) { + guard let windowScene = scene as? UIWindowScene else { return } - func scene(_ scene: UIScene, openURLContexts URLContexts: Set) { - SceneDelegateProxy.shared.scene(scene, openURLContexts: URLContexts) - } + window = UIWindow(windowScene: windowScene) + window?.rootViewController = CAPBridgeViewController() + window?.makeKeyAndVisible() - func scene(_ scene: UIScene, continue userActivity: NSUserActivity) { - SceneDelegateProxy.shared.scene(scene, continue: userActivity) - } -} + SceneDelegateProxy.shared.scene(scene, willConnectTo: session, options: connectionOptions) + } + func scene(_ scene: UIScene, openURLContexts URLContexts: Set) { + SceneDelegateProxy.shared.scene(scene, openURLContexts: URLContexts) + } + func scene(_ scene: UIScene, continue userActivity: NSUserActivity) { + SceneDelegateProxy.shared.scene(scene, continue: userActivity) + } +} diff --git a/ios-spm-template/App/App/AppDelegate.swift b/ios-spm-template/App/App/AppDelegate.swift index 65256aaac9..fec95acae1 100644 --- a/ios-spm-template/App/App/AppDelegate.swift +++ b/ios-spm-template/App/App/AppDelegate.swift @@ -32,12 +32,12 @@ class AppDelegate: UIResponder, UIApplicationDelegate { func applicationWillTerminate(_ application: UIApplication) { // Called when the application is about to terminate. Save data if appropriate. See also applicationDidEnterBackground:. } - + func application(_ application: UIApplication, configurationForConnecting connectingSceneSession: UISceneSession, options: UIScene.ConnectionOptions) -> UISceneConfiguration { let config = UISceneConfiguration(name: "Default Configuration", - sessionRole: connectingSceneSession.role) + sessionRole: connectingSceneSession.role) config.delegateClass = SceneDelegate.self return config } diff --git a/ios-spm-template/App/App/SceneDelegate.swift b/ios-spm-template/App/App/SceneDelegate.swift index c60c9a8ac3..a21dd960c8 100644 --- a/ios-spm-template/App/App/SceneDelegate.swift +++ b/ios-spm-template/App/App/SceneDelegate.swift @@ -2,19 +2,17 @@ import UIKit import Capacitor class SceneDelegate: UIResponder, UIWindowSceneDelegate { - var window: UIWindow? + var window: UIWindow? - func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions) { - SceneDelegateProxy.shared.scene(scene, willConnectTo: session, options: connectionOptions) - } + func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions) { + SceneDelegateProxy.shared.scene(scene, willConnectTo: session, options: connectionOptions) + } - func scene(_ scene: UIScene, openURLContexts URLContexts: Set) { - SceneDelegateProxy.shared.scene(scene, openURLContexts: URLContexts) - } + func scene(_ scene: UIScene, openURLContexts URLContexts: Set) { + SceneDelegateProxy.shared.scene(scene, openURLContexts: URLContexts) + } - func scene(_ scene: UIScene, continue userActivity: NSUserActivity) { - SceneDelegateProxy.shared.scene(scene, continue: userActivity) - } + func scene(_ scene: UIScene, continue userActivity: NSUserActivity) { + SceneDelegateProxy.shared.scene(scene, continue: userActivity) + } } - - diff --git a/ios/Capacitor/Capacitor/CapacitorBridge.swift b/ios/Capacitor/Capacitor/CapacitorBridge.swift index 58af7819ca..2634363950 100644 --- a/ios/Capacitor/Capacitor/CapacitorBridge.swift +++ b/ios/Capacitor/Capacitor/CapacitorBridge.swift @@ -264,15 +264,15 @@ open class CapacitorBridge: NSObject, CAPBridgeProtocol { registerCordovaPlugins() } else { observers.append(NotificationCenter.default.addObserver(forName: UIScene.willEnterForegroundNotification, object: nil, queue: OperationQueue.main) { [weak self] notification in - if let scene = notification.object as? UIWindowScene, scene === self?.viewController?.view.window?.windowScene { - self?.triggerDocumentJSEvent(eventName: "resume") - } - + if let scene = notification.object as? UIWindowScene, scene === self?.viewController?.view.window?.windowScene { + self?.triggerDocumentJSEvent(eventName: "resume") + } + }) observers.append(NotificationCenter.default.addObserver(forName: UIScene.didEnterBackgroundNotification, object: nil, queue: OperationQueue.main) { [weak self] notification in - if let scene = notification.object as? UIWindowScene, scene === self?.viewController?.view.window?.windowScene { - self?.triggerDocumentJSEvent(eventName: "pause") - } + if let scene = notification.object as? UIWindowScene, scene === self?.viewController?.view.window?.windowScene { + self?.triggerDocumentJSEvent(eventName: "pause") + } }) } } diff --git a/ios/Capacitor/Capacitor/WebViewDelegationHandler.swift b/ios/Capacitor/Capacitor/WebViewDelegationHandler.swift index cab0279c4b..866c7e8c5d 100644 --- a/ios/Capacitor/Capacitor/WebViewDelegationHandler.swift +++ b/ios/Capacitor/Capacitor/WebViewDelegationHandler.swift @@ -108,7 +108,7 @@ open class WebViewDelegationHandler: NSObject, WKNavigationDelegate, WKUIDelegat if !isApplicationNavigation, toplevelNavigation { // disallow and let the system handle it if webView.window?.windowScene?.activationState == .foregroundActive { - UIApplication.shared.open(navURL, options: [:], completionHandler: nil) + UIApplication.shared.open(navURL, options: [:], completionHandler: nil) } decisionHandler(.cancel) return From c524ec6f442ea2c7cd8a4154669d6d37df391c2b Mon Sep 17 00:00:00 2001 From: Joseph Pender Date: Wed, 22 Jul 2026 11:44:28 -0500 Subject: [PATCH 10/15] add SceneDelegate to TestsHostApp --- ios/Capacitor/Capacitor.xcodeproj/project.pbxproj | 4 ++++ ios/Capacitor/TestsHostApp/AppDelegate.swift | 9 +++++++++ ios/Capacitor/TestsHostApp/SceneDelegate.swift | 5 +++++ 3 files changed, 18 insertions(+) create mode 100644 ios/Capacitor/TestsHostApp/SceneDelegate.swift diff --git a/ios/Capacitor/Capacitor.xcodeproj/project.pbxproj b/ios/Capacitor/Capacitor.xcodeproj/project.pbxproj index 6cd33b6005..573e90cd9a 100644 --- a/ios/Capacitor/Capacitor.xcodeproj/project.pbxproj +++ b/ios/Capacitor/Capacitor.xcodeproj/project.pbxproj @@ -61,6 +61,7 @@ 62959BA52526475A00A3D7F1 /* Cordova.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 62959BA02526474300A3D7F1 /* Cordova.framework */; }; 6296A77E253A2E49005A202A /* AppDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6296A77D253A2E49005A202A /* AppDelegate.swift */; }; 6296A782253A2E49005A202A /* ViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6296A781253A2E49005A202A /* ViewController.swift */; }; + 6296A7A0253A2E49005A202A /* SceneDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6296A7A1253A2E49005A202A /* SceneDelegate.swift */; }; 6296A785253A2E49005A202A /* Main.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 6296A783253A2E49005A202A /* Main.storyboard */; }; 6296A787253A2E49005A202A /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 6296A786253A2E49005A202A /* Assets.xcassets */; }; 6296A78A253A2E49005A202A /* LaunchScreen.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 6296A788253A2E49005A202A /* LaunchScreen.storyboard */; }; @@ -218,6 +219,7 @@ 6296A77B253A2E49005A202A /* TestsHostApp.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = TestsHostApp.app; sourceTree = BUILT_PRODUCTS_DIR; }; 6296A77D253A2E49005A202A /* AppDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppDelegate.swift; sourceTree = ""; }; 6296A781253A2E49005A202A /* ViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ViewController.swift; sourceTree = ""; }; + 6296A7A1253A2E49005A202A /* SceneDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SceneDelegate.swift; sourceTree = ""; }; 6296A784253A2E49005A202A /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/Main.storyboard; sourceTree = ""; }; 6296A786253A2E49005A202A /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Assets.xcassets; sourceTree = ""; }; 6296A789253A2E49005A202A /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/LaunchScreen.storyboard; sourceTree = ""; }; @@ -446,6 +448,7 @@ isa = PBXGroup; children = ( 6296A77D253A2E49005A202A /* AppDelegate.swift */, + 6296A7A1253A2E49005A202A /* SceneDelegate.swift */, 6296A781253A2E49005A202A /* ViewController.swift */, 62E0735125535E6500BAAADB /* configurations */, 6296A783253A2E49005A202A /* Main.storyboard */, @@ -784,6 +787,7 @@ files = ( 6296A782253A2E49005A202A /* ViewController.swift in Sources */, 6296A77E253A2E49005A202A /* AppDelegate.swift in Sources */, + 6296A7A0253A2E49005A202A /* SceneDelegate.swift in Sources */, ); runOnlyForDeploymentPostprocessing = 0; }; diff --git a/ios/Capacitor/TestsHostApp/AppDelegate.swift b/ios/Capacitor/TestsHostApp/AppDelegate.swift index f8b87fe2d1..9107e3c451 100644 --- a/ios/Capacitor/TestsHostApp/AppDelegate.swift +++ b/ios/Capacitor/TestsHostApp/AppDelegate.swift @@ -6,4 +6,13 @@ class AppDelegate: UIResponder, UIApplicationDelegate { // Override point for customization after application launch. return true } + + func application(_ application: UIApplication, + configurationForConnecting connectingSceneSession: UISceneSession, + options: UIScene.ConnectionOptions) -> UISceneConfiguration { + let config = UISceneConfiguration(name: "Default Configuration", + sessionRole: connectingSceneSession.role) + config.delegateClass = SceneDelegate.self + return config + } } diff --git a/ios/Capacitor/TestsHostApp/SceneDelegate.swift b/ios/Capacitor/TestsHostApp/SceneDelegate.swift new file mode 100644 index 0000000000..e0be6e9cfe --- /dev/null +++ b/ios/Capacitor/TestsHostApp/SceneDelegate.swift @@ -0,0 +1,5 @@ +import UIKit + +class SceneDelegate: UIResponder, UIWindowSceneDelegate { + var window: UIWindow? +} From f2e6a3dd64172238336e933ec4b23428a2ce007d Mon Sep 17 00:00:00 2001 From: Joseph Pender Date: Wed, 22 Jul 2026 11:44:55 -0500 Subject: [PATCH 11/15] fmt --- .../cordova/MockCordovaWebViewImpl.java | 14 ++++++------- .../com/getcapacitor/plugin/SystemBars.java | 20 +++++++++---------- .../plugin/util/HttpRequestHandlerTest.java | 4 ++-- 3 files changed, 18 insertions(+), 20 deletions(-) diff --git a/android/capacitor/src/main/java/com/getcapacitor/cordova/MockCordovaWebViewImpl.java b/android/capacitor/src/main/java/com/getcapacitor/cordova/MockCordovaWebViewImpl.java index 1115429d7b..020c1457a1 100644 --- a/android/capacitor/src/main/java/com/getcapacitor/cordova/MockCordovaWebViewImpl.java +++ b/android/capacitor/src/main/java/com/getcapacitor/cordova/MockCordovaWebViewImpl.java @@ -70,14 +70,12 @@ public CapacitorEvalBridgeMode(WebView webView, CordovaInterface cordova) { @Override public void onNativeToJsMessageAvailable(final NativeToJsMessageQueue queue) { - cordova - .getActivity() - .runOnUiThread(() -> { - String js = queue.popAndEncodeAsJs(); - if (js != null) { - webView.evaluateJavascript(js, null); - } - }); + cordova.getActivity().runOnUiThread(() -> { + String js = queue.popAndEncodeAsJs(); + if (js != null) { + webView.evaluateJavascript(js, null); + } + }); } } diff --git a/android/capacitor/src/main/java/com/getcapacitor/plugin/SystemBars.java b/android/capacitor/src/main/java/com/getcapacitor/plugin/SystemBars.java index fd71370945..b3c95916a7 100644 --- a/android/capacitor/src/main/java/com/getcapacitor/plugin/SystemBars.java +++ b/android/capacitor/src/main/java/com/getcapacitor/plugin/SystemBars.java @@ -43,17 +43,17 @@ public class SystemBars extends Plugin { private static final int WEBVIEW_VERSION_WITH_SAFE_AREA_KEYBOARD_FIX = 144; static final String viewportMetaJSFunction = """ - function capacitorSystemBarsCheckMetaViewport() { - const meta = document.querySelectorAll("meta[name=viewport]"); - if (meta.length == 0) { - return false; - } - // get the last found meta viewport tag - const metaContent = meta[meta.length - 1].content; - return metaContent.includes("viewport-fit=cover"); + function capacitorSystemBarsCheckMetaViewport() { + const meta = document.querySelectorAll("meta[name=viewport]"); + if (meta.length == 0) { + return false; } - capacitorSystemBarsCheckMetaViewport(); - """; + // get the last found meta viewport tag + const metaContent = meta[meta.length - 1].content; + return metaContent.includes("viewport-fit=cover"); + } + capacitorSystemBarsCheckMetaViewport(); + """; private String insetsHandling = INSETS_HANDLING_CSS; private boolean hasViewportCover = false; diff --git a/android/capacitor/src/test/java/com/getcapacitor/plugin/util/HttpRequestHandlerTest.java b/android/capacitor/src/test/java/com/getcapacitor/plugin/util/HttpRequestHandlerTest.java index fd8b686ee6..1006721235 100644 --- a/android/capacitor/src/test/java/com/getcapacitor/plugin/util/HttpRequestHandlerTest.java +++ b/android/capacitor/src/test/java/com/getcapacitor/plugin/util/HttpRequestHandlerTest.java @@ -11,8 +11,8 @@ public class HttpRequestHandlerTest { static final String BASE_URL = "https://httpbin.org/get"; static final String PARAMS_JSON = """ - {"k": "a&b"} - """; + {"k": "a&b"} + """; @Test public void testHttpURLConnectionBuilderSetUrlParamsEncoded() throws Exception { From 23ec4a0824cedbd61e13cbc28283e041e2fdfa4d Mon Sep 17 00:00:00 2001 From: Joseph Pender Date: Mon, 27 Jul 2026 12:47:18 -0500 Subject: [PATCH 12/15] Initialize window with CAPBridgeViewController in SceneDelegate --- ios-spm-template/App/App/SceneDelegate.swift | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/ios-spm-template/App/App/SceneDelegate.swift b/ios-spm-template/App/App/SceneDelegate.swift index a21dd960c8..0194fad6df 100644 --- a/ios-spm-template/App/App/SceneDelegate.swift +++ b/ios-spm-template/App/App/SceneDelegate.swift @@ -5,7 +5,13 @@ class SceneDelegate: UIResponder, UIWindowSceneDelegate { var window: UIWindow? func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions) { - SceneDelegateProxy.shared.scene(scene, willConnectTo: session, options: connectionOptions) + guard let windowScene = scene as? UIWindowScene else { return } + + window = UIWindow(windowScene: windowScene) + window?.rootViewController = CAPBridgeViewController() + window?.makeKeyAndVisible() + + SceneDelegateProxy.shared.scene(scene, willConnectTo: session, options: connectionOptions) } func scene(_ scene: UIScene, openURLContexts URLContexts: Set) { From ee5b0f0e5124a4fd60da8ee1119552d55eb4e09c Mon Sep 17 00:00:00 2001 From: Joseph Pender Date: Mon, 27 Jul 2026 12:54:37 -0500 Subject: [PATCH 13/15] Defer scene connect URL/activity delivery until plugins load --- .../Capacitor/CAPSceneDelegateProxy.swift | 20 +++++++++++++------ 1 file changed, 14 insertions(+), 6 deletions(-) diff --git a/ios/Capacitor/Capacitor/CAPSceneDelegateProxy.swift b/ios/Capacitor/Capacitor/CAPSceneDelegateProxy.swift index 1ec16af7fd..a172a1c1f7 100644 --- a/ios/Capacitor/Capacitor/CAPSceneDelegateProxy.swift +++ b/ios/Capacitor/Capacitor/CAPSceneDelegateProxy.swift @@ -17,12 +17,20 @@ public class SceneDelegateProxy: NSObject, UISceneDelegate { public func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions) { NotificationCenter.default.post(name: .capacitorSceneWillConnect, object: scene) - if !connectionOptions.urlContexts.isEmpty { - self.scene(scene, openURLContexts: connectionOptions.urlContexts) - } - - for userActivity in connectionOptions.userActivities { - self.scene(scene, continue: userActivity) + // Plugins haven't loaded yet on a cold start, so notifications posted here are + // missed. Deliver them on the first capacitorViewDidAppear, once plugins are + // registered. + var token: NSObjectProtocol? + token = NotificationCenter.default.addObserver(forName: .capacitorViewDidAppear, object: nil, queue: .main) { _ in + if let token { + NotificationCenter.default.removeObserver(token) + } + if !connectionOptions.urlContexts.isEmpty { + self.scene(scene, openURLContexts: connectionOptions.urlContexts) + } + for userActivity in connectionOptions.userActivities { + self.scene(scene, continue: userActivity) + } } } From 5832336d8a9d57d250a437718ec92102c361d717 Mon Sep 17 00:00:00 2001 From: Joseph Pender Date: Mon, 27 Jul 2026 12:54:42 -0500 Subject: [PATCH 14/15] fmt --- ios-spm-template/App/App/SceneDelegate.swift | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/ios-spm-template/App/App/SceneDelegate.swift b/ios-spm-template/App/App/SceneDelegate.swift index 0194fad6df..f352e1e959 100644 --- a/ios-spm-template/App/App/SceneDelegate.swift +++ b/ios-spm-template/App/App/SceneDelegate.swift @@ -5,13 +5,13 @@ class SceneDelegate: UIResponder, UIWindowSceneDelegate { var window: UIWindow? func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions) { - guard let windowScene = scene as? UIWindowScene else { return } + guard let windowScene = scene as? UIWindowScene else { return } - window = UIWindow(windowScene: windowScene) - window?.rootViewController = CAPBridgeViewController() - window?.makeKeyAndVisible() + window = UIWindow(windowScene: windowScene) + window?.rootViewController = CAPBridgeViewController() + window?.makeKeyAndVisible() - SceneDelegateProxy.shared.scene(scene, willConnectTo: session, options: connectionOptions) + SceneDelegateProxy.shared.scene(scene, willConnectTo: session, options: connectionOptions) } func scene(_ scene: UIScene, openURLContexts URLContexts: Set) { From c590693f243ba3a824d99e3cd442a22dd1f1bc77 Mon Sep 17 00:00:00 2001 From: Joseph Pender Date: Mon, 27 Jul 2026 12:56:44 -0500 Subject: [PATCH 15/15] Remove Phase 2 multi-window TODO stubs from SceneDelegateProxy --- .../Capacitor/CAPSceneDelegateProxy.swift | 22 ------------------- 1 file changed, 22 deletions(-) diff --git a/ios/Capacitor/Capacitor/CAPSceneDelegateProxy.swift b/ios/Capacitor/Capacitor/CAPSceneDelegateProxy.swift index a172a1c1f7..782efe4cff 100644 --- a/ios/Capacitor/Capacitor/CAPSceneDelegateProxy.swift +++ b/ios/Capacitor/Capacitor/CAPSceneDelegateProxy.swift @@ -73,28 +73,6 @@ public class SceneDelegateProxy: NSObject, UISceneDelegate { ]) } - // TODO: Not until Phase 2 of the UI modernization project - - public func sceneDidDisconnect(_ scene: UIScene) { - // TODO: multi-window — tear down the bridge associated with this scene. - } - - public func sceneDidBecomeActive(_ scene: UIScene) { - // TODO: multi-window — forward per-scene active event to the bridge. - } - - public func sceneWillResignActive(_ scene: UIScene) { - // TODO: multi-window — forward per-scene resign-active event to the bridge. - } - - public func sceneWillEnterForeground(_ scene: UIScene) { - // TODO: multi-window — drive JS `resume` from this instead of UIApplication.willEnterForegroundNotification. - } - - public func sceneDidEnterBackground(_ scene: UIScene) { - // TODO: multi-window — drive JS `pause` from this instead of UIApplication.didEnterBackgroundNotification. - } - private static func openURLOptions(from sceneOptions: UIScene.OpenURLOptions) -> [UIApplication.OpenURLOptionsKey: Any] { var options: [UIApplication.OpenURLOptionsKey: Any] = [:] if let sourceApplication = sceneOptions.sourceApplication {