IntlProvider中的属性变更,并不会触发FormattedMessage重新渲染
解决:在组件中加入key
大型项目不建议使用这种方案,因为:会引起此<IntlProvider>包裹下的所有组件全部被更新
import { FormattedMessage } from 'react-intl';<FormattedMessage id="common.search" defaultMessage="查询" /><FormattedMessage id="common.reset" defaultMessage="重置" /><FormattedMessage id="common.title" defaultMessage="页面标题" /><Modaltitle={<FormattedMessage id="common.add" defaultMessage="新增" />}visible={visible}onOk={this.handleOk}onCancel={this.handleCancel}><Form onSubmit={this.handleSubmit}><Item{...attrs} // 展开多属性label={<FormattedMessage id="common.department" defaultMessage="部门" />}/></Form>
var defaultProps = {formats: {},messages: {},textComponent: 'span',defaultLocale: 'en',defaultFormats: {}};
FormattedMessage常用的属性
- id 文件中的属性名,唯一的,重复报错
- defaultMessage 中的name和values中的key对应,动态传递参数
- 当在locale配置文件中,没有找到这个id的时候,输出的结果就是 defaultMessage的值
- tagName 设置生成html标签
- description 这个位置替代的字符串的描述,便于维护代码
```jsx
<a name="g8bG7"></a>## FormattedMessage细节1. FormattedMessage 用于组件的渲染场景,并不适合用于占位符,替换文本等2. placeholder 不能使用 FormattedMessage,实际占位符中返回[Object object],1. 因为:FormattedMessage是个组件,对象类型,placeholder接收的 String类型1. FormattedMessage 默认生成一个 span,不是纯文本字符串;默认返回 <span>标签2. 解决:用 injectIntl 将 intl注入到组件<a name="o0hOg"></a>### tabList```jsximport { FormattedMessage, injectIntl, defineMessages } from 'react-intl';const tabList = [{key: 'title',tab: <FormattedMessage id="table.tab1" defaultMessage="名称" />,},{key: 'phone',tab: <FormattedMessage id="table.tab2" defaultMessage="电话" />,},];
injectIntl处理字符串
import {injectIntl, defineMessages} from 'react-intl';import {connect} from 'react-redux';import PageTitle from './PageTitle';const lang = defineMessages({label: {id: "common.home.title", defaultMessage: "首页"},});function mapStateToProps(state, props) {const { intl } = propsreturn {label: intl.formatMessage(lang.label),}}export default injectIntl(connect(mapStateToProps)(MyComponent))
import React from 'react';import { injectIntl, intlShape, FormattedRelative } from 'react-intl';Parent.propTypes = {intl: intlShape.isRequired}function Parent(props) {const { intl: {formatMessage} } = propsconst placeholder = formatMessage({id: 'messageId'});// 动态传值 第一个参数 id;第二个参数 valueconst name = formatMessage({id: 'intl.name'},{name: 'lucy'})return(<div><input placeholder={placeholder} /><p title={intl.formatDate(date)}><FormattedRelative value={date}/></p><FormattedMessageid="intl.name"values={{name: <b>{name}</b>}}/></div>);}export default injectIntl(Parent);
class组件
injectIntl(Component);this.props.intl.formatMessage(...)@injectIntlclass Parent extends Component {render() {const {intl} = this.propsconst defineMessage = defineMessages({batchPlaceholder: {id: 'list.placeholder',defaultMessage: '请选择用户'}})return (<div>{intl.formatMessage(defineMessage.batchPlaceholder)}</div>)}}
defineMessages 定义key值
优点:自动的多语言提取
缺点:
- 组件多语言方便
- 字符串多语言每次都要注入 intl;原因?formatMessage react-i18n不直接暴露 ```jsx import { injectIntl, defineMessages } from ‘react-intl’;
@injectIntl const defineMessage = defineMessages({ placeholder: { id: ‘member.info.placeholder’, defaultMessage: ‘请选择’ } })
intl.formatMessage(defineMessage.placeholder)
<a name="QJkvX"></a>## 动态传值locales/```jsx// en-US.jsonconst en_US = {hello: "Hello, {name}!"}// zh-CN.jsonconst zh_CN = {hello: "{name},你好!"}
defineMessage.json定义常量
- 定义常量 utils/defineMessage.js
- 在组件引入常量使用
defineMessage.js
import { defineMessages } from 'react-intl';const RuleMessage = defineMessages({rule: {id: 'common.rule',defaultMessage: '第{number}条规则',},title: {id: 'login.title',defaultMessage: '管理员登录'},placeholder: {id: 'common.placeholder',defaultMessage: '请输入 {value}',},help: {id: 'common.help',defaultMessage: '需要帮助'}}
Component组件使用
import { injectIntl } from 'react-intl';import { defineMessage as lang } from '$utils/defineMessage';// hooksfunction App({intl}) {const { formatMessage } = intl;const {name: formatMessage(lang.rule, { number }),user: 'lucy',}}// class组件@injectIntlclass Login extends React.PureComponent {render () {const { intl: formatMessage } = this.props;return (<Card title={forMatMessage(lang.title)} />)}}export default Login
FormattedMessage 传值
import { FormattedMessage } from 'react-intl';<FormattedMessageid="intl.name"tagName="div"description="用户名"defaultMessage="Hello, {name}!"values={{name: <b>{name}</b>}}/>
