2

Is it possible to load a component in place of loading... between <app-root> within the index.html of an Angular project?

When the Angular app is loading, if the connection is slow etc while the page loads, whatever is displayed between the <app-root></app-root> tags within the index.html file will be displayed on the screen.

I am wanting to place a spinner at the point such that it will look like something is happening in the background rather than have an blank white screen.

Here is the code for the spinner:

.lds-ring {
  display: inline-block;
  position: relative;
  width: 64px;
  height: 64px;
}
.lds-ring div {
  box-sizing: border-box;
  display: block;
  position: absolute;
  width: 51px;
  height: 51px;
  margin: 6px;
  border: 6px solid var(--pa-red);
  border-radius: 50%;
  animation: lds-ring 1.2s cubic-bezier(0.5, 0, 0.5, 1) infinite;
  border-color: var(--pa-red) transparent transparent transparent;
}
.lds-ring div:nth-child(1) {
  animation-delay: -0.45s;
}
.lds-ring div:nth-child(2) {
  animation-delay: -0.3s;
}
.lds-ring div:nth-child(3) {
  animation-delay: -0.15s;
}
@keyframes lds-ring {
  0% {
    transform: rotate(0deg);
  }
  100% {
    transform: rotate(360deg);
  }
}

body {
  background: grey;
}
<div class="lds-ring">
  <div></div>
  <div></div>
  <div></div>
</div>

If I use this in the actual index.html file it does indeed work. However, If I have this as a component amongst my others and load it with the selector, ie:

<app-root>
   <app-spinner></app-spinner>
</app-root>

Nothing is displayed and the white screen is seen while waiting.

Is there a solution to this?

2 Answers 2

6

There is no solution, because the reason the loading takes long is because it's loading the app module. The parsing of the template is done in here, so what you want, is just not possible. Angular also ignores anything inside the app-root tag.

The only way to do it is just plain html and css inside the index.html, or perhaps have a look at Server Side Rendering.

You can also try to create a sort of app shell which loads really fast, and have a spinner component loading in between.

Or create two different angular applications, one that is just a spinner, and the other on the actual app. Your spinner will load first and be very quick, and gets replaced by the main app quickly, this is cute but not trivial at all, and will take quite some time to implement.

Sooo, I'm still sticking with my original answer, don't do that, and just use plain html and css to add a spinner. This is the quickest and most responsive. If you are worried about SEO, then you can have a look at SSR.

Sign up to request clarification or add additional context in comments.

Comments

2

There is great solution with html and css in this article by Tomas Trajan. You can add this css to head of index.html or in your styles.css file.

<style type="text/css">
  body, html {
    height: 100%;
  }
  .app-loading {
    position: relative;
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
    height: 100%;
  }
  .app-loading .spinner {
    height: 200px;
    width: 200px;
    animation: rotate 2s linear infinite;
    transform-origin: center center;
    position: absolute;
    top: 0;
    bottom: 0;
    left: 0;
    right: 0;
    margin: auto;
  }
  .app-loading .spinner .path {
    stroke-dasharray: 1, 200;
    stroke-dashoffset: 0;
    animation: dash 1.5s ease-in-out infinite;
    stroke-linecap: round;
    stroke: #ddd;
  }
  @keyframes rotate {
    100% {
      transform: rotate(360deg);
    }
  }
  @keyframes dash {
    0% {
      stroke-dasharray: 1, 200;
      stroke-dashoffset: 0;
    }
    50% {
      stroke-dasharray: 89, 200;
      stroke-dashoffset: -35px;
    }
    100% {
      stroke-dasharray: 89, 200;
      stroke-dashoffset: -124px;
    }
  }
</style>

and in index.html body add

  <app-root>
    <!-- selector from app.component.ts -->

     <!-- loading layout replaced by app after startupp -->
     <div class="app-loading">
       <svg class="spinner" viewBox="25 25 50 50">
        <circle class="path" cx="50" cy="50" r="20" fill="none" stroke- 
         width="2" stroke-miterlimit="10"/>
       </svg>
     </div>

</app-root>

Here is the link for full article.

https://medium.com/@tomastrajan/how-to-style-angular-application-loading-with-angular-cli-like-a-boss-cdd4f5358554 ,you can check there.Hope it was helpful.

1 Comment

Please put the solution to the problem in your actual answer, as the linked website might change or become unavailable, rendering your post useless.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.