Lightning Application Event 实例:TODO 列表
Application Event
在 Lightning 框架中有两种事件:
- Component Event:组件事件
- Application Event:应用事件
Application Event 是一个典型的“观察者模式”的实现,它从某一个组件中发出,然后所有定义了其 handler 的组件都会被触发相应的函数。
在本文中我们以一个 TODO 列表的实例来阐述 Application Event 是如何工作的。
效果如下图:
实例功能
在实例中,我们可以让用户添加、修改、删除各种 TODO 项目,然后点击“保存”按钮进行保存。
假设在 Salesforce 中已经建立了 TODO 项目的数据模型,其中包括一个“内容”的字段。
实例结构
在实例中主要包括:
一个应用:
- AppEventExample_App:应用的入口
两个组件:
- AppEventExample_Main:主组件,包含了添加、保存按钮,以及各种 TODO 子组件
- AppEventExample_Input:TODO 子组件,用于输入或删除一个 TODO 项目
三个事件:
- AppEventExample_DeleteInput:用于删除某个 TODO 项目
- AppEventExample_GetInputs:用于从主组件中发送信号,让子组件开始发送其中的内容给主组件
- AppEventExample_SendInputs:用于从自组件中发送其内容
主要包括了三个功能:
添加一个 TODO 项目
在主组件中定义一个 “Aura.Component[]” 类型的属性,然后每次当用户点击“添加”按钮时,动态建立一个新的 TODO 子组件,添加到这个属性中,并显示在主组件中
删除一个 TODO 项目
所有的 TODO 项目都是由子组件来展示的。当需要删除一个子组件时,我们使用 AppEventExample_DeleteInput 事件来传递子组件的 id 值,然后在主组件中将相应的子组件删除掉
保存所有的 TODO 项目
这个功能是将所有 TODO 子组件中的内容都发送到主组件中,然后一起保存到后端。
它使用了两个事件。
首先,当用户点击“保存”按钮时,AppEventExample_GetInputs 事件被触发。这个事件不包含任何的参数,只是告诉各个子组件“现在要保存数据了,将你们的内容发送给我”。
当子组件收到这个信号之后,AppEventExample_SendInputs 事件被分别出发,每个子组件中的内容都被发送出来,由主组件进行接收并处理。
源代码
AppEventExample_DeleteInput
<aura:event type="APPLICATION">
<aura:attribute name="id" type="Integer" access="public" />
</aura:event>
在每个 TODO 组件中都有一个 id 属性,可以在删除某一行的时候指明这一行的 id 值。
AppEventExample_GetInputs
<aura:event type="APPLICATION" />
AppEventExample_SendInputs
<aura:event type="APPLICATION">
<aura:attribute name="content" type="String" access="public" />
</aura:event>
AppEventExample_Input
<aura:component >
<aura:attribute name="content" type="String" access="public" />
<aura:attribute name="id" type="Integer" access="public" />
<aura:registerEvent name="deleteInput" type="c:AppEventExample_DeleteInput" />
<aura:registerEvent name="AppEventExample_SendInputs" type="c:AppEventExample_SendInputs" />
<aura:handler event="c:AppEventExample_GetInputs" action="{!c.sendInput}" />
<tr>
<td>
<lightning:input label="" name="contentInput" value="{!v.content}" />
</td>
<td>
<lightning:button label="删除" onclick="{! c.deleteThis }" />
</td>
</tr>
</aura:component>
({
// 启用事件,发送 id 值,让主组件删除相应的子组件
deleteThis : function(component, event, helper) {
var appEvent = $A.get("e.c:AppEventExample_DeleteInput");
appEvent.setParams({
"id" : component.get('v.id')
});
appEvent.fire();
},
// 启用事件,将其中的内容发送出去
sendInput : function(component, event, helper) {
var appEvent = $A.get("e.c:AppEventExample_SendInputs");
appEvent.setParams({
"content" : component.get('v.content')
});
appEvent.fire();
},
})
AppEventExample_Main
<aura:component >
<aura:attribute name="inputs" type="Aura.Component[]" access="public" />
<aura:attribute name="nextId" type="Integer" access="public" default="1" />
<aura:attribute name="contentList" type="String[]" access="public" />
<aura:registerEvent name="AppEventExample_GetInputs" type="c:AppEventExample_GetInputs" />
<aura:handler event="c:AppEventExample_DeleteInput" action="{!c.deleteInput}" />
<aura:handler event="c:AppEventExample_SendInputs" action="{!c.receiveInput}" />
<lightning:button label="添加" onclick="{! c.addOne }" />
<lightning:button label="保存" onclick="{! c.save }" />
<table class="slds-table">
{!v.inputs}
</table>
</aura:component>
({
// 动态建立 TODO 项目的子组件
addOne : function(component, event, helper) {
var inputs = component.get('v.inputs');
var nextId = component.get('v.nextId');
$A.createComponent(
"c:AppEventExample_Input",
{
"id": nextId,
"content": ''
},
function(newComponent, status, errorMessage){
if (status === "SUCCESS") {
inputs.push(newComponent);
component.set('v.inputs', inputs);
component.set('v.nextId', nextId + 1);
}
}
);
},
// 接收 TODO 的子组件发送的 id 值,然后从 inputs 列表中删除相应的子组件
deleteInput : function(component, event, helper) {
var inputs = component.get('v.inputs');
var id = event.getParam('id');
var indexToRemove = -1;
for (var i = 0; i < inputs.length; i++) {
if (inputs[i].get('v.id') == id) {
indexToRemove = i;
break;
}
}
inputs.splice(i, 1);
component.set('v.inputs', inputs);
},
// 启用事件,然后收到子组件发送的内容,最后保存到后端
save : function(component, event, helper) {
var appEvent = $A.get("e.c:AppEventExample_GetInputs");
appEvent.fire();
// 为了演示方便,直接显示收到的所有内容
var contentList = component.get('v.contentList');
alert(contentList);
},
// 接收子组件发送的内容
receiveInput : function(component, event, helper) {
var content = event.getParam("content");
var contentList = component.get('v.contentList');
contentList.push(content);
component.set('v.contentList', contentList);
}
})
AppEventExample_App
<aura:application extends="force:slds">
<c:AppEventExample_Main />
</aura:application>