Lesson Description

The "Event Listeners" Lesson is part of the full, Getting Started with JavaScript, v3 course featured in this preview video. Here's what you'd learn in this lesson:

Kyle introduces event listeners as a core concept in DOM manipulation, explaining how they make web pages interactive by allowing code to run based on user actions like clicking buttons or typing in input fields. He demonstrates adding a click event listener to a button, showing how multiple event listeners can be added without overwriting each other, and then discusses the process of removing event listeners, emphasizing the importance of passing a reference to a function for successful removal. Finally, he explores the event object passed to event listeners, highlighting properties like e.target and e.current target to differentiate between the element interacted with and the element being listened to.

Preview

Transcript from the "Event Listeners" Lesson

[00:00:00]
>> WebDevSimplified: Now moving on, I want to talk about event listeners, which are probably the core thing you're going to be doing inside of the DOM, and event listeners are what makes the page actually interactive. So when you click on a button or do something, you can run code based on those actions. And these events can be literally anything, but for the most part there are different things that the user does with the page.

[00:00:16]
Clicking on a button, typing in an input field, resizing the window even has a specific event we can listen for. Now, the basic event listeners in JavaScript are going to be like a click event listener. So let's go ahead and look at what creating a click event listener would look like. Let's say we have a button here, and that's just going to be equal to document.querySelector, and we want to get a button.

[00:00:37]
And of course we'll want to add a button onto our page. So inside of here instead of this H1, we'll just add in a button that just says click. There we go. So now you can see we have a button on the right-hand side of our screen. Now that we've selected that button to add an event listener to it, we can say button.addEventListener, and of course we have a ton of different properties. The one we care about is addEventListener.

[00:00:58]
So type out the word addEventListener—that allows you to add an event listener—and this takes a few different properties. The first thing that you need to pass to it is the type of event you want to listen for. You can see there are a lot of events inside of JavaScript. For the most part, you're probably only going to use a handful of these events, maybe three, four, five of them at any given time.

[00:01:16]
The most common is going to be the click event listener. This allows you to do something when you click on an element. In our case, when we click on our button, we want to run some code. To determine what type of code we want to run, we need to pass it a function. So we're going to be using an inline arrow function, which is what I generally use for these types of situations. And now anytime we click on a button, the code inside of here is going to run.

[00:01:37]
So I'm just going to say console.log "Clicked", so it's going to just print out "Clicked" to the console every time I click my button. You'll notice by default nothing happens, but as soon as I click on this button, you can see the text "Clicked" gets printed out in my console, and every single time I click that, it just keeps logging out "Clicked" over and over again. So the key to addEventListener is you need to make sure you call it on some type of element on your page.

[00:01:59]
You pass it in the type of event that you want to listen for, and then you pass it the code you want to run whenever that event occurs, whether it's a click or an input or any other type of event that you care about. Now moving on, we can add event listeners to anything. For example, we can add them to specific elements like an input element or a button. We can add them directly to the document. We can even add event listeners directly to the window object itself.

[00:02:20]
It really depends on where you want those event listeners to live. You can also add multiple event listeners to the same exact object. So I'm going to come in here, I'm going to add a brand new event listener to our button. This one will say "Clicked 2", and this first one will say "Clicked 1". There we go. And now when we click on our button, you're probably thinking, okay, what will happen? Is it going to log out "Clicked 2"?

[00:02:40]
Is it going to log out "Clicked 1"? Is it going to log out both? Well, what happens in JavaScript is when you add event listeners, they just keep adding on. They don't overwrite each other. So when I click on this, you'll notice it prints out "Clicked 1" and it'll print out "Clicked 2". It essentially puts them out in whatever order you add them. So I first add "Clicked 1", and then I add "Clicked 2".

[00:02:59]
So it's going to run the first one I add first and the second one that I add second. So every time you add event listeners, it just keeps piling them on to each other until eventually you get all the event listeners that you want. They never overwrite each other or remove each other. Now, speaking of removing event listeners though, obviously sometimes you want to stop having an event listener inside of your code.

[00:03:19]
To do that is a little bit complicated and you'll definitely run into some problems potentially. So first of all, let's create a function that we want to do. So we'll say function printClick, and this is a function that's just going to console.log "Clicked". So at least we have something that'll show up inside of our page whenever we click on our button, and we want that to be the thing we add as our event listener.

