如何在深层嵌套ngRepeat中获取不同层级的$index

如题所述

var appData = [
{
name: 'C++从入门到放弃',
author: 'dreamapple',
books: [
{name: 'github'},
{name: 'google'},
{name: 'nodejs'},
{name: 'react'}
]
},
{
name: 'Java从入门到跑路',
author: '呵呵哒',
books: [
{name: '雪碧'},
{name: '百事可乐'},
{name: '鸡尾酒'}
]
}
];

现在有这么一个要求,我需要将上面的那个 appData
循环出来,其中还要循环出来 books
里面的每一项,然后每一个 books
里面的每一项都可以进行删除,也可以给每一个 books
数组里面添加新的一项。

(1)循环出来这个 appData
数据还是很容易的,通过嵌套的 ngRepeat
很方便的就可以搞定了。

(2)关于嵌套我们能够使用的索引是 $index
,但是两层以上的话,如果每一层嵌套都使用 $index
作为索引的话,势必会引起混乱。这个时候就需要我们想一些办法去得到每一层的索引。

(3)我们目前比较好的一个做法就是通过 ngInit
指令,然后在循环开始的时候将每一层的索引保存在一个变量中,然后就可以在循环的不同层级之间使用了。

(4)我们还需要定义另一个数组 vm.tempItem
,这个数组也用于循环,循环出来的每一项用作被添加项的数据模型。

注意:循环 books
数组我们还有一些需要注意的地方,我们要使用 track by
语法,不然每次增加或者删除 books
里面的内容时, books
每一项的 $index
不会发生变化,那么就不好进行删除操作了。

我把里面的重点部分单独拿了出来,然后大家一起来看一看:页面部分:
<ul class="list-group" ng-repeat="item in vm.appData" ng-init="outerIndex = $index">
<h3>{{item.name}}<span class="outer-index">outerIndex:{{outerIndex}}</span></h3>
<h4>{{item.author}}</h4>
<li class="list-group-item">
<ul class="list-group">
<li class="list-group-item" ng-repeat="v in item.books track by $index" ng-init="innerIndex = $index">
{{v.name}} <span class="inner-index">innerIndex:{{innerIndex}}</span><button class="btn btn-danger" ng-click="vm.removeItem(outerIndex, innerIndex)">删除</button>
</li>
<li class="list-group-item">
<form class="form-inline">
<input class="form-control" ng-model="vm.tempItem[$index]" type="text">
<button class="btn btn-primary" ng-click="vm.addItem(outerIndex)">添加一项</button>
</form>
</li>
</ul>

</li>
<hr ng-show="!$last">
</ul>

控制器部分:
function removeItem(outerIndex, innerIndex) {
vm.appData[outerIndex].books.splice(innerIndex, 1);
}

我们可以先看控制器里面的函数, removeItem
这个函数有两个参数,一个是 outerIndex
,一个是 innerIndex
,其中 outerIndex
表示的是第一层循环的 $index
索引, innerIndex
表示的是第二层的 $index
索引。每次删除一项我们都需要知道是删除第一层循环中哪一个对象中的哪一项。

在页面中我们通过 ng-init="outerIndex = $index"
保存了第一层循环的 $index
,通过使用 ng-init="innerIndex = $index"
保存了第二层循环的 $index
。所以接下来的操作都很方便了。

如果对我上面所说的还没有很好理解的话,你可以尝试自己练习一下。下面是源码部分:

HTML部分
<head>
<meta charset="UTF-8">
<title>1</title>
<link rel="stylesheet" href="http://cdn.bootcss.com/bootstrap/3.3.6/css/bootstrap.css">
<link rel="stylesheet" href="../lib/jsonFormater/jsonFormater.css">
<script src="http://cdn.bootcss.com/jquery/2.0.0/jquery.js"></script>
<script src="http://cdn.bootcss.com/bootstrap/3.3.6/js/bootstrap.js"></script>
<script src="../lib/jsonFormater/jsonFormater.js"></script>
<script src="../../angular-1.4.5/angular.js"></script>
<script src="app.js"></script>
<style>
.outer-index {
color: #FF0000;
background-color: #f8f8f8;
padding: 3px;
border-radius: 6px;
}
.inner-index {
color: #00AA00;
background-color: #f8f8f8;
padding: 3px;
border-radius: 6px;
}
</style>
</head>
<body>
<div class="container-fluid" ng-controller="AppController as vm">
<div class="row">
<div class="col-md-6">
<ul class="list-group" ng-repeat="item in vm.appData" ng-init="outerIndex = $index">
<h3>{{item.name}}<span class="outer-index">outerIndex:{{outerIndex}}</span></h3>
<h4>{{item.author}}</h4>
<li class="list-group-item">
<ul class="list-group">
<li class="list-group-item" ng-repeat="v in item.books track by $index" ng-init="innerIndex = $index">
{{v.name}} <span class="inner-index">innerIndex:{{innerIndex}}</span><button class="btn btn-danger" ng-click="vm.removeItem(outerIndex, innerIndex)">删除</button>
</li>
<li class="list-group-item">
<form class="form-inline">
<input class="form-control" ng-model="vm.tempItem[$index]" type="text">
<button class="btn btn-primary" ng-click="vm.addItem(outerIndex)">添加一项</button>
</form>
</li>
</ul>

</li>
<hr ng-show="!$last">
</ul>
</div>
<div id="show-container" class="col-md-6">
<h3>vm.appData:</h3>
<div id="json-container"></div>
</div>
</div>
</div>
</body>

JavaScript部分
(function() {
angular.module('app', [])
.controller('AppController', AppController);

AppController.$inject = ['$scope'];

function AppController($scope) {
var vm = this;
// 初始化原始数据
var appData = [
{
name: 'C++从入门到放弃',
author: 'dreamapple',
books: [
{name: 'github'},
{name: 'google'},
{name: 'nodejs'},
{name: 'react'}
]
},
{
name: 'Java从入门到跑路',
author: '呵呵哒',
books: [
{name: '雪碧'},
{name: '百事可乐'},
{name: '鸡尾酒'}
]
}
];

vm.appData = appData;
vm.tempItem = [];
vm.addItem = addItem;
vm.removeItem = removeItem;

config();

function addItem(outerIndex) {
if(vm.tempItem[outerIndex]) {
vm.appData[outerIndex].books.push({
name: vm.tempItem[outerIndex]
});
vm.tempItem[outerIndex] = '';
vm.jf.doFormat(vm.appData);
}
else {
alert('添加项不能为空!')
}
}

function removeItem(outerIndex, innerIndex) {
vm.appData[outerIndex].books.splice(innerIndex, 1);
vm.jf.doFormat(vm.appData);
}

function config() {
var options = {
dom : '#json-container',
tabSize: 2,
quoteKeys: true,
imgCollapsed: "../lib/jsonFormater/images/collapsed.gif",
imgExpanded: "../lib/jsonFormater/images/expanded.gif",
isCollapsible: true
};
vm.jf = new JsonFormater(options);
vm.jf.doFormat(vm.appData);
}
}
})();
温馨提示:答案为网友推荐,仅供参考