66#endif
77#import < objc/message.h>
88#import < objc/runtime.h>
9+ #include < TargetConditionals.h>
910#include < sstream>
1011#include < mutex>
1112#include < limits>
@@ -736,7 +737,20 @@ static void RenderErrorModalUI(v8::Isolate* isolate, const std::string& title,
736737 bool alreadyShowing = isErrorDisplayShowing;
737738
738739 UIApplication* app = [UIApplication sharedApplication ];
739- if (!alreadyShowing && app.windows .count == 0 && app.connectedScenes .count == 0 ) {
740+ BOOL hasAnyWindows = NO ;
741+ #if TARGET_OS_VISION
742+ if (@available (iOS 13.0 , *)) {
743+ for (UIScene* scene in app.connectedScenes ) {
744+ if ([scene isKindOfClass: [UIWindowScene class ]]) {
745+ UIWindowScene* ws = (UIWindowScene*)scene;
746+ if (ws.windows .count > 0 ) { hasAnyWindows = YES ; break ; }
747+ }
748+ }
749+ }
750+ #else
751+ hasAnyWindows = app.windows .count > 0 ;
752+ #endif
753+ if (!alreadyShowing && !hasAnyWindows && app.connectedScenes .count == 0 ) {
740754 Log (@" Note: JavaScript error during boot." );
741755 Log (@" ================================" );
742756 Log (@" %s " , stackForModal.c_str ());
@@ -781,7 +795,19 @@ static void ShowErrorModalSynchronously(const std::string& title,
781795 UIApplication* sharedApp = [UIApplication sharedApplication ];
782796
783797 // If no windows exist, create a foundational window to establish the hierarchy
784- if (sharedApp.windows .count == 0 ) {
798+ BOOL appHasWindows = NO ;
799+ #if TARGET_OS_VISION
800+ if (@available (iOS 13.0 , *)) {
801+ for (UIScene* scene in sharedApp.connectedScenes ) {
802+ if ([scene isKindOfClass: [UIWindowScene class ]]) {
803+ if (((UIWindowScene*)scene).windows .count > 0 ) { appHasWindows = YES ; break ; }
804+ }
805+ }
806+ }
807+ #else
808+ appHasWindows = sharedApp.windows .count > 0 ;
809+ #endif
810+ if (!appHasWindows) {
785811 // Log(@"🚀 Bootstrap: No app windows exist - creating foundational window hierarchy");
786812
787813 // Create a basic foundational window that mimics what UIApplicationMain would create
@@ -805,12 +831,18 @@ static void ShowErrorModalSynchronously(const std::string& title,
805831 // Log(@"🚀 Bootstrap: Created foundation window with existing scene");
806832 } else {
807833 // If no scenes exist, create a window without scene (iOS 12 style fallback)
834+ // On visionOS, UIScreen is unavailable. Skip frame-based creation there.
835+ #if !TARGET_OS_VISION
808836 foundationWindow = [[UIWindow alloc ] initWithFrame: [UIScreen mainScreen ].bounds];
837+ #endif
809838 // Log(@"🚀 Bootstrap: Created foundation window without scene (emergency mode)");
810839 }
811840 } else {
812841 // iOS 12 and below - simple window creation
842+ // On visionOS, UIScreen is unavailable; this branch is only for iOS 12 and below.
843+ #if !TARGET_OS_VISION
813844 foundationWindow = [[UIWindow alloc ] initWithFrame: [UIScreen mainScreen ].bounds];
845+ #endif
814846 // Log(@"🚀 Bootstrap: Created foundation window for iOS 12");
815847 }
816848
@@ -833,7 +865,19 @@ static void ShowErrorModalSynchronously(const std::string& title,
833865
834866
835867 // Detailed window hierarchy inspection
836- if (sharedApp.windows .count == 0 ) {
868+ BOOL appHasWindowsAfterBootstrap = NO ;
869+ #if TARGET_OS_VISION
870+ if (@available (iOS 13.0 , *)) {
871+ for (UIScene* scene in sharedApp.connectedScenes ) {
872+ if ([scene isKindOfClass: [UIWindowScene class ]]) {
873+ if (((UIWindowScene*)scene).windows .count > 0 ) { appHasWindowsAfterBootstrap = YES ; break ; }
874+ }
875+ }
876+ }
877+ #else
878+ appHasWindowsAfterBootstrap = sharedApp.windows .count > 0 ;
879+ #endif
880+ if (!appHasWindowsAfterBootstrap) {
837881 // Log(@"🚀 Bootstrap: 🚨 CRITICAL: Foundation window not in app.windows hierarchy!");
838882 // Log(@"🚀 Bootstrap: This indicates a fundamental iOS window system issue");
839883
@@ -883,12 +927,18 @@ static void ShowErrorModalSynchronously(const std::string& title,
883927 // Log(@"🎨 Created error window with existing scene");
884928 } else {
885929 // Fallback: create window with screen bounds (older behavior)
930+ // On visionOS, UIScreen is unavailable. Guard frame-based creation.
931+ #if !TARGET_OS_VISION
886932 errorWindow = [[UIWindow alloc ] initWithFrame: [UIScreen mainScreen ].bounds];
933+ #endif
887934 // Log(@"🎨 Created error window with screen bounds (no scene available)");
888935 }
889936 } else {
890937 // iOS 12 and below
938+ // On visionOS, UIScreen is unavailable; this branch is only for iOS 12 and below.
939+ #if !TARGET_OS_VISION
891940 errorWindow = [[UIWindow alloc ] initWithFrame: [UIScreen mainScreen ].bounds];
941+ #endif
892942 // Log(@"🎨 Created error window for iOS 12");
893943 }
894944
@@ -1104,7 +1154,22 @@ static void ShowErrorModalSynchronously(const std::string& title,
11041154 [errorWindow bringSubviewToFront: errorViewController.view];
11051155
11061156 // Verify the window is in the window hierarchy
1107- NSArray * windows = [UIApplication sharedApplication ].windows ;
1157+ NSArray <UIWindow*>* windows = nil ;
1158+ #if TARGET_OS_VISION
1159+ if (@available (iOS 13.0 , *)) {
1160+ NSMutableArray <UIWindow*>* acc = [NSMutableArray array ];
1161+ for (UIScene* scene in [UIApplication sharedApplication ].connectedScenes ) {
1162+ if ([scene isKindOfClass: [UIWindowScene class ]]) {
1163+ [acc addObjectsFromArray: ((UIWindowScene*)scene).windows];
1164+ }
1165+ }
1166+ windows = [acc copy ];
1167+ } else {
1168+ windows = @[];
1169+ }
1170+ #else
1171+ windows = [UIApplication sharedApplication ].windows ;
1172+ #endif
11081173 BOOL windowInHierarchy = [windows containsObject: errorWindow];
11091174 // Log(@"Error window in app windows: %@", windowInHierarchy ? @"YES" : @"NO");
11101175
0 commit comments