scratch语言配置文件
语言配置文件所在路径:scratch-gui\src\reducers\local.js。
import {addLocaleData} from 'react-intl';
import {localeData} from 'scratch-l10n';
import editorMessages from 'scratch-l10n/locales/editor-msgs';
import {isRtl} from 'scratch-l10n';
addLocaleData(localeData);
const UPDATE_LOCALES = 'scratch-gui/locales/UPDATE_LOCALES';
const SELECT_LOCALE = 'scratch-gui/locales/SELECT_LOCALE';
const initialState = {
isRtl: false,
locale: 'en',
messagesByLocale: editorMessages,
messages: editorMessages.en
};
...
语言源文件
文件所在文件夹: scratch-gui\node_modules\scratch-l10n
image.pngblocks是block块的翻译文件。
extensions是扩展的翻译文件。
interface 是gui界面的翻译文件。
pain-editor是造型页面的翻译文件。
一、语言文件的使用
-
引入
react-intl
src\containers\gui.jsx
是我们遇到的第一个用到多语言的地方
import {defineMessages, injectIntl, intlShape} from 'react-intl';
-
defineMessages
defineMessages中,id相当于一个key,将来在scratch-l10导出的多语言文件中查找,defaultMessage
表示默认显示,如果id没有对应的值,就显示默认的。description
表示属性描述。
const messages = defineMessages({
defaultProjectTitle: {
id: 'gui.gui.defaultProjectTitle',
description: 'Default title for project',
defaultMessage: 'Scratch Project'
}
});
-
在组件中注入 injectIntl
const ConnectedGUI = injectIntl(connect(
mapStateToProps,
mapDispatchToProps,
)(GUI));
二、通过 LocalizationHOC 高阶组件为GUI提供本地化状态
react-int包还需要用 <IntlProvider />
包裹在组件的最外层,scratch-gui中通过LocalizationHOC高阶组件来封装
const WrappedGui = compose(
// 提供本地化状态的高阶组件。
LocalizationHOC,
// 提供封装组件错误边界的高阶组件,传入一个string类型的action,用于GA跟踪错误标签
ErrorBoundaryHOC('Top Level App'),
// 加载字体高阶组件
FontLoaderHOC,
// 从URL查询字符串获取参数并初始化redux状态的高阶组件
QueryParserHOC,
// 提供通过id加载项目的行为的高阶组件。如果没有id,则加载默认的项目。
ProjectFetcherHOC,
// 提供项目保存功能的高阶组件
ProjectSaverHOC,
// 监听VM事件的高阶组件
vmListenerHOC,
// 发送VM事件的高阶组件
vmManagerHOC,
// 连接云服务器的高阶组件
cloudManagerHOC
)(ConnectedGUI);
LocalizationHOC组件:
import React from 'react';
import PropTypes from 'prop-types';
import {connect} from 'react-redux';
import ConnectedIntlProvider from './connected-intl-provider.jsx';
/*
* Higher Order Component to provide localiztion state. Creates a nested IntlProvider
* to handle Gui intl context. The component accepts an onSetLanguage callback that is
* called when the locale chagnes.
* @param {React.Component} WrappedComponent - component to provide state for
* @returns {React.Component} component with intl state provided from redux
*/
// 提供本地化状态的高阶组件。
//创建一个嵌套的IntlProvider来处理Gui intl上下文。
//组件接受一个onSetLanguage回调函数,该函数在语言环境chagnes时调用。
const LocalizationHOC = function (WrappedComponent) {
class LocalizationWrapper extends React.Component {
componentDidUpdate (prevProps) {
if (prevProps.locale !== this.props.locale) {
this.props.onSetLanguage(this.props.locale);
}
}
render () {
const {
locale, // eslint-disable-line no-unused-vars
onSetLanguage, // eslint-disable-line no-unused-vars
...componentProps
} = this.props;
return (
<ConnectedIntlProvider>
<WrappedComponent {...componentProps} />
</ConnectedIntlProvider>
);
}
}
LocalizationWrapper.propTypes = {
locale: PropTypes.string,
onSetLanguage: PropTypes.func
};
LocalizationWrapper.defaultProps = {
onSetLanguage: () => {}
};
const mapStateToProps = state => ({
locale: state.locales.locale
});
const mapDispatchToProps = () => ({});
return connect(
mapStateToProps,
mapDispatchToProps
)(LocalizationWrapper);
};
export default LocalizationHOC;
三、添加 localedata
定义在“src\reducers\locales.js”:
import {addLocaleData} from 'react-intl';
import {localeData} from 'scratch-l10n';
// 国际化只取中英文
import editorMessages from '../locales/editor-msgs';
// import editorMessages from 'scratch-l10n/locales/editor-msgs';
import {isRtl} from 'scratch-l10n';
addLocaleData(localeData);
const UPDATE_LOCALES = 'scratch-gui/locales/UPDATE_LOCALES';
const SELECT_LOCALE = 'scratch-gui/locales/SELECT_LOCALE';
const initialState = {
isRtl: false,
locale: 'en',
messagesByLocale: editorMessages,
messages: editorMessages.en
};
...
这里我们可以看到 scratch-l10n的多语言文件由node-modlue包的scratch-l10n/locales/editor-msgs.js文件导出
四、应用 FormattedMessage 来格式化多语言
setReduxTitle (newTitle) {
if (newTitle === null || typeof newTitle === 'undefined') {
this.props.onUpdateReduxProjectTitle(
this.props.intl.formatMessage(messages.defaultProjectTitle)
);
} else {
this.props.onUpdateReduxProjectTitle(newTitle);
}
}
这里是gui组件挂载完成后 ,componentDidMount()生命周期函数调用:
componentDidMount () {
setIsScratchDesktop(this.props.isScratchDesktop);
this.setReduxTitle(this.props.projectTitle);
this.props.onStorageInit(storage);
}
我们可以看到挂载完成后,设置项目标题,并保存到redux中,在这里用到了多语言
this.props.intl.formatMessage(messages.defaultProjectTitle)
。在第一步injectIntl注入到组件后,组件的prop上就有了一个intl
对象,然后formatMessage来应用。
作者:LiviSun
链接:https://www.jianshu.com/p/c97b88ca7631
来源:简书
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。
网友评论