У меня есть проект, в котором вы пишете заметку в формуляре. Затем вы отправляете эту заметку в информационный контейнер (теперь это просто массив для тестирования, но он должен быть позже).
Формулировка имеет следующий контроллер:
app.controller('controlFormulario', ['$scope', 'SubmitService', function($scope, submitService) {
$scope.formData = {
"titulo":"",
"texto":"",
"fecha": new Date()
};
$scope.submit = function() {
var temp = $scope.formData;
submitService.prepForBroadcast(temp);
}
// more things we don't need now
... который связан с этой частью DOM, которая добавляется в нее, через директиву:
<form ng-controller="controlFormulario as formCtrl">
<div class="element">
<div class="form-group" ng-class="{'has-error': formData.titulo.length > 50 }">
<label for="inputTitulo">Título</label>
<input type="titulo" class="form-control" id="inputTitulo" ng-model="formData.titulo">
<span ng-show="formData.titulo.length > 50" id="helpBlock" class="help-block">El título no puede exceder los 50 caracteres.</span>
</div>
<div class="form-group">
<label for="inputTexto">Texto</label>
<textarea class="form-control" id="inputTexto" ng-model="formData.texto"></textarea>
</div>
<div class="form-group">
<label for="fecha">Fecha</label>
<input type="fecha" class="form-control" id="fecha" ng-model="formData.fecha" disabled>
</div>
<div class="form-group" >
<button class="btn btn-primary" style="height:35px;width:100px;float:right;" id="submit"
ng-disabled="isDisabled()" ng-click="submit()">
Enviar
</button>
</div>
</div>
<div class="note" ng-show="formData.titulo.length > 0">
<div class="title" ng-model="formData.titulo" class="title">{{formData.titulo | limitTo:50}}</div>
<div class="text" ng-model="formData.texto" class="text">{{formData.texto}}</div>
<div class="date" ng-model="formData.fecha" class="date">{{formData.fecha | date}}</div>
</div>
</form>
Это моя директива (я не думаю, что это действительно необходимо, но на всякий случай):
app.directive('formulario', [function() {
return {
restrict: 'E', // C: class, E: element, M: comments, A: attributes
templateUrl: 'modules/formulario.html',
};
}]);
Я использую службу для передачи данных между предыдущим контроллером и контроллером заметок (который управляет объектами заметки массива). Это сервис:
app.factory('SubmitService', function($rootScope) {
var data = {};
data.prepForBroadcast = function(recvData) {
data.data = recvData;
this.broadcastItem();
};
data.broadcastItem = function() {
$rootScope.$broadcast('handleBroadcast');
};
return data;
});
... и я получаю его в этой части моего контроллера заметок:
app.controller('noteController', ['$scope', 'SubmitService', function($scope, submitService) {
var nc = this;
$scope.$on('handleBroadcast', function() {
nc.pruebaNota.push(submitService.data);
$scope.formData.titulo = "";
$scope.formData.texto= "";
$scope.formData.fecha = new Date();
});
// more things, the array, etc...
ОК. Это должно работать, и это происходит, но происходит что-то странное: как вы можете видеть, предварительная записка привязана к форме ng-model. Это отлично работает, хорошо. Но когда я отправляю форму, новый объект примечания привязывается к форме (поэтому, если я удаляю текст формы, примечание отображается пустым, а если я что-то пишу, оно автоматически обновляется как в примечании к просмотру, так и в новом примечание), когда между ними нет никакой связи. Новая заметка, которая динамически отображается на экране, не должна быть привязана ни к чему.
Я делаю что-то неправильно? Некоторая помощь будет очень приятной!
Вы забываете что-то действительно важное. Адрес памяти. Итак, грубая идея - это что-то вроде: представьте, что $scope.formData
находится в адресе 123123. Сначала вы создаете temp
переменную, указывающую на 123123, затем отправляете ее в службу, и служба хранит тот же адрес 123123 в data.data
.
Затем во втором контроллере вы говорите: эй, я хочу работать с data.data
(AKA ваши данные в 123123), у вас есть SubmitService
.
Теперь, когда вы снова изменяете $scope.formData
, вы обновляете то, что у вас есть в этом 123123, и все, что "смотрит" на этот адрес, будет обновляться.
Это грубая идея. Чтобы указать на это просто, вы изменяете ту же самую информацию повсюду.
См. Здесь: http://plnkr.co/edit/zcEDQLHFWxYg4D7FqlmP?p=preview
Как предложил AWolf, чтобы исправить эту проблему, вы можете использовать angular.copy
следующим образом:
nc.pruebaNota.push(angular.copy(submitService.data));
angular.copy(...)
чтобы создать копию переменной. Пожалуйста, посмотрите на этот обновленный plunkr .