React實作多語言切換
工作上遇到的需求,要利用React實作多語言切換
Install react-i18next i18next
Import react-i18next i18next.\
npm install react-i18next i18next
範例程式 LanguageSelector.jsx
import React, { useState } from 'react';
import styles from './LanguageSelector.module.css'
import { useTranslation } from "react-i18next";
import IconCN from '../assets/cn.svg'
import IconGB from '../assets/gb.svg'
const LanguageSelector = () => {
// Initialize the i18n object for translation
const { i18n } = useTranslation();
// Initialize state for the selected language
const [selectedLanguage, setSelectedLanguage] = useState('zh-cn'); // Default to Chinese
// Handle language selection
const handleLanguageChange = (languageCode) => {
// Update the selected language in state
setSelectedLanguage(languageCode);
// Change the language using i18n
i18n.changeLanguage(languageCode.replace("-", ""));
};
return (
<div className={styles.languageSelector}>
{/* Create a button for selecting Chinese language */}
<div
className={`${styles.lang_button} ${selectedLanguage === 'zh-cn' ? 'selected' : ''}`}
onClick={() => handleLanguageChange('zh-cn')}
>
<img className={styles.img} src={IconCN} alt="IconCN" />
</div>
{/* Create a button for selecting English language */}
<div
className={`${styles.lang_button} ${selectedLanguage === 'en' ? 'selected' : ''}`}
onClick={() => handleLanguageChange('en')}
>
<img className={styles.img} src={IconGB} alt="IconGB" />
</div>
</div>
);
};
export default LanguageSelector;
範例程式 LanguageSelector.module.css
.languageSelector {
display: flex;
}
.img {
width: 40px;
height: 40px;
border-radius: 50%;
}
.lang_button {
margin-left: 3px;
margin-right: 3px;
background-color: #ffffff00;
}
範例程式 Header.jsx
import { React, useState } from 'react';
import Logo from '../assets/logo.svg'
import { AiOutlineMenu, AiOutlineClose, } from 'react-icons/ai';
import styles from './Header.module.css'
import LanguageSelector from './LanguageSelector'; // import LanguageSelector
import { useTranslation } from "react-i18next"; // import react-i18next
const Header = () => {
// create Translation t
const { t } = useTranslation();
// Create a state variable 'nav' and a function 'setNav' to toggle the navigation menu
const [nav, setNav] = useState(false);
return (
<>
<header>
<img src={Logo} alt='Logo' />
<nav>
<ul className={nav ? [styles.menu, styles.active].join(' ') : [styles.menu]} >
<li>
<a href='/#'>{t("home")}</a>
</li>
<li>
<a href='/#'>{t("about_us")}</a>
</li>
<li>
< a href='/#'>{t("contact_us")}</a>
</li>
<li>
<LanguageSelector />
</li>
</ul>
</nav>
{/* Create a button to toggle the mobile menu */}
<div onClick={() => setNav(!nav)} className={styles.mobile_btn}>
{/* Display the close or menu icon based on the 'nav' state */}
{nav ? <AiOutlineClose size={30} color='white' /> : <AiOutlineMenu size={30} color='white' />}
</div>
</header>
</>
);
}
export default Header;
範例程式 main.jsx
import React from 'react';
import ReactDOM from 'react-dom/client';
import App from './App.jsx';
import './main.css';
import { I18nextProvider } from "react-i18next";
import locales_en from "./locales/en.json";
import locales_cn from "./locales/cn.json";
import i18next from "i18next";
// Initialize i18next for internationalization
i18next.init({
interpolation: { escapeValue: false },
lng: "zhcn", // Set the default language to Chinese
resources: {
zhcn: {
translation: locales_cn // Define translations for Chinese
},
en: {
translation: locales_en // Define translations for English
}
}
});
// Render the React app with internationalization support
ReactDOM.createRoot(document.getElementById('root')).render(
<React.StrictMode>
<I18nextProvider i18n={i18next}>
<App />
</I18nextProvider>
</React.StrictMode>
);
範例程式 en.json
{
"home":"Home",
"about_us":"About us",
"contact_us":"Contact us"
}
範例程式 cn.json
{
"home":"主页",
"about_us":"关于我",
"contact_us":"联系我"
}
成果
網頁版
手機版
結語
本次實作多語言,下次會介紹Route