I'm trying to add a new object to an ng-repeat array. The array is created with data acquired through an $http request. I need to be able to pass data that I've entered in a dialog to a function that then pushes this data, as an object, onto the array and updates the view. I can log the values of the inputs in the console just fine and even when I log the array it will show the updated values but it won't update the view. Also, it will update the array if I add an object with a button that is not in the dialog.
UPDATE
After viewing the scopes overview with Chrome's Angular ng-Inspector, I can see that the new object is being added to the array within the scope of the controller which is a parent of the element where the ng-repeat takes place. The element where the ng-repeat takes place has its own scope and I can see that the array is not being updated there. I need this array to be the one that is updated since that is where the ng-repeat is and that is what is being viewed. I'm still a little confused by how there can be two of the same array where one changes while the other doesn't. When I push the object onto '$scope.plots' I need to target the scope of the ng-repeat parent element. I still haven't found a good way to do this.
Here is my dialog
function showAdd(ev) {
$mdDialog
.show({
controller: DialogController,
templateUrl: '/templates/addDialog.html', //contains inputs that are modeled to values as seen in the push function below. A button calls addPlant()
targetEvent: ev,
clickOutsideToClose: true,
openFrom: 'left'
}).then(function(added) {
newPlant(added);
})
}
Here is my dialog controller
function DialogController($scope, $mdDialog, $http) {
$scope.addPlant = function (added) {
for (var i = 0; i < added.quantity; i++) {
$http.post('/addPlant', added).then(function () { //this is just posting the data to a database, not related to the issue.
$mdDialog.hide(added);
}
});
}
};
And the push function
var newPlant = function(added) {
$scope.plots.push({
'plot': added.plot,
'varieties': [{
'count': added.quantity,
'variety': added.variety
}],
'count': added.quantity
});
I ended up having to create a service and broadcast the added object from the rootScope. I created a separate controller for the ng-repeat element that listened for the broadcast.
When the dialog is closed it resolves the promise passing the form data to the service.
$mdDialog
.show({
controller: 'DialogCtrl as dc',
templateUrl: '/templates/addDialog.html',
targetEvent: ev,
clickOutsideToClose: true,
openFrom: 'left'
}).then(function(added) {
addPlant.prepForBroadcast(added) //calling service in promise, passing 'added' input values
})
I created a service to broadcast the object
var myApp= angular.module('myApp');
myApp.factory('addPlant', ['$rootScope', function($rootScope) {
var box= {}; //I like to call the designated factory object a 'box'
box.newPlant = {};
box.prepForBroadcast = function(added) {
box.newPlant = added;
this.broadcastItem();
};
box.broadcastItem = function() {
$rootScope.$broadcast('broadcast');
};
return box; //ship out the box with the newPlant
}]);
And a separate controller for the ng-repeat element, listening for broadcast
myApp.controller('ListCtrl', ['$scope','addPlant', function($scope, addPlant) {
$scope.$on('broadcast', function() { //listening for broadcast
$scope.plots.push({
'plot': addPlant.newPlant.plot,
'count': addPlant.newPlant.quantity,
'varieties': [{
'variety': addPlant.newPlant.variety,
'count': addPlant.newPlant.quantity
}]
});
})
}]);