<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Manali Khattar</title>
    <description>The latest articles on DEV Community by Manali Khattar (@khattarmanali).</description>
    <link>https://dev.to/khattarmanali</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F965022%2F302f49eb-e51c-4c4f-80a4-cedd124d2897.jpeg</url>
      <title>DEV Community: Manali Khattar</title>
      <link>https://dev.to/khattarmanali</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/khattarmanali"/>
    <language>en</language>
    <item>
      <title>JavaScript’s Event Loop Explained Visually — Once and for All</title>
      <dc:creator>Manali Khattar</dc:creator>
      <pubDate>Thu, 19 Jun 2025 08:30:31 +0000</pubDate>
      <link>https://dev.to/khattarmanali/javascripts-event-loop-explained-visually-once-and-for-all-2eag</link>
      <guid>https://dev.to/khattarmanali/javascripts-event-loop-explained-visually-once-and-for-all-2eag</guid>
      <description>&lt;p&gt;Ever wondered why console.log() inside a setTimeout(..., 0) runs after everything else?&lt;/p&gt;

&lt;p&gt;Or why your Promise logs show up before your timer, even if both seem async?&lt;/p&gt;

&lt;p&gt;Welcome to the world of the Event Loop — one of JavaScript’s most powerful (and misunderstood) features.&lt;/p&gt;

&lt;p&gt;In this post, I’ll walk you through exactly how the Event Loop works using:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Minimal theory&lt;/li&gt;
&lt;li&gt;Real-world examples&lt;/li&gt;
&lt;li&gt;Simple visual diagrams&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Let’s dig in.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;What’s Inside the JavaScript Runtime?&lt;/strong&gt;&lt;br&gt;
Before we talk about the Event Loop, here’s a quick overview of the runtime environment.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;+--------------------+
|    Call Stack      |  ← Executes your functions
+--------------------+
         ↓
+--------------------+
|     Web APIs        |  ← Timers, fetch, DOM
+--------------------+
         ↓
+------------------------+
|   Macrotask Queue       | ← setTimeout, I/O
+------------------------+
         ↓
+------------------------+
|   Microtask Queue       | ← Promises, async/await
+------------------------+
         ↓
+--------------------+
|    Event Loop       | ← Coordinates everything
+--------------------+

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Synchronous Example&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;function sayHi() {
  console.log("Hi");
}
sayHi();

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This runs top to bottom inside the call stack.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Asynchronous Example with setTimeout&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;console.log("Start");

setTimeout(() =&amp;gt; {
  console.log("Timer");
}, 0);

console.log("End");

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Output:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Start
End
Timer

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Why?&lt;/strong&gt;&lt;br&gt;
Because setTimeout doesn’t go directly on the call stack. It goes to Web APIs, waits for the timer, and then gets added to the macrotask queue, which only runs when the call stack is empty.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Microtasks vs Macrotasks&lt;/strong&gt;&lt;br&gt;
Try this code:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;console.log("Start");

Promise.resolve().then(() =&amp;gt; {
  console.log("Microtask");
});

setTimeout(() =&amp;gt; {
  console.log("Macrotask");
}, 0);

console.log("End");

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Output:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Start
End
Microtask
Macrotask

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;Promises (microtasks) always run before setTimeouts (macrotasks), even if both are async.&lt;/li&gt;
&lt;li&gt;That’s how the Event Loop prioritizes execution.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;Visual: The Event Loop Flow&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;[ Is Call Stack Empty? ]
         ↓
     Run All Microtasks
         ↓
     Run One Macrotask
         ↓
         Repeat

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This is what makes JavaScript non-blocking — and yet single-threaded.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;async/await in Action&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;async function demo() {
  console.log("1");
  await Promise.resolve();
  console.log("2");
}

demo();
console.log("3");

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Output:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;1
3
2

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;await splits the function. The part after await is queued as a microtask, and it runs after the current call stack completes.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Takeaways&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;JavaScript is single-threaded, but async thanks to the Event Loop.&lt;/li&gt;
&lt;li&gt;Microtasks (Promises) run before Macrotasks (setTimeout, fetch, etc.).&lt;/li&gt;
&lt;li&gt;Use this mental model to debug better and write cleaner async code.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;Want to Visualize It?&lt;/strong&gt;&lt;br&gt;
I've created this Event Loop diagram to help you internalize the flow:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fj34jaxgpsti0ly1zzymb.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fj34jaxgpsti0ly1zzymb.png" alt="event" width="800" height="1200"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Wrapping Up&lt;/strong&gt;&lt;br&gt;
The Event Loop isn’t just theory — it directly affects how your code runs. Whether you’re dealing with React effects, API calls, or DOM events, mastering this concept can help you avoid weird bugs and timing issues.&lt;/p&gt;

&lt;p&gt;Let me know what confused you the most about the Event Loop when you first learned it.&lt;/p&gt;

&lt;p&gt;And if you found this helpful, consider giving it a ❤️ or sharing it with a fellow developer.&lt;/p&gt;

