文章出處

前言:

  昨日周六,再登梧桐山。六點半,起。未到頂,雨紛飛。冒雨行,終封頂,只為合照一張。五點半,下山行。聆聽大自然的律動,雙腿隨其自然而顫抖!今早起,我的雙腿猶如叛逆期的少年,或如領家的孩童,遂決定今天宅一天,為打發閑暇時光,寫篇博文。

為什么要用directive?

  ng的directive從字面上理解就是ng框架的一個指令。

  假如我們發現要寫很多公共或是重用的dom、class、attr屬性或是需要操作scope作用域,就要考慮代碼最好不要copy、不要出現重復的代碼段,好像是哪位大牛說的話,具體記不清了,反正就是為了性能優化等方面。

  說的更專業點就是:

  1. 使你的html更具語義化,不需要深入研究代碼和邏輯即可知道頁面的大致邏輯。
  2. 抽象一個自定義組件,在其他地方進行重用。

直接上代碼:

<!DOCTYPE html>
<html ng-app="nick">
<head>
  <meta charset="UTF-8">
  <title>nick directive</title>
</head>
<body>
<hi></hi>
<script src="http://apps.bdimg.com/libs/angular.js/1.4.6/angular.min.js"></script>
<script>
  var myModule = angular.module('nick',[]);
  myModule.directive('hi', function() {
    return {
      template: '<p>my name is nick</p>',
      replace: true,
      restrict: 'E',
    };
  });
</script>
</body>
</html>

這就是我們常用的最簡單的寫法,其實有2種寫法。

