71 lines
2.6 KiB
TypeScript
71 lines
2.6 KiB
TypeScript
import { BrowserRouter } from 'react-router-dom';
|
|
import { useMemo, useEffect } from 'react';
|
|
import { ThemeProvider, createTheme } from '@mui/material/styles';
|
|
import CssBaseline from '@mui/material/CssBaseline';
|
|
import { useTLDraw } from './contexts/TLDrawContext';
|
|
import { theme } from './services/themeService';
|
|
import { AuthProvider } from './contexts/AuthContext';
|
|
import { TLDrawProvider } from './contexts/TLDrawContext';
|
|
import { UserProvider } from './contexts/UserContext';
|
|
import AppRoutes from './AppRoutes';
|
|
import { ErrorBoundary } from './components/ErrorBoundary';
|
|
import React from 'react';
|
|
|
|
/**
|
|
* Syncs tldraw's color scheme to data-color-mode on <html>.
|
|
* Must live inside TLDrawProvider so useTLDraw() reads live preferences.
|
|
* This activates the [data-color-mode="dark"] overrides in cc-design-system.css.
|
|
* tldraw itself uses tl-theme__dark class on .tl-container — we mirror that
|
|
* to the document root so --cc-* token overrides apply globally.
|
|
*/
|
|
const DarkModeSync: React.FC = () => {
|
|
const { tldrawPreferences } = useTLDraw();
|
|
const prefersDarkMode =
|
|
typeof window !== 'undefined' &&
|
|
window.matchMedia('(prefers-color-scheme: dark)').matches;
|
|
|
|
useEffect(() => {
|
|
const scheme = tldrawPreferences?.colorScheme ?? 'system';
|
|
const isDark = scheme === 'dark' || (scheme === 'system' && prefersDarkMode);
|
|
document.documentElement.setAttribute('data-color-mode', isDark ? 'dark' : 'light');
|
|
}, [tldrawPreferences?.colorScheme, prefersDarkMode]);
|
|
|
|
return null;
|
|
};
|
|
|
|
const App = React.memo(() => {
|
|
const prefersDarkMode =
|
|
typeof window !== 'undefined' &&
|
|
window.matchMedia('(prefers-color-scheme: dark)').matches;
|
|
|
|
const appTheme = useMemo(() => {
|
|
// App is outside TLDrawProvider so tldrawPreferences is always null here.
|
|
// Theme defaults to OS preference; DarkModeSync (inside TLDrawProvider) handles
|
|
// updating data-color-mode once tldraw preferences are loaded.
|
|
const mode = prefersDarkMode ? 'dark' : 'light';
|
|
return createTheme({ palette: { mode } });
|
|
}, [prefersDarkMode]);
|
|
|
|
return (
|
|
<ErrorBoundary>
|
|
<BrowserRouter future={{ v7_startTransition: true, v7_relativeSplatPath: true }}>
|
|
<AuthProvider>
|
|
<UserProvider>
|
|
<TLDrawProvider>
|
|
<DarkModeSync />
|
|
<ThemeProvider theme={appTheme}>
|
|
<CssBaseline />
|
|
<AppRoutes />
|
|
</ThemeProvider>
|
|
</TLDrawProvider>
|
|
</UserProvider>
|
|
</AuthProvider>
|
|
</BrowserRouter>
|
|
</ErrorBoundary>
|
|
);
|
|
});
|
|
|
|
App.displayName = import.meta.env.VITE_APP_NAME;
|
|
|
|
export default App;
|