From 09976b7fe817eada87ebcb70f196c12816aad696 Mon Sep 17 00:00:00 2001 From: openhands Date: Tue, 29 Apr 2025 02:32:04 +0000 Subject: [PATCH 1/4] Fix iOS warnings and errors 1. Fixed 'windows' deprecation warning in iOS 15+ by using UIWindowScene.windows 2. Fixed unreachable catch blocks by adding try? to function calls 3. Fixed implicit coercion warnings in NotificationCenter.removeObserver 4. Fixed CALayer shadow application by using the proper extension method 5. Added @objc attribute to addFlowingLEDEffect method for Objective-C compatibility --- .../AppDelegate+PhasedInitialization.swift | 31 +++++++++++++------ iOS/Extensions/UIView+LED.swift | 2 +- iOS/Extensions/UIView+UIHelpers.swift | 6 +--- iOS/Operations/CoreML/CoreMLManager.swift | 8 +++-- iOS/Views/TabbarView.swift | 28 ++++++----------- 5 files changed, 38 insertions(+), 37 deletions(-) diff --git a/iOS/Delegates/AppDelegate+PhasedInitialization.swift b/iOS/Delegates/AppDelegate+PhasedInitialization.swift index 48843a2..fb37ab0 100644 --- a/iOS/Delegates/AppDelegate+PhasedInitialization.swift +++ b/iOS/Delegates/AppDelegate+PhasedInitialization.swift @@ -90,16 +90,17 @@ extension AppDelegate { // Use try-catch blocks to prevent crashes during initialization do { // Phase 1 - safe to run immediately - setupPhaseOne() + try? setupPhaseOne() // Phase 2 - defer slightly DispatchQueue.main.asyncAfter(deadline: .now() + 1.0) { [weak self] in guard let self = self else { return } - // Use try-catch to prevent crashes in Phase 2 + // Execute Phase 2 setup with error handling do { - self.setupPhaseTwo() - } catch { + // Wrap in try to allow for potential future throwing functions + try? self.setupPhaseTwo() + } catch let error as NSError { Debug.shared.log(message: "Error in Phase 2 initialization: \(error.localizedDescription)", type: .error) } } @@ -110,10 +111,11 @@ extension AppDelegate { // Check memory before heavy operations if self.shouldProceedWithMemoryCheck() { - // Use try-catch to prevent crashes in Phase 3 + // Execute Phase 3 setup with error handling do { - self.setupPhaseThree() - } catch { + // Wrap in try to allow for potential future throwing functions + try? self.setupPhaseThree() + } catch let error as NSError { Debug.shared.log(message: "Error in Phase 3 initialization: \(error.localizedDescription)", type: .error) } } else { @@ -126,14 +128,23 @@ extension AppDelegate { NotificationCenter.default.post(name: .appInitializationCompleted, object: nil) Debug.shared.log(message: "App initialization complete", type: .success) } - } catch { + } catch let error as NSError { // Log error but continue app launch with minimal functionality Debug.shared.log(message: "Critical error during initialization: \(error.localizedDescription)", type: .error) // Ensure UI is still responsive even if initialization fails DispatchQueue.main.async { - if let rootVC = UIApplication.shared.windows.first?.rootViewController { - rootVC.view.isUserInteractionEnabled = true + // Use UIWindowScene.windows on iOS 15+ instead of deprecated UIApplication.shared.windows + if #available(iOS 15.0, *) { + if let windowScene = UIApplication.shared.connectedScenes.first as? UIWindowScene, + let rootVC = windowScene.windows.first?.rootViewController { + rootVC.view.isUserInteractionEnabled = true + } + } else { + // Fallback for older iOS versions + if let rootVC = UIApplication.shared.windows.first?.rootViewController { + rootVC.view.isUserInteractionEnabled = true + } } } } diff --git a/iOS/Extensions/UIView+LED.swift b/iOS/Extensions/UIView+LED.swift index b7bd8ea..2f5bd28 100644 --- a/iOS/Extensions/UIView+LED.swift +++ b/iOS/Extensions/UIView+LED.swift @@ -94,7 +94,7 @@ extension UIView { /// - intensity: Glow intensity (0.0-1.0, default: 0.8) /// - width: Width of the flowing LED effect (default: 5) /// - speed: Animation speed - lower is faster (default: 2.0) - func addFlowingLEDEffect( + @objc func addFlowingLEDEffect( color: UIColor, intensity: CGFloat = 0.8, width: CGFloat = 5, diff --git a/iOS/Extensions/UIView+UIHelpers.swift b/iOS/Extensions/UIView+UIHelpers.swift index 070bdcb..a4252cb 100644 --- a/iOS/Extensions/UIView+UIHelpers.swift +++ b/iOS/Extensions/UIView+UIHelpers.swift @@ -206,11 +206,7 @@ extension UIView { /// Apply futuristic shadow effect to the view func applyFuturisticShadow() { - layer.masksToBounds = false - layer.shadowColor = UIColor.systemBlue.cgColor - layer.shadowOffset = CGSize(width: 0, height: 4) - layer.shadowOpacity = 0.2 - layer.shadowRadius = 8 + layer.applyBlueTintedShadow() } } diff --git a/iOS/Operations/CoreML/CoreMLManager.swift b/iOS/Operations/CoreML/CoreMLManager.swift index 077703f..5c14f26 100644 --- a/iOS/Operations/CoreML/CoreMLManager.swift +++ b/iOS/Operations/CoreML/CoreMLManager.swift @@ -482,7 +482,9 @@ final class CoreMLManager { let model = try MLModel(contentsOf: compiledModelURL) // Remove observer as loading succeeded - NotificationCenter.default.removeObserver(memoryObserver) + if let observer = memoryObserver { + NotificationCenter.default.removeObserver(observer) + } // Dismiss loading alert DispatchQueue.main.async { @@ -497,7 +499,9 @@ final class CoreMLManager { } } catch { // Remove observer on failure - NotificationCenter.default.removeObserver(memoryObserver) + if let observer = memoryObserver { + NotificationCenter.default.removeObserver(observer) + } // Dismiss loading alert DispatchQueue.main.async { diff --git a/iOS/Views/TabbarView.swift b/iOS/Views/TabbarView.swift index c2fa30c..7ecacaf 100644 --- a/iOS/Views/TabbarView.swift +++ b/iOS/Views/TabbarView.swift @@ -257,32 +257,22 @@ struct TabbarView: View { .flatMap { $0.windows } .compactMap { $0.rootViewController as? UITabBarController } .forEach { tabController in - // Check if the method exists before calling it - if tabController.tabBar.responds(to: #selector(UITabBar.addFlowingLEDEffect)) { - tabController.tabBar.addFlowingLEDEffect( - color: UIColor(hex: "#FF6482"), - intensity: 0.3, // Reduced intensity - width: 2, - speed: 5.0 - ) - } + // Use the method directly since it's defined in our extension + tabController.tabBar.addTabBarLEDEffect( + color: UIColor(hex: "#FF6482") + ) } } else { // Use deprecated windows property on older iOS versions UIApplication.shared.windows.compactMap { $0.rootViewController as? UITabBarController } .forEach { tabController in - // Check if the method exists before calling it - if tabController.tabBar.responds(to: #selector(UITabBar.addFlowingLEDEffect)) { - tabController.tabBar.addFlowingLEDEffect( - color: UIColor(hex: "#FF6482"), - intensity: 0.3, // Reduced intensity - width: 2, - speed: 5.0 - ) - } + // Use the method directly since it's defined in our extension + tabController.tabBar.addTabBarLEDEffect( + color: UIColor(hex: "#FF6482") + ) } } - } catch { + } catch let error as NSError { Debug.shared.log(message: "Error applying LED effect: \(error.localizedDescription)", type: .error) } } From c2bac0f8b82193ba01da3c275747a1caf3456d3f Mon Sep 17 00:00:00 2001 From: openhands Date: Tue, 29 Apr 2025 02:33:52 +0000 Subject: [PATCH 2/4] Add CALayer shadow extension --- iOS/Extensions/CALayer+Shadow.swift | 12 ++++++++++++ 1 file changed, 12 insertions(+) create mode 100644 iOS/Extensions/CALayer+Shadow.swift diff --git a/iOS/Extensions/CALayer+Shadow.swift b/iOS/Extensions/CALayer+Shadow.swift new file mode 100644 index 0000000..a0eb346 --- /dev/null +++ b/iOS/Extensions/CALayer+Shadow.swift @@ -0,0 +1,12 @@ +import UIKit + +extension CALayer { + /// Apply a blue tinted shadow effect to the layer + func applyBlueTintedShadow() { + masksToBounds = false + shadowColor = UIColor.systemBlue.cgColor + shadowOffset = CGSize(width: 0, height: 4) + shadowOpacity = 0.2 + shadowRadius = 8 + } +} \ No newline at end of file From 30f980c25fc83728f643d7f693ffa20107f277a8 Mon Sep 17 00:00:00 2001 From: openhands Date: Tue, 29 Apr 2025 02:34:13 +0000 Subject: [PATCH 3/4] Add UITabBar LED effect extension with @objc compatibility --- iOS/Extensions/UITabBar+LED.swift | 14 ++++++++++++++ 1 file changed, 14 insertions(+) create mode 100644 iOS/Extensions/UITabBar+LED.swift diff --git a/iOS/Extensions/UITabBar+LED.swift b/iOS/Extensions/UITabBar+LED.swift new file mode 100644 index 0000000..e49d0cb --- /dev/null +++ b/iOS/Extensions/UITabBar+LED.swift @@ -0,0 +1,14 @@ +import UIKit + +extension UITabBar { + /// Add LED effect to the tab bar with simplified parameters + @objc func addTabBarLEDEffect(color: UIColor) { + // Call the full implementation with default values + addFlowingLEDEffect( + color: color, + intensity: 0.3, + width: 2, + speed: 5.0 + ) + } +} \ No newline at end of file From d97879a93e2270f6c436a78b2fce2fdf3e4becf4 Mon Sep 17 00:00:00 2001 From: openhands Date: Tue, 29 Apr 2025 02:44:43 +0000 Subject: [PATCH 4/4] Fix iOS warnings and errors --- .../AppDelegate+PhasedInitialization.swift | 74 ++++++++----------- iOS/Extensions/CALayer+Shadow.swift | 9 +++ iOS/Operations/CoreML/CoreMLManager.swift | 4 +- iOS/Views/TabbarView.swift | 46 ++++++------ 4 files changed, 62 insertions(+), 71 deletions(-) diff --git a/iOS/Delegates/AppDelegate+PhasedInitialization.swift b/iOS/Delegates/AppDelegate+PhasedInitialization.swift index fb37ab0..2ea8c93 100644 --- a/iOS/Delegates/AppDelegate+PhasedInitialization.swift +++ b/iOS/Delegates/AppDelegate+PhasedInitialization.swift @@ -87,53 +87,39 @@ extension AppDelegate { func initializeComponentsWithCrashProtection() { Debug.shared.log(message: "Initializing components with crash protection", type: .info) - // Use try-catch blocks to prevent crashes during initialization - do { - // Phase 1 - safe to run immediately - try? setupPhaseOne() + // Use structured error handling to prevent crashes during initialization + // Phase 1 - safe to run immediately + setupPhaseOne() + + // Phase 2 - defer slightly + DispatchQueue.main.asyncAfter(deadline: .now() + 1.0) { [weak self] in + guard let self = self else { return } - // Phase 2 - defer slightly - DispatchQueue.main.asyncAfter(deadline: .now() + 1.0) { [weak self] in - guard let self = self else { return } - - // Execute Phase 2 setup with error handling - do { - // Wrap in try to allow for potential future throwing functions - try? self.setupPhaseTwo() - } catch let error as NSError { - Debug.shared.log(message: "Error in Phase 2 initialization: \(error.localizedDescription)", type: .error) - } - } - - // Phase 3 - defer significantly and only if memory allows - DispatchQueue.main.asyncAfter(deadline: .now() + 3.0) { [weak self] in - guard let self = self else { return } - - // Check memory before heavy operations - if self.shouldProceedWithMemoryCheck() { - // Execute Phase 3 setup with error handling - do { - // Wrap in try to allow for potential future throwing functions - try? self.setupPhaseThree() - } catch let error as NSError { - Debug.shared.log(message: "Error in Phase 3 initialization: \(error.localizedDescription)", type: .error) - } - } else { - Debug.shared.log(message: "Skipping Phase 3 due to high memory usage", type: .warning) - } - } + // Execute Phase 2 setup + self.setupPhaseTwo() + } + + // Phase 3 - defer significantly and only if memory allows + DispatchQueue.main.asyncAfter(deadline: .now() + 3.0) { [weak self] in + guard let self = self else { return } - // Post initialization complete notification after all phases - DispatchQueue.main.asyncAfter(deadline: .now() + 4.0) { - NotificationCenter.default.post(name: .appInitializationCompleted, object: nil) - Debug.shared.log(message: "App initialization complete", type: .success) + // Check memory before heavy operations + if self.shouldProceedWithMemoryCheck() { + // Execute Phase 3 setup + self.setupPhaseThree() + } else { + Debug.shared.log(message: "Skipping Phase 3 due to high memory usage", type: .warning) } - } catch let error as NSError { - // Log error but continue app launch with minimal functionality - Debug.shared.log(message: "Critical error during initialization: \(error.localizedDescription)", type: .error) - - // Ensure UI is still responsive even if initialization fails - DispatchQueue.main.async { + } + + // Post initialization complete notification after all phases + DispatchQueue.main.asyncAfter(deadline: .now() + 4.0) { + NotificationCenter.default.post(name: .appInitializationCompleted, object: nil) + Debug.shared.log(message: "App initialization complete", type: .success) + } + + // Ensure UI is responsive regardless of initialization state + DispatchQueue.main.async { // Use UIWindowScene.windows on iOS 15+ instead of deprecated UIApplication.shared.windows if #available(iOS 15.0, *) { if let windowScene = UIApplication.shared.connectedScenes.first as? UIWindowScene, diff --git a/iOS/Extensions/CALayer+Shadow.swift b/iOS/Extensions/CALayer+Shadow.swift index a0eb346..501f6d4 100644 --- a/iOS/Extensions/CALayer+Shadow.swift +++ b/iOS/Extensions/CALayer+Shadow.swift @@ -9,4 +9,13 @@ extension CALayer { shadowOpacity = 0.2 shadowRadius = 8 } + + /// Apply a futuristic shadow effect to the layer + func applyFuturisticShadow() { + masksToBounds = false + shadowColor = UIColor(red: 0.1, green: 0.6, blue: 1.0, alpha: 1.0).cgColor + shadowOffset = CGSize(width: 0, height: 3) + shadowOpacity = 0.3 + shadowRadius = 10 + } } \ No newline at end of file diff --git a/iOS/Operations/CoreML/CoreMLManager.swift b/iOS/Operations/CoreML/CoreMLManager.swift index 5c14f26..9ef89be 100644 --- a/iOS/Operations/CoreML/CoreMLManager.swift +++ b/iOS/Operations/CoreML/CoreMLManager.swift @@ -483,7 +483,7 @@ final class CoreMLManager { // Remove observer as loading succeeded if let observer = memoryObserver { - NotificationCenter.default.removeObserver(observer) + NotificationCenter.default.removeObserver(observer as Any) } // Dismiss loading alert @@ -500,7 +500,7 @@ final class CoreMLManager { } catch { // Remove observer on failure if let observer = memoryObserver { - NotificationCenter.default.removeObserver(observer) + NotificationCenter.default.removeObserver(observer as Any) } // Dismiss loading alert diff --git a/iOS/Views/TabbarView.swift b/iOS/Views/TabbarView.swift index 7ecacaf..06ef739 100644 --- a/iOS/Views/TabbarView.swift +++ b/iOS/Views/TabbarView.swift @@ -249,31 +249,27 @@ struct TabbarView: View { // Set up LED effects after a delay to ensure tab bar is ready DispatchQueue.main.asyncAfter(deadline: .now() + 1.0) { // Apply flowing LED effect to all tab bars - safely - do { - if #available(iOS 15.0, *) { - // Use UIWindowScene.windows on iOS 15+ - UIApplication.shared.connectedScenes - .compactMap { $0 as? UIWindowScene } - .flatMap { $0.windows } - .compactMap { $0.rootViewController as? UITabBarController } - .forEach { tabController in - // Use the method directly since it's defined in our extension - tabController.tabBar.addTabBarLEDEffect( - color: UIColor(hex: "#FF6482") - ) - } - } else { - // Use deprecated windows property on older iOS versions - UIApplication.shared.windows.compactMap { $0.rootViewController as? UITabBarController } - .forEach { tabController in - // Use the method directly since it's defined in our extension - tabController.tabBar.addTabBarLEDEffect( - color: UIColor(hex: "#FF6482") - ) - } - } - } catch let error as NSError { - Debug.shared.log(message: "Error applying LED effect: \(error.localizedDescription)", type: .error) + if #available(iOS 15.0, *) { + // Use UIWindowScene.windows on iOS 15+ + UIApplication.shared.connectedScenes + .compactMap { $0 as? UIWindowScene } + .flatMap { $0.windows } + .compactMap { $0.rootViewController as? UITabBarController } + .forEach { tabController in + // Use the method directly since it's defined in our extension + tabController.tabBar.addTabBarLEDEffect( + color: UIColor(hex: "#FF6482") + ) + } + } else { + // Use deprecated windows property on older iOS versions + UIApplication.shared.windows.compactMap { $0.rootViewController as? UITabBarController } + .forEach { tabController in + // Use the method directly since it's defined in our extension + tabController.tabBar.addTabBarLEDEffect( + color: UIColor(hex: "#FF6482") + ) + } } } }