In the previous topic, we learned how JavaScript can manipulate the DOM—changing text, styles, attributes, and even creating or removing elements.
But there's another important question:
How does JavaScript know that something happened on the webpage?
For example:
A user clicked a button.
They typed something into an input.
The mouse moved over an element.
A form was submitted.
The webpage finished loading.
These actions are called events.
What is a DOM Event?
A DOM event is an action or occurrence that happens in the browser and can be detected and handled using JavaScript.
For example, when a user clicks a button, the browser generates a click event.
JavaScript can listen for that event and run some code.
User performs an action
↓
Browser detects the event
↓
JavaScript listens for it
↓
Event handler runsThis is what allows webpages to become interactive.
The addEventListener() Method
The most common way to handle DOM events is addEventListener().
Syntax
element.addEventListener("event", function);For example, suppose we have:
<button id="btn">Click Me</button>We can listen for a click:
const button = document.querySelector("#btn");
button.addEventListener("click", () => {
console.log("Button clicked!");
});Now every time the user clicks the button, the message is printed.
Common DOM Events
JavaScript supports many different events.
Event | Happens when... |
|---|---|
| An element is clicked |
| An element is double-clicked |
| Mouse button is pressed |
| Mouse button is released |
| Mouse moves |
| Mouse enters an element |
| Mouse leaves an element |
| A keyboard key is pressed |
| A keyboard key is released |
| Input value changes |
| An input's committed value changes |
| An element receives focus |
| An element loses focus |
| A form is submitted |
| HTML document has been loaded and parsed |
Let's look at some of the important ones.
Click Event
The click event is probably the first event you'll use.
HTML:
<button id="btn">Click Me</button>JavaScript:
const button = document.querySelector("#btn");
button.addEventListener("click", () => {
console.log("You clicked the button!");
});Every click triggers the function.
Changing the Page on Click
Events become more useful when we combine them with DOM manipulation.
HTML:
<h1 id="title">Hello World</h1>
<button id="btn">Change Text</button>JavaScript:
const title = document.querySelector("#title");
const button = document.querySelector("#btn");
button.addEventListener("click", () => {
title.textContent = "Text Changed!";
});Now clicking the button changes the heading.
This is the basic pattern behind many interactive web features:
Event → JavaScript logic → DOM updateKeyboard Events
We can also detect keyboard actions.
For example:
document.addEventListener("keydown", (event) => {
console.log("Key pressed:", event.key);
});If the user presses the A key, we might get:
Key pressed: aThe event object gives us information about what happened.
For example:
document.addEventListener("keydown", (event) => {
if (event.key === "Enter") {
console.log("Enter was pressed!");
}
});This can be useful for keyboard shortcuts, search boxes, games, and form handling.
The Event Object
When an event occurs, the browser provides information about that event.
We can receive it as a parameter:
button.addEventListener("click", (event) => {
console.log(event);
});This event object contains useful information about what happened.
For example:
button.addEventListener("click", (event) => {
console.log(event.type);
});Output:
clickWe can also find the element that triggered the event:
button.addEventListener("click", (event) => {
console.log(event.target);
});event.target refers to the element that actually triggered the event.
Input Events
Suppose we have an input field:
<input id="username" type="text">We can detect whenever its value changes:
const input = document.querySelector("#username");
input.addEventListener("input", (event) => {
console.log(event.target.value);
});If the user types:
Johnthe handler runs as the value changes.
This is useful for live search, validation, character counters, and similar features.
Form Submit Event
Forms are another important place where events are used.
HTML:
<form id="loginForm">
<input type="text" id="username">
<button type="submit">Login</button>
</form>JavaScript:
const form = document.querySelector("#loginForm");
form.addEventListener("submit", (event) => {
event.preventDefault();
console.log("Form submitted!");
});What does preventDefault() do?
Normally, submitting a form may cause the browser to navigate or reload the page.
event.preventDefault();prevents that default browser behavior.
This is very useful when you want JavaScript to handle the form submission yourself.
Mouse Events
We can respond to mouse interactions too.
For example:
const box = document.querySelector("#box");
box.addEventListener("mouseenter", () => {
console.log("Mouse entered the box");
});
box.addEventListener("mouseleave", () => {
console.log("Mouse left the box");
});This can be used for things like tooltips, menus, hover effects, and interactive components.
Adding Multiple Event Listeners
An element can have multiple listeners for the same or different events.
button.addEventListener("click", () => {
console.log("First handler");
});
button.addEventListener("click", () => {
console.log("Second handler");
});When the button is clicked, both handlers can run.
Removing an Event Listener
We can remove an event listener using removeEventListener().
However, there's an important detail: we need to provide the same function reference that was used when adding the listener.
function handleClick() {
console.log("Clicked!");
}
button.addEventListener("click", handleClick);
button.removeEventListener("click", handleClick);After removing it, clicking the button will no longer trigger handleClick.
This won't work as expected:
button.addEventListener("click", () => {
console.log("Clicked!");
});
button.removeEventListener("click", () => {
console.log("Clicked!");
});These are two different function objects, even though their code looks identical.
Event Delegation
When working with many elements, we don't always need to add an event listener to every single element.
Instead, we can listen on a parent element and use event delegation.
For example:
<ul id="list">
<li>Apple</li>
<li>Banana</li>
<li>Mango</li>
</ul>Instead of adding a listener to every <li>:
const list = document.querySelector("#list");
list.addEventListener("click", (event) => {
if (event.target.matches("li")) {
console.log(event.target.textContent);
}
});Now the parent <ul> handles clicks from its list items.
This becomes especially useful when elements are added dynamically.
Event Bubbling
One important concept behind event delegation is event bubbling.
Suppose we have:
<div id="parent">
<button id="child">Click Me</button>
</div>If we click the button, the event can first occur on the button and then bubble upward through its ancestors.
Conceptually:
button
↑
div
↑
body
↑
documentFor example:
const parent = document.querySelector("#parent");
const child = document.querySelector("#child");
parent.addEventListener("click", () => {
console.log("Parent clicked");
});
child.addEventListener("click", () => {
console.log("Child clicked");
});Clicking the button can produce:
Child clicked
Parent clickedbecause the click event bubbles from the button to the parent.
Stopping Event Propagation
Sometimes we don't want an event to continue bubbling.
We can use:
event.stopPropagation();For example:
child.addEventListener("click", (event) => {
event.stopPropagation();
console.log("Child clicked");
});Now the click won't continue bubbling to the parent listener.
DOM Events vs Inline Events
You may sometimes see event handlers directly inside HTML:
<button onclick="sayHello()">Click Me</button>Although this can work, using addEventListener() is generally preferred:
button.addEventListener("click", sayHello);It keeps your HTML structure and JavaScript logic separate, which makes larger applications easier to maintain.
A Practical Example
Let's create a simple counter using DOM events.
HTML:
<h2 id="count">0</h2>
<button id="increase">Increase</button>
<button id="decrease">Decrease</button>JavaScript:
const count = document.querySelector("#count");
const increase = document.querySelector("#increase");
const decrease = document.querySelector("#decrease");
let value = 0;
increase.addEventListener("click", () => {
value++;
count.textContent = value;
});
decrease.addEventListener("click", () => {
value--;
count.textContent = value;
});Now the buttons actually interact with the webpage:
0
↓ Increase
1
↓ Increase
2
↓ Decrease
1This small example combines several concepts we've already learned:
Variables
Functions
Arrow functions
DOM selection
textContentEvent listeners
Conclusion
DOM events are what make webpages interactive.
The most important concept is:
element.addEventListener("event", handler);For example:
button.addEventListener("click", () => {
console.log("Button clicked!");
});Remember these important ideas:
Event → Something happens in the browser.
Event listener → JavaScript waits for that event.
Event handler → Code that runs when the event occurs.
Event object → Contains information about the event.
preventDefault()→ Stops the browser's default behavior.stopPropagation()→ Stops the event from propagating further.Event delegation → Handle events from child elements using a parent.
Once you understand DOM events, you can start building genuinely interactive features such as forms, menus, buttons, modals, live search, counters, dropdowns, and interactive UI components.