Create a Birthday Countdown | HTML, CSS, JavaScript Tutorial

Faraz

By Faraz -

Learn how to create a birthday countdown timer with HTML, CSS, and JavaScript. Engage your website visitors with this interactive widget.


Create a Birthday Countdown  HTML, CSS, JavaScript Tutorial.jpg

Table of Contents

  1. Project Introduction
  2. HTML Code
  3. CSS Code
  4. JavaScript Code
  5. Preview
  6. Conclusion

There's something uniquely thrilling about counting down to a special day, especially when it's your birthday! Imagine the joy and anticipation as each second brings you closer to that momentous occasion. In this comprehensive tutorial, we're about to embark on a journey into the world of web development, where you'll learn how to craft a dynamic and visually captivating birthday countdown.

Using the powerful trio of HTML, CSS, and JavaScript, we will guide you through the process of creating an interactive birthday countdown widget. This widget can be seamlessly integrated into your website, adding an extra layer of excitement and engagement for your audience.

So, fasten your seatbelt and get ready to embark on this coding adventure. By the end of this tutorial, you'll have a fully functional countdown timer that not only keeps track of the moments leading up to your birthday but also serves as a testament to your newly acquired web development skills. Let's dive in!

Source Code

Step 1 (HTML Code):

To get started, we will first need to create a basic HTML file. In this file, we will include the main structure for our birthday countdown timer.

After creating the files just paste the following codes into your file. Make sure to save your HTML document with a .html extension, so that it can be properly viewed in a web browser.

Let's break down the code step by step:

1. <!DOCTYPE html>: This declaration tells the browser that the document is written in HTML5, the latest version of HTML.

2. <html lang="en">: This opening tag defines the start of the HTML document and specifies that the document's primary language is English ("en").

3. <head>: This section contains metadata and other information about the web page but is not visible to the user.

  • <meta charset="UTF-8">: This meta tag specifies the character encoding for the document, which is UTF-8, a character encoding that supports a wide range of characters from various languages.
  • <meta name="viewport" content="width=device-width, initial-scale=1.0">: This meta tag is used for responsive web design. It ensures that the web page will adapt to the width of the user's device and initial zoom level.
  • <link rel="stylesheet" href="styles.css">: This line links an external CSS (Cascading Style Sheets) file named "styles.css" to the HTML document. This CSS file is used to define the visual styling and layout of the web page.
  • <title>Birthday Countdown</title>: This sets the title of the web page to "Birthday Countdown," which is displayed in the browser's title bar or tab.

4. <body>: This is the main content area of the web page that is visible to the user.

5. <div class="countdown-container">: This is a container div that wraps the entire content of the web page. It helps with styling and organizing the page's elements.

6. <h1>Birthday Countdown</h1>: This is a top-level heading that displays "Birthday Countdown" as the main title of the web page.

7. <div id="confetti" class="container"></div>: This empty div element with the ID "confetti" and a class "container" is used for displaying confetti animation when the countdown reaches zero.

8. <div class="input-container">: This div element is a container for user input elements.

  • <input type="date" id="birthday-input">: This is an input field of type "date" where the user can select a date, representing the date of their birthday. It has an ID "birthday-input," which can be used to access this input element in JavaScript.
  • <button id="start-countdown">Start Countdown</button>: This is a button element with the ID "start-countdown." When clicked, it triggers a JavaScript function to start the countdown based on the selected date.

9. <div class="countdown" id="countdown">: This div element is a container for displaying the countdown.

10. Inside this div, there are four "countdown-item" divs, each containing:

  • <span id="days">00</span>: A span element with the ID "days" to display the number of days in the countdown.
  • <p>Days</p>: A paragraph element that labels the unit of time is displayed (in this case, "Days"). Similar structures exist for hours, minutes, and seconds.

11. <script src="script.js"></script>: This line includes an external JavaScript file named "script.js." This JavaScript file contains the code responsible for handling user interactions and updating the countdown timer.

This is the basic structure of our countdown timer using HTML, and now we can move on to styling it using CSS.

Step 2 (CSS Code):

