62 lines
1.9 KiB
TypeScript
62 lines
1.9 KiB
TypeScript
|
|
'use client'
|
||
|
|
|
||
|
|
import { useTransition } from 'react'
|
||
|
|
import { useLocale } from 'next-intl'
|
||
|
|
import { useRouter } from 'next/navigation'
|
||
|
|
import { Button } from '@/components/ui/button'
|
||
|
|
import {
|
||
|
|
DropdownMenu,
|
||
|
|
DropdownMenuContent,
|
||
|
|
DropdownMenuItem,
|
||
|
|
DropdownMenuTrigger,
|
||
|
|
} from '@/components/ui/dropdown-menu'
|
||
|
|
import { Globe, Check } from 'lucide-react'
|
||
|
|
|
||
|
|
const LANGUAGES = [
|
||
|
|
{ code: 'en', label: 'English', flag: 'EN' },
|
||
|
|
{ code: 'fr', label: 'Fran\u00e7ais', flag: 'FR' },
|
||
|
|
] as const
|
||
|
|
|
||
|
|
type LanguageCode = (typeof LANGUAGES)[number]['code']
|
||
|
|
|
||
|
|
export function LanguageSwitcher() {
|
||
|
|
const locale = useLocale() as LanguageCode
|
||
|
|
const router = useRouter()
|
||
|
|
const [isPending, startTransition] = useTransition()
|
||
|
|
|
||
|
|
const currentLang = LANGUAGES.find((l) => l.code === locale) ?? LANGUAGES[0]
|
||
|
|
|
||
|
|
const switchLanguage = (code: LanguageCode) => {
|
||
|
|
// Set cookie with 1 year expiry
|
||
|
|
document.cookie = `locale=${code};path=/;max-age=${365 * 24 * 60 * 60};samesite=lax`
|
||
|
|
// Refresh to re-run server components with new locale
|
||
|
|
startTransition(() => {
|
||
|
|
router.refresh()
|
||
|
|
})
|
||
|
|
}
|
||
|
|
|
||
|
|
return (
|
||
|
|
<DropdownMenu>
|
||
|
|
<DropdownMenuTrigger asChild>
|
||
|
|
<Button variant="ghost" size="sm" className="gap-2" disabled={isPending}>
|
||
|
|
<Globe className="h-4 w-4" />
|
||
|
|
<span className="font-medium">{currentLang.flag}</span>
|
||
|
|
</Button>
|
||
|
|
</DropdownMenuTrigger>
|
||
|
|
<DropdownMenuContent align="end">
|
||
|
|
{LANGUAGES.map((lang) => (
|
||
|
|
<DropdownMenuItem
|
||
|
|
key={lang.code}
|
||
|
|
onClick={() => switchLanguage(lang.code)}
|
||
|
|
className="gap-2"
|
||
|
|
>
|
||
|
|
<span className="font-medium w-6">{lang.flag}</span>
|
||
|
|
<span>{lang.label}</span>
|
||
|
|
{locale === lang.code && <Check className="ml-auto h-4 w-4" />}
|
||
|
|
</DropdownMenuItem>
|
||
|
|
))}
|
||
|
|
</DropdownMenuContent>
|
||
|
|
</DropdownMenu>
|
||
|
|
)
|
||
|
|
}
|