- GET /v1/members with search across all members (includes account name) - POST /members/:id/move with optional accountId (creates new account if omitted) - primary_member_id on account table, auto-set when first member added - isMinor flag on member create (manual override when no DOB provided) - Account search now includes member names - New account form includes primary contact fields, auto-generates name - Members page in sidebar with global search
360 lines
11 KiB
TypeScript
360 lines
11 KiB
TypeScript
export interface ThemeColors {
|
|
background: string
|
|
foreground: string
|
|
card: string
|
|
cardForeground: string
|
|
popover: string
|
|
popoverForeground: string
|
|
primary: string
|
|
primaryForeground: string
|
|
secondary: string
|
|
secondaryForeground: string
|
|
muted: string
|
|
mutedForeground: string
|
|
accent: string
|
|
accentForeground: string
|
|
destructive: string
|
|
destructiveForeground: string
|
|
border: string
|
|
input: string
|
|
ring: string
|
|
sidebar: string
|
|
sidebarForeground: string
|
|
sidebarPrimary: string
|
|
sidebarPrimaryForeground: string
|
|
sidebarAccent: string
|
|
sidebarAccentForeground: string
|
|
sidebarBorder: string
|
|
}
|
|
|
|
export interface ThemePreset {
|
|
name: string
|
|
label: string
|
|
light: ThemeColors
|
|
dark: ThemeColors
|
|
}
|
|
|
|
export const themes: ThemePreset[] = [
|
|
{
|
|
name: 'slate',
|
|
label: 'Slate',
|
|
light: {
|
|
background: '210 20% 97%',
|
|
foreground: '222 47% 11%',
|
|
card: '0 0% 100%',
|
|
cardForeground: '222 47% 11%',
|
|
popover: '0 0% 100%',
|
|
popoverForeground: '222 47% 11%',
|
|
primary: '215 25% 27%',
|
|
primaryForeground: '210 40% 98%',
|
|
secondary: '210 40% 94%',
|
|
secondaryForeground: '222 47% 11%',
|
|
muted: '210 40% 94%',
|
|
mutedForeground: '215 16% 47%',
|
|
accent: '210 40% 94%',
|
|
accentForeground: '222 47% 11%',
|
|
destructive: '0 72% 51%',
|
|
destructiveForeground: '210 40% 98%',
|
|
border: '214 32% 89%',
|
|
input: '214 32% 89%',
|
|
ring: '215 25% 27%',
|
|
sidebar: '210 25% 95%',
|
|
sidebarForeground: '215 16% 47%',
|
|
sidebarPrimary: '215 25% 27%',
|
|
sidebarPrimaryForeground: '210 40% 98%',
|
|
sidebarAccent: '210 40% 92%',
|
|
sidebarAccentForeground: '222 47% 11%',
|
|
sidebarBorder: '214 32% 89%',
|
|
},
|
|
dark: {
|
|
background: '222 30% 8%',
|
|
foreground: '210 20% 86%',
|
|
card: '222 30% 10%',
|
|
cardForeground: '210 20% 86%',
|
|
popover: '222 30% 10%',
|
|
popoverForeground: '210 20% 86%',
|
|
primary: '215 20% 72%',
|
|
primaryForeground: '222 30% 8%',
|
|
secondary: '217 20% 15%',
|
|
secondaryForeground: '210 20% 86%',
|
|
muted: '217 20% 15%',
|
|
mutedForeground: '215 15% 55%',
|
|
accent: '217 20% 15%',
|
|
accentForeground: '210 20% 86%',
|
|
destructive: '0 55% 48%',
|
|
destructiveForeground: '210 20% 92%',
|
|
border: '217 20% 17%',
|
|
input: '217 20% 17%',
|
|
ring: '215 20% 55%',
|
|
sidebar: '222 30% 7%',
|
|
sidebarForeground: '215 15% 65%',
|
|
sidebarPrimary: '215 20% 72%',
|
|
sidebarPrimaryForeground: '0 0% 100%',
|
|
sidebarAccent: '217 20% 13%',
|
|
sidebarAccentForeground: '210 20% 86%',
|
|
sidebarBorder: '217 20% 15%',
|
|
},
|
|
},
|
|
{
|
|
name: 'emerald',
|
|
label: 'Emerald',
|
|
light: {
|
|
background: '150 20% 97%',
|
|
foreground: '150 40% 10%',
|
|
card: '0 0% 100%',
|
|
cardForeground: '150 40% 10%',
|
|
popover: '0 0% 100%',
|
|
popoverForeground: '150 40% 10%',
|
|
primary: '160 84% 29%',
|
|
primaryForeground: '150 20% 98%',
|
|
secondary: '150 20% 93%',
|
|
secondaryForeground: '150 40% 10%',
|
|
muted: '150 20% 93%',
|
|
mutedForeground: '150 10% 45%',
|
|
accent: '150 20% 93%',
|
|
accentForeground: '150 40% 10%',
|
|
destructive: '0 72% 51%',
|
|
destructiveForeground: '150 20% 98%',
|
|
border: '150 15% 88%',
|
|
input: '150 15% 88%',
|
|
ring: '160 84% 29%',
|
|
sidebar: '150 20% 95%',
|
|
sidebarForeground: '150 10% 45%',
|
|
sidebarPrimary: '160 84% 29%',
|
|
sidebarPrimaryForeground: '150 20% 98%',
|
|
sidebarAccent: '150 20% 91%',
|
|
sidebarAccentForeground: '150 40% 10%',
|
|
sidebarBorder: '150 15% 88%',
|
|
},
|
|
dark: {
|
|
background: '155 30% 7%',
|
|
foreground: '150 15% 85%',
|
|
card: '155 30% 9%',
|
|
cardForeground: '150 15% 85%',
|
|
popover: '155 30% 9%',
|
|
popoverForeground: '150 15% 85%',
|
|
primary: '160 72% 42%',
|
|
primaryForeground: '155 30% 7%',
|
|
secondary: '155 20% 14%',
|
|
secondaryForeground: '150 15% 85%',
|
|
muted: '155 20% 14%',
|
|
mutedForeground: '150 10% 52%',
|
|
accent: '155 20% 14%',
|
|
accentForeground: '150 15% 85%',
|
|
destructive: '0 55% 48%',
|
|
destructiveForeground: '150 15% 92%',
|
|
border: '155 20% 16%',
|
|
input: '155 20% 16%',
|
|
ring: '160 72% 42%',
|
|
sidebar: '155 30% 6%',
|
|
sidebarForeground: '150 10% 62%',
|
|
sidebarPrimary: '160 72% 42%',
|
|
sidebarPrimaryForeground: '0 0% 100%',
|
|
sidebarAccent: '155 20% 12%',
|
|
sidebarAccentForeground: '150 15% 85%',
|
|
sidebarBorder: '155 20% 14%',
|
|
},
|
|
},
|
|
{
|
|
name: 'violet',
|
|
label: 'Violet',
|
|
light: {
|
|
background: '260 15% 97%',
|
|
foreground: '260 40% 11%',
|
|
card: '0 0% 100%',
|
|
cardForeground: '260 40% 11%',
|
|
popover: '0 0% 100%',
|
|
popoverForeground: '260 40% 11%',
|
|
primary: '262 83% 58%',
|
|
primaryForeground: '260 15% 98%',
|
|
secondary: '260 20% 94%',
|
|
secondaryForeground: '260 40% 11%',
|
|
muted: '260 20% 94%',
|
|
mutedForeground: '260 10% 47%',
|
|
accent: '260 20% 94%',
|
|
accentForeground: '260 40% 11%',
|
|
destructive: '0 72% 51%',
|
|
destructiveForeground: '260 15% 98%',
|
|
border: '260 15% 89%',
|
|
input: '260 15% 89%',
|
|
ring: '262 83% 58%',
|
|
sidebar: '260 18% 95%',
|
|
sidebarForeground: '260 10% 47%',
|
|
sidebarPrimary: '262 83% 58%',
|
|
sidebarPrimaryForeground: '260 15% 98%',
|
|
sidebarAccent: '260 20% 92%',
|
|
sidebarAccentForeground: '260 40% 11%',
|
|
sidebarBorder: '260 15% 89%',
|
|
},
|
|
dark: {
|
|
background: '260 30% 8%',
|
|
foreground: '260 15% 86%',
|
|
card: '260 30% 10%',
|
|
cardForeground: '260 15% 86%',
|
|
popover: '260 30% 10%',
|
|
popoverForeground: '260 15% 86%',
|
|
primary: '262 83% 65%',
|
|
primaryForeground: '260 30% 8%',
|
|
secondary: '260 20% 15%',
|
|
secondaryForeground: '260 15% 86%',
|
|
muted: '260 20% 15%',
|
|
mutedForeground: '260 10% 54%',
|
|
accent: '260 20% 15%',
|
|
accentForeground: '260 15% 86%',
|
|
destructive: '0 55% 48%',
|
|
destructiveForeground: '260 15% 92%',
|
|
border: '260 20% 17%',
|
|
input: '260 20% 17%',
|
|
ring: '262 83% 65%',
|
|
sidebar: '260 30% 7%',
|
|
sidebarForeground: '260 10% 64%',
|
|
sidebarPrimary: '262 83% 65%',
|
|
sidebarPrimaryForeground: '0 0% 100%',
|
|
sidebarAccent: '260 20% 13%',
|
|
sidebarAccentForeground: '260 15% 86%',
|
|
sidebarBorder: '260 20% 15%',
|
|
},
|
|
},
|
|
{
|
|
name: 'amber',
|
|
label: 'Amber',
|
|
light: {
|
|
background: '36 20% 97%',
|
|
foreground: '28 40% 10%',
|
|
card: '0 0% 100%',
|
|
cardForeground: '28 40% 10%',
|
|
popover: '0 0% 100%',
|
|
popoverForeground: '28 40% 10%',
|
|
primary: '25 95% 40%',
|
|
primaryForeground: '36 20% 98%',
|
|
secondary: '36 25% 93%',
|
|
secondaryForeground: '28 40% 10%',
|
|
muted: '36 25% 93%',
|
|
mutedForeground: '28 10% 47%',
|
|
accent: '36 25% 93%',
|
|
accentForeground: '28 40% 10%',
|
|
destructive: '0 72% 51%',
|
|
destructiveForeground: '36 20% 98%',
|
|
border: '36 20% 88%',
|
|
input: '36 20% 88%',
|
|
ring: '25 95% 40%',
|
|
sidebar: '36 22% 95%',
|
|
sidebarForeground: '28 10% 47%',
|
|
sidebarPrimary: '25 95% 40%',
|
|
sidebarPrimaryForeground: '36 20% 98%',
|
|
sidebarAccent: '36 25% 91%',
|
|
sidebarAccentForeground: '28 40% 10%',
|
|
sidebarBorder: '36 20% 88%',
|
|
},
|
|
dark: {
|
|
background: '28 25% 7%',
|
|
foreground: '36 15% 85%',
|
|
card: '28 25% 9%',
|
|
cardForeground: '36 15% 85%',
|
|
popover: '28 25% 9%',
|
|
popoverForeground: '36 15% 85%',
|
|
primary: '30 90% 52%',
|
|
primaryForeground: '28 25% 7%',
|
|
secondary: '28 18% 14%',
|
|
secondaryForeground: '36 15% 85%',
|
|
muted: '28 18% 14%',
|
|
mutedForeground: '28 10% 52%',
|
|
accent: '28 18% 14%',
|
|
accentForeground: '36 15% 85%',
|
|
destructive: '0 55% 48%',
|
|
destructiveForeground: '36 15% 92%',
|
|
border: '28 18% 16%',
|
|
input: '28 18% 16%',
|
|
ring: '30 90% 52%',
|
|
sidebar: '28 25% 6%',
|
|
sidebarForeground: '28 10% 62%',
|
|
sidebarPrimary: '30 90% 52%',
|
|
sidebarPrimaryForeground: '0 0% 100%',
|
|
sidebarAccent: '28 18% 12%',
|
|
sidebarAccentForeground: '36 15% 85%',
|
|
sidebarBorder: '28 18% 14%',
|
|
},
|
|
},
|
|
{
|
|
name: 'rose',
|
|
label: 'Rose',
|
|
light: {
|
|
background: '350 15% 97%',
|
|
foreground: '350 40% 10%',
|
|
card: '0 0% 100%',
|
|
cardForeground: '350 40% 10%',
|
|
popover: '0 0% 100%',
|
|
popoverForeground: '350 40% 10%',
|
|
primary: '347 77% 50%',
|
|
primaryForeground: '350 15% 98%',
|
|
secondary: '350 20% 94%',
|
|
secondaryForeground: '350 40% 10%',
|
|
muted: '350 20% 94%',
|
|
mutedForeground: '350 10% 47%',
|
|
accent: '350 20% 94%',
|
|
accentForeground: '350 40% 10%',
|
|
destructive: '0 72% 51%',
|
|
destructiveForeground: '350 15% 98%',
|
|
border: '350 15% 89%',
|
|
input: '350 15% 89%',
|
|
ring: '347 77% 50%',
|
|
sidebar: '350 18% 95%',
|
|
sidebarForeground: '350 10% 47%',
|
|
sidebarPrimary: '347 77% 50%',
|
|
sidebarPrimaryForeground: '350 15% 98%',
|
|
sidebarAccent: '350 20% 92%',
|
|
sidebarAccentForeground: '350 40% 10%',
|
|
sidebarBorder: '350 15% 89%',
|
|
},
|
|
dark: {
|
|
background: '350 25% 7%',
|
|
foreground: '350 12% 86%',
|
|
card: '350 25% 9%',
|
|
cardForeground: '350 12% 86%',
|
|
popover: '350 25% 9%',
|
|
popoverForeground: '350 12% 86%',
|
|
primary: '347 77% 58%',
|
|
primaryForeground: '350 25% 7%',
|
|
secondary: '350 18% 14%',
|
|
secondaryForeground: '350 12% 86%',
|
|
muted: '350 18% 14%',
|
|
mutedForeground: '350 10% 54%',
|
|
accent: '350 18% 14%',
|
|
accentForeground: '350 12% 86%',
|
|
destructive: '0 55% 48%',
|
|
destructiveForeground: '350 12% 92%',
|
|
border: '350 18% 16%',
|
|
input: '350 18% 16%',
|
|
ring: '347 77% 58%',
|
|
sidebar: '350 25% 6%',
|
|
sidebarForeground: '350 10% 62%',
|
|
sidebarPrimary: '347 77% 58%',
|
|
sidebarPrimaryForeground: '0 0% 100%',
|
|
sidebarAccent: '350 18% 12%',
|
|
sidebarAccentForeground: '350 12% 86%',
|
|
sidebarBorder: '350 18% 14%',
|
|
},
|
|
},
|
|
]
|
|
|
|
function camelToKebab(str: string): string {
|
|
return str.replace(/[A-Z]/g, (m) => '-' + m.toLowerCase())
|
|
}
|
|
|
|
export function applyThemeColors(colors: ThemeColors) {
|
|
const root = document.documentElement
|
|
for (const [key, value] of Object.entries(colors)) {
|
|
const prop = `--${camelToKebab(key)}`
|
|
const hsl = `hsl(${value})`
|
|
root.style.setProperty(prop, hsl)
|
|
}
|
|
// Also set on body for portaled components (dialogs, dropdowns, popovers)
|
|
for (const [key, value] of Object.entries(colors)) {
|
|
document.body.style.setProperty(`--${camelToKebab(key)}`, `hsl(${value})`)
|
|
}
|
|
}
|
|
|
|
export function getThemeByName(name: string): ThemePreset {
|
|
return themes.find((t) => t.name === name) ?? themes[0]
|
|
}
|