1. 程式人生 > >AngularJS中ng-repeat渲染完成事件和中間變數的引用

AngularJS中ng-repeat渲染完成事件和中間變數的引用

ng-repeat渲染完成事件

因為在用AngularJS期間, 經常用到ng-repeat, 而有時需要在其渲染完成時操作已經渲染的物件, 所以特在此記錄一下新增渲染事件的方法, 以方便以後的使用;

程式碼如下

myApp.directive('onRepeatFinishedRender', function ($timeout) {
  return {
    restrict: 'A',
    link: function (scope, element, attr) {
      if (scope.$last === true) {
        $timeout(function
()
{ //這裡element, 就是ng-repeat渲染的最後一個元素 scope.$emit('ngRepeatFinished', element); }); } } }; });

這其實是一個指令, 像使用一般指令一樣使用就行了, 因為這裡設定restrict為"A", 所以只能作為屬性插入, 另外, 向回撥函式傳入element元素, 是為了方便區分多個使用此指令的元素, 比如有兩個地方使用, 程式碼如下

<ul repeat-id="r1">
  <li ng-repeat="p in persons track by $index"
on-repeat-finished-render>
{{p}}</li> </ul> <ul repeat-id="r2"> <li ng-repeat="a in animates track by $index" on-repeat-finished-render>{{a}}</li> </ul> <script> myApp.controller('userCtrl', function ($scope) { $scope.$on("ngRepeatFinished", function (repeatFinishedEvent, element
)
{ var repeatId = element.parent().attr("repeat-id"); switch (repeatId){ case "r1": //repeat-id為r1的ul, repeat渲染完成 break; case "r2": //repeat-id為r2的ul, repeat渲染完成 break; } }) });
</script>

中間變數的引用

另外還有一個要用到的, 就是在用filter等的時候, 有時需要用一箇中間變數引用filter後的陣列, 方便在html中使用, 比如, 我需要在將persons中的資料, 按照'sort'屬性排列, 並且需要在repeat元素內需要訪問排序後的陣列, 可以這麼做

<ul>
  <li ng-repeat="p in ps=(persons|orderBy:'sort') track by $index" ng-click="upOne(ps, index, $first)">{{p.name}}</li>
</ul>
<script>
  myApp.controller('userCtrl', function ($scope) {
    //這裡傳過來就是排序後的陣列
    //此函式的作用就是, 點選元素後, 將當前點選的元素和其上面的元素交換位置
    $scope.upOne = function (arr, index, first){
      if(!first){
        var tmp = arr[index].sort;
        arr[index].sort = arr[index-1].sort;
        arr[index-1].sort = tmp;
      }
    }
  });
</script>

綜合例項

下面是一個完整的例子點選下載, 可以通過點選右側按鈕, 進行上移或下移進行排序, 大家可以測試一下

<!DOCTYPE html>
<html>
  <head>
    <meta charset="UTF-8">
    <script src="http://apps.bdimg.com/libs/angular.js/1.3.9/angular.min.js"></script>
    <style>
      table{width:600px; margin: auto; border: none; border-padding:0; border-spacing: 0;}
      table td{text-align: center;}
      table td .button{cursor: pointer; color: #571d00; font-weight: bold;}
      table tr{height: 2.5em; vertical-align: middle;}
      table tbody tr:nth-child(2n+1){background-color: #f0f0f0;}
      table tbody tr:nth-child(2n){background-color: #f0e0ff;}
    </style>
  </head>
  <body ng-app="myApp" ng-controller="userCtrl">
    <table>
      <thead>
        <tr>
          <th>索引</th><th>學號</th><th>姓名</th><th>性別</th><th>年齡</th><th>操作</th>
        </tr>
      </thead>
      <tbody repeat-id="r0">
        <tr ng-repeat="(si,stu) in students=(persons|orderBy:'sort') track by $index" on-repeat-finished-render>
          <td>{{si+1}}</td>
          <td>{{stu.id}}</td>
          <td>{{stu.name}}</td>
          <td>{{stu.gender}}</td>
          <td>{{stu.age}}</td>
          <td>
            <span class="button" ng-click="changeSort(students, si, -1, 'sort')" ng-if="!$first">上移</span>
            <span class="split" ng-if="!$first&&!$last"></span>
            <span class="button" ng-click="changeSort(students, si, 1, 'sort')" ng-if="!$last">下移</span>
          </td>
        </tr>
      </tbody>
    </table>
    <script>
      var myApp = angular.module('myApp', []);
      myApp.directive('onRepeatFinishedRender', function ($timeout) {
        return {
          restrict: 'A',
          link: function (scope, element, attr) {
            if (scope.$last === true) {
              $timeout(function () {
                scope.$emit('ngRepeatFinished', element);
              });
            }
          }
        };
      });
      myApp.controller('userCtrl', function ($scope, $http) {
        $scope.persons = [{
          id: "161112001",
          sort: 0,
          name: "趙子龍",
          gender: "男",
          age: "18"
        }, {
          id: "161112002",
          sort: 2,
          name: "呂布",
          gender: "男",
          age: "18"
        }, {
          id: "161112003",
          sort: 1,
          name: "貂蟬",
          gender: "女",
          age: "18"
        }, {
          id: "161112004",
          sort: 3,
          name: "孫尚香",
          gender: "女",
          age: "18"
        }];
        $scope.changeSort = function (arr, index, up, attr) {
          var temp;
          temp = arr[index].sort;
          arr[index][attr] = arr[index + up][attr];
          arr[index + up][attr] = temp;
          return false;
        };
        $scope.$on("ngRepeatFinished", function (repeatFinishedEvent, element){
          console.log(element.parent().attr("repeat-id"));
        })
      })
    </script>
  </body>
</html>


文/jicemoon(簡書作者)
原文連結:http://www.jianshu.com/p/4ead962e9dac
著作權歸作者所有,轉載請聯絡作者獲得授權,並標註“簡書作者”。

源引:http://www.jianshu.com/p/4ead962e9dac

相關推薦

AngularJSng-repeat渲染完成事件中間變數引用

ng-repeat渲染完成事件 因為在用AngularJS期間, 經常用到ng-repeat, 而有時需要在其渲染完成時操作已經渲染的物件, 所以特在此記錄一下新增渲染事件的方法, 以方便以後的使用; 程式碼如下 myApp.directive('onRepeatFin

AngularJS監聽ng-repeat渲染完成事件

1.在html,加上on-finish-render-filters="completeRepeat" <li ng-repeat="categorie in result.categories" ng-click="clickCategory($index,cate

angularJs監聽ng-repeat渲染完成

監聽ng-repeat渲染完成有兩種方法 一、最實用的方法: <ul class="pprt_content"> <li ng-repeat="src in i

利用angular指令監聽ng-repeat渲染完成後執行函式

很多時候,我們需要在ng-repeat渲染完成後再對其進行操作,那麼怎麼知道什麼時候渲染完成呢?今天工作中就遇到了這個問題,在網上查了一下,感謝大神的無私分享,整理了一下,加深記憶1.在ng-repea

AngularJSng-repeat使用心得

ng-repeat這樣類似的指令是會建立一個新的作用域的,並且建立的新的作用域是原型繼承的。這點其實和我的一篇《AngularUI之Modal的子作用域研究 》類似,這次我也對指令的子作用域進行了研究,發現他們的建立子作用的方式是一樣的。 下面是我的實驗程式碼

AngularJSng-include指令實現頭部尾部的共用

在使用AngularJS的時候,我們可以使用ng-include指令實現頁面頭部和尾部的共用,。不過在使用ng-include指令的時候也是需要注意一些細節的。就是共用的頭部和尾部的路徑在ng-include中寫法 <!DOCTYPE html> <htm

解決AngularJSng-repeat不更新檢視的問題

最近寫AngularJS專案中,遇到一個問題,先對陣列進行賦值,ng--repeat正常工作,然後對陣列進行修改,ng-repeat似乎沒有工作,檢視沒有更新。 原因是ng-repeat會已預設值排序,由於我的陣列中的元素有重複,所以ng-repeat沒有對重複的元素進行

Angularjsng-repeat與移動端滑動外掛iScroll的衝突

IScroll是在移動端開發的過程中會經常使用到的一個外掛,但當其與angularjs中的ng-repeat指令配合使用時,很有可能會導致iScroll外掛失效或者滑動不正常,另外當ng-repeat迴圈的列表動態增加時也會導致滑動不正常。 滑動不正常原因:

AngularJS ng-repeat 排序後的 $index變化

“有客戶投訴,說在刪除指定的某條記錄時,結果刪掉的卻是另外一條記錄!” 看起來是個很嚴重的BUG。 有一次我們在工作中碰到了這個問題。 要定位這個BUG非常麻煩, 因為客戶也不清楚如何重現這個問題。 後來發現這個Bug是由於在 ng-repeat 中使用了 $inde

angularJsng-repeat遍歷動態生成的表單元素繫結ng-model無效的問題

  我在做練習中偶然遇到這個問題,與大家分享一下。我也是剛開始接觸angularJs,相信也有人同樣遇到過。   問題描述:在使用anjularJs框架核心模組ng雙向資料繫結,在ng-repeat遍歷物件或陣列的時候,用ng-model繫結動態生成表單元素時,利用$sco

利用angular指令監聽ng-repeat渲染完成後執行指令碼

業務中有時需要在非同步獲取資料並用ng-repeat遍歷渲染完頁面後執行某個操作,angular本身並沒有提供監聽ng-repeat渲染完成的指令,所以需要自己動手寫。有經驗的同學都應該知道,在ng-repeat模板例項內部會暴露出一些特殊屬性$index/$first/$middle/$last/$o

關於AngularJSng-repeat問題(問卷遍歷問題)

option_val = [];         var count = 0;         $scope.submitText = function () {             var type = document.getElementsByTagName("input");          

AngularJSng-repeat迴圈如何獲得被迴圈列表的索引值

使用angularJS框架的話都需要引入angular.min.js檔案,這個想必各位大佬都懂得,我就不多說了。 這裡主要說說AngularJS的ng-repeat迴圈中如何獲得被迴圈列表的索引值。 假如有一個表格: 程式碼如下: <table class="tabl

angular監聽dom渲染完成,判斷ng-repeat迴圈完成

一、前言 最近做了一個圖片懶載入的小外掛,功能需要dom渲染完成後,好獲取那些需要懶載入的dom元素。那麼問題來了,如果只是感知靜態的dom用ready,onload都可以,但專案用的angular,ng-repeat什麼時候迴圈完,或者說angular自身的生命週期中dom渲染完成怎麼知道,這裡做個解決問

AngularJsng-repeat動態使用ng-model進行雙向資料繫結

首先說明一下功能需求: 當點選一次增加按鈕的時候,下方就會多一行輸入框; 當點選一次刪除按鈕的時候,所點選的刪除按鈕那行的輸入框會消失; 當點選列印資訊按鈕的時候,把所有輸入框中的資料讀取出來,並列印到控制檯上。 由此可看出,帶有刪除按鈕的這部分DIV是動態的。

angularjs ng-repeat單選框下拉框的實現

單選框 見以下程式碼: <div class="form-group " > <label class="col-sm-2 control-label"&

Angularjsng-selectng-options用法【select聯動資料】

1、使用前景 最近在使用angualr專案中遇到select聯動資料,嘗試了很多次都失敗,終於在查找了很多資料以後解決了問題。 2、介紹ng-select ng-select用來將資料同HTML的標籤進行繫結。這個指令可以和ng-model以及ng-

angularjsng-repeatfilter)生成多級選單

需求如下: 後端通過資料庫生成無序的陣列,傳到前端,資料結構如下(pid即parentId,如本級的pid為4,則它上一級的menu_id為4): [ {pid:1,menu_id:7}, {pid:4,menu_id

AngularJS ng-model通過$watch動態取值

blog html lib brush google java logs con head 這個例子的意思是,當xxxx的長度不超過6時,xxxx和yyyy兩個input的model是無關的,但當xxxx超過6,則yyyy會跟隨其值而變化。 <!doctype

AngularJS 獲取ng-repeat的動態ng-model

con $scope 對象 文件 spec input ram ng-repeat ng-model 首先ng-model設置為$parent.conf[$index]: 用$parent的原因是ng-repeat產生的,他會為每一個input生成一個子scope對象,而