React 多國語言簡介(使用 react-intl) 使用 Yahoo react-intl

me
林彥成
2017-09-21 | 2 min.
文章目錄
  1. 1. 什麼是 React Intl?
  2. 2. React Intl 主要功能
    1. 2.1. 基本配置
    2. 2.2. locale
    3. 2.3. Placeholder
    4. 2.4. 設計 HOC

什麼是 React Intl?

React Intl 這套函式庫讓 React 實做多國語系更加直觀,透過現成的元件和 API 能處理字串、日期、數字的轉換。

React Intl 主要功能

React Intl 主要提供下列的功能:

  • 支援數字和分隔符號格式
  • 日期與時間的格式
  • 顯示距離現在多久
  • 支援 150+ 種語言
  • 在瀏覽器以及 Node 環境都可運行
  • 依照標準建立的一套函式庫

基本配置

使用 Yahoo react-intl 來幫 React 專案做多國語系處理,最重要的就是安裝 npm install --save react-intl

專案配置先加入addLocaleData各語系配置檔,呆丸專用繁體中文 zh-Hant-TW 已包含在 zh 中可以直接使用,然後透過 IntlProvider 注入相關環境及設定到我們的 App 中,其中像是現在要顯示的語系(locale)及翻譯黨(messages),然後就可以透過更改 local 及 message 達到語言切換的目的~

1
2
3
4
5
6
7
8
9
10
import { addLocaleData } from "react-intl";
import en from "react-intl/locale-data/en";
import zh from "react-intl/locale-data/zh";
import es from "react-intl/locale-data/es";

addLocaleData([...en, ...zh, ...es]);

<IntlProvider locale={localeProp} key={localeProp} messages={messagesProp}>
<App />
</IntlProvider>;

假設雙語的話,就是三位一體的概念,首先必須把專案裏需要雙語的地方改成特定元件或是變數,接著配合剛才的元件或變數中的 id 撰寫翻譯檔,然後透過改變剛剛提到的 locale, message 去對應切換相關語言翻譯檔~

一般顯示

1
<FormattedMessage id="App.hello" />

當成變數使用,注入後使用

1
2
3
4
5
const App = (props) => {
const { intl } = props;
const strHello = intl.formatMessage({ id: "App.hello" });
};
injectIntl(App);

英文語言

1
2
3
{
"App.hello": "hello"
}

中文語言

1
2
3
{
"App.hello": "哈囉"
}

locale

透過 injectIntl() 這個 HOC 就可以使用程式取得現在 React Intl 設定的語系

1
2
3
4
5
6
7
8
9
10
11
12
13

import { injectIntl, intlShape } from 'react-intl'

const LocaleComponent = ({ intl }) => (
<div>{`語系: ${intl.locale}`}</div>
)

LocaleComponent.propTypes = {
intl: intlShape.isRequired
}

export default injectIntl(LocaleComponent)

Placeholder

這時候需要用到比元件更底層 API formatMessage(),在使用 injectIntl() 注入 intl 物件到元件中後,就可以透過 formatMessage() 來進行字串的轉換

1
2
3
4
5
6
7
8
9
10
11
12
13
import React from 'react'
import { injectIntl, intlShape } from 'react-intl'

const LocaleComponent = ({ intl }) => {
const placeholder = intl.formatMessage({id: 'messageId'})
return <input placeholder={placeholder} />
}

LocaleComponent.propTypes = {
intl: intlShape.isRequired
}

export default injectIntl(LocaleComponent)

設計 HOC

完全建議在專案一開始就加入多國語言的配置,這樣才不會到後來各種麻煩,底下 Demo 了一個交換語言用的 Container,透過每次改變語言去改變狀態並傳入 IntlProvide 中,當然也可以考慮用 HOC 的方式去包裝~

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
class HotSwappingIntlProvider extends React.Component {
constructor(props) {
super(props);
const { initialLocale: locale, initialMessages: messages } = props;
this.state = { locale, messages };
this.handleChange = this.handleChange.bind(this);
}

handleChange(locale) {
let messages = enJson;
if (locale !== "en") {
messages = zhJson;
}

this.setState({
locale: locale,
messages: messages,
});
}

render() {
return (
<IntlProvider
locale={this.state.locale}
key={this.state.locale}
messages={this.state.messages}
>
{this.props.children}
</IntlProvider>
);
}
}

喜歡這篇文章,請幫忙拍拍手喔 🤣

share