[00:03:40]
So here instead of passing that function inline, we'll just pass that printClick function just like this. And now if we've done everything correctly, clicking the button should log out the text "Clicked". But let's say that we eventually want to remove that. We don't want to have that on there anymore. Well, I can come in here and I can actually remove that by just saying button.removeEventListener, so it's the opposite of add—instead of add, we remove the event listener.

[00:04:02]
We then need to tell it what type of event we want to listen for or to remove. In our case we're removing a click event listener. And finally, we want to tell it what function we're removing. In our case we're removing the printClick function. Now when I click on this button, you'll notice it doesn't actually print anything because we removed the event listener. Now you may be wondering why I went ahead and created a brand new function for printClick.

[00:04:23]
Why don't I just do it inline? So let's go ahead and do that. We'll just make this an inline function, turn it back into an arrow function just like that, and we'll do the exact same thing down here. So now we are essentially adding that clicked function and we're removing that clicked function. So it seems like it should be doing the same thing, but when we click over here, you'll notice it's still logging out "Clicked".

[00:04:44]
The reason for that brings us all the way back to reference versus value. These functions, while they look exactly the same, they reference two different places because we create a brand new function here and we're creating a brand new function here. So these are two entirely separate functions that have no idea about each other. So when I add this function, it adds it fine, and when I go to remove this function, it's trying to remove a function that is brand new.

[00:05:06]
It doesn't already exist on it. So whenever you want to remove a function as an event listener, you need to make sure that you have it as a separate function so they can both reference the same thing. You can see here printClick and printClick both reference this same exact original function. This is one of the biggest problems you'll run into is passing inline functions to addEventListener means that you can never remove them.

[00:05:26]
You need to specifically pass a reference to some other function to be able to remove it at a later point. And here's kind of a showcase of that. You can see when we pass these inline like this, it doesn't actually remove it because it creates a new function here every single time. Now another nice thing about these event listeners is they give us a lot of information in the form of the event object.

[00:05:45]
So inside of our event listeners, we are passed along an event object. Let me just bring this back to where we had an inline function version. There we go. We'll get rid of all the code we have here and up here, and we have access to this event object. Often you'll see this called e, maybe event. It doesn't matter what you call it, you can call it anything you want. We'll call it event to be a little bit more self-explanatory, and we'll just log out whatever that event is.

[00:06:07]
And this will give us all the information about the event that occurs. So when I click on this button, you can see we get something called a PointerEvent, and this PointerEvent contains a bunch of information such as what buttons I clicked, where I clicked on my screen, all these other things. You can see there's a ton of different information inside here. But the important thing is this gives you more details about what happened in your event.

[00:06:27]
Where did you click? What did you click on? Did I use a right click? Did I use a left click? All of that information is inside of here somewhere, and every different type of event has different information. For example, if I have an event for when I resize my screen, that'll tell me things like how big my screen is, while when I click on a button, that's not going to tell me how big my screen is because it's not relevant to that type of event.

[00:06:49]
Now some common properties you're going to see in type events. First of all, e.target. This tells you the element that caused the event to be triggered. So in our case, inside of here, if I did event.target, whenever I click on my button, that's going to give me my button element because that's the thing that I clicked on on my page. We also have the currentTarget, and this is the thing that you added your event listener to.

[00:07:11]
So if I were to change this to currentTarget, currentTarget here specifically references the button because that's the thing I added the event listener on. Doesn't matter what triggers the event, all that this cares about is what I added this element to. In many cases, these are going to be exactly the same, but I'll show you reasons why they may be different in the very next section. And moving on a little further, we also have some events right here for mouse-related stuff.

[00:07:33]
So for example, the clientX and the clientY—that tells you where you clicked on the screen for things like a click event listener or any mouse-related event. And we also have modifiers, so like e.ctrlKey or e.shiftKey, e.altKey. These will be true or false depending on if I'm holding down Control or Shift or Alt when I do things such as clicking on the screen. So you can do different things if someone's holding down Control when they click versus if they're not.

[00:07:55]
Now to talk a little bit about the difference between target and currentTarget, like I said, target is the specific thing that you interact with to cause the event to occur, while the currentTarget is the element that is actually being listened to. So here we can change button here to document. So now I have my document and I want to log out what my currentTarget and my target are. So when I click on my document, you can see that it's going to log out the body as the target while my currentTarget is the document.

