组件间通信:
龟兔赛跑-React组件间通信Demo:http://js.jirengu.com/yowec/edit
React的每一帧都是重绘,所以每一次数据变动,每个组件都会先重新计算一下自己的状态。
eventHub发布订阅模式:
定义:发布/订阅模式
订阅者把自己想订阅的事件注册到调度中心,当该事件触发时候,发布者发布该事件到调度中心(顺带上下文),由调度中心统一调度订阅者注册到调度中心的处理代码。
禁止组件直接修改数据。所有修改都应该由eventHub审核以后进行。
【初】子组件修改后发布事件的模式:
http://js.jirengu.com/jolox/50/edit?js,console,output
- 先看一下父组件AB的状态。父组件之间使用全局变量时,当子组件修改了全局变量后,父组件不会进行数据的更新。没有进行setState操作,数据不会被更新。
- 所以我们需要知道在哪里进行setState操作。简单的想法是:如果组件使用了这个数据,就需要告知一个管理员(这里是eventHub)
“我用了这个数据,如果修改它请告诉我”。(监听事件onEventListener) - 任何组件改变数据时,也要通知管理员eventHub:“我修改了这个数据,你告诉大家需要更新”。(triggerEvent)
-
这个模型中eventHub仅负责通知事项。
【进】子组件提请eventHub修改数据的模式:
http://js.jirengu.com/zovaz/40/edit?js,console,output
eventHub简单代码
// ---------- EventHub ---------- //
let fnLists={};
let eventHub = {
// 触发一个事件,将发布到所有监听这个事件的组件。
trigger(eventName, data){
// console.log("trigger "+eventName +". data="+data)
let fnList = fnLists[eventName];
if(!fnList) return false;
for(let i=0; i<fnList.length; i++){
fnList[i](data);
}
},
// 接受到一个事件被触发,则执行下面的代码。
on(eventName, fn){
// console.log("on "+eventName)
if(!fnLists[eventName]){
fnLists[eventName]=[]
}
fnLists[eventName].push(fn);
}
}