Angular $watch 只是父对象而不是它的多个子对象
Angular $watch just parent object instead of its multiple children
我有一个 div,列出了对象 POI = {"address":"Martinsicuro (TE), Italy", "phone":"+39 333 45657", "website':'http://mysite.it"}
的属性。服务拥有的对象 POI si。该指令的控制器具有从服务获取 POI 的函数 getPoi()
,并将其 returns 传递给指令。
我现在的HTML是这样的:
<table ng-controller="Controller as ctrl">
<tr> <!-- address -->
<td>{{ctrl.getPoi().address}}</td>
</tr>
<tr> <!-- phone -->
<td>{{ctrl.getPoi().phone}}</td>
</tr>
<tr> <!-- website -->
<td>
<a ng-href="{{ctrl.getPoi().website}}">
{{ctrl.getPoi().website}}
</a>
</td>
</tr>
</table>
控制器
.controller('Controller', function(CurrentPoiService)
{
this.getPoi = function()
{ return CurrentPoiService.POI; }
}
服务
.service('CurrentPoiService', function()
{
this.POI = {"address":"Martinsicuro (TE), Italy", "phone":"+39 333 45657", "website':'http://mysite.it"}
}
通过这种方式,我添加了 3 个观察者。有没有办法只添加 1 个观察者,因为它是同一个父对象?这是一个 JSFiddle
谢谢
[更新 1]
这是(仍然不起作用)JSFiddle 使用@Charlie
提出的解决方案
[更新 2]
这是工作 JSFiddle
在你的控制器中尝试:
$scope.POI = ctrl.getPoi();
HTML :
<tr> <!-- address -->
<td>{{POI.address}}</td>
</tr>
<tr> <!-- phone -->
<td>{{POI.phone}}</td>
</tr>
正如 Claies 在评论中提到的,您永远不应该从
以这种方式通过函数查看。
在这种情况下,您可以使用 objectEquality
参数 true
为 POI
对象创建一个监视,以监视单个 $watch 中对象的属性。然后在侦听器中找到您的元素并以您想要的方式更改值。
$scope.$watch('POI', function(){
//Assume that $scope.propertyIndex is the current property to display
angular.element($document[0].querySelector("#myTd" + $scope.propertyIndex)).html(POI.address);
angular.element($document[0].querySelector("#myTd" + $scope.propertyIndex)).html(POI.phone);
//etc...
}, true);
这样你控制得更好。但请记住,如果 POI 是一个复杂的对象,则此方法不适用。
更新:
这是一个使用手表和工厂每秒显示一个随机数的工作示例。您应该能够从中学习并将其应用到您的项目中。
myApp.controller('myController', function($scope, dataSource) {
$scope.poi = {rand: 0};
$scope.$watch('poi', function() {
$('#rand').html($scope.poi.rand);
}, true);
dataSource.open($scope);
});
myApp.factory('dataSource', function($interval) {
return {
open: function(scope){
$interval(function() {
scope.poi.rand = Math.random();
}, 1000);
}
}
});
我有一个 div,列出了对象 POI = {"address":"Martinsicuro (TE), Italy", "phone":"+39 333 45657", "website':'http://mysite.it"}
的属性。服务拥有的对象 POI si。该指令的控制器具有从服务获取 POI 的函数 getPoi()
,并将其 returns 传递给指令。
我现在的HTML是这样的:
<table ng-controller="Controller as ctrl">
<tr> <!-- address -->
<td>{{ctrl.getPoi().address}}</td>
</tr>
<tr> <!-- phone -->
<td>{{ctrl.getPoi().phone}}</td>
</tr>
<tr> <!-- website -->
<td>
<a ng-href="{{ctrl.getPoi().website}}">
{{ctrl.getPoi().website}}
</a>
</td>
</tr>
</table>
控制器
.controller('Controller', function(CurrentPoiService)
{
this.getPoi = function()
{ return CurrentPoiService.POI; }
}
服务
.service('CurrentPoiService', function()
{
this.POI = {"address":"Martinsicuro (TE), Italy", "phone":"+39 333 45657", "website':'http://mysite.it"}
}
通过这种方式,我添加了 3 个观察者。有没有办法只添加 1 个观察者,因为它是同一个父对象?这是一个 JSFiddle 谢谢
[更新 1] 这是(仍然不起作用)JSFiddle 使用@Charlie
提出的解决方案[更新 2] 这是工作 JSFiddle
在你的控制器中尝试:
$scope.POI = ctrl.getPoi();
HTML :
<tr> <!-- address -->
<td>{{POI.address}}</td>
</tr>
<tr> <!-- phone -->
<td>{{POI.phone}}</td>
</tr>
正如 Claies 在评论中提到的,您永远不应该从 以这种方式通过函数查看。
在这种情况下,您可以使用 objectEquality
参数 true
为 POI
对象创建一个监视,以监视单个 $watch 中对象的属性。然后在侦听器中找到您的元素并以您想要的方式更改值。
$scope.$watch('POI', function(){
//Assume that $scope.propertyIndex is the current property to display
angular.element($document[0].querySelector("#myTd" + $scope.propertyIndex)).html(POI.address);
angular.element($document[0].querySelector("#myTd" + $scope.propertyIndex)).html(POI.phone);
//etc...
}, true);
这样你控制得更好。但请记住,如果 POI 是一个复杂的对象,则此方法不适用。
更新:
这是一个使用手表和工厂每秒显示一个随机数的工作示例。您应该能够从中学习并将其应用到您的项目中。
myApp.controller('myController', function($scope, dataSource) {
$scope.poi = {rand: 0};
$scope.$watch('poi', function() {
$('#rand').html($scope.poi.rand);
}, true);
dataSource.open($scope);
});
myApp.factory('dataSource', function($interval) {
return {
open: function(scope){
$interval(function() {
scope.poi.rand = Math.random();
}, 1000);
}
}
});