</description>
      <category>javascript</category>
      <category>asyncawait</category>
      <category>webdev</category>
      <category>programming</category>
    </item>
    <item>
      <title>Mastering Event Propagation in JavaScript: Bubbling vs Capturing</title>
      <dc:creator>Manali Khattar</dc:creator>
      <pubDate>Tue, 17 Jun 2025 05:25:50 +0000</pubDate>
      <link>https://dev.to/khattarmanali/mastering-event-propagation-in-javascript-bubbling-vs-capturing-1bja</link>
      <guid>https://dev.to/khattarmanali/mastering-event-propagation-in-javascript-bubbling-vs-capturing-1bja</guid>
      <description>&lt;p&gt;Events are a core part of JavaScript development. Whether you're building interactive UIs or handling user inputs, understanding event propagation is key to writing clean, maintainable code.&lt;/p&gt;

&lt;p&gt;In this post, we’ll explore how events travel through the DOM using bubbling and capturing, the difference between the two, and when to use each.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;What is Event Propagation?&lt;/strong&gt;&lt;br&gt;
Event propagation refers to the order in which event handlers are invoked when an event occurs in the DOM. There are two main phases:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Capturing Phase (a.k.a. trickling)&lt;/li&gt;
&lt;li&gt;Bubbling Phase&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Let’s break them down.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Event Bubbling&lt;/strong&gt;&lt;br&gt;
Event bubbling is the default phase in JavaScript. When an event is triggered on an element, it first runs the handler on the target element, then "bubbles up" to its ancestors.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Example:&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;If you click a button inside nested divs, the event is handled by the button first, then moves up to its parent, grandparent, and so on.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Event Capturing&lt;/strong&gt;&lt;br&gt;
In capturing, the event starts at the topmost ancestor and travels down the DOM tree to the target element. You need to explicitly enable capturing by passing true as the third parameter in addEventListener.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;!DOCTYPE html&amp;gt;
&amp;lt;html&amp;gt;
&amp;lt;head&amp;gt;
  &amp;lt;title&amp;gt;Event Propagation Example&amp;lt;/title&amp;gt;
&amp;lt;/head&amp;gt;
&amp;lt;body&amp;gt;
  &amp;lt;div id="parent"&amp;gt;
    &amp;lt;div id="child"&amp;gt;
      &amp;lt;button id="button"&amp;gt;Click Me&amp;lt;/button&amp;gt;
    &amp;lt;/div&amp;gt;
  &amp;lt;/div&amp;gt;

  &amp;lt;script&amp;gt;
    function parentClick() {
      console.log("Parent clicked");
    }

    function childClick() {
      console.log("Child clicked");
    }

    function buttonClick() {
      console.log("Button clicked");
    }

    var parent = document.getElementById("parent");
    var child = document.getElementById("child");
    var button = document.getElementById("button");

    parent.addEventListener("click", parentClick, true); // Use capturing phase
    child.addEventListener("click", childClick, true); // Use capturing phase
    button.addEventListener("click", buttonClick); // Default: bubbling phase
  &amp;lt;/script&amp;gt;
&amp;lt;/body&amp;gt;
&amp;lt;/html&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Expected Output in Console (on button click):&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Parent clicked
Child clicked
Button clicked

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Why this order? Because parentClick and childClick use capturing, they execute before the bubbling-phase buttonClick.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;When to Use Bubbling vs Capturing&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Use Bubbling when:&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;You want parent components to react to child actions.&lt;/li&gt;
&lt;li&gt;You’re implementing event delegation (e.g., handling clicks from multiple child elements in one parent handler).&lt;/li&gt;
&lt;li&gt;You want to close a modal when clicking outside of it.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;Use Capturing when:&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;You need to intercept an event before it reaches the target.&lt;/li&gt;
&lt;li&gt;You want to prevent a default action early (e.g., prevent link navigation).&lt;/li&gt;
&lt;li&gt;You’re building analytics or monitoring tools that listen high up in the DOM.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;Stopping Propagation&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;You can take control of the flow using:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;event.stopPropagation() – stops the event from bubbling or capturing further.&lt;/li&gt;
&lt;li&gt;event.stopImmediatePropagation() – stops all other listeners on the same element.
Use them wisely to avoid breaking complex interactions.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;Final Thoughts&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Understanding event propagation helps you build more powerful and optimized JavaScript applications. Whether you're debugging weird event behaviors or designing reusable components, mastering bubbling and capturing gives you a real edge.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Visual Reference&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fxv7paalnlvwu92kh6q5f.webp" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fxv7paalnlvwu92kh6q5f.webp" alt="Mastering Event Propagation in JavaScript" width="800" height="450"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Got Questions?&lt;/strong&gt;&lt;br&gt;
Have you faced tricky situations due to event propagation? Share your story or doubts in the comments — let’s learn together!&lt;/p&gt;

</description>
      <category>javascript</category>
      <category>webdev</category>
      <category>beginners</category>
      <category>frontend</category>
    </item>
  </channel>
</rss>
