[关闭]
@xiaoqq 2016-08-03T12:09:09.000000Z 字数 5114 阅读 1030

AngularJS学习笔记——问题

AngularJS


一、 深入作用域

$scope是Scope类的实例。

  1. var HelloCtrl = function($scope){
  2. $scope.name = "world";
  3. }

Q: 上述代码中的$scope从何而来呢?
A: ng-controller会调用scope对象的$new()方法创建新的作用域$scope;

其实说白了,$scope和javascript继承机制是一样的,只不过绑定了ng-model的控件在输入的时候会自动创建一个新的属性。

二、 AngularJS问题

  1. ng-if跟ng-show/hide的区别有哪些?
    第一点区别是,ng-if 在后面表达式为 true 的时候才创建这个 dom 节点,ng-show是初始时就创建了,用 display:block 和 display:none 来控制显示和不显示。
    第二点区别是,ng-if 会(隐式地)产生新作用域,ng-switch 、 ng-include等会动态创建一块界面的也是如此。

  2. ng-repeat迭代数组的时候,如果数组中有相同值,会有什么问题,如何解决?
    会提示 Duplicates in a repeater are not allowed. 加 track by $index 可解决。当然,也可以 trace by 任何一个普通的值,只要能唯一性标识数组中的每一项即可(建立 dom 和数据之间的关联)。

  3. ng-click中写的表达式,能使用JS原生对象上的方法,比如Math.max之类的吗?为什么?
    不可以。只要是在页面中,就不能直接调用原生的 JS 方法,因为这些并不存在于与页面对应的 Controller 的 $scope 中。除非在 $scope 中添加了这个函数。

  4. {{now | 'yyyy-MM-dd'}}这种表达式里面,竖线和后面的参数通过什么方式可以自定义?

    1. app.filter('过滤器名称',function(){
    2. return function(需要过滤的对象, 过滤器参数1, 过滤器参数2, ...){
    3. //...做一些事情
    4. return 处理后的对象;
    5. }
    6. });

    使用方式:直接放在页面中或者放在js中$filter('date')(now, 'yyyy-MM-dd hh:mm:ss');

  5. factory和service,provider是什么关系?
    factory 把 service 的方法和数据放在一个对象里,并返回这个对象;service 通过构造函数方式创建 service,返回一个实例化对象;provider 创建一个可通过 config 配置的 service。

    从底层实现上来看,service 调用了 factory,返回其实例;factory 调用了 provider,将其定义的内容放在 $get 中返回。factory 和 service 功能类似,只不过 factory 是普通 function,可以返回任何东西(return 的都可以被访问,所以那些私有变量怎么写你懂的);service 是构造器,可以不返回(绑定到 this 的都可以被访问);provider 是加强版 factory,返回一个可配置的 factory。

三、 AngularJS中的Promise

  1. 创建一个promise
    首先,需要把$q服务注入到想要使用它的对象中。
    其次,调用defer()方法,创建一个deferred对象,
  1. var deferred = $q.defer();

deferred对象暴露了三个方法resolve、reject和notify
notify:这个方法用promise的执行状态来进行响应,如果要从promise返回一个状态,可以使用notify()函数来传送它。

  1. 链式请求

四、 AngularJS中的依赖注入

依赖注入(Dependency Injection)是一种软件设计模式,用来处理代码的依赖关系

每一个AngularJS应用都有一个注入器(injector)用来处理依赖的创建。注入器是一个负责查找和创建依赖的服务定位器。
下面是使用注入器服务的例子:

  1. angular.module('myApp', []).
  2. // Teach the injector how to build a 'greeter'
  3. // Notice that greeter itself is dependent on '$window'
  4. factory('greeter', function($window) {
  5. // This is a factory function, and is responsible for
  6. // creating the 'greet' service.
  7. return {
  8. greet: function(text) {
  9. $window.alert(text);
  10. }
  11. };
  12. }).
  13. // New injector is created from the module.
  14. // (This is usually done automatically by angular bootstrap)
  15. var injector = angular.injector(['ng','myApp']);
  16. // Request any dependency from the injector
  17. var greeter = injector.get('greeter');

注入器怎么知道需要注入什么依赖呢?

  1. 推断依赖
    假设函数名就是参数的名字

    1. function MyController($scope, greeter) {
    2. ...
    3. }
  2. $inject 标记
    要允许压缩类库重命名函数参数,同时注入器又能正确处理依赖的话,函数需要使用$inject属性。这个属性是一个包含依赖的名称的数组。

    1. var MyController = function(renamed$scope, renamedGreeter) {
    2. ...
    3. };
    4. MyController.$inject = ['$scope', 'greeter'];
  3. 行内标记

    1. someModule.factory('greeter', ['$window', function(renamed$window) {
    2. ...;
    3. }]);

