Theming
Qafka has three layers of theming, applied in order — base theme → dashboard config → code-level override. You can stop at any layer.
Built-in Base Themes
Two built-in starting points:
<Qafka theme="light" />
<Qafka theme="dark" />The base theme provides every required token (colors, spacing, typography, shadows, animation). Higher layers only need to specify what they want to change.
Dashboard-Configured Theme
Each project has a chat theme editor in the dashboard. Anything you set there is loaded automatically when the SDK initializes — no extra prop required:
<Qafka />The dashboard editor lets non-developers tweak:
- Container background, paddings, border radius
- User & AI message bubble colors, padding, max width, border radius
- Input field background, border, text, send button
- Font size, weight, line height
- Greeting & initial message
- Voice availability
These overrides are merged on top of the chosen base theme (light or dark). For more, see Dashboard › Chat Theme.
Code-Level Overrides (themeOverride)
When you need fine-grained control that the dashboard doesn’t expose — or per-screen variations — pass themeOverride. It accepts a deep-partial of the full Theme interface, so you only specify what you want to change.
<Qafka
themeOverride={{
colors: {
userBubble: '#007AFF',
userBubbleText: '#FFFFFF',
aiBubble: '#F0F0F0',
aiBubbleText: '#000000',
background: '#FFFFFF',
inputBackground: '#F5F5F5',
},
typography: {
fontFamily: 'Inter',
fontSize: { md: 15, lg: 17 },
},
borderRadius: { lg: 16, xl: 24 },
spacing: { md: 14 },
messages: {
user: { padding: 12, maxWidth: 75 },
ai: { padding: 12, maxWidth: 85 },
},
}}
/>Override Surface
themeOverride is a DeepPartial<Theme> — every category and every key is optional. Available top-level slots:
| Slot | What it controls |
|---|---|
colors | 28 named tokens — primary, primaryLight, primaryDark, background, surface, overlay, text, textSecondary, textLight, textInverse, userBubble, userBubbleText, aiBubble, aiBubbleText, border, divider, error, success, warning, info, inputBackground, inputBorder, inputPlaceholder, buttonBackground, buttonText, buttonDisabled, badge, badgeText |
spacing | xs, sm, md, lg, xl, xxl |
borderRadius | sm, md, lg, xl, full |
typography | fontFamily, fontSize.{xs,sm,md,lg,xl,xxl}, fontWeight.{regular,medium,semibold,bold}, lineHeight.{tight,normal,relaxed}, plus optional fonts map for per-weight Android font files (regular, medium, semibold, bold, italic, light, code) |
shadows | small, medium, large (RN-style shadow + elevation objects) |
animation | duration.{fast,normal,slow}, easing.{easeIn,easeOut,easeInOut} |
messages | Per-bubble overrides: user.{padding,maxWidth}, ai.{padding,maxWidth} (maxWidth is a percentage) |
For the full type, import it:
import { ThemeOverride } from '@qafka/react-native'Theme Priority
Themes are applied in this order — last wins:
- Base theme —
lightordark(whichever you pick via thethemeprop) - Dashboard theme — loaded automatically for the active project
themeOverrideprop — highest priority, deep-merged on top