2016-02-25 18 views
2

我正在建立一个即时通讯功能到我的项目。该项目使用React和Relay。即时通讯功能类似于Facebook聊天功能,您可以在其中看到要与之聊天的人员列表,点击某人将打开聊天窗口进行一对一讨论。如何从中继容器数组中组成碎片?

在我的实施中,可以与谁聊天的用户列表与打开的聊天窗口列表分开。所以,用户列表对于这个问题并不重要。

关于打开聊天窗口的渲染,我的方法是创建一个父React组件/中继容器。这个父组件将跟踪用户打开的聊天窗口,并将构建聊天窗口React组件数组并最终呈现它们。这个打开的聊天窗口列表在父React Component中都是本地状态。

个人聊天窗口阵营组件/继电器容器具有从参数场,其中参数是聊天窗口的讨论是与用户的ID查询片段。所以,如果这个聊天窗口是与Bob的讨论,那么这将是Bob的ID。

随着所有的这一点,这里有一个例子父组件实现...

class FloatingDiscussionPane extends React.Component { 
    render() { 
    return (
     <ul> 
     {this.renderDiscussions()} 
     </ul> 
    ); 
    } 

    renderDiscussions() { 
    const {teamIds} = this.props; 
    return teamIds.map(teamId => { 
     return (
     <FloatingDiscussionPaneDiscussion 
      teamId={teamId} /> 
    ); 
    }); 
    } 
}; 

export default Relay.createContainer(FloatingDiscussionPane, { 
    fragments: { 
    session:() => Relay.QL` 
     fragment on Session { 
     ${/* how to get fragments from the array of discussion windows */} 
     } 
    ` 
    } 
}); 

而这里将是聊天窗口的示例实现...

class FloatingDiscussionPaneDiscussion extends React.Component { 
    render() { 
    ... 
    } 
}; 

export default Relay.createContainer(FloatingDiscussionPaneDiscussion, { 
    fragments: { 
    session:() => Relay.QL` 
     fragment on Session { 
     messages: myDiscussionMessages(team: $teamId) { 
      ... 
     } 
     } 
    ` 
    } 
}); 

,你可以请参见FloatingDiscussionPaneDiscussion容器中有一个片段需要包含在父容器FloatingDiscussionPane中。父组件FloatingDiscussionPane将拥有一个FloatingDiscussionPaneDiscussion的数组,但都需要将其自己的片段包含在父片段中。

我该如何做到这一点?

回答

0

我假设一下,如果你的模式是这样的团队有消息(复数场,用GraphQLList支持)和会话具有团队。

的窗格组件可以加载了所有的队和它们的嵌套消息。

class FloatingDiscussionPane extends React.Component { 
    render() { 
    return (
     <ul> 
     {this.renderDiscussions()} 
     </ul> 
    ); 
    } 

    renderDiscussions() { 
    const {session: {teams}} = this.props; 
    return teams.map(({id, messages}) => { 
     return (
     <li key={id}> 
      <FloatingDiscussionPaneDiscussion messages={messages} /> 
     </li> 
    ); 
    }); 
    } 
}; 

export default Relay.createContainer(FloatingDiscussionPane, { 
    fragments: { 
    session:() => Relay.QL` 
     fragment on Session { 
     teams { 
      id 
      ${FloatingDiscussionPaneDiscussion.getFragment('team')} 
     } 
     } 
    `, 
    }, 
}); 

而且每个窗格可以消耗的那些消息,并显示它们:

class FloatingDiscussionPaneDiscussion extends React.Component { 
    render() { 
    const {team: {messages}} = this.props; 
    return (
     <ul> 
     {messages.map(({id, text, sender: {name: senderName}}) => 
      <li key={id}>{senderName}: {text}</li> 
     )} 
     </ul> 
    ); 
    } 
}; 

export default Relay.createContainer(FloatingDiscussionPaneDiscussion, { 
    fragments: { 
    team:() => Relay.QL` 
     fragment on Team { 
     messages { 
      id 
      recipient { name } 
      sender { name } 
      text 
     } 
     } 
    `, 
    }, 
}); 
+0

上面的组件层次结构是有点粗糙。您可能会想打破它自己的,这样你有一个应用程序,一个团队,一个讨论和消息组件,片段树的每个拥有它自己的一小部分。 – steveluscher