【问题标题】:React: Inject common render logic from parentReact:从父级注入通用渲染逻辑
【发布时间】:2015-11-25 21:41:49
【问题描述】:

假设我有一个反应组件类,它在单击按钮时显示一个模式对话框。

可以这样创建(在 jsx 中):

<Modal text={"some text"}/>

现在,我有一堆组件类(我们称它们为面板),它们都有一个名为 getMessage 的函数,我希望所有这些组件都具有相同的行为:模式对话框应该显示字符串从对getMessage 的调用返回。

这样做的直接方法是包含

<Modal text={this.getMessage()}/>

在每个此类组件的 render() 函数中。

现在,假设涉及更多逻辑。例如,如果getMessage 已定义并且不返回null,我只想渲染此组件。

现在开始看起来像这样:

var Panel1 = React.createClass({
    getMessage: function() {return 'wow';},
    render: function() {
        var modal = null;
        if (this.hasOwnProperty('getMessage' && this.getMessage() !== null) {
            modal = <Modal text={this.getMessage()}/>
        }
        return (
            <div>
                {modal}
                ...all other stuff done in panel
            </div>
        );
    }
});

这开始变得很麻烦,因为我需要为我定义的每个组件类都有这个逻辑。

如何在这种情况下实现 DRYness,这样我就不必重复了?

一种方法是定义一个包含此逻辑的实用程序函数,我们将其称为displayModalIfNeeded,然后从渲染中调用它。现在看起来像这样:

return (
    <div>
        {displayModalIfNeeded.call(this)}
        ....all other stuff needed in Panel
    </div>
);

现在是我的实际问题(抱歉冗长的说明):

假设我有一个名为 &lt;Dashboard&gt; 的父组件,它的所有面板都为其子组件:

<Dashboard>
    <Panel1>
    <Panel2>
    <Panel3>
</Dashboard>

我是否可以在Dashboard 的实现中编写一些内容来完全消除在每个面板中指定关于这些模态组件的任何内容的需要?

意味着 Panel1 实现现在可以是

<div>
    ...all other stuff done in panel
</div>

当它被渲染为Dashboard 的子元素时,它将具有模态对话框和伴随的逻辑。

【问题讨论】:

  • 如果你负责渲染模态的这些组件,你不知道getMessage是否被定义? if/else 子句似乎是多余的。无论是否定义,如果没有,甚至不包括这些组件中的模态。除此之外,如果 getMessage 返回 null 消息,则模式不应呈现,因此其本身具有显示逻辑。
  • @HenrikAndersson 这些面板可以由其他人编写,作为一种插件。如果小组作者想要定义消息,他们可以,如果不是,他们不必
  • 我猜 - 两年后。我不知道。

标签: javascript reactjs code-reuse react-jsx


【解决方案1】:

我建议使用带有 children 属性的包装器组件。你的父组件应该是这样的:

<Dashboard>
    <ModalWrapper text={msg1}>
        <Panel1 />
    </ModalWrapper>
    <ModalWrapper text={msg2}>
        <Panel2 />
    </ModalWrapper>
    <ModalWrapper text={msg3}>
        <Panel3 />
    </ModalWrapper>
</Dashboard>

现在您所有的条件逻辑都可以放在ModalWrapper 中。如果您的问题有“.... Panel 中需要的所有其他内容”,请使用 this.props.children。例如

var ModalWrapper = React.createClass({
    render: function () {
        var text = this.props.text;
        return (
            <div>
                {text ? <Modal text={text} /> : null}
                {this.props.children}
            </div>
        );
    }
});

【讨论】:

  • 我需要编写不同面板的人来控制 getMessage 文本,所以我不能从上面注入它
猜你喜欢
  • 2021-02-21
  • 1970-01-01
  • 2017-03-06
  • 1970-01-01
  • 2021-10-01
  • 1970-01-01
  • 2016-06-07
  • 2020-09-10
  • 2018-06-27
相关资源
最近更新 更多