how to make child controllers within ng-repeat load one at a time?
我有一个主控制器,它获取表示表(行和列)的x和y坐标的数据。
在每个单元中,我都有一个子控制器,它根据父控制器的X&Y值准备要呈现的值。
目前,在处理整个事件之前,屏幕上不会呈现任何内容。
The behaviour I am after is that first the whole table is rendered showing only column header values and first cell values within each row. 然后让子控制器一次加载一个单元值…
非通缉行为的简化演示:https://jsfiddle.net/coolcatdev/xmtg3q31/1/
模板:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 | <table class="table-bordered"> <tr> <th>Y/X</th> <th ng-repeat="valX in x">{{valX}}</th> <tr> <tr ng-repeat="valY in y"> <td>{{valY}}</td> <td ng-repeat="valX in x"> {{value}} </td> <tr> </table> |
控制器:
1 2 3 4 5 6 7 8 9 10 | var myApp = angular.module('myApp',[]); function MyCtrl($scope) { $scope.x = ['a','b','c','d','e','f','g']; $scope.y = ['1','2','3','4','5','6','7','8','9','10','1','2','3','4','5','6','7','8','9','10','1','2','3','4','5','6','7','8','9','10','1','2','3','4','5','6','7','8','9','10','1','2','3','4','5','6','7','8','9','10','1','2','3','4','5','6','7','8','9','10','1','2','3','4','5','6','7','8','9','10']; } function MyCtrl2($scope) { $scope.value = $scope.valX + $scope.valY; } |
真实的东西:
模板:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 | <script type="text/ng-template" id="comparison"> Choose comparison table structure <button ng-if="colXoptionsModel && colYoptionsModel && colValueoptionsModel && colGroupingoptionsModel" ng-click="createTable()" type="button" class="btn btn-default btn-sm col-xs-12"><span class=""></span> Create table</button> <table ng-if="tableReady" class="table-bordered" style="width:100%;overflow-x:scroll;"> <tr> <th>{{colYoptionsModel.attobj.name}}/{{colXoptionsModel.attobj.name}}</th> <th ng-repeat="x in uniqueX" ng-init="colHeader = x.get4(colXoptionsModel.key)[0].attributes.displayName[0] || x.get4(colXoptionsModel.key).toString()"> {{colHeader}} </th> </tr> <tr ng-repeat="y in uniqueY" ng-init="rowIndex = y.get4(colYoptionsModel.key)[0].attributes.displayName[0] || y.get4(colYoptionsModel.key).toString()"> <td>{{rowIndex}}</td> <td ng-repeat="x in uniqueX"> <span style="clear:both;"></span> </td> </tr> </table> |
控制器:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 | app.controller('comparisonValues', ['$scope', function ($scope) { console.log('loading cell'); //filter allDBOS where xmodel col = x and ymodel col = y var checkX = $scope.x.get4($scope.colXoptionsModel.key)[0].cid || $scope.x.get4($scope.colXoptionsModel.key).toString(); var checkY = $scope.y.get4($scope.colYoptionsModel.key)[0].cid || $scope.y.get4($scope.colYoptionsModel.key).toString(); $scope.cellValues = _.filter($scope.allDBOS, function(dbo){ var checkDboX = dbo.get4($scope.colXoptionsModel.key)[0].cid || dbo.get4($scope.colXoptionsModel.key).toString(); var checkDboY = dbo.get4($scope.colYoptionsModel.key)[0].cid || dbo.get4($scope.colYoptionsModel.key).toString(); if(checkDboX == checkX && checkDboY == checkY){ return dbo; } }); if($scope.cellValues.length > 1){ $scope.grouping = true; } $scope.compressed=false; }]); app.controller('comparisonController', ['$scope', '$location', '$http', '$q', 'templateService', function ($scope, $location, $http, $q, templateService) { $scope.getAttributeTemplate = templateService.getAttributeTemplate; $scope.tableReady = false; $scope.compare.val = false; $scope.colXoptions = $scope.columns; $scope.colXoptionsModel={} $scope.settingsXaxisBtn = {closeOnSelect:true, displayProp: 'key', idProp: 'key', externalIdProp:'', selectionLimit: 1, buttonClasses:'graphDropDowns', smartButtonMaxItems: 1, showUncheckAll:false, showCheckAll:false}; $scope.xBtnLabel = {buttonDefaultText:'X-Axis'}; $scope.updateModleX = { onItemSelect: function(item) { $scope.updateModleX = $scope.updateModleX; }, onItemDeselect: function(item) { $scope.updateModleX = {}; } }; $scope.colYoptions = $scope.columns; $scope.colYoptionsModel={} $scope.settingsYaxisBtn = {closeOnSelect:true, displayProp: 'key', idProp: 'key', externalIdProp:'', selectionLimit: 1, buttonClasses:'graphDropDowns', smartButtonMaxItems: 1, showUncheckAll:false, showCheckAll:false}; $scope.yBtnLabel = {buttonDefaultText:'Y-Axis'}; $scope.updateModleY = { onItemSelect: function(item) { $scope.colYoptionsModel = $scope.colYoptionsModel; }, onItemDeselect: function(item) { $scope.colYoptionsModel = {}; } }; $scope.colValueoptions = $scope.columns; $scope.colValueoptionsModel={} $scope.settingsValueaxisBtn = {closeOnSelect:true, displayProp: 'key', idProp: 'key', externalIdProp:'', selectionLimit: 1, buttonClasses:'graphDropDowns', smartButtonMaxItems: 1, showUncheckAll:false, showCheckAll:false}; $scope.valueBtnLabel = {buttonDefaultText:'Value-Axis'}; $scope.updateModleV = { onItemSelect: function(item) { $scope.colValueoptionsModel = $scope.colValueoptionsModel; }, onItemDeselect: function(item) { $scope.colValueoptionsModel = {}; } }; $scope.colGroupingoptions = $scope.columns; $scope.colGroupingoptionsModel={} $scope.settingsGroupingaxisBtn = {closeOnSelect:true, displayProp: 'key', idProp: 'key', externalIdProp:'', selectionLimit: 1, buttonClasses:'graphDropDowns', smartButtonMaxItems: 1, showUncheckAll:false, showCheckAll:false}; $scope.groupingBtnLabel = {buttonDefaultText:'Grouping-Axis'}; $scope.updateModleG = { onItemSelect: function(item) { $scope.colGroupingoptionsModel = $scope.colGroupingoptionsModel; }, onItemDeselect: function(item) { $scope.colGroupingoptionsModel = {}; } }; //get all dbos from query without pagination $scope.createTable = function(){ $scope.tableReady=false; $scope.query2 = angular.copy($scope.queryObj); var url = '/api/list2/json/' + $scope.class; $scope.query2.count = 0; $scope.query2.page = 1; var len = url.length + JSON.stringify($scope.query2).length + $location.url().length; var prom = (len > 2000) ? $http.post(url, {'q':JSON.stringify($scope.query2), 'hashfragment' : $location.url()}, {transformResponse: transformResponse}) : $http.get(url, {cache:true, params:{"q":JSON.stringify($scope.query2)}, headers:{'hashfragment':$location.url()}, transformResponse: transformResponse}); prom.then( function (response) { $scope.allDBOS = response.data.data.requested; console.log('alldbos'); console.log($scope.allDBOS.length); $scope.getUniqueXY(); }, function (response) { // console.log('response failed to load'); }); return prom; } //get distinct values for allDBOS.x and allDBOS.y model to use as table col headers(x) and table row indexes(y) $scope.getUniqueXY = function(){ $scope.uniqueX = _.uniq($scope.allDBOS, function(dbo) { return dbo.get4($scope.colXoptionsModel.key)[0].cid || dbo.get4($scope.colXoptionsModel.key).toString(); }); $scope.uniqueY = _.uniq($scope.allDBOS, function(dbo) { return dbo.get4($scope.colYoptionsModel.key)[0].cid || dbo.get4($scope.colYoptionsModel.key).toString(); }); // console.log('unique x vals in dbos'); // console.log($scope.uniqueX.length); // console.log('unique y vals in dbos'); // console.log($scope.uniqueY.length); //table starts to render nad directive for each cell kicks in: app.directive('loadComparisonValues'... $scope.tableReady = true; console.log($scope.tableReady); } }]); |
下面是一个例子,说明如何使用$timeout执行此操作。
首先,通过添加计数来跟踪视图中的当前行
1 2 3 4 5 6 7 8 9 10 11 12 13 14 | <table class="table-bordered"> <tr> <th>Y/X</th> <th ng-repeat="valX in x">{{valX}}</th> <tr> <tr ng-repeat="valY in y" ng-init="count = $index;"> <td>{{valY}}</td> <td ng-repeat="valX in x"> {{value}} </td> <tr> </table> |
并使用myctrl2控制器中的计数,将时间与计数器相乘,使行依次呈现。
1 2 3 4 5 | function MyCtrl2($scope, $timeout) { $timeout(function(){ $scope.value = $scope.valX + $scope.valY; }, 100 * $scope.count); } |
举个例子