iOS使用UISceneDelegate初始化FlutterMethodChannel崩溃求助
解决方案
核心问题
didInitializeImplicitFlutterEngine回调触发时,应用的window或其rootViewController可能还未完成初始化或赋值,强制类型转换as!自然会崩溃。
推荐方案:在SceneDelegate的场景初始化回调中处理
改用SceneDelegate的scene(_:willConnectTo:options:)方法来初始化MethodChannel,这个时机下window和rootViewController已经处于就绪状态:
import UIKit import Flutter 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并关联到当前场景 let window = UIWindow(windowScene: windowScene) self.window = window // 获取AppDelegate中隐式初始化的FlutterEngine guard let flutterEngine = (UIApplication.shared.delegate as? AppDelegate)?.flutterEngine else { fatalError("FlutterEngine未正确初始化") } // 创建并设置FlutterViewController为根控制器 let flutterViewController = FlutterViewController(engine: flutterEngine, nibName: nil, bundle: nil) window.rootViewController = flutterViewController window.makeKeyAndVisible() // 初始化MethodChannel let methodChannel = FlutterMethodChannel(name: "com.your.app.channel", binaryMessenger: flutterViewController.binaryMessenger) methodChannel.setMethodCallHandler { call, result in // 处理Flutter侧的方法调用 switch call.method { case "someMethod": // 执行对应逻辑 result(nil) default: result(FlutterMethodNotImplemented) } } } }
备选方案:延迟执行(不推荐)
如果必须在didInitializeImplicitFlutterEngine中处理,可以通过延迟执行确保UI层级就绪,但这种方式依赖系统调度,可靠性较低:
extension AppDelegate { func didInitializeImplicitFlutterEngine(_ flutterEngine: FlutterEngine) { DispatchQueue.main.asyncAfter(deadline: .now() + 0.1) { guard let window = UIApplication.shared.windows.first, let flutterVC = window.rootViewController as? FlutterViewController else { print("无法获取有效的FlutterViewController") return } let methodChannel = FlutterMethodChannel(name: "com.your.app.channel", binaryMessenger: flutterVC.binaryMessenger) // 设置MethodChannel处理逻辑 } } }
额外检查项
- 确认
Info.plist中已正确配置Scene相关条目,指定SceneDelegate类:<key>UIApplicationSceneManifest</key> <dict> <key>UISceneConfigurations</key> <dict> <key>UIWindowSceneSessionRoleApplication</key> <array> <dict> <key>UISceneDelegateClassName</key> <string>$(PRODUCT_MODULE_NAME).SceneDelegate</string> <key>UISceneConfigurationName</key> <string>Default Configuration</string> </dict> </array> </dict> </dict> - 确保
AppDelegate中已正确初始化隐式FlutterEngine:@UIApplicationMain class AppDelegate: FlutterAppDelegate { override func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool { GeneratedPluginRegistrant.register(with: self.flutterEngine) return super.application(application, didFinishLaunchingWithOptions: launchOptions) } }
内容的提问来源于stack exchange,提问作者Carl Smith
相关产品推荐
相关产品推荐