六、Angular代码结构

  1. 1~1497行,定义各种工具函数,主要包括bind, copy, forEach, equals, isArray, isString uppercase, merge, extend等等,这些函数会在publishExternalAPI函数中被绑定在Angular全局中,可以通过angular.来进行访问;

  2. 1498~1787行,定义Angular初始化函数,首先是angularInit函数,文档加载完毕后,这个函数作为初始化的入口,接着调用bootstrap函数,在doBootstrap函数中,会创建注射器,加载module,对Angular中的Service进行实例化;

  3. 1788~1983行,定义bindJQuery函数和其他函数,没啥好说的;

  4. 1984~2660行,定义了加载Module函数,首先执行publishExternalAPI函数,挂载程序开头定义的工具函数,并且调用setupModuleLoader函数,生成angularModule,并加载provider和directive;在生成模型的过程中,会将controller、service、directive等放入_invokeQueue中,等在初始化的时候才真正执行,实现懒加载;

  5. 2661~3835行,定义$$jqLiteProvider,对jqLite进行增强;

  6. 3836~4742行,定义了注射器injector,在bootstrap时候,会调用createInjector函数,这个函数中会创建providerCache, providerInjector, instanceCache, instanceInjector四个变量,通过这四个变量来实现Service的单例模式、和依赖注入;此外,createInjector内部函数还定义了provider, factory, service, value等函数,这些函数会被挂载到module上,通过这些函数可以创建Service;最后,通过调用内部的loadModules函数加载module;

  7. 4743~5168行,定义了$AnchorScrollProvider服务,实现页面锚点跳转;
  8. 5169~5909行,定义了$AnimateProvider动画服务,依赖于ngAnimateModule;
  9. 5910~6270行,定义了$BrowserProvider服务,生成浏览器对象模型$browser
  10. 6271~6672行,定义了$CacheFactoryProvider$TemplateCacheProvider服务,主要用来创建$cacheFactory

  11. 6673~10095行,定义了$CompileProvider服务,提供注册directivecomponent的函数,提供compile函数;

  12. 10096~10262行,定义了$ControllerProvider服务,被Angular用来创建新的controller;

  13. 10263~10294行,定义了$DocumentProvider服务,包裹window.document对象;
  14. 10295~10344行,定义了$ExceptionHandlerProvider服务,返回$exceptionHandler对象,Any uncaught exception in angular expressions is delegated to this service;
  15. 10345~10367行,定义了$$ForceReflowProvider服务,返回啥,我也母鸡啊;

  16. 10368~11949行,主要是定义了$HttpProvider服务,返回$http对象,这是Angular中获取http请求的核心方法;

  17. 11950~12341行,定义了$InterpolateProvider服务,返回$interpolateProvider对象,主要用来自定义markup标记;
  18. 12342~12540行,定义了$IntervalProvider服务,返回$interval对象,包裹window.setInterval函数;$interval返回的对象是一个promise;
  19. 12541~13550行,主要定义了$LocationProvider服务,返回$location对象,主要用来解析浏览器地址栏的URL;
  20. 13551~13713行,定义了$LogProvider服务,打日志用的;

  21. 13714~15850行,定义了$ParseProvider词法解析器服务,好高深,存下来看;

  22. 15851~16474行,定义了$QProvider服务,实现了Angular中的promise;

  23. 16475~17849行,定义了$RootScopeProvider服务,返回$rootScope对象,所有的子$scope都可以通过其中的createChildScopeClass函数来进行创建,并且实现原型式继承;$rootScope是通过Scope构造函数创建,具有$new, $watch, $digest, $destroy, $apply, $on, $emit, $broadcast等函数;

  24. 17850~19000行,定义了$SceDelegateProvider$SceDelegateProvider服务,提供 Strict Contextual Escaping(严格上下文隔离),
  25. 19001~19091行,定义了$SnifferProvider服务,返回$sniffer,网络嗅探器;
  26. 19092~19606行,定义了$TemplateRequestProvider, $TimeoutProvider$WindowProvider等服务;

  27. 19607~21558行,定义了$FilterProvider服务和相关的过滤器,$filterProvider通过register方法注册filter,(其实本质上调用的是$provider.factory方法);该服务返回$filter对象;Angular中注册了currency, date, filter, json, limitTo, lowercase, number, orderBy, uppercase等过滤器;

  28. 21559~31302行,定义了各种Directive,//TODO 指令太多,以后再写
添加新批注
在作者公开此批注前,只有你和作者可见。
回复批注