React.CloneElement返回一个对象而不是函数

时间:2017-11-26 07:04:40

标签: reactjs components clone element

我很难理解React.cloneElement()功能

的行为

我的组件结构就像这样

A.js

export default class A extends React.Component {
     render() {
         return (<h1>{ this.props.message }</h1>)
     }
 }

B.js

import A from "./A"

const newComponent = React.cloneElement(A,{
    message: "Hello World"
})

export default newComponent

C.js

import B from "./B"
import { BrowserRouter as Router, Route } from "react-router-dom"

// To Be very precise
 export default class C extends React.Component {
     render() {
         return (
             <Router>
                <Route path="/" component={B}  />
            </Router>
         )
     }
 }

但是我得到了这个错误

提供给component的{​​{1}}类型的道具object无效,预期为Route

但是当我将组件function直接传递到A组件时,它会呈现正常。

当我在组件Route的渲染函数中console.log组件A时,我得到一个函数但是 当我在组件C的渲染函数中console.log组件B时,我得到一个对象

我错过了什么?

1 个答案:

答案 0 :(得分:12)

首先,您需要了解difference between React component and React element。两者实际上都不同。

要在jsx中具体说明,在您的情况下,A是反应component<A />是反应element。如果您查看React.cloneElement文档,那么它会期望element作为第一个参数,但在这里您传递的是component。因此,首先需要做的是将元素传递给React.cloneElement,如此

const newComponent = React.cloneElement(<A />,{
    message: "Hello World"
})

第二件事是Route组件要求react componentcomponent prop,但React.cloneElement会返回react element而非组件(这意味着{{} 1}}是一个元素,而不是组件)。因此,您不能只从newComponent文件中导出newComponent。您必须导出B.js。为此,您可以创建component / class component。所以你的stateless component应该看起来像这样

B.js

顺便说一下,在你的情况下,你甚至不需要// B.js import A from "./A" const newComponent = React.cloneElement(<A />, { message: "Hello World" }) export default class B extends React.Component { render() { return (<div>{newComponent}</div>) } } 。您只需返回cloneElement的呈现B.js的组件即可。这只是为了理解目的。