寫法一:return寫法(常用

 var myModule = angular.module();
  myModule.directive('directiveName', function() {
    return {
        //內容
    };
  });

寫法二:定義js域

var myModule = angular.module();
  myModule.directive('directiveName', function() {
     var myObj={
        //內容
    };
    return myObj;
  });

一般我們都是用第一種寫法,下面以寫法一為例:

var myModule = angular.module();
  myModule.directive('directiveName', function() {
    return {
      priority: 0,
      template: '<p>nick</p>',
      templateUrl: 'nick.html',
      replace: true,
      transclude: true,
      restrict: 'E',
      scope: false,
      controller:'someController',
      controllerAs:'mainController',
      compile: function compile(meElement, meAttrs, transclude) {
        return {
          pre: function preLink(scope, iElement, iAttrs, controller) {},
          post: function postLink(scope, iElement, iAttrs, controller) { }
        }
      },
      link: function postLink(scope, iElement, iAttrs) { }
    };
  });

這是我總結出目前directive最全的參數了。下面對參數進行一一介紹:

directiveName

  自定義directive指令的名字,應該做到見名知義,方便調用。

priority

  (Number),可選參數(作為了解,使用幾率極小)指明指令的優先級,當有多個directive定義在同一個DOM元素時,有時需要明確它們的執行順序。這屬性用于在directive的compile function調用之前進行排序。如果優先級相同,則執行順序是不確定的(經初步試驗,優先級高的先執行,同級時按照類似棧的“后綁定先執行”。另外,測試時有點不小心,在定義directive的時候,兩次定義了一個相同名稱的directive,但執行結果發現,compile或者link都執行)。

restrict

  (String)可選參數,指明指令在DOM的聲明形式;

  取值:

  1. E(DOM元素)
  2. A(attr屬性)
  3. C(class類)
  4. M(注釋)

  默認值為A;可以多個一起用,如EA.表示即可以是元素也可以是屬性。

template(template和templateUrl二選一)

  (Sting或Function) 可選參數,如果replace為true,則將模版內容替換當前的HTML元素,并將原來元素的屬性、class一并遷移;如果為false,則將模版元素當作當前元素的子元素處理。  

寫法一:(Sting)

<!DOCTYPE html>
<html ng-app="nick">
<head>
  <meta charset="UTF-8">
  <title>nick directive</title>
</head>
<body>
<hi></hi>
<script src="http://apps.bdimg.com/libs/angular.js/1.4.6/angular.min.js"></script>
<script>
  var myModule = angular.module('nick',[]);
  myModule.directive('hi', function() {
    return {
      restrict: 'E',
      template: '<div><h1>Hi nick</h1></div>',
      replace: true
    };
  });
</script>
</body>
</html>

寫法二:(Fucntion)

<!DOCTYPE html>
<html ng-app="nick">
<head>
  <meta charset="UTF-8">
  <title>nick directive</title>
</head>
<body>
<hi1></hi1>
<hi2 title = 'directive2'></hi2>
<script src="http://apps.bdimg.com/libs/angular.js/1.4.6/angular.min.js"></script>
<script>
  var myModule = angular.module('nick',[]);
  myModule.directive('hi1', function() {
    return {
      restrict: 'E',
      template: '<div><h1>Hi nick</h1></div>',
      replace: true
    };
  });
  myModule.directive("hi2",function(){
    return{
      restrict:'E',
      template: function(tElement,tAttrs){
        var _html = '';
        _html += '<div>' +'hello '+tAttrs.title+'</div>';
        return _html;
      }
    };
  });
</script>
</body>
</html>

雖然寫法一為常用寫法,但是寫法二也應該了解。親們,發現了么?寫法二使用到了html中hi2標簽的title屬性。

templateUrl(template和templateUrl二選一)

  (Sting或Function) 可選參數,如果replace為true,則將模版內容替換當前的HTML元素,并將原來元素的屬性、class一并遷移;如果為false,則將模版元素當作當前元素的子元素處理。但模版通過指定的url進行加載。因為模版加載是異步的,所以compilation、linking都會暫停,等待加載完畢后再執行。

注意:

  在本地開發時候,需要運行一個服務器,不然使用templateUrl會報錯 Cross Origin Request Script(CORS)錯誤。由于加載html模板是通過異步加載的,若加載大量的模板會拖慢網站的速度,這里有個技巧,就是先緩存模板你可以再你的index頁面加載好后,將下列代碼作為你頁面的一部分包含在里面。

<!DOCTYPE html>
<html ng-app="nick">
<head>
  <meta charset="UTF-8">
  <title>nick directive</title>
</head>
<body>
<hi></hi>
<script src="http://apps.bdimg.com/libs/jquery/2.1.1/jquery.min.js"></script>
<script src="http://apps.bdimg.com/libs/angular.js/1.4.6/angular.min.js"></script>
<script type="text/javascript">
  var app = angular.module('nick', []);
  app.directive('hi', function() {
    return {
      restrict: 'E',
      templateUrl: 'hi.html',
      replace: true
    };
  });
</script>
<script type='text/ng-template' id='hi.html'>
  <div><h1>Hi nick</h1></div>
</script>
</body>
</html>

replace

  (Boolean),默認值為false,設置為true時候,hi這個標簽不在了,反之,則存在。這里比較簡單,就不上代碼了。

scope

  1. false(默認值):表示繼承父作用域。
  2. true:表示繼承父作用域,并創建自己的作用域(子作用域);如果在同一個元素中有多個directive需要新的scope的話,它還是只會創建一個scope。新的作用域規則不適用于根模版(root of the template),因此根模版往往會獲得一個新的scope。
  3. {}:表示創建一個全新的隔離作用域;這對于創建可復用的組件是很有幫助的,可以有效防止讀取或者修改父級scope的數據。這個獨立的scope會創建一個擁有一組來源于父scope的本地scope屬性的object hash。

結語:

  scope是一個重點,也是坑出現最多的地方,我將在后面的博文中總結寫我的理解!

現在補上scope作用域的總結!

  還有controller、controllerAs、compile、link,可以看看這篇博客!

以上便是我對ng directive的理解,如有不當或許補充的地方,望各位多多評論、不吝賜教!

 


文章列表


不含病毒。www.avast.com
arrow
arrow
    全站熱搜
    創作者介紹
    創作者 大師兄 的頭像
    大師兄

    IT工程師數位筆記本

    大師兄 發表在 痞客邦 留言(0) 人氣()