Theming

Learn how to add your own branding to the UI Kit

The WDK React Native UI Kit provides a theming system that allows you to:

  • Use built-in themes for quick setup with light and dark modes

  • Create brand themes from your brand colors and fonts

  • Customize individual components with fine-grained control

  • Access theme values anywhere in your application

  • Switch themes dynamically based on user preferences


Basic Setup

Wrap your app with the ThemeProvider to enable theming:

Basic Theme Setup
import { ThemeProvider, lightTheme } from '@tetherto/wdk-uikit-react-native'

function App() {
  return (
    <ThemeProvider initialTheme={lightTheme}>
      {/* Your app content */}
    </ThemeProvider>
  )
}

The UI Kit comes with two built-in themes:

import { ThemeProvider, lightTheme, darkTheme } from '@tetherto/wdk-uikit-react-native'

// Light theme
<ThemeProvider initialTheme={lightTheme}>
  {/* Your app */}
</ThemeProvider>

// Dark theme
<ThemeProvider initialTheme={darkTheme}>
  {/* Your app */}
</ThemeProvider>

Manual Theme Control

Manual Theme Toggle
import { useTheme } from '@tetherto/wdk-uikit-react-native'

function ThemeToggle() {
  const { mode, setMode } = useTheme()

  return (
    <Button onPress={() => setMode(mode === 'dark' ? 'light' : 'dark')}>
      Toggle Theme
    </Button>
  )
}

Custom Themes

Brand Themes

Apply your brand colors and fonts using createThemeFromBrand:

Brand Theme Creation
import { ThemeProvider, createThemeFromBrand } from '@tetherto/wdk-uikit-react-native'

const brandTheme = createThemeFromBrand({
  primaryColor: '#007AFF',
  secondaryColor: '#FF3B30',
  fontFamily: {
    regular: 'Inter-Regular',
    bold: 'Inter-Bold',
  },
}, 'light')

<ThemeProvider initialTheme={brandTheme}>
  {/* Your branded app */}
</ThemeProvider>

BrandConfig Interface

BrandConfig Type
type BrandConfig = {
  primaryColor: string
  secondaryColor?: string
  fontFamily?: {
    regular?: string
    medium?: string
    semiBold?: string
    bold?: string
  }
}

Custom Theme

Create a completely custom theme with full control over all design tokens:

Custom Theme
import { ThemeProvider } from '@tetherto/wdk-uikit-react-native'

const myLightTheme = {
  mode: 'light' as const,
  colors: {
    primary: '#007AFF',
    primaryLight: '#4DA6FF',
    primaryDark: '#0056CC',
    onPrimary: '#FFFFFF',
    secondary: '#FF3B30',
    secondaryLight: '#FF6B60',
    secondaryDark: '#CC2F26',
    background: '#FFFFFF',
    surface: '#F9FAFB',
    surfaceVariant: '#F3F4F6',
    surfaceElevated: '#E5E7EB',
    text: '#111827',
    textSecondary: '#6B7280',
    textDisabled: '#9CA3AF',
    border: '#E5E7EB',
    borderLight: '#F3F4F6',
    error: '#EF4444',
    warning: '#F59E0B',
    success: '#10B981',
    info: '#3B82F6',
  },
  typography: {
    fontFamily: { 
      regular: 'System', 
      medium: 'System', 
      semiBold: 'System', 
      bold: 'System' 
    },
    fontSize: { 
      xs: 10, sm: 12, base: 14, md: 16, lg: 18, xl: 20, xxl: 24, xxxl: 30 
    },
    fontWeight: { 
      regular: '400', medium: '500', semiBold: '600', bold: '700' 
    },
  },
  spacing: { 
    xs: 4, sm: 8, base: 12, md: 16, lg: 24, xl: 32, xxl: 48, xxxl: 64 
  },
  borderRadius: { 
    none: 0, sm: 4, md: 8, lg: 16, xl: 24, xxl: 32, full: 9999 
  },
}

<ThemeProvider customLightTheme={myLightTheme}>
  {/* Your app */}
</ThemeProvider>

Theme Interface

Theme Type
type Theme = {
  mode: 'light' | 'dark' | 'auto'
  colors: ColorPalette
  typography: Typography
  spacing: Spacing
  borderRadius: BorderRadius
  componentVariants?: ComponentVariant
  componentOverrides?: ComponentOverrides
}

Component Customization

You can customize the components with fine-grained control.

