我們之所以要定義指令,目的是重用指令。假設有這么一個應用場景:在同一個html里使用了兩次my-directive,第一個my-directive要展示的是Hello World,第二個my-directive要展示的是Hello AngularJs。
為了實現上面的想法,一個做法是創建兩個控制器(因為控制器會創建子作用域,與外界隔離開),分別定義‘World’和‘AngularJs’輸出:
<!DOCTYPE html> <html> <head lang="en"> <meta charset="UTF-8"> <script src="../lib/angular-1.3.16/angular.min.js"></script> <script src=""></script> <title></title> <script language="JavaScript"> angular.module('app',[]) .controller('myController',function($scope){ $scope.greeting = 'World'; }) .controller('myController2',function($scope){ $scope.greeting = 'AngularJs'; }) .directive('myDirective',function(){ return{ template:'Hello {{greeting}}!' }; }); </script> </head> <body ng-app="app"> <div ng-controller="myController" my-directive></div> <div ng-controller="myController2" my-directive></div> </body> </html>
目的是達到了,但是做法顯得繁瑣,這樣的指令重用不夠簡潔。
最好的做法當然是類似下面的形式:
<div my-directive greeting="World"></div> <div my-directive greeting="AngularJs"></div>
怎么做到這一點呢?答案就是使用指令的scope參數,隔離指令的作用域:
<!DOCTYPE html> <html> <head lang="en"> <meta charset="UTF-8"> <script src="../lib/angular-1.3.16/angular.min.js"></script> <script src=""></script> <title></title> <script language="JavaScript"> angular.module('app',[]) .directive('myDirective',function(){ return{ template:'Hello {{greeting}}!', scope:{ greeting:'@' } }; }); </script> </head> <body ng-app="app"> <div my-directive greeting="World"></div> <div my-directive greeting="AngularJs"></div> </body> </html>
如果不希望屬性名還是greeting,想改個別名,可以這樣:
<!DOCTYPE html> <html> <head lang="en"> <meta charset="UTF-8"> <script src="../lib/angular-1.3.16/angular.min.js"></script> <script src=""></script> <title></title> <script language="JavaScript"> angular.module('app',[]) .directive('myDirective',function(){ return{ template:'Hello {{greeting}}!', scope:{ greeting:'@greet' } }; }); </script> </head> <body ng-app="app"> <div my-directive greet="World"></div> <div my-directive greet="AngularJs"></div> </body> </html>
注意template里還是使用的greeting,如果改為greet,就解析不出來了!
再看下面的代碼:
<!DOCTYPE html> <html> <head lang="en"> <meta charset="UTF-8"> <script src="../lib/angular-1.3.16/angular.min.js"></script> <script src=""></script> <title></title> <script language="JavaScript"> angular.module('app',[]) .directive('myDirective',function(){ return{ template:'Hello {{myGreet}}! ', scope:{ } }; }) .directive('myDirective2',function(){ return{ template:'Hello {{myGreet}}! ' }; }); </script> </head> <body ng-app="app"> <div ng-init="myGreet='World'"></div> <div my-directive></div> <div my-directive2></div> <div>Hello {{myGreet}}!</div> </body> </html>
在瀏覽器中查看:
Hello !
Hello World!
Hello World!
可見,指令里若添加了scope:{},不管給定的是空對象還是什么,都會隔離指令的作用域。
這使得上面例子里的my-directive指令無法解析myGreet,而未隔離作用域的my-directive2指令卻可以解析myGreet
下面簡單說明一下@=&三個符號的意義。
=不同於@,它綁定的是變量引用,例子:
<!DOCTYPE html> <html> <head lang="en"> <meta charset="UTF-8"> <script src="../lib/angular-1.3.16/angular.min.js"></script> <script src=""></script> <title></title> <script language="JavaScript"> angular.module('app',[]) .directive('myDirective',function(){ return{ template:'Hello {{greeting}}! ', scope:{ greeting:'=' } }; }); </script> </head> <body ng-app="app"> <div ng-init="greet='world'" my-directive greeting="greet"></div> </body> </html>
輸出:
Hello world!
如果=號改成@,那么輸出的就是“Hello greet!”了。
我就不愛用=,我非要用@,那也可以:
<!DOCTYPE html> <html> <head lang="en"> <meta charset="UTF-8"> <script src="../lib/angular-1.3.16/angular.min.js"></script> <script src=""></script> <title></title> <script language="JavaScript"> angular.module('app',[]) .directive('myDirective',function(){ return{ template:'Hello {{greeting}}! ', scope:{ greeting:'@' } }; }); </script> </head> <body ng-app="app"> <div ng-init="greet='world'" my-directive greeting="{{greet}}"></div> </body> </html>
輸出:
Hello world!
來個雙向綁定玩玩:
<input ng-model="greet"/> <div ng-init="greet='world'" my-directive greeting="greet"></div>
輸出:

符號&表示綁定一個函數:
<!DOCTYPE html> <html> <head lang="en"> <meta charset="UTF-8"> <script src="../lib/angular-1.3.16/angular.min.js"></script> <script src=""></script> <title></title> <script language="JavaScript"> angular.module('app',[]) .run(function($rootScope){ $rootScope.test = function(){ alert('ok'); }; }) .directive('myDirective',function(){ return{ template:'<button ng-click="greeting()">click me!</button>', scope:{ greeting:'&' } }; }); </script> </head> <body ng-app="app"> <div my-directive greeting="test()"></div> </body> </html>
注意在template里,函數名必須跟scope里定義的一致,都是greeting