Once the basic HTML structure of the countdown timer is in place, the next step is to add styling to the countdown timer using CSS.

Next, we will create our CSS file. In this file, we will use some basic CSS rules to style our countdown timer. Let's break down the code step by step:

1. Styling for the body element:

  • It sets the font family to Arial or a generic sans-serif font.
  • The background color is set to a light gray (#f4f4f4).
  • Margins and padding for the body are set to 0 to remove any default spacing.
  • The display property is set to flex, and justify-content and align-items are set to center, which will horizontally and vertically center the content within the body.
  • min-height: 100vh; ensures that the body takes up at least the full height of the viewport.
  • overflow: hidden; hides any overflowing content.

2. Styling for the .countdown-container class:

  • This class is used to style a container that holds the countdown timer.
  • Text is centered using text-align: center.
  • The background color is white (#fff), and it has padding, a rounded border, and a box shadow to give it a card-like appearance.
  • max-width: 400px; limits the width of the container, and width: 90%; ensures it takes up most of its parent's width.

3. Styling for h1 elements:

  • Sets the font size to 2rem and adds a bottom margin of 20px.

4. Styling for the .input-container class:

  • Adds a bottom margin of 20px.

5. Styling for input[type="date"] elements:

  • Adds padding and sets the font size to 1rem.

6. Styling for button elements:

  • Sets the background color to a red shade (#f44336), text color to white, removes the border, and adds padding.
  • cursor: pointer; makes the cursor change to a pointer when hovering over the button.
  • button:hover changes the background color when the button is hovered.

7. Styling for elements with the .countdown class:

  • Centers the content both horizontally and vertically.

8. Styling for elements with the .countdown-item class:

  • Adds margin, font size, and flex properties.
  • The font size for the inner span elements is increased, and they are made bold and colored in red (#f44336).

9. Styling for elements with the .container class:

  • Sets the width to 100% of the viewport width.

10. Styling for elements with the .confetti class:

  • It positions confetti elements absolutely, outside of the normal document flow.
  • The z-index property sets the stacking order of elements.
  • It's used for creating confetti animations.

11. Keyframes animations:

  • Define animations for confetti with different speeds, including confetti-slow, confetti-medium, and confetti-fast. These animations use 3D transformations to simulate confetti falling.

12. Media query:

  • When the viewport width is less than or equal to 600px, it adjusts the font sizes for elements with the .countdown-item class and their span elements to maintain a responsive design.

This will give our countdown timer an upgraded presentation. Create a CSS file with the name of styles.css and paste the given codes into your CSS file. Remember that you must create a file with the .css extension.

body {
  font-family: Arial, sans-serif;
  background-color: #f4f4f4;
  margin: 0;
  padding: 0;
  display: flex;
  justify-content: center;
  align-items: center;
  min-height: 100vh;
  overflow: hidden;
}

.countdown-container {
  text-align: center;
  background-color: #fff;
  padding: 20px;
  border-radius: 10px;
  box-shadow: 0px 0px 10px rgba(0, 0, 0, 0.2);
  max-width: 500px;
  width: 90%;
}

h1 {
  font-size: 2rem;
  margin-bottom: 20px;
}

.input-container {
  margin-bottom: 20px;
}

input[type="date"] {
  padding: 8px;
  font-size: 1rem;
}

button {
  background-color: #f44336;
  color: #fff;
  border: none;
  padding: 10px 20px;
  font-size: 1rem;
  cursor: pointer;
}

button:hover {
  background-color: #d32f2f;
}

.countdown {
  display: flex;
  justify-content: center;
  align-items: center;
}

.countdown-item {
  margin: 10px;
  font-size: 2rem;
  flex: 1;
  text-align: center;
}

.countdown-item span {
  font-size: 3rem;
  font-weight: bold;
  color: #f44336;
}

.container {
  width: 100vw;
}

.confetti {
  position: absolute;
  z-index: 1;
  top: -10px;
  border-radius: 0%;
}

.confetti--animation-slow {
  animation: confetti-slow 2.25s linear 1 forwards;
}
.confetti--animation-medium {
  animation: confetti-medium 1.75s linear 1 forwards;
}
.confetti--animation-fast {
  animation: confetti-fast 1.25s linear 1 forwards;
}

@keyframes confetti-slow {
  0% {
    transform: translate3d(0, 0, 0) rotateX(0) rotateY(0);
  }
  100% {
    transform: translate3d(25px, 105vh, 0) rotateX(360deg) rotateY(180deg);
  }
}
@keyframes confetti-medium {
  0% {
    transform: translate3d(0, 0, 0) rotateX(0) rotateY(0);
  }
  100% {
    transform: translate3d(100px, 105vh, 0) rotateX(100deg) rotateY(360deg);
  }
}
@keyframes confetti-fast {
  0% {
    transform: translate3d(0, 0, 0) rotateX(0) rotateY(0);
  }
  100% {
    transform: translate3d(-50px, 105vh, 0) rotateX(10deg) rotateY(250deg);
  }
}

/* Media Queries for Responsive Design */
@media (max-width: 600px) {
  .countdown-item {
      font-size: 1.5rem;
  }

  .countdown-item span {
      font-size: 2.5rem;
  }
} 

Step 3 (JavaScript Code):

Finally, we need to create a function in JavaScript. This JavaScript code is responsible for creating a countdown timer for a user's birthday and triggering a confetti effect when the birthday date is reached. Let's break down the code step by step:

1. let birthdayDate;: This declares a variable called birthdayDate to store the user's birthday as a timestamp (milliseconds since January 1, 1970).

2. The code uses the addEventListener method to attach a click event handler to an element with the id "start-countdown." When this element is clicked, it executes an anonymous function.

3. Inside the click event handler:

  • It retrieves the value entered by the user in an input field with the id "birthday-input."
  • It checks whether the entered date is in a valid format (YYYY-MM-DD) using the isValidDate function.
  • If the date is not valid, it displays an alert and returns, preventing further execution.
  • If the date is valid, it converts the input date into a timestamp and stores it in the birthdayDate variable.
  • It hides the input fields by changing the style of an element with the class "input-container."
  • Finally, it calls the updateCountdown function to start the countdown.

4. updateCountdown function:

  • It calculates the time left until the birthday by subtracting the current timestamp from the birthdayDate.
  • If the time left is less than or equal to 0, it displays a "Happy Birthday!" message, triggers a confetti effect, and exits.
  • If there is time left, it calculates and updates the days, hours, minutes, and seconds left until the birthday. It uses setTimeout to call itself again after one second to continuously update the countdown.

5. isValidDate function:

  • It validates whether a given date string matches the format YYYY-MM-DD using a regular expression.
  • If the format is invalid, it returns false.
  • If the format is valid, it tries to create a Date object with the given date string and time set to midnight. If the date is not valid, it returns false. Otherwise, it returns true.

6. confettiEffect function:

  • This function defines a constructor called Confettiful that is responsible for creating a confetti animation when called with an element.
  • It sets default values for confetti frequency, colors, and animations.
  • The _renderConfetti method generates and animates confetti elements by creating DOM elements with random properties and appending them to a container.
  • The confetti animation runs at a regular interval using setInterval.

Create a JavaScript file with the name script.js and paste the given codes into your JavaScript file and make sure it's linked properly to your HTML document so that the scripts are executed on the page. Remember, you’ve to create a file with .js extension.

let birthdayDate;

document.getElementById("start-countdown").addEventListener("click", function () {
    const inputDate = document.getElementById("birthday-input").value;
    
    if (!isValidDate(inputDate)) {
        alert("Please enter a valid date (YYYY-MM-DD).");
        return;
    }

    birthdayDate = new Date(inputDate + "T14:03:00").getTime();
    document.querySelector(".input-container").style.display = "none"; // Hide input fields
    updateCountdown();
});

function updateCountdown() {
    const countdownElement = document.getElementById("countdown");
    const currentDate = new Date().getTime();
    const timeLeft = birthdayDate - currentDate;

    if (timeLeft <= 0) {
        // Birthday has passed
        countdownElement.innerHTML = "<h2>Happy Birthday!</h2>";

        // Trigger confetti effect
        confettiEffect();
        return;
    }

    const days = Math.floor(timeLeft / (1000 * 60 * 60 * 24));
    const hours = Math.floor((timeLeft % (1000 * 60 * 60 * 24)) / (1000 * 60 * 60));
    const minutes = Math.floor((timeLeft % (1000 * 60 * 60)) / (1000 * 60));
    const seconds = Math.floor((timeLeft % (1000 * 60)) / 1000);

    document.getElementById("days").textContent = days.toString().padStart(2, '0');
    document.getElementById("hours").textContent = hours.toString().padStart(2, '0');
    document.getElementById("minutes").textContent = minutes.toString().padStart(2, '0');
    document.getElementById("seconds").textContent = seconds.toString().padStart(2, '0');

    // Update the countdown every second
    setTimeout(updateCountdown, 1000);
}

// Function to validate the date format
function isValidDate(dateString) {
    const regEx = /^\d{4}-\d{2}-\d{2}$/;
    if (!dateString.match(regEx)) return false; // Invalid format
    const d = new Date(dateString + "T00:00:00");
    return !isNaN(d.getTime());
}

function confettiEffect() {
  const Confettiful = function (el) {
    this.el = el;
    this.containerEl = null;
  
    this.confettiFrequency = 3;
    this.confettiColors = ['#fce18a', '#ff726d', '#b48def', '#f4306d'];
    this.confettiAnimations = ['slow', 'medium', 'fast'];
  
    this._renderConfetti();
  };
  
  
  Confettiful.prototype._renderConfetti = function () {
    const confettiContanier = document.getElementById("confetti");
    this.confettiInterval = setInterval(() => {
      const confettiEl = document.createElement('div');
      const confettiSize = Math.floor(Math.random() * 3) + 7 + 'px';
      const confettiBackground = this.confettiColors[Math.floor(Math.random() * this.confettiColors.length)];
      const confettiLeft = Math.floor(Math.random() * this.el.offsetWidth) + 'px';
      const confettiAnimation = this.confettiAnimations[Math.floor(Math.random() * this.confettiAnimations.length)];
  
      confettiEl.classList.add('confetti', 'confetti--animation-' + confettiAnimation);
      confettiEl.style.left = confettiLeft;
      confettiEl.style.width = confettiSize;
      confettiEl.style.height = confettiSize;
      confettiEl.style.backgroundColor = confettiBackground;
  
      confettiEl.removeTimeout = setTimeout(function () {
        confettiEl.parentNode.removeChild(confettiEl);
      }, 3000);
  
      confettiContanier.appendChild(confettiEl);
    }, 25);
  };
  
  window.confettiful = new Confettiful(document.querySelector('.container'));
}

Final Output:

Create a Birthday Countdown  HTML, CSS, JavaScript Tutorial.gif

Conclusion:

Congratulations! You've successfully embarked on a journey into the world of web development, and you've emerged with a fantastic birthday countdown widget. This captivating creation is more than just a timer; it's a testament to your newfound coding skills and creativity.

As you've learned, the fusion of HTML for structure, CSS for style, and JavaScript for interactivity can bring your digital ideas to life. Whether you plan to use this countdown for your birthday or share it with the world, you now have a valuable addition to your web development toolkit.

We hope this tutorial has been a valuable learning experience. Now, go ahead and share your birthday countdown with friends, family, and website visitors. Build anticipation, create excitement, and make every moment leading up to your special day even more memorable.

Thank you for joining us on this coding adventure. I wish you the best of luck with your future web development endeavors!

That’s a wrap!

I hope you enjoyed this post. Now, with these examples, you can create your own amazing page.

Did you like it? Let me know in the comments below 🔥 and you can support me by buying me a coffee.

And don’t forget to sign up to our email newsletter so you can get useful content like this sent right to your inbox!

Thanks!
Faraz 😊

End of the article

Subscribe to my Newsletter

Get the latest posts delivered right to your inbox


Latest Post