Freewind @ Thoughtworks scala java javascript dart 工具 编程实践 月结 math python english [comments admin] [feed]

(2013-01-01) 11.域对象

广告: 云梯:翻墙vpn (省10元) 土行孙:科研用户翻墙http proxy (有优惠)

原文:http://docs.angularjs.org/guide/scope

什么是域对象(Scopes)

scope用于指代程序的model,它是angularjs表达式的运行上下文。Scope使用了分层结构,与程序相应的DOM结构相似。Scope可以观察表达式,也可以传播事件。

Scope的特色

Scope as Data-Model

Scope是程序的controller和view之间的胶水。在模板linking阶段,directives会在scope上设置$watch表达式。$watch允许当属性变化时,directives会得到通知,因此可更新相应的DOM上的内容。

controller与directives都有到scope的引用,但它们两者之间没有引用。这么做让controller与directive与DOM之间都保持独立。这一点很重要,因为它让controllers没有绑死在代码中,大大方便了写测试用例。

Source

index.html

<!doctype html>
<html ng-app>
  <head>
    <script src="http://code.angularjs.org/angular-1.0.1.min.js"></script>
    <script src="script.js"></script>
  </head>
  <body>
    <div ng-controller="MyController">
      Your name:
        <input type="text" ng-model="username">
        <button ng-click='sayHello()'>greet</button>
      <hr>
      {{greeting}}
    </div>
  </body>
</html>

**script.js**

function MyController($scope) {
  $scope.username = 'World';

  $scope.sayHello = function() {
    $scope.greeting = 'Hello ' + $scope.username + '!';
  };
}

jsfiddle

在上面的例子中,请注意在`MyController`中,把`World`赋给了`username`。然后,scope将这次赋值通知了`input`,input中会显示新值。这里演示了controller如何把数据写入到scope中。

与之相似,controller也可以把行为赋给scope,比如那个`sayHello`方法,当用户点击了`greet`按钮时将会调用它。该方法会从scope中读取`username`属性,并新建了一个`greeting`属性。这里演示了HTML上的部件可以自动更新scope上的属性。

逻辑上,`{{greeting}}`的渲染涉及到:

Scopes and Directives

在编译阶段,编译器从DOM模板中来匹配directives。这些directives通常会被归到两类中:

当外部事件(例如用户操作,timer或者XHR)到达了,相关联的表达式必须使用$apply方法把它们应用到scope中,才能让所有的监听器(listener)正确的更新。

会创建scope的directives

在大多数情况下,directives和scopes互相作用,但不创建新的scope实例。但是,某些directives,比如ng-controllerng-repeat,会创建新的scope并把它们关联到相应的DOM上。

你可以从任意的DOM元素上使用angular.element(aDomElement).scope()方法,来取得相应的scope。

Controllers and Scopes

在以下情况,scopes和controllers互相作用:

详情参考ng-controller

Scope $watch 的性能考虑

在angularjs中,当属性变化时,对scope进行“脏数据”检查是一件很常见的操作,因此该检查必须很高效。注意在检查中,不要进行任何的DOM访问,因为DOM访问要比JavaScript对象访问慢上几个数量级。

comments powered by Disqus