[00:08:22]
If I were to clear this out and instead click on my button, you'll now see here that button is my target while the currentTarget is document. You'll see this currentTarget always refers to whatever you're adding the event listener to, while target is the thing you specifically interacted with. In our case, it's the thing that I clicked on. If I click on a button, it'll render button. If I click on the body, it'll render body, and so on.

[00:08:42]
So these two properties, while they may seem really similar, can be different, and you may want to use one over the other depending on what you're asking yourself. If you care about the current target, use currentTarget. If you care about the thing you clicked on or interacted with, make sure you use target. Now, some common event types, I just have a bunch of them listed out here. There's a link right here that goes to all the event types.

[00:09:04]
There's literally hundreds of them. When it comes to mouse events, by far the most common is the click event. That's the one you'll use 99% of the time. Focus events—these are focus and blur. These determine if an element is focused currently by you or not. So essentially if you have an input that allows you to type text into a page, when you click that input, you are focusing on that input, so it'll run the focus event.

[00:09:24]
And when you click outside of that input, it'll be considered a blur event, so it'll say that you're losing focus and call this blur event. Inputs have two types of events that you're going to be using. The input event, which is a little bit kind of confusingly named, that happens every single time you change something in your input. To show you the difference, let's just add an input to our page.

[00:09:49]
There we go. So now we have an input on our page that I can type different text inside of. And what I want to do is I want to select that input element. Here we go, and I want to add an event listener to that input element. And for our case, we're going to add an event listener here on input, which again will run every single time we change something inside of our input, and we can just render out whatever we want.

[00:10:10]
There we go. So now every single time I type something inside of here, doesn't matter what I do, typing, removing, anytime I change that input value, it's going to log out this particular event. The other type of event is the change event, and this one only fires when you change an input and then you stop focusing on it. So if we change this back to a change event instead. There we go. And now I come into this input.

[00:10:32]
As I'm typing and changing things, you'll notice nothing is being logged out, but as soon as I click off of my input, now it's going to log that I changed the value inside that input. Now if I click on this input and click off of it without changing anything, you notice that nothing actually changes or fires. But if I change something and then click off, that change event will occur. This is why more often than not when I'm using input event listeners, I use the input event because I usually care about every time the user changes and not just when they unfocus my particular input element.

[00:11:01]
Now when it comes to window events, the only one you really care about is resize because when I resize my browser, I may want to listen to that. That's where the resize event is going to come in specifically. Now another thing that you can do with events is you can prevent the default behavior. Certain elements have default behavior, for example, a form when you click to submit the form, it'll automatically submit that data to wherever you tell the form to submit the data.

[00:11:26]
Anchor tags, for example, if you click on a link, it'll bring you to whatever that page is by default. You can prevent that behavior though. So we come into our application, I'm just going to add a link. And we'll just add in an href and we'll just say that this goes anywhere, it doesn't matter. Here we go, google.com. So normally when I click on this link, it would bring me to Google. That's perfectly fine, but I want to prevent that default behavior.

[00:11:52]
So let's access our link element, we'll just call it a here. And what I want to do is we want to add an event listener when we click on this because that's the thing we want to override. And I can use that event object that I can call the preventDefault function directly on this object. Now when I click on this link, instead of actually redirecting me to Google, it's going to prevent that default logic and let's just say it's going to log out something to the screen.

[00:12:13]
It doesn't really matter what it is. So now when I click on this, you can see it didn't redirect me to Google, but it did log out some data to my screen. So using preventDefault can help you prevent that default behavior that's built in if it's something you don't want. I would recommend never preventing the default behavior of a link because usually you want links to actually work, but this is really useful for things like forms where you may want to handle all that form-related code on your own.

[00:12:36]
Now some common mistakes that you may run into is when you try to add an event listener, you may accidentally call that function by putting the parentheses afterwards. Remember, if you're passing a function to another function, you don't want to call the function, you want to pass it as a variable without those extra parentheses. And then of course, using target instead of currentTarget could land you in some weird problems.

[00:12:56]
For example, here, I have a span inside of my button. So when I click my button, it'll actually say the span is the target because that's the thing that I clicked on since it's in my button, while my currentTarget is going to reference my button. So depending on which one you want, you want to make sure you use target or currentTarget properly.

Learn Straight from the Experts Who Shape the Modern Web

  • 250+
    In-depth Courses
  • Industry Leading Experts
  • 24
    Learning Paths
  • Live Interactive Workshops
Get Unlimited Access Now