Empresas
Empregos
  • Sobre nós
  • Soluções
    • Publicação de vagas
      Publique sua vaga e receba candidatos qualificados em 48h.
    • Avaliações de candidatos
      Mais de 500 testes técnicos e psicológicos, mais anti-fraude.
    • Headhunting
      Busca executiva personalizada do início ao fim.
    • Folha de Pagamento + EOR
      Dispersão de folha e EOR em mais de 15 países da LATAM.
  • Preços
  • Empregos

0

335
Visualizações
Countdown timer error when changing inside my web page using Angular, TypeScript

I set a countdown timer in typescript to my webpage on the home page. But when I change to another page I get a console error every second.

.TS

countDown() {
    var countDownDate = new Date("Jan 1, 2022 00:00:00").getTime();

    // Update the count down every 1 second
    var x = setInterval(function () {
      var now = new Date().getTime();

      // Find the distance between now an the count down date
      var distance = countDownDate - now;

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

      // Display the result in an element with id="demo"
      var contadorElement =  document.getElementById("contador") as HTMLElement; // <- Line 37
      contadorElement.innerHTML = days + "d " + hours + "h "
        + minutes + "m " + seconds + "s ";

      if (distance < 0) {
        clearInterval(x);
        contadorElement.innerHTML = "EXPIRED";
      }
    }, 1000);
  }

.HTML

<p id="contador" style="font-size:30px"></p>

The code above works under 'localhost:4200/'. However if I go to 'localhost:4200/anotherStuf' (for example) I get this console error every second:

core.js:6456 ERROR TypeError: Cannot set properties of null (setting 'innerHTML')
    at home.component.ts:37
    at timer (zone.js:2561)
    at ZoneDelegate.invokeTask (zone.js:406)
    at Object.onInvokeTask (core.js:28661)
    at ZoneDelegate.invokeTask (zone.js:405)
    at Zone.runTask (zone.js:178)
    at invokeTask (zone.js:487)
    at ZoneTask.invoke (zone.js:476)
    at data.args.<computed> (zone.js:2541)

Any thoughts?

about 4 years ago · Santiago Gelvez
1 Respostas
Responde à pergunta

0

When you change your page, the part of the DOM that your contador element resides in gets destroyed. Since you do not clean up your setInterval in the ngOnDestroy hook, your code is still running, even when you navigate away (i.e. your component gets destroyed). This would lead to an error along the lines of cannot read undefined of contadorElement (reading: innerHTML) or something similiar.

The solution is simple: clean up your setInterval, which you can achieve by calling clearInterval in the ngOnDestroy hook, using the return value of your setInterval as the parameter.

private interval;

countDown() {
   this.interval = setTimeout(() => { /* Omitted for readability */}, 1000);
}

ngOnDestroy() {
   clearInterval(this.interval);
}

Since you are clearing the interval already when the distance reaches 0, you might want to polish this a bit by setting the variable to undefined or null after clearing the interval and only calling clearInterval when you did not already stop it.

private interval;

countDown() {
   this.interval = setTimeout(() => { 
      /* Omitted for readability */
      
      if (distance < 0) {
        this.stopInterval();
        contadorElement.innerHTML = "EXPIRED";
      }
   }, 1000);
}

ngOnDestroy() {
   clearInterval(this.interval);
}

private stopInterval() {
   if (this.interval) {
      clearInterval(this.interval);
      this.interval = null;
   }
}

If you can't stop the timer in ngOnDestroy (if, for example, your code resides inside a service and you don't want to call a stopCountDown method in ngOnDestroy), you will have to check if the element exists in each setInterval loop and possibly destroy the interval if it does not exist anymore.

countDown() {

    // Update the count down every 1 second
    var x = setInterval(function () {
      /* Omitted for readability */
       
      var contadorElement =  document.getElementById("contador") as HTMLElement; 

      if (contadorElement) {
         contadorElement.innerHTML = days + "d " + hours + "h " + minutes + "m " + seconds + "s ";
      } else {
         clearInterval(x);
      }

      if (distance < 0) {
        clearInterval(x);
        contadorElement.innerHTML = "EXPIRED";
      }
    }, 1000);
  }
about 4 years ago · Santiago Gelvez Relatório
Responde à pergunta
Encontrar trabalhos remotos

Descubra a nova forma de encontrar um emprego!

melhores empregos
Principais categorias de trabalho
Empresas
Postar vaga Preços Comercial
Jurídico
Termos e Condições Política de privacidade
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Recomende algumas ofertas para mim
Preciso de ajuda