我有一个主控制器,它获取表示表格(行和列)的x和y坐标的数据。
在每个单元格中,我有一个子控制器,它准备基于x和amp; y父控制器的值。
此时屏幕上没有任何内容呈现,直到处理完所有内容。
我所追求的行为是,首先渲染整个表,仅显示列标题值和每行中的第一个单元格值。并且让子控制器一次加载一个单元格值......
非想要行为的简化演示: https://jsfiddle.net/coolcatDev/xmtg3q31/1/
模板:
<div ng-controller="MyCtrl">
<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">
<div ng-controller="MyCtrl2">
{{value}}
</div>
</td>
<tr>
</table>
</div>
控制器:
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;
}
真实的事情:
模板:
<script type="text/ng-template" id="comparison">
<div ng-controller="comparisonController" class="container-fluid">
<h3>Choose comparison table structure</h3>
<div class="multiDropMenus" ng-dropdown-multiselect="" options="colXoptions" selected-model="colXoptionsModel" translation-texts="xBtnLabel" extra-settings="settingsXaxisBtn" events="updateModelX">
</div>
<div class="multiDropMenus" ng-dropdown-multiselect="" options="colYoptions" selected-model="colYoptionsModel" translation-texts="yBtnLabel" extra-settings="settingsYaxisBtn" events="updateModelY">
</div>
<div class="multiDropMenus" ng-dropdown-multiselect="" options="colValueoptions" selected-model="colValueoptionsModel" translation-texts="valueBtnLabel" extra-settings="settingsValueaxisBtn" events="updateModelV">
</div>
<div class="multiDropMenus" ng-dropdown-multiselect="" options="colGroupingoptions" selected-model="colGroupingoptionsModel" translation-texts="groupingBtnLabel" extra-settings="settingsGroupingaxisBtn" events="updateModelG">
</div>
<br>
<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>
<br>
<div class="container-fluid" style="overflow-x:scroll;">
<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">
<div ng-controller="comparisonValues">
<div ng-repeat="dbo in cellValues">
<div ng-if="grouping" ng-init="attobj = colGroupingoptionsModel; key = attobj.key; values=dbo.get4(attobj.key); template = attobj.template || getAttributeTemplate(dbo.clazz + attobj.key);">
<div class="contentDecompressed" customtemp></div>
</div>
<span style="clear:both;"></span>
<div ng-init="attobj = colValueoptionsModel; key = attobj.key; values=dbo.get4(attobj.key); template = attobj.template || getAttributeTemplate(dbo.clazz + attobj.key);">
<div class="contentDecompressed" customtemp></div>
</div>
</div>
</div>
</td>
</tr>
</table>
</div>
</div>
</script>
控制器:
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);
}
}]);
答案 0 :(得分:1)
以下是使用$timeout
执行此操作的示例首先,通过添加计数来跟踪视图中的当前行
"index_exclude_patterns": ["*.log", "node_modules/*", "vendor/*"]
并使用MyCtrl2控制器中的计数通过将时间与计数器相乘来使行相互渲染
<div ng-controller="MyCtrl">
<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">
<div ng-controller="MyCtrl2">
{{value}}
</div>
</td>
<tr>
</table>
</div>
这里是example