Color Scheme

Appearance and Color Scheme Detection

Appearance.getColorScheme() returns 'light' or 'dark' (null without the native module), and addChangeListener() reports switches, including scheduled ones at sunset. In components, prefer the useColorScheme() hook, which re-renders when the scheme changes. Appearance.setColorScheme('dark') forces a scheme for the app and its native dialogs, and 'unspecified' follows the system again. React Native 0.87 36,878 renamed that value 'auto', which 0.86.3 (Expo SDK 57 6,418 ) silently ignores (Building a Dark Mode Toggle).

src/info/Themed.tsx: one palette per scheme, chosen on every render (excerpt)TSX
  const scheme = useColorScheme();                  // 'light' | 'dark', re-renders on change
  const c = palette[scheme === 'dark' ? 'dark' : 'light'];
  useEffect(() => {
    const sub = Appearance.addChangeListener(({ colorScheme }) =>
      console.log('colorScheme ->', colorScheme));
    return () => sub.remove();
  }, []);

Here palette holds a light and a dark set of background, text and card colors. Switching the emulator with adb shell cmd uimode night yes, then no, logged the two changes and repainted the screen without a restart (left and middle screens of the figure in DevSettings):

Output of 78
 LOG  colorScheme -> dark
 LOG  colorScheme -> light

The Android template's MainActivity declares uiMode in configChanges, so the activity is not recreated. Expo's userInterfaceStyle in app.json pins a scheme, but on Android it takes effect only with the expo-system-ui package installed; this project has none, so it followed the system despite "light".