0

Below code show binding for a List emails but I am having trouble binding the newly added emails to the $scope.emails (does not contain the new email user added). Any idea?

// emails is a List on server side // email is a string

so i bind ng-model= email but

but doing the below does not work

$scope.contactInformation.Emails.push(email); --> complains about duplicates


<div ng-repeat="email in emails">
    <div class="form-group">
    <label for="email">Email</label>
    <div class="input-group input-group-sm input-group-minimal">
         <span class="input-group-addon">
               <i class="linecons-mail"></i>
         </span>
         <input type="text" class="form-control" ng-model="email" />
     </div>
     <button class="btn btn-primary" ng-show="$last" ng-click="AddEmail()">Add Email</button>

Controller.js

// modelParams.ContactInformation.Emails = new List(string)() when retrieved on server side

$scope.emails = modelParams.ContactInformation.Emails;

$scope.AddEmail = function () {
    $scope.contactInformation.Emails.push({ email: null });
};
Sudheer
  • 2,955
  • 2
  • 21
  • 35
ove
  • 3,092
  • 6
  • 34
  • 51
  • your html template uses lowercase `emails` while in your controller use `Emails` with a capital 'E'. If that's a mistake in your post then you need to correct it. – T.V. Nov 06 '14 at 03:28
  • `$scope.contactInformation.Emails` isn't clearly defined. your `AddEmail` method needs to either be `$scope.emails.push(...)` or `modelParams.ContactInformation.Emails.push(...)` – T.V. Nov 06 '14 at 03:50
  • // emails is a List on server side // email is a string so i bind ng-model= email but but doing the below does not work $scope.contactInformation.Emails.push(email); --> complains about duplicates – ove Nov 06 '14 at 03:53
  • Mind showing your solution on pluckr or smilar? cheers – ove Nov 06 '14 at 03:53
  • If you can create a plunker reproducing the issue, I'll take a look. At this point, based on your post, I'm not sure you have a problem, assuming I've interpreted your post correctly. Have you consider making the change that @NewDev suggested with changing `ng-model="email"` to `ng-model="email.email"` – T.V. Nov 06 '14 at 04:08
  • I think it should be `$scope.contactInformation.Emails.push({ email: $scope.email });` – Sebastian Osuna Nov 06 '14 at 04:13
  • why was the question edited to - problem solved?? – Sudheer Nov 06 '14 at 06:46

1 Answers1

0

I'm amending the answer to avoid confusion... Here's is how it should be done - fill in the blanks to fit it for your scenario.

controller.js

// assuming emails is an array of strings (whether defined locally or from a server)
$scope.emails = ["email1", "email2", ...];

$scope.addEmail = function(){
  $scope.emails.push(""); // push an empty array as new not-yet-set email
}

The HTML is largely correct. I would have moved the "add" button to outside of the ng-repeat div instead of relying on $last:

<div ng-repeat="email in emails track by $index">
  <input type="text" ng-model="email" />
</div>
<button ng-click="addEmail()">Add Email</button>

EDIT:

The example above would, actually, not work because the ng-model within ng-repeat binds to a primitive (string) email.

There are 2 ways to fix:

approach 1

Make an array of objects. If you get an array of strings from the server, you'd need to convert to an array of objects, like so:

$scope.emails = [];
angular.forEach(arrayOfEmailStrings, function(v, k){ $scope.emails.push({value: v}); });

And access like so:

<input type="text" ng-model="email.value" />

approach 2

Use the $index property:

<input type="text" ng-model="emails[$index]" />
Community
  • 1
  • 1
New Dev
  • 48,427
  • 12
  • 87
  • 129
  • // emails is a List on server side // email is a string so i bind ng-model= email but but doing the below does not work $scope.contactInformation.Emails.push(email); --> complains about duplicates – ove Nov 06 '14 at 03:50
  • What is `$scope.emails`? Is it an array of strings? – New Dev Nov 06 '14 at 04:01
  • Yes, array of strings. I thought this would be simple enough to do but not so – ove Nov 06 '14 at 04:06
  • $scope.emails.push(""); --> will fail on click twice. Angularjs does not allow duplicates in ng-repeat – ove Nov 06 '14 at 04:14
  • track by $index allows adding and for some reasons $scope.emails do not add the newly typed email but only contain "" – ove Nov 06 '14 at 04:26
  • Ah, that's right.. That's because `ng-repeat` creates a child scope and because `email` is a primitive (and not an object), the edit happens in the child scope and not in the parent scope. Ugh... Let me fix this. – New Dev Nov 06 '14 at 04:30