⚠️ This lesson is retired and might contain outdated information.

Modify State with ng-model and an AngularJS controller

Lukas Ruebbelke
InstructorLukas Ruebbelke
Share this video with your friends

Social Share Links

Send Tweet
Published 10 years ago
Updated 2 years ago

We are going to learn how to edit an existing bookmark by building on a lot of the same techniques from the previous video. We will also learn how to edit a bookmark and not actually save the change back to the collection until we are ready.

Find the code on Github. Tags correspond to the lesson.

Lukas Ruebbelke: [00:00] Welcome to another video in the Eggly series where I am going to show you how to edit a bookmark. In the previous video we saw how to actually create a bookmark and how using forms in AngularJS worked.

[00:17] We are going to continue along that line of thinking by using those same techniques to edit an existing bookmark. If we go here and we click the edit icon or the pencil icon, we are going to replace this edit bookmark placeholder with the actual edit form.

[00:42] Let's hop into the code and I am going to paste in the actual edit form. This is very similar to the create form that we saw in the previous video. We're toggling this div by the value that is returned from shouldShowEditing.

[01:09] Then we're also keeping track of the bookmark that we're editing through an edited bookmark property. Then we have this form that we're calling "updateBookmark" on submit and it's sending in the edited bookmark, so we're going to see that in the code in just a moment.

[01:29] From there, we are binding using ng-model to the title and URL of edited bookmark. In the JavaScript -- let's just hop down here...The first thing we need to do is create an editedBookmark property. We're going to set this to null.

[01:52] Then from here, we are going to create a method called setEditedBookmark, that accepts a bookmark parameter and simply assigns the value of editedBookmark to this parameter. Then we are going to go down and assign this to the scope, like so.

[02:26] Now it is available to the view. Let's hop in here and in an incremental step set the editedBookmark. We are going to do that when the user clicks the edit icon. The cool thing about AngularJS and the ng-click, ng-submit, and other action directives is you can actually call more than one method when that action is actually executed by the users.

[03:01] In this case it's setEditedBookmark, passing the bookmark, colon. It's going to set the editedBookmark and then initiate the startEditing state. Let's hop into the HTML and see what we are working with.

[03:22] You can see that it actually is setting the editedBookmark property and binding to it in the form. Now, the problem is when I start to type here, not only does it update the property on the form itself, but also up here. The problem is if I cancel, the changes that I've made have already taken place and I have no way to undo them.

[03:45] What we're actually going to do is hop back into the code and the way around that is to, when you set the editedBookmark, we are going to use angular.copy and actually create a copy of the bookmark and assign that to editedBookmark.

[04:03] Then, when we are done and we actually going to edit the bookmark and we've completed that, then we will write it back to the bookmarks collection.

[04:14] Let's see this in action, just refresh. Here, as you can see that when I type it updates locally in the edit form, but it does not actually update outside of that to the actual bookmark that we are editing.

[04:33] The next step is to actually hook up the edit method, so we are going to create a method called updateBookmark that takes a bookmark property. From here we are going to get the index of the bookmark that we are editing. This is where lo-dash comes in. We're going to call findIndex and we're going to loop over bookmarks and then we're just going to set this method in here to compare the current bookmark.id to the bookmark.id that we passed in.

[05:21] Then from here, we are going to simply say bookmarks [index] = bookmark. A little bit of housecleaning, we are going to set editedBookmark to null and we are going to set the isEditing state to false.

[05:50] Let's make this available to the view. There we go. Let's refresh the page, click on the edit icon, and let's update this. Click enter and then now you can see the bookmark has actually been copied back. The edited bookmark has been copied back to the bookmarks array.

[06:18] Then when we click on this again, the state is actually persisting and then we can set this back, click save, and it's good to go.

[06:29] Now, one UX improvement that we can make is when you are editing a bookmark, it would be nice if we actually could visually show that this is the bookmark that's being edited.

[06:42] We can do that fairly easy. Let's add one more feature to this before we call it a day. I'm going to create one more method called isSelectedBookmark and this is going to be similar to what we did with the selected category.

[07:03] We are going to, first, check to see if editedBookmark is not equal to null and if the editedBookmark.id equals bookmarkId. If it returns true, then we know we have the selected bookmark. Just hop in here...

[07:40] Then, in the HTML, we are going to attach an ng-class. We are going to set an active class here. We are going to call isSelectedBookmark and pass in the bookmark.id.

[08:10] Let's see what happens when we refresh this and edit a bookmark. You can see here, we are now applying the active class and its setting the bookmark that is currently active to blue. That's just a nice visual indicator to show this is the bookmark we're editing and we're doing this by actually binding the CSS to the state of the application or, essentially, your view model, which is the controller and the scope together.

[08:41] That's pretty cool. Then we just cancel and we are good to go.

[08:50] This concludes our video for editing a bookmark. Stay tuned for the next video where I'm going to show you how to delete a bookmark, thus completing the create, read, update, and delete cycle.

[09:06] It's been super awesome hanging out with you on this video. Stay tuned for the next video. I'll see you in just a moment.

Israel
Israel
~ 10 years ago

for some reason my active class didn't work to highlight the bookmark being edited. The div surrounded this code has the main class which in the css seems to be correct.

<div ng-class="{'active':isSelectedBookmark(bookmark.id)}" ng-repeat="bookmark in bookmarks | filter:{category:currentCategory.name}"> <button type="button" class="close">&times;</button> <button type="button" ng-click="setEditedBookmark(bookmark);startEditing()" class="btn btn-link"><span class="glyphicon glyphicon-pencil"></span></button> <a href="{{bookmark.url}}" target="_blank">{{bookmark.title}}</a> </div>

CSS:

.main .active span, .main .active > a { color: #5bc0de; }

Jay
Jay
~ 10 years ago

There is a minor bug with the active class on the bookmark. When you cancel editing, it still shows that the bookmark you were editing is active. The fix is similar to the fix in the create video - set editedBookmark to null when cancelEditing is called.

Xavier
Xavier
~ 9 years ago

I second that, I added setEditedBookmark(null);

Piyush
Piyush
~ 9 years ago

Is there an alternative to using Lodash for finding a bookmark in the collection? I'd love to go learn Lodash, but for the moment I want to stay here.

Henrique Zavareze
Henrique Zavareze
~ 8 years ago

For some reason my underscore function always returns -1. Any thoughts?

''' var index = _.findIndex($scope.bookmarks, function (b) { return b.id = bookmark.id; }); '''

Kyle Kerley
Kyle Kerley
~ 8 years ago

Everything in this video is working except for the actual updating of the record. No matter what I do, when I hit "save" on the edit form, the changes are not reflected in the list of bookmarks.

EDIT: Turns out, it's because I was coding this in a simple HTML file without Bootstrap (or using the provided code on Github so I could get a feel for coding it all myself) and therefore missed the part where I had to manually include the lodash library. After that was added, everything worked fine.

Sina
Sina
~ 7 years ago

using '=' is for assigning values. If you want to compare, you need to use '==' or '==='

Markdown supported.
Become a member to join the discussionEnroll Today