Skip to content

fix: support scene-based AppDelegate in Expo SDK 58 - #59

Open
plrdev wants to merge 1 commit into
vonovak:mainfrom
plrdev:fix/scene-lifecycle-sdk-58
Open

plrdev wants to merge 1 commit into
vonovak:mainfrom
plrdev:fix/scene-lifecycle-sdk-58

Conversation

@plrdev

@plrdev plrdev commented Oct 6, 2026 •

Copy link
Copy Markdown

Fixes #58

Expo SDK 58 moved to the scene-based life cycle: the AppDelegate no longer creates a UIWindow, SceneDelegate does. That broke the library in two ways:

  1. Prebuild failed because the config plugin anchored the theme recovery on window = UIWindow(frame: UIScreen.main.bounds).
  2. The recovered theme didn't reach native UI. recoverApplicationTheme() now runs in didFinishLaunching, before any window exists, so forceTheme had no windows to style. JS got the right scheme (via RCTOverrideAppearancePreference), but the window kept following the system, so status bar, alerts and pickers were in the wrong theme until the next setThemePreference call.

Changes

  • Config plugin: when the AppDelegate has no window creation, insert the recovery right before return super.application(application, didFinishLaunchingWithOptions: launchOptions). Older AppDelegates keep the existing anchor, so their generated code is unchanged.
  • iOS: forceTheme also applies the forced style to windows that become visible later (UIWindowDidBecomeVisibleNotification, observer registered once). Nothing changes when the style is unspecified.
  • Added unit tests for the plugin's AppDelegate edit, covering both template shapes.

Testing

On a fresh blank-typescript@sdk-58 app (expo 58.0.4, RN 0.88.0-rc.3, Xcode 27.1, iOS 27.1 simulator):

  • expo prebuild succeeds; the recovery lands above the return.
  • Set the preference to dark with the system in light, kill the app, relaunch: JS scheme is dark and a native Alert is dark. With the plugin fix alone (old native code), JS is dark but the native alert is light.
without iOS change with iOS change
alert-without-fix alert-with-fix

yarn test, yarn typescript and yarn lint pass.

Side note, not addressed here: the react-native: >=0.79.0 peer range doesn't match RN prereleases like 0.88.0-rc.3, so npm needs --legacy-peer-deps on SDK 58 for now.

The SDK 58 AppDelegate no longer creates a UIWindow; SceneDelegate does.
The config plugin now inserts the theme recovery before didFinishLaunching
returns when there is no window creation to anchor to, and the recovered
theme is applied to windows that become visible later.

Fixes vonovak#58
@plrdev
plrdev marked this pull request as ready for review October 6, 2026 11:31
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Config plugin misses scene-based AppDelegate (Expo SDK 58 / iOS 27)

1 participant