Angular - 我可以在嵌套的 ng-repeat 中对多个对象使用单个函数来触发该对象的 ng-show 吗?
Angular - can I use a single function on multiple objects within a nested ng-repeat that triggers the ng-show of just that object?
SUMMARY
我有一个品牌列表和一个产品列表。我正在使用 ng-repeat 来显示品牌列表,并使用带有过滤器的 ng-repeat 来显示各自品牌内的产品列表。我希望每个品牌和每个产品都有一个按钮来显示更多相关信息 brand/product。 所有这些按钮在控制器上应使用相同的功能。
问题
显示更多关于该品牌的按钮也显示更多关于该品牌的每个产品,除非(这对我来说是奇怪的部分)我先点击该品牌内产品的按钮,在这种情况下它会正常工作。
CODE
请在此处查看 Plunker,并注意当您点击品牌上的 'show type' 时,它还会显示所有类型该品牌内的产品:http://plnkr.co/edit/gFnq3O3f0YYmBAB6dcwe?p=preview
HTML
<!DOCTYPE html>
<html>
<head>
<link rel="stylesheet" href="style.css">
<script src="script.js"></script>
</head>
<body>
<div ng-app="myApp">
<div ng-controller="MyController as vm">
<div ng-repeat="brand in brands">
<h1>
{{brand.name}}
</h1>
<button ng-click="showType(brand)">
Show Brand Type
</button>
<div ng-show="show">
{{brand.type}}
</div>
<div ng-repeat="product in products
| filter:filterProducts(brand.name)">
<h2>
{{product.name}}
</h2>
<button ng-click="showType(product)">
Show Product Type
</button>
<div ng-show="show">
{{product.type}}
</div>
</div>
</div>
</div>
</div>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.3/angular.min.js"></script>
<script src="script.js"></script>
</body>
</html>
JAVASCRIPT
var app = angular.module('myApp', []);
app.controller('MyController', function($scope) {
$scope.brands = [{
name: 'Kewl',
type: 'Cereal'
}, {
name: 'Joku',
type: 'Toy'
}, {
name: 'Loko',
type: 'Couch'
}]
$scope.products = [{
name: 'Kewlio',
type: 'Sugar Cereal',
brand: 'Kewl'
}, {
name: 'Kewliano',
type: 'Healthy Cereal',
brand: 'Kewl'
}, {
name: 'Jokurino',
type: 'Rattle',
brand: 'Joku'
}, {
name: 'Lokonoko',
type: 'Recliner',
brand: 'Loko'
}, {
name: 'Lokoboko',
type: 'Love Seat',
brand: 'Loko'
}]
$scope.showType = function(item) {
this.show = !this.show;
}
$scope.filterProducts = function(brand) {
return function(value) {
if(brand) {
return value.brand === brand;
} else {
return true;
}
}
}
});
重要说明:我意识到我可以向对象添加一个属性 (brand.show) 并将对象传递给函数,然后将该属性更改为 true/false,但我不想这样做,因为在我的实际应用程序中,按钮将显示一个编辑 brand/product 并将信息提交给 Firebase 的表单,我不希望该对象具有一个 'show' 属性。我不想每次想在 Firebase 中编辑信息时都删除 'show' 属性。
您的 show
布尔属性对整棵树都相同(在同一范围内)。在 ng-repeat
中使用带有子作用域 scope:true
的 angular 指令有助于隔离每个 show
属性。我已经分叉了你的 plunker 代码:
如果您不介意在数据中放置临时属性,最简单的解决方法是进行以下更改:
<div ng-show="product.show">
{{product.type}}
</div>
和
<div ng-show="brand.show">
{{brand.type}}
</div>
然后在你的控制器中
$scope.showType = function(item) {
item.show = !item.show;
}
或者,如果您不想触及对象属性,您可以创建一个 $scope.shownTypes 数组,然后单击将对象推入或从显示的数组中删除对象。然后您可以检查对象是否存在于数组中并适当地显示或不显示类型。如果您需要样品,请告诉我。
ng-repeat
指令创建自己的范围,当你做
this.show = !this.show
you create/change show
属性 in current scope, if click brand button -对于品牌范围,对于产品是全局的,当单击 产品 按钮时 - 对于范围具体产品。
为避免这种情况,您应该在单击按钮之前创建此 属性,例如使用 ng-init
,如
ng-init="show=false;"
在带有 `ng-repeat" 指令的元素上
样本
var app = angular.module('myApp', []);
app.controller('MyController', function($scope) {
$scope.brands = [{
name: 'Kewl',
type: 'Cereal'
}, {
name: 'Joku',
type: 'Toy'
}, {
name: 'Loko',
type: 'Couch'
}]
$scope.products = [{
name: 'Kewlio',
type: 'Sugar Cereal',
brand: 'Kewl'
}, {
name: 'Kewliano',
type: 'Healthy Cereal',
brand: 'Kewl'
}, {
name: 'Jokurino',
type: 'Rattle',
brand: 'Joku'
}, {
name: 'Lokonoko',
type: 'Recliner',
brand: 'Loko'
}, {
name: 'Lokoboko',
type: 'Love Seat',
brand: 'Loko'
}]
$scope.showType = function(item) {
this.show = !this.show;
}
$scope.filterProducts = function(brand) {
return function(value) {
if (brand) {
return value.brand === brand;
} else {
return true;
}
}
}
});
/* Styles go here */
h1 {
font-family: impact;
}
h2 {
font-family: arial;
color: blue;
margin-bottom: 0;
}
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.8/angular.js"></script>
<div ng-app="myApp">
<div ng-controller="MyController as vm">
<div ng-repeat="brand in brands" ng-init="show=false">
<h1>
{{brand.name}}
</h1>
<button ng-click="showType(brand)">
Show Brand Type
</button>
<div ng-show="show">
{{brand.type}}
</div>
<div ng-repeat="product in products
| filter:filterProducts(brand.name)" ng-init="show=false">
<h2>
{{product.name}}
</h2>
<button ng-click="showType(product)">
Show Product Type
</button>
<div ng-show="show">
{{product.type}}
</div>
</div>
</div>
</div>
</div>
SUMMARY
我有一个品牌列表和一个产品列表。我正在使用 ng-repeat 来显示品牌列表,并使用带有过滤器的 ng-repeat 来显示各自品牌内的产品列表。我希望每个品牌和每个产品都有一个按钮来显示更多相关信息 brand/product。 所有这些按钮在控制器上应使用相同的功能。
问题
显示更多关于该品牌的按钮也显示更多关于该品牌的每个产品,除非(这对我来说是奇怪的部分)我先点击该品牌内产品的按钮,在这种情况下它会正常工作。
CODE
请在此处查看 Plunker,并注意当您点击品牌上的 'show type' 时,它还会显示所有类型该品牌内的产品:http://plnkr.co/edit/gFnq3O3f0YYmBAB6dcwe?p=preview
HTML
<!DOCTYPE html>
<html>
<head>
<link rel="stylesheet" href="style.css">
<script src="script.js"></script>
</head>
<body>
<div ng-app="myApp">
<div ng-controller="MyController as vm">
<div ng-repeat="brand in brands">
<h1>
{{brand.name}}
</h1>
<button ng-click="showType(brand)">
Show Brand Type
</button>
<div ng-show="show">
{{brand.type}}
</div>
<div ng-repeat="product in products
| filter:filterProducts(brand.name)">
<h2>
{{product.name}}
</h2>
<button ng-click="showType(product)">
Show Product Type
</button>
<div ng-show="show">
{{product.type}}
</div>
</div>
</div>
</div>
</div>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.3/angular.min.js"></script>
<script src="script.js"></script>
</body>
</html>
JAVASCRIPT
var app = angular.module('myApp', []);
app.controller('MyController', function($scope) {
$scope.brands = [{
name: 'Kewl',
type: 'Cereal'
}, {
name: 'Joku',
type: 'Toy'
}, {
name: 'Loko',
type: 'Couch'
}]
$scope.products = [{
name: 'Kewlio',
type: 'Sugar Cereal',
brand: 'Kewl'
}, {
name: 'Kewliano',
type: 'Healthy Cereal',
brand: 'Kewl'
}, {
name: 'Jokurino',
type: 'Rattle',
brand: 'Joku'
}, {
name: 'Lokonoko',
type: 'Recliner',
brand: 'Loko'
}, {
name: 'Lokoboko',
type: 'Love Seat',
brand: 'Loko'
}]
$scope.showType = function(item) {
this.show = !this.show;
}
$scope.filterProducts = function(brand) {
return function(value) {
if(brand) {
return value.brand === brand;
} else {
return true;
}
}
}
});
重要说明:我意识到我可以向对象添加一个属性 (brand.show) 并将对象传递给函数,然后将该属性更改为 true/false,但我不想这样做,因为在我的实际应用程序中,按钮将显示一个编辑 brand/product 并将信息提交给 Firebase 的表单,我不希望该对象具有一个 'show' 属性。我不想每次想在 Firebase 中编辑信息时都删除 'show' 属性。
您的 show
布尔属性对整棵树都相同(在同一范围内)。在 ng-repeat
中使用带有子作用域 scope:true
的 angular 指令有助于隔离每个 show
属性。我已经分叉了你的 plunker 代码:
如果您不介意在数据中放置临时属性,最简单的解决方法是进行以下更改:
<div ng-show="product.show">
{{product.type}}
</div>
和
<div ng-show="brand.show">
{{brand.type}}
</div>
然后在你的控制器中
$scope.showType = function(item) {
item.show = !item.show;
}
或者,如果您不想触及对象属性,您可以创建一个 $scope.shownTypes 数组,然后单击将对象推入或从显示的数组中删除对象。然后您可以检查对象是否存在于数组中并适当地显示或不显示类型。如果您需要样品,请告诉我。
ng-repeat
指令创建自己的范围,当你做
this.show = !this.show
you create/change show
属性 in current scope, if click brand button -对于品牌范围,对于产品是全局的,当单击 产品 按钮时 - 对于范围具体产品。
为避免这种情况,您应该在单击按钮之前创建此 属性,例如使用 ng-init
,如
ng-init="show=false;"
在带有 `ng-repeat" 指令的元素上
样本
var app = angular.module('myApp', []);
app.controller('MyController', function($scope) {
$scope.brands = [{
name: 'Kewl',
type: 'Cereal'
}, {
name: 'Joku',
type: 'Toy'
}, {
name: 'Loko',
type: 'Couch'
}]
$scope.products = [{
name: 'Kewlio',
type: 'Sugar Cereal',
brand: 'Kewl'
}, {
name: 'Kewliano',
type: 'Healthy Cereal',
brand: 'Kewl'
}, {
name: 'Jokurino',
type: 'Rattle',
brand: 'Joku'
}, {
name: 'Lokonoko',
type: 'Recliner',
brand: 'Loko'
}, {
name: 'Lokoboko',
type: 'Love Seat',
brand: 'Loko'
}]
$scope.showType = function(item) {
this.show = !this.show;
}
$scope.filterProducts = function(brand) {
return function(value) {
if (brand) {
return value.brand === brand;
} else {
return true;
}
}
}
});
/* Styles go here */
h1 {
font-family: impact;
}
h2 {
font-family: arial;
color: blue;
margin-bottom: 0;
}
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.8/angular.js"></script>
<div ng-app="myApp">
<div ng-controller="MyController as vm">
<div ng-repeat="brand in brands" ng-init="show=false">
<h1>
{{brand.name}}
</h1>
<button ng-click="showType(brand)">
Show Brand Type
</button>
<div ng-show="show">
{{brand.type}}
</div>
<div ng-repeat="product in products
| filter:filterProducts(brand.name)" ng-init="show=false">
<h2>
{{product.name}}
</h2>
<button ng-click="showType(product)">
Show Product Type
</button>
<div ng-show="show">
{{product.type}}
</div>
</div>
</div>
</div>
</div>