feat(theme): add theme switching functionality with ModeSwitcher and ThemeProvider
This commit is contained in:
parent
398c56b38b
commit
8808b4fb9b
@ -23,6 +23,7 @@
|
||||
"lucide-react": "^0.468.0",
|
||||
"next": "15.0.4",
|
||||
"next-auth": "^5.0.0-beta.25",
|
||||
"next-themes": "^0.4.4",
|
||||
"react": "^19.0.0",
|
||||
"react-dom": "^19.0.0",
|
||||
"tailwind-merge": "^2.5.5",
|
||||
|
@ -14,6 +14,7 @@ import {
|
||||
import { SessionProvider } from "next-auth/react";
|
||||
import { AppSidebar } from "@/components/app-sidebar";
|
||||
import { Separator } from "@/components/ui/separator";
|
||||
import { ModeSwitcher } from "@/components/mode-switcher";
|
||||
import ConfirmationDialog from "@/dialogs/ConfirmationDialog";
|
||||
|
||||
export default function DashboardLayout({
|
||||
@ -27,6 +28,7 @@ export default function DashboardLayout({
|
||||
<header className="flex h-16 shrink-0 items-center gap-2">
|
||||
<div className="flex items-center gap-2 px-4">
|
||||
<SidebarTrigger className="-ml-1" />
|
||||
<ModeSwitcher />
|
||||
<Separator orientation="vertical" className="mr-2 h-4" />
|
||||
<Breadcrumb>
|
||||
<BreadcrumbList>
|
||||
|
@ -2,6 +2,7 @@ import "@/app/globals.css";
|
||||
import { cn } from "@/lib/utils";
|
||||
import type { Metadata } from "next";
|
||||
import { Inter } from "next/font/google";
|
||||
import { ThemeProvider } from "@/components/theme-provider";
|
||||
|
||||
const inter = Inter({ subsets: ["latin"], variable: "--font-sans" });
|
||||
|
||||
@ -20,8 +21,15 @@ export default function RootLayout({
|
||||
<html lang="en" className="h-full" suppressHydrationWarning>
|
||||
<body
|
||||
className={cn("font-sans antialiased flex min-h-full", inter.variable)}
|
||||
>
|
||||
<ThemeProvider
|
||||
attribute="class"
|
||||
defaultTheme="system"
|
||||
enableSystem
|
||||
disableTransitionOnChange
|
||||
>
|
||||
<div className="w-full">{children}</div>
|
||||
</ThemeProvider>
|
||||
</body>
|
||||
</html>
|
||||
);
|
||||
|
26
src/components/mode-switcher.tsx
Normal file
26
src/components/mode-switcher.tsx
Normal file
@ -0,0 +1,26 @@
|
||||
"use client";
|
||||
|
||||
import * as React from "react";
|
||||
import { useTheme } from "next-themes";
|
||||
import { Sun, Moon } from "lucide-react";
|
||||
import { Button } from "@/components/ui/button";
|
||||
|
||||
export function ModeSwitcher() {
|
||||
const { setTheme, resolvedTheme } = useTheme();
|
||||
|
||||
const toggleTheme = React.useCallback(() => {
|
||||
setTheme(resolvedTheme === "dark" ? "light" : "dark");
|
||||
}, [resolvedTheme, setTheme]);
|
||||
|
||||
return (
|
||||
<Button
|
||||
variant="ghost"
|
||||
className="group/toggle h-8 w-8 px-0"
|
||||
onClick={toggleTheme}
|
||||
>
|
||||
<Sun className="hidden [html.dark_&]:block" />
|
||||
<Moon className="hidden [html.light_&]:block" />
|
||||
<span className="sr-only">Toggle theme</span>
|
||||
</Button>
|
||||
);
|
||||
}
|
11
src/components/theme-provider.tsx
Normal file
11
src/components/theme-provider.tsx
Normal file
@ -0,0 +1,11 @@
|
||||
"use client";
|
||||
|
||||
import * as React from "react";
|
||||
import { ThemeProvider as NextThemesProvider } from "next-themes";
|
||||
|
||||
export function ThemeProvider({
|
||||
children,
|
||||
...props
|
||||
}: React.ComponentProps<typeof NextThemesProvider>) {
|
||||
return <NextThemesProvider {...props}>{children}</NextThemesProvider>;
|
||||
}
|
Loading…
Reference in New Issue
Block a user