Skip to content

Theme System

PIP AI ships with 5 built-in themes, each with comprehensive design tokens covering colors, fonts, surfaces, borders, and status indicators.

Available Themes

ThemeIDLabelTypeAccentDescription
MidnightdarkMidnightDark#ffffffDeep dark theme with crisp white accents
DaylightlightDaylightLight#0b0b0fClean light theme with subtle warmth
SandstonesandstoneSandstoneDark#c9a86cWarm earthy tones with desert vibes
Neo Mintneo-mintNeo MintDark#5fd4b8Cool minimal aesthetic with mint accents
CorporatecorporateCorporateLight#3B82F6Clean professional look with blue accents

The default theme is corporate.

Theme Architecture

Themes are defined in app/constants/themes.ts and managed through:

  1. app/constants/themes.ts — Theme definitions with tokens
  2. app/stores/app.ts — Theme state in Pinia store (useAppStore)
  3. app/plugins/theme.client.ts — Client-side theme initialization from localStorage

Theme Tokens

Each theme defines a comprehensive set of design tokens:

Font Tokens

TokenDescriptionExample (Corporate)
fontDisplayHeading/display fontSF Pro Display
fontBodyBody text fontSF Pro Text
fontMonoMonospace/code fontSF Mono

Color Tokens

TokenDescriptionExample (Corporate)
bodyBgPage background#F8F9FB
bodyTextPrimary text#1F2937
mutedTextSecondary text#6B7280
accentPrimary accent#3B82F6
accentHoverAccent hover state#2563EB
successSuccess indicator#10B981
warningWarning indicator#F59E0B
errorError indicator#EF4444

Surface Tokens

TokenDescription
panelBgPanel background (with transparency)
panelBgSolidSolid panel background
borderColorDefault border color
borderColorStrongEmphasized border color

UI Element Tokens

TokenDescription
scrollbarTrackScrollbar track color
scrollbarThumbScrollbar thumb color
checkboxBgCheckbox background
checkboxCheckedBgChecked checkbox background
noiseOpacityHero noise overlay opacity

Theme Switching

typescript
const appStore = useAppStore()

// Set theme
appStore.setTheme('neo-mint')

// Cycle to next theme
import { getNextThemeId } from '~/constants/themes'
const nextId = getNextThemeId(appStore.currentTheme)
appStore.setTheme(nextId)

Theme selection is persisted to localStorage and restored on page load by the theme.client.ts plugin.

Helper Functions

typescript
import { themes, getTheme, validateThemeId, getNextThemeId, themeList } from '~/constants/themes'

// Get theme object by ID
const theme = getTheme('corporate')

// Validate and fallback to default
const themeId = validateThemeId(someString) // Returns valid ThemeId or 'corporate'

// Get all themes as array
const allThemes = themeList

// Cycle themes
const nextId = getNextThemeId('dark') // → 'light'

Built with VitePress