路由的事件

事件这个词在前端出现的频率真是高,根本拦不住,哪都是.$route服务在路由过程中的每个阶段都会触发不同的事件,可以为这些不同的路由事件设置监听器并做出响应.

一共有4个事件用来监听路由的状态变化: $routeStartChange, $routeChangeSuccess, $routeChangeError, $routeUpdate.

其中最常用的是前两个,这里稍微解释一下.

(1) $routeStartChange

看名字就能猜出来它表示的是路由开始变化的事件,在浏览器地址栏发生变化之前AngularJS会先广播一下这个事件.路由会开始加载所有需要的依赖,模板和resolve部分的内容也会注入.

1
2
3
4
5
6
angular.module('myApp', [])
  .run(['$rootScope''$location'function($rootScope, $location){
    $rootScope.$on('$routeChangeStart'function(evt, next, current){
    console.log('route begin change');
  }); 
}]);

解释一下事件的参数,evt是事件对象,可以从中读取到一些route的信息.next是将要导航到的路由,current是当前的URL.

可以看见在这个时期我们可以做很多有用的事,因为此时仅仅是路由开始变化,对应的内容都还没来得及发生改变.这里我们可进行permission的校验,loading画面的加载,对应路由信息的读取等等.

(2) $routeChangeSuccess

在路由的所有依赖都被注入加载后,AngularJS会对外广播路由跳转成功的事件.

1
2
3
4
5
6
angular.module('myApp', [])
  .run(['$rootScope''$location'function($rootScope, $location) {
    $rootScope.$on('$routeChangeSuccess'function(evt, current, previous) {
      console.log('route have already changed');
    }); 
}])

这里也稍微解释下三个参数,evt是AngularJS事件对象,current是当前所处路由,previous是上一个路由.

剩下两个不太常用的事件,大家去看官方API说明吧,这里不介绍了

----------------------------------------------------------------------

  • $emit只能向parent controller传递event与data( $emit(name, args) )
  • $broadcast只能向child controller传递event与data( $broadcast(name, args) )
  • $on用于接收event与data( $on(name, listener) )
 

本节课程源码:

1
2
3
4
5
6
7
8
9
10
     
<div ng-controller="ParentCtrl">              <!--父级-->
  <div ng-controller="SelfCtrl">              <!--自己-->
    <a ng-click="click()">click me</a>
    <div ng-controller="ChildCtrl"></div>     <!--子级-->
  </div>
  <div ng-controller="BroCtrl"></div>         <!--平级-->
</div>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
var app = angular.module('myApp', []);
app.controller('SelfCtrl', function($scope) {
  $scope.click = function () {
    $scope.$broadcast('to-child', 'child');
    $scope.$emit('to-parent', 'parent');
  }
});
 
app.controller('ParentCtrl', function($scope) {
  $scope.$on('to-parent', function(event,data) {
    console.log('ParentCtrl', data);       //父级能得到值
  });
  $scope.$on('to-child', function(event,data) {
    console.log('ParentCtrl', data);       //子级得不到值
  });
});
 
app.controller('ChildCtrl', function($scope){
  $scope.$on('to-child', function(event,data) {
    console.log('ChildCtrl', data);      //子级能得到值
  });
  $scope.$on('to-parent', function(event,data) {
    console.log('ChildCtrl', data);      //父级得不到值
  });
});
 
app.controller('BroCtrl', function($scope){
  $scope.$on('to-parent', function(event,data) {
    console.log('BroCtrl', data);         //平级得不到值
  });
  $scope.$on('to-child', function(event,data) {
    console.log('BroCtrl', data);         //平级得不到值
  });
});

在$on的方法中的event事件参数,其对象的属性和方法如下

事件属性 目的
event.targetScope 发出或者传播原始事件的作用域
event.currentScope 目前正在处理的事件的作用域
event.name 事件名称
event.stopPropagation() 一个防止事件进一步传播(冒泡/捕获)的函数(这只适用于使用`$emit`发出的事件)
event.preventDefault() 这个方法实际上不会做什么事,但是会设置`defaultPrevented`为true。直到事件监听器的实现者采取行动之前它才会检查`defaultPrevented`的值。
event.defaultPrevented 如果调用了`preventDefault`则为true

----------------------------------------------------------

