使用场景:用ng-repeat几个部分,每个部分调用同一个函数,但是每个模块之间的功能不能相互干扰
问题:在用repeat实现.content块repeat的时候打算这样做:新建一个空的数组(nmber_arr),因为数组里面的length可以决定repeat出几个content块,这样我就可以通过控制数组里面的length来实现repeat几个.content块;顺着这个思路我做了一个add按钮,希望在点击add按钮的时候number_arr的length会相应的增加一个,于是想到了用push操作:点击一次按钮往number_arr里面增加一个类容:代码:
HTML:
<button class="btn btn-primary demo-btn" ng-click="host.add_input()">add</button>
<div class="content" ng-repeat="x in host.number_arr">
<button type="button" class="btn btn-primary" ng-click="host.add(x,'count')">add</button>
<button type="button" class="btn btn-primary" ng-click="host.dec(x,'count')">dec</button>
</div>
js:
vm.number_arr = [];
var number_object = {
count: 0
}
function add_input(){
if (vm.number_arr.length<3) {
vm.number_arr.push (number_object);
}
}
然后点击add按钮的时候只能出现一次repeat效果,于是就纳闷了,,,,,
解决:angula repeat数组的时候里面的值是不能一样的,比如:如果 vm.number_arr = [1,1,1];其实函数是会报错的,因为里面的值是一样的,而我这里bush进去的只是对象的一个指针,它们实际指向的是内存中的同一个值,看了网上的资料,如果可以在repeat后面加上:track by index:ng-repeat="x in host.number_arr track by $index"或者使用angular copy(): vm.number_arr.push(angular.copy(number_object));这样解决了repeat的问题
接下来做add和dec的部分:
问题:我是用数组对象里面的count的值关联到input里面的value。所以这里我可以通过对count的操作实现对input输入框value的控制,于是想到:将对对象数组里面的值作为参数传到add和dec函数里面:
HTML:
<button type="button" class="btn btn-primary" ng-click="host.add(x.count)">add</button>
<button type="button" class="btn btn-primary" ng-click="host.dec(x.count)">dec</button>
js:
function add(num){
if (num < 500) {
num++;
}else{
num = 500;
}
};
然后给将函数加到按钮上,点击的时候input的值并没有什么反应
解决:想起一句话:函数是按值传递的,这里x.count实际上就是一个值,把这个值作为一个参数传给参数,函数会把这个值进行加减操作,但是要注意:其实这里的x.count在函数执行前后是没有发生变化的,换句话说,函数只是将一个数字进行了加减操作,然后并不会返回什么,当然这样就不会在视图上有任何变化;换了个思路,改变参数的形式,让函数的值能和数组对象里面的属性值(count)相互关联起来:
html:
<button type="button" class="btn btn-primary" ng-click="host.add(x,'count')">add</button>
<button type="button" class="btn btn-primary" ng-click="host.dec(x,'count')">dec</button>
js:
function add(obj,s){
if (obj[s] < 500) {
obj[s]++;
}else{
obj[s] = 500;
}
};
需要说明的一点:x in repeat中的x实际是:对应的那个对象,如果是第一条input那么就是对应的第一个数组对象:arr[0],实际上这是一个指针,因此我这里这里使用两个参数,第一个是指针,用于函数和数组对象的属性相互关联,第二个参数是对应的属性值,让函数知道我操作的是对象的哪个值,需要说明的一点:引用数组对象的属性值,我们一般是这样的写法:arr[0].count;但是我这里采用的是:arr[0]['count'],为什么采用这样的方式呢:如果采用第一种方式。js代码需要写成:
js:function add(obj){
if (obj.count < 500) {
obj.count++;
}else{
obj.count = 500;
}
};
html:参数变成:x;
虽然在这个函数里面不会影响到功能,但是如果下次需要复用这个add函数就需要改变数组对象里面的属性名和函数里面的的执行对象名,这样不利于函数的复用
具体代码:
html:
<!DOCTYPE html> <html> <head> <meta charset="utf-8"> <link rel="stylesheet" href="src/bootstrap.min.css"> <script src="src/angular.min.js"></script> <script src="src/jquery.min.js"></script> <script src="src/bootstrap.min.js"></script> <script src="demo.js"></script> <link rel="stylesheet" href="demo.css" /> <style> input { display: inline-block; height: 30px; width: 300px } .content { height: 30px; margin-bottom: 20px; } button { height: 30px; line-height: 30px; } .demo-btn { display: block; width: 100%; margin-top: 30px; } </style> </head> <body ng-app="myApp" ng-controller="formCtrl as host"> <div class="container"> <div class="content" ng-repeat="x in host.number_arr track by $index"> <input type="text" ng-model="x.count" /> <button type="button" class="btn btn-primary" ng-click="host.add(x,'count')">add</button> <button type="button" class="btn btn-primary" ng-click="host.dec(x,'count')">dec</button> </div> <div ng-show="host.number_arr.length < 3"> <span class="count">{{host.count}}</span> <button class="btn btn-primary demo-btn" ng-click="host.add_input()">add</button> </div> </div> </body> </html>
js:
var app = angular.module('myApp', []); app.controller('formCtrl', function($scope) { var vm = this; console.log(vm) //ng-repeat里面的内容不能是同一个值,如果是同一个值需要给repeat加上track by index vm.add_input = add_input; vm.dec = dec; vm.add = add; vm.number_arr = []; var number_object = { count: 0 } vm.count = 3; function add_input() { if (vm.number_arr.length < 3) { vm.number_arr.push(angular.copy(number_object)); //copy执行的操作是copy一份新的内存空间,返回的是这个新内存空间的一个指针 //还有一点:如果不使用copy的话push到数组里面的只是一个指针,而这些指针指到的位置又是同一个内存空间, //但是angular是不允许repeat一个同样的内存空间, //解决的方法一:repeat出来的需要给打上标记,通过track by index来实现,还有一种方法就是通过angularcopy的方法来解决 vm.count = vm.count - 1; } } function dec(obj, s) { //因为函数是按值传递的, //应数组对象arr[{conunt: 0}]的方法有两种:一:arr[0].count二:arr[0]['count']; //这里是使用第二种方法来实现加减的 //为什么不使用第一种方式实现呢:第一种方式不利于函数复用 if (obj[s] > 0) { obj[s]--; } else { obj[s] = 0; } }; function add(obj, s) { if (obj[s] < 500) { obj[s]++; } else { obj[s] = 500; } }; //第二种方式 // function add(obj){ // if (obj.count < 500) { // obj.count++; // }else{ // obj.count = 500; // } // }; } )