-
Notifications
You must be signed in to change notification settings - Fork 60
Message
TANG edited this page Dec 14, 2016
·
8 revisions
组件通信对解决复杂的交互也有很大的用处,sugar
支持冒泡通信(fire)、广播通信(broadcast)、一对一通信(notify) 和全局广播通信(globalCast) 4 种通信方式,这四种通信方式能解决大部分的组件通信需求。
消息的接收统一在组件内部用 on
+ 消息名称首字母大写的函数方法来接收(如:onMessage
)。
冒泡通信要求通信的组件之间是“父子关系”,消息由子组件发出,父组件接收,并且消息会“冒泡”到父组件的父组件:
var ComponentOne = sugar.Component.extend({
init: function (config) {
this.Super('init', config);
},
afterRender: function () {
// fire 会将消息发到父组件,以及父组件的父组件……
this.fire('msgFromOne', 123);
}
});
var ComponentTwo = sugar.Component.extend({
init: function (config) {
this.Super('init', config, {
view: '<SubComponent></SubComponent>',
childs: {
SubComponent: ComponentOne
}
});
},
// 该消息由 ComponentOne 发出
// 因为 ComponentTwo 是 ComponentOne 的父组件,所以能接收到冒泡消息
onMsgFromOne: function (msg) {
console.log(msg.param); // 123 消息参数
console.log(msg.type); // 'fire'
console.log(msg.count); // 1 消息被传递的次数
console.log(msg.from); // ComponentOne 实例,消息发送源
}
});
var ComponentThree = sugar.Component.extend({
init: function (config) {
this.Super('init', config, {
view: '<SubComponent></SubComponent>',
childs: {
SubComponent: ComponentTwo
}
});
},
// 该消息由 ComponentOne 发出
// 因为 ComponentThree 是 ComponentTwo 的父组件,所以也能接收到冒泡消息
onMsgFromOne: function (msg) {
console.log(msg.param); // 123 消息参数
console.log(msg.type); // 'fire'
console.log(msg.count); // 2 消息被传递的次数
console.log(msg.from); // ComponentOne 实例,消息发送源
}
});
广播通信也要求通信的组件之间是“父子关系”,但广播通信与冒泡通信的消息流动机制相反,消息由父组件发出,每个子组件接收,并且消息会广播到到每一个子组件的子组件:
var ComponentOne = sugar.Component.extend({
init: function (config) {
this.Super('init', config);
},
// 该消息由 ComponentThree 发出
// 因为 ComponentOne 是 ComponentTwo 的子组件,所以也能接收到广播消息
onMsgFromThree: function (msg) {
console.log(msg.param); // 456
console.log(msg.type); // 'broadcast'
}
});
var ComponentTwo = sugar.Component.extend({
init: function (config) {
this.Super('init', config, {
view: '<SubComponent></SubComponent>',
childs: {
SubComponent: ComponentOne
}
});
},
// 该消息由 ComponentThree 发出
// 因为 ComponentTwo 是 ComponentThree 的子组件,所以能接收到广播消息
onMsgFromThree: function (msg) {
console.log(msg.param); // 456
}
});
var ComponentThree = sugar.Component.extend({
init: function (config) {
this.Super('init', config, {
view: '<SubComponent></SubComponent>',
childs: {
SubComponent: ComponentTwo
}
});
},
afterRender: function () {
// broadcast 会将消息发到所有子组件,以及每个子组件的所有子组件……
this.broadcast('msgFromThree', 456);
}
});
冒泡和广播通信都要求通信组件之间是父子关系,而一对一通信 notify
则可用于任意两个有关系或没关系组件之间的通信。通信的依据是组件创建时的名称(同一层级的组件的名称是不允许重复的)
var SubComponent = sugar.Component.extend({
init: function (config) {
this.Super('init', config);
},
// 从 ComponentB 发来的消息
onMsgToSubComponent: function (msg) {
console.log(msg.param); // 456
}
});
var ComponentA = sugar.Component.extend({
init: function (config) {
config = this.cover(config, {
target: document.body,
view: '<Sub></Sub>',
childs: {
Sub: SubComponent
}
});
},
// 从 ComponentB 发来的消息
onMsgToComponentA: function (msg) {
console.log(msg.param); // 123
}
});
var compA = sugar.core.create('componentA', ComponentA);
var ComponentB = sugar.Component.extend({
init: function (config) {
this.Super('init', config);
},
afterRender: function () {
// 与 ComponentA 通信,'componentA' 是组件创建时的名称
this.notify('componentA', 'msgToComponentA', 123);
// 也可以传入组件实例进行通信:
// this.notify(compA, 'msgToComponentA', 123);
// 与 ComponentA 的子组件 SubComponent 通信
// 由于是 ComponentA 的子组件,所以需要指定组件的路径层级,用 . 分割
this.notify('componentA.Sub', 'msgToComponentA', 123);
// 也可以传实例进行通信:
// this.notify(compA.getChild('Sub'), 'msgToComponentA', 123);
}
});
顾名思义,全局广播通信是向所有组件发送消息,这个方法只挂载在 sugar.core
实例上(sugar.core
实际上是一个只有组件系统而没有视图的顶级模块实例)。一个使用场景比如用户的登入和登出状态发生了改变,可以很方便的使用 globalCast
来通知所有组件,从而更新组件内部对于登入和登出的数据和信息。
var user = 'Kobe';
sugar.core.globalCast('userLogin', user);
sugar.core.globalCast('userLogout', user);
上一篇:组件的嵌套
下一篇:完整 API