父传($scope.$broadcast)子接收($scope.$on)
angular.module('myApp', [])
.controller('ParentCtrl', ['$scope', function($scope) {
$scope.message = "Child updated from parent controller";

$scope.clickFunction = function() {
$scope.$broadcast('update_parent_controller', $scope.message);
};
}
])
.controller('ChildCtrl', ['$scope', function($scope) {
$scope.message = "Some text in child controller";

$scope.$on("update_parent_controller", function(event, message) {
$scope.message = message;
});
}
]);

Here a plunker for a live demo.

Instead, if it need to send data from the SecondController (child) to the FirstController (parent), it should use the $emit method.
Here the javascript code:
子传($scope.$emit)父接收($scope.$on)
angular.module('myApp', [])
.controller('ParentCtrl', ['$scope', function ($scope) {
$scope.message = "Some text in parent";
$scope.$on("update_parent_controller", function(event, message){
$scope.message = message;
});

}])
.controller('ChildCtrl', ['$scope', function ($scope) {
$scope.clickFunction = function() {
$scope.message = "Parent updated";

$scope.$emit('update_parent_controller', $scope.message);
}

}]);

Here a plunker for a live demo.

Finally, here a little trick where two controller have no parent/child relationship.
It should pass data from one controller through $rootScope and the $broadcast method.
Here the javascript code:
兄弟传($rootScope.$broadcast)兄弟接收($rootScope.$on)
angular.module('myApp', [])
.controller('FirstCtrl', ['$scope', '$rootScope', function($scope, $rootScope) {
$scope.message = "Clicked!";

$rootScope.clickFunction = function() {
$rootScope.$broadcast("Update", $scope.message);
};
}])
.controller('SecondCtrl', ['$scope','$rootScope', function($scope,$rootScope) {
$scope.message = "Waiting for a click...";

$rootScope.$on("Update", function(event, message) {
$scope.message = message;
});
}]);

Here a plunker for a live demo.

----------------------------------------------------------------------------------

发送消息: $scope.$emit(name, data) 或者 $scope.$broadcast(name, data);

接收消息: $scope.on(name,function(event,data){ });

区别: $emit 广播给父controller   $broadcast 广播给子controller

broadcast 是从发送者向他的子scope广播一个事件。

这里就是ParentController发送, ParentController 和 ChildController 会接受到, 而MainController是不会收到的

$emit 广播给父controller,父controller 是可以收到消息

$on 有两个参数function(event,msg)  第一个参数是事件对象,第二个参数是接收到消息信息

var app = angular.module('onBroadcastEvent', ['ng']);

app.controller('MainController', function($scope) {
$scope.$on('To-MainController', function(event,msg) {
console.log('MainController received:' + msg);
});
}); app.controller('ParentController', function($scope) {
$scope.click = function (msg) {
$scope.$emit('To-MainController',msg + ',from ParentController to MainController');
$scope.$broadcast('To-ChildController', msg + ',from ParentController to ChildController');
$scope.$broadcast('To-BrotherController', msg + ',from ParentController to BrotherController');
}
}); app.controller('ChildController', function($scope){
$scope.$on('To-ChildController', function(event,msg) {
console.log('ChildController received:' + msg);
});
}); app.controller('BrotherController', function($scope){
$scope.$on('To-BrotherController', function(event, msg) {
console.log('BrotherController received:' + msg);
});
});
 
 

