Skip to main content

Creating a Dynamic Progress Bar with HTML, CSS, and JavaScript

A Step by Step Guide


Introduction:

In this tutorial, we'll walk through the process of building a dynamic progress bar using HTML, CSS, and JavaScript. Progress bars are commonly used in web applications to visualize the completion status of a task or process.

By the end of this tutorial, you'll have a functional progress bar that updates in real-time based on user input.





Figure: Preview (tap to see clearly)






Prerequisites:

Before diving into this tutorial, you should have a basic understanding of HTML, CSS, and JavaScript. Familiarity with concepts such as HTML elements, CSS styling, and JavaScript functions will be beneficial.

Step-by-Step Guide:

  1. Setting up the HTML structure
  2. Styling the progress bar with CSS
  3. Adding interactivity with JavaScript


1. Setting up the HTML structure


Code:
<!DOCTYPE html>
<html lang="en">
    <head>
        <meta charset="UTF-8">
        <meta name="viewport" content="width=device-width, initial-scale=1.0">
        <title>Progress Bar</title>
    </head>
    <body>
        <div class="container">
            <div id="progress-bar">
                <p id="percentage">100%</p>
                <svg width="200" height="200">
                    <defs>
                        <linearGradient id="my-gradient" x1="0%" x2="100%" y1="100%" y2="0%">
                            <stop offset="0%" stop-color="gold" />
                            <stop offset="100%" stop-color="red" />
                        </linearGradient>
                    </defs>
                    <circle id="progress-circle" cx="100" cy="100" r="85"></circle>
                </svg>
            </div>
            
            <input type="number" placeholder="Percentage">
            <button onclick="update()">Update</button>
        </div>
    </body>
</html>

1. HTML Structure:

  • Create a new HTML file and add the basic structure with <html>, <head>, and <body> tags.
  • Inside the <body> tag, add a <div> element with a class of "container" to hold the progress bar components.
  • Inside the container <div>, add another <div> with an id of "progress-bar" to contain the progress bar itself.
  • Within the progress bar <div>, add a <p> element with an id of "percentage" to display the progress percentage.
  • Add an SVG element with a circle inside to represent the progress visually.
  • Include an <input> element of type "number" for the user to input the desired percentage.
  • Finally, add a <button> element with an onclick attribute set to a JavaScript function called "update()" to trigger the progress update.



2. Styling the progress bar with CSS


Code:
* {
     margin: 0;
     padding: 0;
     font-family: Arial;
 }

body {
    background-color: black;
    display: flex;
    justify-content: center;
    align-items: center;
    height: 100vh;
}

.container {
    color: white;
    display: flex;
    flex-direction: column;
    align-items: center;
    width: 300px;
}

#progress-bar {
    display: flex;
    justify-content: center;
    align-items: center;
    width: 200px;
    height: 200px;
    font-weight: bold;
    font-size: 1.5em;
    position: relative;
    margin-bottom: 40px;
}

svg {
    position: absolute;
    top: 0;
    left: 0;
}

