TorbatYar/frontend/lib/theme.ts
Mortezakoohjani 800b0ba2c5 Deploy TorbatYar for torbatyar.ir with nginx multi-tenant routing.
Wire production domain, CORS for tenant subdomains, celery volume mounts, and nginx reverse proxy configs for apex, API, identity, auth, and wildcard tenants.

Co-authored-by: Cursor <cursoragent@cursor.com>
2026-07-21 21:43:33 +03:30

51 lines
1.7 KiB
TypeScript

/**
* ابزار بارگذاری و اعمال تم White-label.
* برند از theme.config.json یا API تنظیمات خوانده می‌شود.
*/
export interface ThemeConfig {
site_name: string;
primary_color: string;
secondary_color: string;
logo_url: string;
support_email: string;
}
export const DEFAULT_THEME: ThemeConfig = {
site_name: "SuperApp",
primary_color: "#0284c7",
secondary_color: "#0f172a",
logo_url: "/assets/logo.png",
support_email: "support@example.com",
};
export function applyTheme(
theme: ThemeConfig,
root: HTMLElement = document.documentElement
): void {
root.style.setProperty("--color-primary", theme.primary_color);
root.style.setProperty("--color-secondary", theme.secondary_color);
root.style.setProperty("--color-primary-muted", hexWithAlpha(theme.primary_color, 0.12));
root.style.setProperty("--color-primary-soft", hexWithAlpha(theme.primary_color, 0.08));
root.style.setProperty("--color-secondary-muted", hexWithAlpha(theme.secondary_color, 0.06));
}
function hexWithAlpha(hex: string, alpha: number): string {
const normalized = hex.replace("#", "");
if (normalized.length !== 6) return hex;
const r = parseInt(normalized.slice(0, 2), 16);
const g = parseInt(normalized.slice(2, 4), 16);
const b = parseInt(normalized.slice(4, 6), 16);
return `rgba(${r}, ${g}, ${b}, ${alpha})`;
}
export async function loadTheme(url = "/theme.config.json"): Promise<ThemeConfig> {
try {
const res = await fetch(url);
if (!res.ok) return DEFAULT_THEME;
return { ...DEFAULT_THEME, ...(await res.json()) };
} catch {
return DEFAULT_THEME;
}
}