global.css and mirrored in lib/theme.ts that you can also change/get the theme variables during runtime.
App-wide theme state
Inapp/_layout.tsx, the app calls useUniwind() to read the current theme and then passes a matching navigation theme into React Navigation’s ThemeProvider:
app/_layout.tsx
themeis managed by Uniwind and can be"light"or"dark"(or extended with custom themes).NAV_THEMEmaps these modes to React Navigation color schemes, so headers, backgrounds and text in the navigation UI adapt automatically.
@/global.css, which contains the Tailwind-style design tokens (such as bg-background, text-foreground) that change values depending on the active theme. This comes from the ui.shadcn.com theming logic.
CSS variables in global.css
global.css defines all color tokens inside @variant light and @variant dark blocks. Uniwind picks up these variables and makes them available as Tailwind className utilities automatically.
global.css
You never use these raw CSS variables directly in JSX. Instead, Uniwind converts them into Tailwind-like utility classes you use via
className. See the table below.CSS variable → className cheatsheet
Each CSS variable has a matching Tailwind class. The color flips automatically when the theme changes - you never need to writedark: variants manually.
Example - a custom card that uses semantic tokens and adapts to both themes automatically:
ThemingExample.tsx
The two files that define your theme
The theme is split across two files that must always be kept in sync:global.css
Defines colors as CSS variables inside
@variant light and @variant dark blocks. Used by Uniwind to generate the className utilities.lib/theme.ts
Mirrors the same colors like in
global.css for React Navigation’s ThemeProvider (since React Navigation does not read CSS variables). Contains THEME and NAV_THEME exports.global.css, you must update the matching entry in lib/theme.ts with an equivalent HSL value, otherwise the navigation header will show a different color than the rest of the app.
lib/theme.ts (excerpt)
ThemeToggle: switching light / dark mode
TheThemeToggle component in the header provides a single button to flip the theme:
ThemeToggle.tsx
useUniwind()gives you the current theme.- Calling
Uniwind.setTheme(newTheme)updates the global theme state, which immediately re-renders components using Uniwind classes. - The button and icon are React Native Reusables components styled with Tailwind-like class names, and their appearance (colors, background, icon) follows the active theme.
How theming affects components
Because Uniwind integrates with React Native’sclassName prop, every component that uses classes like bg-background and text-foreground automatically switches style when the theme changes.
This includes:
- Navigation containers and headers (via
NAV_THEMEinThemeProvider). - React Native Reusables components such as
Button,Card, etc., which are wired to Uniwind under the hood. - Any custom components where you use Tailwind-like classes in
className.
You do not need to manually manage a separate theme context. Uniwind’s global theme plus the existing
ThemeProvider setup means your job is only to use the right className utilities.Task 4: Change the Theme Optional
1
Read the Documentation
Firstly read the documentation (it’s not that much… don’t worry :)And choose what theme you want from here:
2
Update theme.ts and global.css
After finding a nice Tailwind v3 theme version, copy the CSS variables into Save both files check if you can see your new color scheme applied everywhere - components, navigation header, etc.
global.css under the correct @variant light / @variant dark blocks.Then open lib/theme.ts and update every matching HSL value in THEME.light and THEME.dark to reflect your new colors.We recommend doing this with AI since it is pure meticulous work:Press 'Copy prompt' and append the the new app/globals.css to the prompt