circle {
    fill: none;
    stroke: url(#my-gradient);
    stroke-width: 30px;
    stroke-dasharray: 534;
    stroke-linecap: round;
    transition: stroke-dashoffset 2s linear;
}

input {
    width: 100%;
    height: 40px;
    border-radius: 20px;
    border: none;
    text-align: center;
    color: #555;
    font-size: 1.1em;
    margin-bottom: 10px;
}

button {
    width: 100%;
    height: 40px;
    border-radius: 20px;
    border: none;
    background-color: gold;
    color: #555;
    font-size: 1.1em;
    font-weight: bold;
}

Here's a breakdown of the CSS code provided:

  1. Universal Reset:
    • *: Selects all elements on the page.
    • margin: 0; padding: 0;: Resets the margin and padding of all elements to zero.
    • font-family: Arial;: Sets the default font family to Arial for all text elements.
  2. Body Styles:
    • background-color: black;: Sets the background color of the body to black.
    • display: flex; justify-content: center; align-items: center;: Centers the content vertically and horizontally within the body using flexbox.
    • height: 100vh;: Sets the height of the body to 100% of the viewport height.
  3. Container Styles:
    • .container: Styles the container div.
    • color: white;: Sets the text color inside the container to white.
    • display: flex; flex-direction: column; align-items: center;: Positions the elements inside the container in a column layout and centers them horizontally.
    • width: 300px;: Sets the width of the container to 300 pixels.
  4. Progress Bar Styles:
    • #progress-bar: Styles the progress bar container.
    • display: flex; justify-content: center; align-items: center;: Centers the progress bar content vertically and horizontally.
    • width: 200px; height: 200px;: Sets the width and height of the progress bar container to 200 pixels.
    • font-weight: bold; font-size: 1.5em;: Applies bold font weight and increases the font size to 1.5em for the progress percentage display.
    • position: relative;: Sets the position of the progress bar container to relative for positioning the SVG element.
  5. SVG Styles:
    • svg: Styles the SVG element inside the progress bar.
    • position: absolute; top: 0; left: 0;: Positions the SVG element at the top left corner of the progress bar container.
  6. Circle Styles:
    • circle: Styles the circle element inside the SVG.
    • fill: none;: Removes fill color from the circle.
    • stroke: url(#my-gradient);: Applies a linear gradient stroke color defined by the my-gradient ID.
    • stroke-width: 30px;: Sets the width of the stroke to 30 pixels.
    • stroke-dasharray: 534;: Defines the length of the dash pattern for the stroke.
    • stroke-linecap: round;: Sets the style of the stroke line cap to round.
    • transition: stroke-dashoffset 2s linear;: Adds a transition effect to the stroke-dashoffset property with a duration of 2 seconds and linear easing.
  7. Input and Button Styles:
    • input: Styles the input element.
    • button: Styles the button element.
    • These styles define the appearance of the input field and button, including width, height, border-radius, border, background color, text color, font size, and font weight.



3. Adding interactivity with JavaScript


Code:
// function for get value from input element entered by user and return it
function getInputValue () {
    // get input element
    const input_el = document.querySelector ("input");
    // get input element value
    const input_val = input_el.value;
    // return it
    return input_val;
}


// function for clear input field
function clearInputField () {
    // get input element
    const input_el = document.querySelector ("input");
    // clear
    input_el.value = "";
}


// function for enable or disable button
function disabledButton (bool) {
    // get button element
    const button_el = document.querySelector ("button");
    // set bool for it
    button_el.disabled = bool;
    // set background color on different state
    if (bool) {
        button_el.style.backgroundColor = "gray";
    }else {
        button_el.style.backgroundColor = "gold";
        // clear input field
        clearInputField ();
    }
}


// This is called when the user clicks the button
// and update percentage text and progress bar
function update () {
    disabledButton(true);
    // get input value from getInputValue function
    let input_val = getInputValue ();
    // condition for check input_val entered by user
    // Number only not empty
    if (input_val) {
        // change input_val to Integer
        input_val = parseInt (input_val);
        // change input_val to absolute (e.g. -75 to 75)
        input_val = Math.abs(input_val);
        // condition for check input_val is greater than 100
        if (input_val > 100) {
            input_val = 100;
        }
    }else {
        input_val = 0;
    }
    // calling function
    updateProgressBar (input_val);
}


// function for change text in paragraph element
function changeTextInPara (num) {
    // get paragraph (para) element (el) by id
    const para_el = document.getElementById ("percentage");
    // change text in paragraph
    para_el.innerText = num + "%";
}


// function for update dash offset value
function updateDashOffset(dashoffset_val) {
    // get circle element by it's Id
    const circle = document.getElementById('progress-circle');
    // set it's transition value to none
    circle.style.transition = 'none'; // Disable transition temporarily
    // set attribute
    circle.setAttribute('stroke-dashoffset', dashoffset_val);
    // Trigger reflow to apply immediate changes
    void circle.offsetWidth;
    // Re-enable transition with empty string (using single quotes)
    circle.style.transition = '';
}


// function for update progress bar
function updateProgressBar (percentage) {
    // here, calculating the dashoffset value from percentage
    const dashoffset_val = Math.round (534 - (534*percentage)/100);
    // update dashoffset with dashoffset_val
    updateDashOffset (dashoffset_val);
    // get paragraph (para) element (el) by id
    const para_el = document.getElementById ("percentage");
    // get innerText value of para_el
    // and remove '%' with replace method
    let current_percentage = para_el.innerText.replace ("%", "");
    // condition
    if (current_percentage < percentage) {
        // calculate the interval time for increasePercentage
        const interval_time = Math.round (2000/(percentage - current_percentage));
        // calling increasePercentage
        increasePercentage (current_percentage, percentage, interval_time);
    }else if (current_percentage > percentage) {
        // calculate the interval time for decreasePercentage
        const interval_time = Math.round (2000/(current_percentage - percentage));
        // calling decreasePercentage
        decreasePercentage (current_percentage, percentage, interval_time);
    }else {
        disabledButton (false);
    }
}


// function for increase percentage
function increasePercentage (current_percentage, percentage, interval_time) {
    const my_interval = setInterval ( () => {
        changeTextInPara (current_percentage);
        current_percentage ++;
        
        if (current_percentage > percentage) {
            clearInterval (my_interval);
            disabledButton (false);
        }
    }, interval_time);
}


// function for decrease percentage
function decreasePercentage (current_percentage, percentage, interval_time) {
    const my_interval = setInterval ( () => {
        changeTextInPara (current_percentage);
        current_percentage --;
        
        if (current_percentage < percentage) {
            clearInterval (my_interval);
            disabledButton (false);
        }
    }, interval_time);
}

Here's a breakdown of the JavaScript code provided:

  1. getInputValue Function:
    • This function retrieves the value entered by the user in the input field and returns it.
  2. clearInputField Function:
    • This function clears the input field by setting its value to an empty string.
  3. disabledButton Function:
    • This function enables or disables the button based on the boolean parameter passed to it.
    • If the button is disabled, its background color is set to gray. Otherwise, it's set to gold.
    • If the button is enabled, the input field is also cleared using the clearInputField function.
  4. update Function:
    • This function is called when the user clicks the button.
    • It disables the button to prevent multiple clicks while updating the progress bar.
    • It retrieves the input value, parses it to an integer, and ensures it's within the range of 0 to 100.
    • Then, it calls the updateProgressBar function with the calculated percentage value.
  5. changeTextInPara Function:
    • This function changes the text content of the paragraph element with the specified ID to the provided number followed by a percentage sign.
  6. updateDashOffset Function:
    • This function updates the dash offset value of the SVG circle to visually represent the progress.
    • It temporarily disables the transition effect to apply immediate changes, updates the dash offset attribute, triggers a reflow to apply the changes immediately, and then re-enables the transition.
  7. updateProgressBar Function:
    • This function calculates the dash offset value based on the percentage and updates the progress bar.
    • It also updates the percentage text displayed on the progress bar and calls either the increasePercentage or decreasePercentage function based on the current and target percentage values.
  8. increasePercentage and decreasePercentage Functions:
    • These functions gradually increase or decrease the percentage displayed on the progress bar to provide a smooth transition effect.
    • They update the percentage text and clear the input field when the transition is complete, then re-enable the button.







Conclusion:

Congratulations! You've successfully created a dynamic progress bar using HTML, CSS, and JavaScript. You can now integrate this progress bar into your web projects to provide visual feedback on task completion or process status.

Experiment with different styling options and functionality enhancements to tailor the progress bar to your specific needs.

Thank You:

Thank you for following along with this tutorial. We hope you found it helpful and informative.
If you have any questions or feedback, feel free to leave a comment below.

Happy coding!







Comments

Popular posts from this blog

TimeCalc: The Ultimate Tool for Time Calculations Made Easy

A Step-by-Step Guide Create an Awesome Time Calculator web application! Introduction: In this project, we will build a web application that allows users to input times in the format "HH:MM:SS" and perform calculations. Get ready to streamline your time calculations and make your life easier with our intuitive and efficient web app. Figure: Preview (tap to see clearly) Prerequisites: Before diving into this tutorial, ensure you have the following prerequisites: Basic Knowledge of HTML: Understanding the structure and syntax of HTML (HyperText Markup Language) is essential for creating the foundation of web pages. Fundamentals of CSS: Familiarize yourself with CSS (Cascading Style Sheets) concepts such as selectors, properties, and values. Learn how to style HTML elements, apply layouts, and manage visual presentation on web ...