Improving the appearance of Chakra UI Locale Switcher in Next.js 13

87 views Asked by At

I'm using Next.js 13 with Chakra UI for my app, and I've implemented internationalization by following this guide. The complete example from the guide is available on GitHub. I've adapted the example to use Chakra UI components, but I'm facing styling issues.

Here's my LocaleSwitcher component:

'use client';

import { ChangeEvent } from 'react';
import { Box, Select, Text, useColorModeValue } from '@chakra-ui/react';
import { useLocale } from 'next-intl';
import { usePathname, useRouter } from 'next-intl/client';

export const LocaleSwitcher = () => {
  const locale = useLocale();
  const router = useRouter();
  const pathname = usePathname();

  const colorModeBg = useColorModeValue('brand.100', 'brand.700');

  const switchLanguage = (event: ChangeEvent<HTMLSelectElement>) => {
    const nextLocale = event.target.value;
    router.replace(pathname, { locale: nextLocale });
  };

  return (
    <Box position="relative" color={colorModeBg}>
      <Select size="sm" defaultValue={locale} onChange={switchLanguage}>
        {['en', 'bg'].map((cur) => (
          <option key={cur} value={cur}>
            {cur.toUpperCase()}
          </option>
        ))}
      </Select>
    </Box>
  );
};

The appearance of the Select component is terrible:

enter image description here

As visible in the image, there are undesired white borders around the dropdown. I'd appreciate any advice on:

  • How to remove or customize the white borders.
  • General improvements on the component's design using Chakra UI.

How can I remove those white borders, or do you have a better idea how to do it?

Edit

'use client';

import {
  Box,
  Button,
  Menu,
  MenuButton,
  MenuList,
  MenuItem,
  useColorModeValue,
} from '@chakra-ui/react';
import { ChevronDownIcon } from '@chakra-ui/icons';
import { useLocale } from 'next-intl';
import { usePathname, useRouter } from 'next-intl/client';

export const LocaleSwitcher = () => {
  const locale = useLocale();
  const router = useRouter();
  const pathname = usePathname();

  const switchLanguage = (nextLocale: string) => {
    router.replace(pathname, { locale: nextLocale });
  };

  return (
    <Menu>
      {({ isOpen }) => (
        <>
          <MenuButton
            as={Button}
            rightIcon={<ChevronDownIcon />}
            variant="ghost"
            isActive={isOpen}
          >
            {locale.toUpperCase()}
          </MenuButton>
          <MenuList>
            {['en', 'bg'].map((cur) => (
              <MenuItem key={cur} onClick={() => switchLanguage(cur)}>
                {cur.toUpperCase()}
              </MenuItem>
            ))}
          </MenuList>
        </>
      )}
    </Menu>
  );
};

enter image description here

This looks much better but I'm sure the code can be refactored.

0

There are 0 answers