shadcn-theme-menu 1.1.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,73 @@
1
+ 'use client'
2
+ import { Moon, Sun, Monitor } from 'lucide-react'
3
+ import { useTheme } from 'next-themes'
4
+
5
+ import { Button } from './components/ui/button'
6
+ import {
7
+ DropdownMenu,
8
+ DropdownMenuContent,
9
+ DropdownMenuItem,
10
+ DropdownMenuTrigger,
11
+ } from './components/ui/dropdown-menu'
12
+
13
+ interface ThemeToggleProps {
14
+ mode?: 'light-dark' | 'light-dark-system'
15
+ Button?: React.ComponentType<any>
16
+ DropdownMenu?: any
17
+ onThemeChange?: (theme: string) => void
18
+ }
19
+
20
+ export function ThemeToggle({
21
+ mode = 'light-dark-system',
22
+ Button: CustomButton,
23
+ DropdownMenu: CustomDropdownMenu,
24
+ onThemeChange
25
+ }: ThemeToggleProps) {
26
+ const { setTheme } = useTheme()
27
+
28
+ const ButtonComp = CustomButton || Button
29
+ const MenuComp = CustomDropdownMenu || {
30
+ Root: DropdownMenu,
31
+ Trigger: DropdownMenuTrigger,
32
+ Content: DropdownMenuContent,
33
+ Item: DropdownMenuItem
34
+ }
35
+
36
+ const handleThemeChange = (theme: string) => {
37
+ setTheme(theme)
38
+ onThemeChange?.(theme)
39
+ }
40
+
41
+ const Root = MenuComp.Root || MenuComp
42
+ const Trigger = MenuComp.Trigger || DropdownMenuTrigger
43
+ const Content = MenuComp.Content || DropdownMenuContent
44
+ const Item = MenuComp.Item || DropdownMenuItem
45
+
46
+ return (
47
+ <Root>
48
+ <Trigger asChild>
49
+ <ButtonComp variant='ghost' size='icon' className='size-8'>
50
+ <Sun className='size-4 rotate-0 scale-100 transition-all dark:-rotate-90 dark:scale-0' />
51
+ <Moon className='absolute size-4 rotate-90 scale-0 transition-all dark:rotate-0 dark:scale-100' />
52
+ <span className='sr-only'>Toggle theme</span>
53
+ </ButtonComp>
54
+ </Trigger>
55
+ <Content align='end'>
56
+ <Item onClick={() => handleThemeChange('light')}>
57
+ <Sun className='mr-2 size-4' />
58
+ Light
59
+ </Item>
60
+ <Item onClick={() => handleThemeChange('dark')}>
61
+ <Moon className='mr-2 size-4' />
62
+ Dark
63
+ </Item>
64
+ {mode === 'light-dark-system' && (
65
+ <Item onClick={() => handleThemeChange('system')}>
66
+ <Monitor className='mr-2 size-4' />
67
+ System
68
+ </Item>
69
+ )}
70
+ </Content>
71
+ </Root>
72
+ )
73
+ }