Dark mode
NextUI comes with two palette modes light (the default) and dark, as we mentioned before.
you can make the theme dark by setting type: dark
.
import { createTheme } from "@nextui-org/react" const darkTheme = createTheme({ type: 'dark', theme: { colors: {...}, // override dark theme colors } });
For further information about
createTheme
, please refer to the typescript documentation.
Using next-themes
If you are using NextUI in conjuction with Next.js the best way to apply the dark mode is using the next-themes package.
NextUI automatically changes the theme when detects that next-themes
changes the current theme.
Here is an example of how to use next-themes
:
// 1. Import `createTheme` import { createTheme, NextUIProvider } from "@nextui-org/react" import { ThemeProvider as NextThemesProvider } from 'next-themes'; // 2. Call `createTheme` and pass your custom values const lightTheme = createTheme({ type: 'light', theme: { colors: {...}, // optional } }) const darkTheme = createTheme({ type: 'dark', theme: { colors: {...}, // optional } }) // 3. Wrap NextUIProvider with NextThemesProvider // _app.jsx // _app.tsx <NextThemesProvider defaultTheme="system" attribute="class" value={{ light: lightTheme.className, dark: darkTheme.className }} > <NextUIProvider> <App /> </NextUIProvider> </NextThemesProvider> // 4. Use `next-themes` to change the theme import { useTheme as useNextTheme } from 'next-themes' import { Switch, useTheme } from '@nextui-org/react' const App = () => { const { setTheme } = useNextTheme(); const { isDark, type } = useTheme(); return ( <div> The current theme is: {type} <Switch checked={isDark} onChange={(e) => setTheme(e.target.checked ? 'dark' : 'light')} /> </div> ) }
And that's it! 🎉
You have a no-flashing
dark theme implementation for your Next.js app.
For more information on the
next-themes
check out the docs
For more information on the default
colors
,fonts
,spaces
, etc.. please refer to the default theme documentation.
Using use-dark-mode
If you are using NextUI in conjuction with plain React.js a good way to apply the dark mode is using the use-dark-mode hook.
Here is an example of how to use use-dark-mode
:
// 1. Import `createTheme` import { createTheme, NextUIProvider } from "@nextui-org/react" import useDarkMode from 'use-dark-mode'; // 2. Call `createTheme` and pass your custom values const lightTheme = createTheme({ type: 'light', theme: { colors: {...}, } }) const darkTheme = createTheme({ type: 'dark', theme: { colors: {...}, } }) // 3. Apply light or dark theme depending on useDarkMode value // App.jsx entry point of your app const darkMode = useDarkMode(false); return ( <NextUIProvider theme={darkMode.value ? darkTheme : lightTheme}> <App /> </NextUIProvider> ) // 4. Use `useDarkMode` to change the theme import { Switch, useTheme } from '@nextui-org/react' import useDarkMode from 'use-dark-mode'; const App = () => { const darkMode = useDarkMode(false); const { type, isDark } = useTheme(); return ( <div> The current theme is: {type} <Switch checked={darkMode.value} onChange={() => darkMode.toggle()} /> </div> ) }
For more information about
use-dark-mode
check out the docs
Custom implementation
NextUI exposes a changeTheme
method that you can use to change the theme but you have to be sure
that you have created the passed theme before.
This method is also useful when you want to change the theme outside a React Component.
Here is an example of how to implement a custom dark mode:
// 1. Import `createTheme` import { createTheme } from "@nextui-org/react" // 2. Call `createTheme` and pass your custom values const lightTheme = createTheme({ type: 'light', theme: { colors: {...}, } }) const darkTheme = createTheme({ type: 'dark', theme: { colors: {...}, } }) // 3. Apply light or dark theme depending on localStorage and `getDocumentTheme` value // App.jsx entry point of your app import React, { useEffect, useState } from 'react'; import { getDocumentTheme } from '@nextui-org/react' const Main = () => { const [isDark, setIsDark] = useState(false); useEffect(() => { // you can use any storage let theme = window.localStorage.getItem('data-theme'); setIsDark(theme === 'dark'); const observer = new MutationObserver((mutation) => { let newTheme = getDocumentTheme(document?.documentElement); setIsDark(newTheme === 'dark'); }); // Observe the document theme changes observer.observe(document?.documentElement, { attributes: true, attributeFilter: ['data-theme', 'style'] }); return () => observer.disconnect(); }, []); return ( <NextUIProvider theme={isDark ? darkTheme : lightTheme}> <App /> </NextUIProvider> ) } // 4. Use `changeTheme` method to control theme changing import { Switch, changeTheme, useTheme } from '@nextui-org/react' const App = () => { const { type, isDark } = useTheme(); const handleChange = () => { const nextTheme = isDark ? 'light' : 'dark'; window.localStorage.setItem('data-theme', nextTheme); // you can use any storage changeTheme(nextTheme); } return ( <div> The current theme is: {type} <Switch checked={isDark} onChange={handleChange} /> </div> ) }
Note: This dark mode implementation is less recommended because it occurs only on the client side, which means that the theme can flash when the page is loaded.