Fine-grained style overrides for specific component parts:

Component Overrides
<ThemeProvider
  initialTheme={lightTheme}
  componentOverrides={{
    TransactionItem: {
      container: {
        backgroundColor: '#F5F5F5',
        borderRadius: 12,
      },
      title: {
        fontSize: 18,
        fontWeight: 'bold',
      },
    },
    TransactionList: {
      emptyStateText: {
        color: '#999999',
      },
    },
  }}
>
  {/* Your app */}
</ThemeProvider>

Set default visual variants per component:

Component Variants
const customTheme = {
  ...lightTheme,
  componentVariants: {
    'AmountInput.default': { /* variant styles */ },
    'TransactionItem.compact': { /* variant styles */ }
  }
}

Using Theme Anywhere

Access theme values anywhere in your components:

useTheme Hook

useTheme Hook
import { useTheme } from '@tetherto/wdk-uikit-react-native'

function MyComponent() {
  const { theme } = useTheme()

  return (
    <View
      style={{
        backgroundColor: theme.colors.background,
        padding: theme.spacing.md,
      }}
    >
      <Text style={{ color: theme.colors.text }}>Hello World</Text>
    </View>
  )
}

Theme Structure

Color Palette

The theming system uses semantic naming for colors:

Token
Purpose

colors.primary

Primary brand color

colors.primaryLight

Light variant of primary

colors.primaryDark

Dark variant of primary

colors.onPrimary

Text color on primary background

colors.secondary

Secondary brand color

colors.secondaryLight

Light variant of secondary

colors.secondaryDark

Dark variant of secondary

colors.background

Main background color

colors.surface

Card/container background

colors.surfaceVariant

Alternative surface color

colors.surfaceElevated

Elevated surface color

colors.text

Primary text color

colors.textSecondary

Secondary text color

colors.textDisabled

Disabled text color

colors.border

Border color

colors.borderLight

Light border color

colors.error

Error state color

colors.warning

Warning state color

colors.success

Success state color

colors.info

Info state color

Typography

Token
Purpose

typography.fontFamily.regular

Regular font family

typography.fontFamily.medium

Medium font family

typography.fontFamily.semiBold

Semi-bold font family

typography.fontFamily.bold

Bold font family

typography.fontSize.xs

Extra small font size (10px)

typography.fontSize.sm

Small font size (12px)

typography.fontSize.base

Base font size (14px)

typography.fontSize.md

Medium font size (16px)

typography.fontSize.lg

Large font size (18px)

typography.fontSize.xl

Extra large font size (20px)

typography.fontSize.xxl

2X large font size (24px)

typography.fontSize.xxxl

3X large font size (30px)

typography.fontWeight.regular

Regular font weight ('400')

typography.fontWeight.medium

Medium font weight ('500')

typography.fontWeight.semiBold

Semi-bold font weight ('600')

typography.fontWeight.bold

Bold font weight ('700')

Spacing

Token
Purpose

spacing.xs

Extra small spacing (4px)

spacing.sm

Small spacing (8px)

spacing.base

Base spacing (12px)

spacing.md

Medium spacing (16px)

spacing.lg

Large spacing (24px)

spacing.xl

Extra large spacing (32px)

spacing.xxl

2X large spacing (48px)

spacing.xxxl

3X large spacing (64px)

Border Radius

Token
Purpose

borderRadius.none

No border radius (0px)

borderRadius.sm

Small border radius (4px)

borderRadius.md

Medium border radius (8px)

borderRadius.lg

Large border radius (16px)

borderRadius.xl

Extra large border radius (24px)

borderRadius.xxl

2X large border radius (32px)

borderRadius.full

Full border radius (9999px)


Advanced Usage

Dynamic Theme Updates

Update themes dynamically at runtime:

Dynamic Theme Updates
function Settings() {
  const { setBrandConfig, setComponentOverrides } = useTheme()

  const updateBrand = () => {
    setBrandConfig({
      primaryColor: '#FF6501',
    })
  }

  const customizeTransactions = () => {
    setComponentOverrides({
      TransactionItem: {
        container: {
          backgroundColor: 'rgba(255, 101, 1, 0.1)',
        },
      },
    })
  }

  return (
    <>
      <Button onPress={updateBrand}>Update Brand</Button>
      <Button onPress={customizeTransactions}>Customize Transactions</Button>
    </>
  )
}

Next Steps


Need Help?