Skip to Content
Course content

193: Building a Real-Time Clock and Alarm App

Click on the "Edit" button in the top corner of the screen to edit your slide content.

When I first started building timers and clocks, I fell into a trap that I still see developers stumble into today: the belief that to make something "real-time," you need to create a loop that runs as fast as possible to "catch" the exact millisecond a second changes. You might be tempted to write a while(true) loop or a recursive setTimeout that fires every 10 milliseconds just to be "precise."

The "Infinite Loop" Trap and Why It Freezes Your Browser

Let's look at why that's a disaster. If you try to do something like this:

while (true) {
  console.log(new Date().toLocaleTimeString());
}

Your browser tab will instantly freeze. You won't see a clock ticking; you'll see a "Page Unresponsive" warning. Because JavaScript is single-threaded, that while loop hogs the entire execution thread. The browser can't paint the UI, it can't handle clicks, and it certainly can't update the text on your screen. You're essentially telling the browser, "Ignore everything in the universe except this loop."

Letting the Browser Breathe with setInterval

The trick to a real-time clock isn't about high-frequency polling; it's about scheduling. We don't need to track every millisecond; we just need the UI to refresh enough that the human eye sees a consistent update. I always recommend setInterval for this. It tells the browser: "Go do other things, and every 1,000 milliseconds, come back and run this specific bit of code."

Here is the core logic I use for a basic ticker:

const clockElement = document.getElementById('clock');

setInterval(() => {
  const now = new Date();
  clockElement.innerText = now.toLocaleTimeString();
}, 1000);

Notice I'm calling new Date() inside the interval. A common rookie mistake is defining the date once outside the loop and then just trying to increment a variable. Don't do that. Let the system clock be your source of truth; it's far more accurate than any counter you'll build manually.

Matching the Alarm to the System String

Adding an alarm sounds complex, but it's actually just a string comparison problem. If you're building a simple alarm app, you don't need complex timestamp math. You just need to know if the "current time string" matches the "alarm time string."

I personally find it easiest to store the alarm time in a format that matches toLocaleTimeString() or a simple HH:MM format. Every time the clock ticks, we run a check:

let alarmTime = "14:30:00"; // Set by user input

setInterval(() => {
  const now = new Date();
  const currentTime = now.toLocaleTimeString();
  
  document.getElementById('clock').innerText = currentTime;

  if (currentTime === alarmTime) {
    alert("Time to wake up!");
  }
}, 1000);

It's simple, it's clean, and it doesn't kill the CPU. One detail to watch out for: toLocaleTimeString() can vary based on the user's locale (some use 12-hour, some 24-hour). In a production app, I'd suggest using a library like Day.js or manually formatting the hours and minutes to ensure the comparison doesn't fail just because the user is in London instead of New York.

Preventing the "Alarm Spam" Effect

If you use the code above, you might notice that the alarm triggers multiple times within that one second if the browser's timing is slightly off, or it might trigger and then immediately trigger again. To fix this, I always implement a "triggered" flag. This ensures the alarm only goes off once per scheduled minute.

let alarmActive = false;

// Inside the interval...
if (currentTime === alarmTime && !alarmActive) {
  triggerAlarm();
  alarmActive = true; 
}

if (currentTime !== alarmTime) {
  alarmActive = false; // Reset the flag once the second passes
}

This little boolean toggle is the difference between a professional tool and an app that crashes the browser with a hundred alert boxes.




📋 Practical Task

Implementing a "Time-Until-Alarm" Countdown Timer

Modify the clock and alarm logic from this lesson to include a live countdown. Instead of only showing the current time, add a second display element that tells the user exactly how many hours, minutes, and seconds remain until the alarm triggers.

  • Create an input field where the user can set the alarm time (e.g., "15:30").
  • Calculate the difference between the current system time and the alarm time.
  • Update a <div id="countdown"> every second to show the remaining time (e.g., "02:15:10 remaining").
  • Ensure that once the alarm is reached, the countdown displays "Alarm Triggered!" instead of negative numbers.
Rating
0 0

There are no comments for now.

to be the first to leave a comment.