Home > Software engineering >  how to hide html elements while waiting for all components to be loaded?
how to hide html elements while waiting for all components to be loaded?

Time:10-06

chromium lighthouse tells me :

performance 89 (orange)

Cumulative Layout Shift 0.388 (red alert !)

Avoid large layout shifts

html :

<html>
   ...
   <body >
   ...some static elements
   </body>
   ...
</html>

css :

body.loading * { display : none; }

js when DOM is loaded :

document.addEventListener('DOMContentLoaded', (e) => {

    //do many dynamic stuff with the DOM depending on user data (&  register events listeners)

  })

& finally when everything is in place in the dom, through window.onload (or if that event comes too soon, a callback once everything is in place) :

document.body.classList.remove('loading')

If I remove the loading class from the html lighthouse says great perf 100.

I thought before seeing this lighthouse analysis that my layout was shifting from a simple loading (css) animation to a completely ready page with no visible changes of the dom for the user during the load so i assume now that i am wrong, doing something wrong & missing something.

How should i do that instead for optimal loading while not risking having elements that are not ready ever being displayed ?

CodePudding user response:

I was waiting to put a bounty but it turns out that now lighthouse doesn't flag for CLS anymore although i didn't make any changes there (on the opposite i've added some code in html, css & js that should have made the page slower... ??)

so answer is (at least until being proven otherwise) :

Hiding elements while the page is loading & javascript is not ready doesn't have negative impact on performance.

here is minimalist code to have a ultra light spinner while the page is not ready yet

const MyOnLoad = function() {
    
    setTimeout(function(){ // only for the sake of displaying here the spinner 2 and half second obv
              
              document.body.classList.remove('loading')
        
        }
        ,2500) 
    
}

window.onload = MyOnLoad
.loading {
  margin: 34vmin auto;
  border: 0; 
  border-radius: 50%;
  border-top: 0.89vmin solid red;
  width: 21vmin;
  height: 21vmin;
  animation: spinner 2s linear infinite;

 }

 @keyframes spinner {
  0%   { transform: rotate(0deg); }
  100% { transform: rotate(360deg); }
 }

 .loading * {display: none;}
<html>
 <body >
    <main>show only when page is ready</main>
 </body>
</html>

  • Related