angularJS 事件广播与接收[转]的更多相关文章

  1. AngularJS 事件广播与接收 $broadcast,$emit,$on 作用域间通信 封装factory服务 发布订阅

    不同作用域之间通过组合使用$broadcast,$emit,$on的事件广播机制来进行通信. 一.说明 1.广播 $broadcast 说明:将事件从父级作用域传播至本作用域及子级作用域. 格式:$b ...

  2. AngularJS 事件广播与接收 $emit $broadcast $on

    AngularJS中的作用域scope有一个非常有层次和嵌套分明的结构. 其中它们都有一个主要的$rootScope(也就说对应的Angular应用或者ng-app),然后其他所有的作用域部分都是继承 ...

  3. angularJS 事件广播与接收

    发送消息: $scope.$emit(name, data) 或者 $scope.$broadcast(name, data); 接收消息: $scope.on(name,function(event ...

  4. Angularjs中的事件广播 —全面解析$broadcast,$emit,$on

    Angularjs中不同作用域之间可以通过组合使用$broadcast,$emit,$on的事件广播机制来进行通信 介绍: $broadcast的作用是将事件从父级作用域传播至子级作用域,包括自己.格 ...

  5. node.js接收异步任务结果的两种方法----callback和事件广播

    事件广播 发送方调用emit方法,接收方调用on方法,无论发送方或是接收方,都会工作在一个频道 声明了一个模块,用于读取mime.json中的记录 var fs = require('fs'); va ...

  6. [spring源码学习]九、IOC源码-applicationEventMulticaster事件广播

    一.代码实例 回到第IOC的第七章context部分,我们看源码分析部分,可以看到在spring的bean加载之后的第二个重要的bean为applicationEventMulticaster,从字面 ...

  7. laravel 事件广播

    Laravel 5.1 之中新加入了事件广播的功能,作用是把服务器中触发的事件通过websocket服务通知客户端,也就是浏览器,客户端js根据接受到的事件,做出相应动作.本文会用简单的代码展示一个事 ...

  8. JS里关于事件的常被考察的知识点:事件流、事件广播、原生JS实现事件代理

    1.JS里面的事件流 DOM2级事件模型中规定了事件流的三个阶段:捕获阶段.目标阶段.冒泡阶段,低版本IE(IE8及以下版本)不支持捕获阶段 捕获事件流:Netscape提出的事件流,即事件由页面元素 ...

  9. Android的有序广播和无序广播(解决安卓8.0版本之后有序广播的接收问题)

    前言 Google从Android8.0版本开始,对在清单文件中静态注册广播做了限制. *** 特殊广播(动态注册广播接收者) 说:有序广播和无序广播之前,咱们先来说下Android中一些特殊的广播如 ...

随机推荐

  1. C#编程(二十六)----------泛型

    泛型 有了泛型,就可以创建独立于被包含类型的类和方法了.我们不必给不同的类型编写功能相同的许多方法或类,只创建一个方法或类即可. 另一个减少代码的选项是使用object类,但object类不是类型安全 ...

  2. 【python】python安装tensorflow报错:python No matching distribution found for tensorflow==1.12.0

    python安装tensorflow报错:python No matching distribution found for tensorflow==1.12.0 python版本是3.7.2 要安装 ...

  3. Robotframework(3):使用pycharm编写和运行RF脚本

    转自:http://blog.csdn.net/ccggaag/article/details/77529724 我们在使用Robotframework时,经常编写脚本的人或许会不习惯,不过没关系!我 ...

  4. 分布式系统唯一ID生成方案汇总 转

    系统唯一ID是我们在设计一个系统的时候常常会遇见的问题,也常常为这个问题而纠结.生成ID的方法有很多,适应不同的场景.需求以及性能要求.所以有些比较复杂的系统会有多个ID生成的策略.下面就介绍一些常见 ...

  5. iOS酷炫动画效果合集

    iOS酷炫动画效果合集 源码地址 https://github.com/YouXianMing/Animations 效果绝对酷炫,包含了多种多样的动画类型,如POP.Easing.粒子效果等等,虽然 ...

  6. 实用ExtJS教程100例-008:使用iframe填充ExtJS Window组件

    上面两节中我们分别演示了ExtJS Window的常用功能 和 如何最小化ExtJS Window组件,在这篇内容中我们来演示一下如何使用iframe填充window组件. 思路很简单,首先创建一个w ...

  7. 整理:FPGA选型

    针对性整理下FPGA选型问题 一.获取芯片资料: 要做芯片的选型,首先就是要对有可能要面对的芯片有整体的了解,也就是说要尽可能多的先获取芯片的资料.现在FPGA主要有4个生产厂家,ALTERA,XIL ...

  8. frp官方中文文档

    frp 是一个可用于内网穿透的高性能的反向代理应用,支持 tcp, udp, http, https 协议. 目录 frp 的作用 开发状态 架构 使用示例 通过 ssh 访问公司内网机器 通过自定义 ...

  9. FastReport.Net 入门

    任何一门编程技术入门体验都是以“Hello World”开始的,但我想再复杂一点的“Hello World”,才能算真正的入门.   FastReport.Net V1.2.76 ,vs2008 在 ...

  10. iOS开发-Instruments性能调优

    性能是苹果审核的一个很重要的部分,CPU,内存,图形绘制,存储空间和网络性能都是应用的重要的评估和组成部分.不管是作为个人应用开发者还是企业的开发人员,都需要遵循的一个原则是站在用户的角度去思考问题, ...