DEV Community

Cover image for How to add a loading status
Peron
Peron

Posted on • Edited on

How to add a loading status

The Problem

Everybody hates when need to wait too much to see something in a webapp. The new frontend frameworks (Vue, React, Angular) are awesome, but they brings us the functionalities with cost: bigger final bundle sizes!

As a advice, you need to analyze if the benefits are greater then the drawbacks. In my case, for example, my project is a big intellingence system that uses Vue3 and Quasar for frontend development. I'm using webpack vite and the final bundle size of the SPA is bigger around 600kb. It's not too much, but if the user is interacting using mobile networks systems, the experience can be annoing, specially here, in Brazil.

The solution

I know that Vue and Quasar have Loading components and i'm really love them, but i only can use it, after the bundle is downloaded and loaded. I want that my user see some animation before Vue, Quasar and all my code is loaded and parsed. Something like this:

Professional Loading Site

And it will work on Vue, React, or any other big framework you use, it's only necessary that you follow these rules:

The magic behind this is that the code doesn't use any javascript or any big rocket cience. Its use the <div id="app"></div> place to run the loading bar, and when Vue finishes loading and mount his content, the loading is replaced by Vue HTML nodes. Easy as that!

Remember, this must work if the user disables javascript. Okey, will not show Vue, but tell the user that he needs to enable-it, showing him something in <noscript></noscript> tags.

1. CSS Code & Animations

I will be honest here. i'm not a reference in this matter. I've used Google and stackoverflow to find an loading bar progress that isn't use Javascript . Found many, but none was what i'm expecting, so i mix some of them and the resulting was this CSS:

<style>
  .nspl {
    position: absolute;
    left: 50%;
    top: 50%;
    z-index: 101;
    flex-direction: column;
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    justify-content: center;
    text-align: center;
  }
  .nspt {
    font-family: 'Roboto', '-apple-system', 'Helvetica Neue', Helvetica, Arial, sans-serif;
    -ms-text-size-adjust: 100%;
    -webkit-text-size-adjust: 100%;
    -webkit-font-smoothing: antialiased;
    -moz-osx-font-smoothing: grayscale;
    line-height: 1.5;
    font-size: 16px;
    padding-top: 16px;
    margin: 0 0 0 -76px;
  }
  #noscr {
    z-index: 99;
    margin: -200px 0 0 -250px;
    height: 400px;
    width: 500px;
    background-color: white;
  }
  .nalps {
    width: 120px;
    height: 120px;
    margin: -114px 0 0 -76px;
    border: 16px solid #f3f3f3;
    border-radius: 50%;
    border-top: 16px solid #3498db;
    -webkit-animation: spin 2s linear infinite;
    animation: spin 2s linear infinite;
  }

  @-webkit-keyframes spin {
    0% {
      -webkit-transform: rotate(0deg);
    }
    100% {
      -webkit-transform: rotate(360deg);
    }
  }

  @keyframes spin {
    0% {
      transform: rotate(0deg);
    }
    100% {
      transform: rotate(360deg);
    }
  }
</style>
Enter fullscreen mode Exit fullscreen mode

2. HTML for loading and mounting app

This is pretty self splanatory. As we already said, i've used the place where React or Vue will mount his data to put three divs. The first, the container <div class=nalp> will hold the text and animation (i've choose that because seem more pretty and informative. Next, we have the image animation (class=nalps) and for the last, the text (<div class=nalpt>)

But this is only how i choose to make this. You are free to change and adapt the way pleases you.

<div  id="app">
    <div class="nspl">
        <div id="nalp" class="nalps"></div>
        <div class="nspt">Loading... Wait!</div>
    </div>
</div>
Enter fullscreen mode Exit fullscreen mode

3. How it works:

Well, as soon as the browser loads all necessary javascript an css, he will run the Vue code that replaces the loading with their App.vue and, magic happends:

import  {  createApp  }  from  "vue";
import  App  from  "./App.vue";
const  app  =  createApp(App);
//i've put this here for you to see the animation
// remove the settimeout in production
setTimeout(()  =>  {
    //if you 
    app.mount("#app");
},  5000 /* waits five seconds for you see loading */);
Enter fullscreen mode Exit fullscreen mode

The best way to learn something is to see working. so, grab that:

Edit serene-platform-7mvmyw

FOOTNOTES:

  • This is my first article, so, be kind with me.
  • If you see some improvement that can be made, please, let me know in the comments.
  • If you liked this article, please, motivate-me in the comments.

Have all a nice week!

Top comments (6)

Collapse
 
kissu profile image
Konstantin BIFERT

Hi, great first Article Peron! 💚
Overall great presentation too. 👍🏻
You could maybe check for a more dedicated highlight regarding the CSS code and indent it back to the left a little bit more.

Collapse
 
mperon profile image
Peron

I really aprecciate the tips. Thank you for your time to help improve myself.

Collapse
 
kissu profile image
Konstantin BIFERT

You're very welcome. Keep up the work man! 💪🏻

Collapse
 
devgancode profile image
Ganesh Patil

Adding this feature to my next project!

Collapse
 
elvarufus profile image
ElvaRufus • Edited

How do I add a loading screen to my website? Brains On Rent

Collapse
 
mperon profile image
Peron

Hi Elva!

In your case, you are using Wordpress i believe. Must be an plugin for this.

If you wanna change your template manually, you must listen window.load event an remove the loading bar when its fires.

Something like this:

window.addEventListener('load', function() {
   let elem = document.querySelector('#app');
   elem.parentNode.removeChild(elem);
})
Enter fullscreen mode Exit fullscreen mode