Skip to main content

14 User Interaction With Ember

Episode 156 · November 21, 2016

See how to add user interaction in your Ember app

Ember Javascript Frontend


Transcripts

So we've created our ember app, and we've created our rails app, and we've hooked them up together through ActiveModel serializers. Now we can get to the fun parts. The first thing we'll do is get a little bit some better styling in here. As you can see, this is just some basic CSS, and some changes to the html. There has been nothing new with ember here, so we'll move on quickly.

Next, we'll add an attributes to our monsters, that says weather it's active or not, this will allow us to add interactivity soon, and it will also give us an opportunity to look at if statements and handle bars, so we'll start with a rails migration rails g migration add-active-attribute to our monster class. Inside that migration we will add a column,

def change 
    add_column :monsters, :active, :boolean 
end 

We can go back to our terminal and run that migration. Then, to make sure we're sending out that active attribute with the JSON, we'll go to our monster serializer, and add it to the attributes. Then you can see that we're sending out the active attribute with the JSON, but they're all null, so we'll need to update some of them in our database. With that done, we'll see that our JSON has both some that are true, and some that null. In JavaScript, null is falsy, so it means it acts sort of like false, and that's made explicit when you to into the ember data model, and we're going to take our active attribute and we're going to make it a boolean active: DS.attri('boolean') so we'll be explicitely turned from a falsy value into an actual false. I'll show you that in the ember inspector. By the way, the ember inspector is very useful, and you can download it as a Chrome add on, and I believe there's also one for FireFox. Anyways, we'll go to our data, and we'll grab our monsters, and you can see that Active is shown as explicitely false, not just null. So we have this data. Let's display it with the user, let's start off super duper simple. It will be Active: {{monster.active}} and that will display true or false. We can do something a little bit easier for the user, let's go ahead and put it first inside the monster div, and then, we'll want to show the word "Active", but only if it's active.

{{#if monster.active}}
    Active 
{{/if}}

If we're using this if helper, and this hash means it's a block helper, so it takes something in between, it's just like our each. There are several different types of things that are block helpers, and you can create your own later. If monsters active will show active. And here we go, we're showing these two as active, but we can do even better. First, we'll create a piece of CSS that gives a darker background on a color for monster, and then we'll see how it is light, and then look how it is there dark. We can use an ifstatement, so if the monster is active, and this is the non block form of the if statement. So if the monster is active, then it will apply the dark CSS class to that div, and you can see that these two are dark end. Therefore, that information is being displayed, no need for that if helper at the bottom. Now we're displaying things differently based on weather the active boolean is true or false. Now let's add a button that let's you toggle between true and false, and you'll see how easy it is to keep your page up to date using ember. So we'll do this with a very simple button, and the button will say "Toggle Active", so it shows up like this, and the user can press it. Now, what should happen when the user presses it? The way that we link that user action with something in the code, is through the action helper, so we'll put in the action helper, and we'll have the toggle active action. Now we go and define this action in a controller, so we will go and we will generate a controller for the application, since that's the route that we're in. Notice that the controller and the route and the template, their name all matches up, so ember will automatically link them, it can do this because of the naming convention, and then you can do cool things like have the ember route inspector in the ember inspector. Anyways, let's define that action

application.js

import Ember from 'ember';


export default Ember.Controller.extend({
    actions: {
        toggleActive(){
            console.log('Hello from the action'), monster
        }
    }
})

Then we see that it's running. Actions, just like functions can take arguments, and that's good, because we'll need to know which monster we're going to want to be toggling this on. This will take in a monster, and then we'll have to feed in that monster from the handlebars, so we'll go ahead and log that monster so you can see what we have. We've got that and it's got some funky stuff here, we can see that the id is 2 there. If we do a different one, it is a different id, so we are indeed grabbing a specific monster. Now we can do with that monster is we can toggle that property

application.js

import Ember from 'ember';


export default Ember.Controller.extend({
    actions: {
        toggleActive(){
            monster.toggleProperty('active')
            monster.save
        }
    }
})

You can see that we're changing weather active is true or false, and that's reflected in the styling, that's really great. It's super easy and the page doesn't have to reload, like you might in peer server side code. Now of course if we reload the page, it will go back to where it was, it's not yet saving it to rails, let's get it to do that. On the ember side, this is really easy. We're just going to call monster.save, and when we do this, it will call monster.save but we'll see that there's an error coming from rails. Let's fix that, that will be in our monsters controller, we'll want the update method, and in this update method, this will look familiar,

monster_controller.rb

def update 
    @monster = Monster.find(params[:id])
    @monster.update_attributes(monster_params)
    render json: @monster 
end

def monster_params 
    params.require(:monster).permit(:active)
end  

Let's go ahead and try that again here, and we toggle it, and no new error message, we'll see that this one has saved, we'll switch everything here, no error messages, and they save. It looks a little different because this on got knocked down to the bottom because it was the most recently updated, and that how we happen to be sorting them. That right there, is your first interactive piece of ember, let's go over that again, let's go through line of it, so we have our rails, we have the active boolean, and then we have the serializer which will send that active boolean out as well. Then we go to our monster.js file, our model, and we add the boolean attribute, and this will make it so even if it's null, if it's a falsy thing, it will coherce it to become false, so that makes it easier to handle in the rest of our application. Then in the handle bars, we have an if statement, where if monster.active is true, then it will have the dark CSS class, then you have the action toggle active, which is triggered whenever you click this button, and it will feed a monster, the current monster into the toggle active action. That toggle active action is stored on the controller, which are different than rails controllers, remember ember routes are close to rails controllers and rails doesn't really have anything like an ember controller anyways, so it does this action, and it takes in that monster, it toggles that property, and then it calls save, this sends a PUT request to your rails server, which is then received here, and so that right there is your first piece of interactivity with ember. I know that this is a long video, but it's actually much quicker to do when you're not explaining everything, and when you have a lot of this already set up. So anyways, now we've covered the core concepts of connecting ember and rails. There is of course a lot more that you can do in ember, so that's why in the next and final video in this series, I'll be showing you just very quickly some of the cool ember features that we didn't get around to talking about and tell you where you can go to find out more about ember. I'll see you there

Transcript written by Miguel

Discussion


Gravatar
Emmanuel LOUISY-GABRIEL on

I think you meant 7:47 "pure client side code" ?


Gravatar
Emmanuel LOUISY-GABRIEL on

amazing ajax made clean !


Gravatar
Mouhamadou DER (40 XP) on

Awesome. Let's jump in ember.


Gravatar
James Shepherd (600 XP) on

How would you recommend dealing with the error "Can't verify CSRF token authenticity"? I added "skip_before_filter :verify_authenticity_token" to the monsters controller so it works fine, but I know this is not the best long term solution. Thanks!


Login or create an account to join the conversation.