Skip to content

Commit

Permalink
feat(dark mode): added theme change with no flash
Browse files Browse the repository at this point in the history
  • Loading branch information
aprendendofelipe committed Mar 27, 2023
1 parent 1fb96d9 commit 3abd1a9
Show file tree
Hide file tree
Showing 4 changed files with 50 additions and 20 deletions.
28 changes: 9 additions & 19 deletions pages/_app.public.js
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { BaseStyles, NextNProgress, PrimerThemeProvider, SSRProvider } from '@/TabNewsUI';
import { ThemeProvider } from '@/TabNewsUI';
import { Analytics } from '@vercel/analytics/react';
import { DefaultHead, UserProvider } from 'pages/interface';
import { SWRConfig } from 'swr';
Expand All @@ -12,25 +12,15 @@ async function SWRFetcher(resource, init) {

function MyApp({ Component, pageProps }) {
return (
<>
<UserProvider>
<DefaultHead />
<SWRConfig
value={{
fetcher: SWRFetcher,
}}>
<SSRProvider>
<PrimerThemeProvider preventSSRMismatch colorMode="day">
<BaseStyles>
<NextNProgress options={{ showSpinner: false }} />
<Component {...pageProps} />
</BaseStyles>
</PrimerThemeProvider>
</SSRProvider>
</SWRConfig>
</UserProvider>
<UserProvider>
<DefaultHead />
<SWRConfig value={{ fetcher: SWRFetcher }}>
<ThemeProvider>
<Component {...pageProps} />
</ThemeProvider>
</SWRConfig>
<Analytics />
</>
</UserProvider>
);
}

Expand Down
8 changes: 7 additions & 1 deletion pages/_document.public.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
import Document, { Html, Head, Main, NextScript } from 'next/document';
import Document, { Head, Html, Main, NextScript } from 'next/document';
import Script from 'next/script';
import { ServerStyleSheet } from 'styled-components';

const noFlashScript = `document.documentElement.setAttribute('data-no-flash', true)`;

export default class MyDocument extends Document {
static async getInitialProps(ctx) {
const sheet = new ServerStyleSheet();
Expand Down Expand Up @@ -32,6 +35,9 @@ export default class MyDocument extends Document {
<Html lang="pt-br">
<Head />
<body>
<Script id="theme" strategy="beforeInteractive">
{noFlashScript}
</Script>
<Main />
<NextScript />
</body>
Expand Down
3 changes: 3 additions & 0 deletions pages/interface/components/TabNewsUI/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ export { default as PasswordInput } from '@/PasswordInput/index.js';
export { default as NextNProgress } from '@/Progressbar/index.js';
export { default as PublishedSince } from '@/PublishedSince/index.js';
export { default as TabCoinButtons } from '@/TabCoinButtons/index.js';
export { default as ThemeProvider } from '@/ThemeProvider/index.js';
export {
ActionList,
ActionMenu,
Expand All @@ -30,11 +31,13 @@ export {
Link as PrimerLink,
NavList,
Pagehead,
SegmentedControl,
SSRProvider,
Text,
TextInput,
ThemeProvider as PrimerThemeProvider,
Tooltip,
Truncate,
useConfirm,
useTheme,
} from '@primer/react';
31 changes: 31 additions & 0 deletions pages/interface/components/ThemeProvider/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
import { BaseStyles, NextNProgress, PrimerThemeProvider, SSRProvider } from '@/TabNewsUI';
import { useEffect, useLayoutEffect, useState } from 'react';
import { createGlobalStyle } from 'styled-components';

// script to be called before interactive in _document.js
// document.documentElement.setAttribute('data-no-flash', true)
const NoFleshGlobalStyle = createGlobalStyle`html[data-no-flash='true']:root {visibility: hidden}`;
const removeNoFlashStyle = () => setTimeout(() => document.documentElement.removeAttribute('data-no-flash'));
const useBrowserLayoutEffect = typeof document === 'undefined' ? useEffect : useLayoutEffect;

export default function ThemeProvider({ children, ...props }) {
const [colorMode, setColorMode] = useState('day');

useBrowserLayoutEffect(() => {
const cachedColorMode = localStorage.getItem('colorMode') || 'auto';
setColorMode(cachedColorMode);
removeNoFlashStyle();
}, []);

return (
<SSRProvider>
<PrimerThemeProvider colorMode={colorMode} {...props}>
<BaseStyles>
<NextNProgress options={{ showSpinner: false }} />
<NoFleshGlobalStyle />
{children}
</BaseStyles>
</PrimerThemeProvider>
</SSRProvider>
);
}

0 comments on commit 3abd1a9

Please sign in to comment.