为什么函数无效为React child?

时间:2018-05-18 14:18:12

标签: reactjs react-native

我正在尝试将基于类的组件转换为功能(无状态)组件。我每次都会收到此错误:

  

函数作为React子函数无效。如果您返回Component而不是......

,则可能会发生这种情况

这是我的组件:

 const ProfileStories = (props) => {
  const renderStory = () => {
    const data = props.userStory ? props.userStory.data : [];
    if (props.isClicked) {
      return (
        <FlatList
          data={data}
          renderItem={renderStoryItem}
          keyExtractor={(item, index) => index.toString()}
          numColumns={2}
        />
      );
    } return null;
  };

  const renderStoryItem = (item) => {
    return (
      <StoryItem
        key={item.id}
        content={item.content}
        date={item.createdAt}
      />
    );
  };

  return (
    <CenterView>
      {renderStory}
    </CenterView>
  );
};

export default ProfileStories;

3 个答案:

答案 0 :(得分:2)

与往常一样,必须使用<...>语法呈现组件。为此,您还将被迫大写组件的名称:

const RenderStory = () => {
}
...
return (
    <CenterView>
      <RenderStory />
    </CenterView>
 );

这与直接调用函数基本相同:

return (
  <CenterView>
    {renderStory()}
  </CenterView>
);

但是,你的内部函数不是真正的组件,因为它是写的。首先,它使用其“父”组件的props。要使其成为真正的组件,您应该直接将props传递给它。目前它只是一个内在的功能。

答案 1 :(得分:2)

下面:

return (
  <CenterView>
    {renderStory}
  </CenterView>
);

您正在传递renderStory,这确实是一个函数。您可能打算将renderStory函数的结果作为子项传递给CenterView,如下所示:

return (
  <CenterView>
    {renderStory()}
  </CenterView>
);

答案 2 :(得分:0)

扩展@hansn的回答:

您面临的问题是您正在传递内部函数(renderStory)作为子项。 React期待的是jsx component或null:这是函数返回的内容。你应该做的只是明确地称之为:

 <CenterView>
   {renderStory()}
 </CenterView>

此外,为了使无状态功能组件更具可重用性,我建议您将单个组件ProfileStories拆分为3:

const Story = (props) => (
  <FlatList
    data={props.data}
    isClicked={props.isClicked}
    renderItem={props.renderItem}
    numColumns={2}
  />
);

Story.defaultProps = {
  data: []
}

const StoryItem = (item) => (
  <StoryItem
    key={item.id}
    content={item.content}
    date={item.createdAt}
  />
);

const ProfileStories = (props) => (
  <CenterView>
    <Story
      data={props.data}
      isClicked={props.isClicked}
      renderItem={StoryItem}
    />
  </CenterView>
);