Stopping an AngularJS timeout from running

I have a multi-platform app created using AngularJS and Onsen/Monaca UI.

In my app, I have a feature that detects button clicks and after a certain number of clicks, the user is directed to a confirmation screen. However, if the user takes too long to make the selections, they should be redirected to another screen (which has not been defined yet).

Although I am trying to use the $timeout function for this purpose, I am facing issues with canceling the timer once the right number of button clicks have been made by the user. Even after progressing to the confirmation page, the $timeout message continues to display after 10 seconds.

Below is the code implementation. It can be assumed that everything works correctly except for the $timeout.cancel() in the stop() function.

// Initialization
var timer;

// Watching for changes on button clicks
$scope.$watch('currentAction', function(newValue, oldValue) {
    if (counter == 6) {
        // User clicked buttons - cancel the timer
        stop();
        // Proceed to next page
        Segue.goTo("confirmation.html");
    }
    else {
        // Start the timer
        timer = $timeout(function () {
            alert("You are taking too long to respond");
        }, 10000);
    }
});

// Cancel the $timeout
function stop() {
    $timeout.cancel(timer);
}

The Segue.goTo() function simply navigates the user to the specified page (not directly related but included for clarity)

var myFunctions = {
    goTo: function (url) {
        var nextPage = url;
        var element = document.querySelector("ons-navigator");
        var scope = angular.element(element).scope();
        scope.myNavigator.pushPage(nextPage);
    },
}

Answer №1

When creating a timer within $scope.$watch, it's important to be mindful of potential issues that may arise if the timer is created multiple times but only one variable is used to keep track of it. In such cases, only the latest timer can be cancelled using $timeout(timer). To address this, consider moving the $timeout section outside of $scope.$watch, or alternatively, store timers in an array and loop through the array to stop them.

If you choose to continue utilizing $scope.$watch, make sure to cancel the previous timer before creating a new one.

if (timer) {
    $timeout.cancel(timer);
}
timer = $timeout(function () {
    alert("You are taking too long to respond");
}, 10000);

Below is a code snippet demonstrating these concepts:

  • The timer is initialized once Angular finishes rendering the page.
  • A new timer will be set when the test variable is changed.

angular.module("app", [])
  .controller("myCtrl", function($scope, $timeout) {
    var timer;
    $scope.$watch('test', function(newValue, oldValue) {
      console.log('$timeout created. value:' + newValue);
      timer = $timeout(function() {
        console.log('$timeout fired. value:' + newValue);
      }, 5000);
    })
    
    $scope.clickEvt = function() {
      console.log('$timeout canceld. currentValue:' + $scope.test);
      $timeout.cancel(timer);
    }
  })
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<div ng-app="app" ng-controller="myCtrl">
  <input type="text" ng-model="test">
  <button ng-click="clickEvt()">Stop<button>
</div>

Answer №2

consider utilizing this suggestion

$timeout.clear(timer);

just make sure to declare timer variable prior to the if statement

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

What exactly is the purpose of measuring "First Load JS" in the @next/bundle-analyzer tool?

The analysis generated by the NextJS bundle analyzer appears as follows: Page Size First Load JS ┌ λ / 12 ...

I am in need of a datepicker for my project that will display the END date as the current date and set the START date as 7 days before the END date

$(document).ready(function () { $("#end").datepicker({ dateFormat: "dd-M-yy", minDate: 0, onSelect: function () { var start = $('#start'); var startDate = $(this).datepicker('getDate') ...

retrieve the variable contained within the callback function

const axios = require('axios'); const options = { url: 'https://api.github.com/repos/axios/axios', headers: { 'User-Agent': 'axios' } }; function handleResponse(error, response, body) { if (!error && re ...

Error message "Property 'name' does not exist on type '{}'" is encountered when using Ionic/Angular HttpClient and no data type is specified

While working on my Ionic project, I encountered an error in Angular when trying to fetch data from an API using HttpClient. The error message that popped up was 'Property 'name' does not exist on type '{}'.'. Below is the cod ...

What is the best way to assign a value to process.env within an npm script?

After creating a new Vue app (using Vite) with npm init vue@latest and selecting Playwright for e2e tests, the configuration file was generated with a field for setting headless mode: const config: PlaywrightTestConfig = { // ... use: { // ... ...

There seems to be an issue with a potentially null object in an Angular project while trying to view a PDF file

IDENTIFY THE ERROR: printContents = document.getElementById('print').innerHTML.toString(); ON LINE 4: print(): void { let printContents!: string; let popupWin!: any; printContents = document.getElementById('print').innerHTM ...

The Highchart formatter function is being called twice on each occasion

My high chart has a formatter function that seems to be running twice. formatter: function() { console.log("starting formatter execution"); return this.value; } Check out the Fiddle for more details! ...

Guide on removing the <hr/> tag only from the final list item (li) in an Angular

This is my Angular view <li class= "riskmanagementlink" ng-repeat="link in links"> <h3> {{link.Description}} </h3> <a> {{link.Title}} </a> <hr/> </li> I need assistance with removing the hr tag for the l ...

Filtering out specific properties in an array using Angular

I am facing an issue with my Angular filter when inputting text for a specific list. initialViewModel.users = [ {user: 'Nithin',phone: 'Azus', price: 13000}, {user: 'Saritha',phone: 'MotoG1',price: 12000}, {user: ...

Enforce the splicing of the ng-repeat array with the utilization of track by

Our app incorporates a task list that can potentially grow to a substantial size. The main task list is accompanied by a sidebar, where selected tasks can be edited using a different controller (TasksSidebarCtrl instead of TasksCtrl which handles the list ...

Utilizing ng-file-upload for seamless integration with WebService

Struggling to implement zip file uploading functionality on a server. The client side is AngularJS, while the server side is C# ASP.NET, but encountering issues in making it work. The code on the server-side appears as follows: [System.Web.Script.Service ...

Creating a PHP script that retrieves data from JavaScript and stores it in MySQL can be accomplished by using AJAX to send the

Hello, I am attempting to create a PHP script that can extract coordinates from this JavaScript code (or from this link ) and store them in a MySQL database. Can someone please provide me with a tutorial on how to accomplish this? <script> var ...

Vue js version 2.5.16 will automatically detect an available port

Every time I run the npm run dev command in Vue.js, a new port is automatically selected for the development build. It seems to ignore the port specified in the config/index.js file. port: 8080, // can be overwritten by process.env.PORT, if port is in u ...

Tips for accelerating the loading of data retrieved through ajax requests

At present, data is being fetched in array form from a PHP script. I have noticed that when retrieving 40 sets of data, it takes approximately 20 seconds for the data to load. This delay may be due to ajax having to wait until all the results are gathered. ...

Express.js: Defining a base route can cause issues with resolving static files

I'm currently working on a project using express.js and react.js, but I've encountered some issues that I can't seem to find solutions for. I have set up a base directory where the express server is located, and within that, there's a ...

The simplest method to make HTML elements inaccessible to the Simple HTML Dom Parser in PHP

Imagine a scenario where a basic web application is running and utilizing Simple HTML Dom Parser. The code snippet below demonstrates this: <?php include('simple_html_dom.php'); $html = file_get_html('http://someurl.com'); ...

What are the methods for accessing data from a local Json file on an html page without using a server?

Looking to access a local Json file from an HTML page, but encountering challenges in reading the file on Chrome and IE. Is there a method to achieve this without relying on a web server? ...

A computer program designed to determine a series of numbers needed to complete a square grid

Given the numbers 1, 2, 3, 4, 5, 6, 7, 8, I am seeking to replace the x's in such a way that each side adds up to the number in the center. *-*---*-* |x| x |x| *-*---*-* |x| 12|x| *-*---*-* |x| x |x| *-*---*-* Initially, I have iterated over the num ...

Utilizing precise data types for return values in React hooks with Typescript based on argument types

I developed a react hook that resembles the following structure: export const useForm = <T>(values: T) => { const [formData, setFormData] = useState<FormFieldData<T>>({}); useEffect(() => { const fields = {}; for (const ...

JQuery Slideshow Automation

I have created a slideshow using Javascript and JQuery for my webpage. However, I am encountering an issue where only one of the slideshows cycles through all the pictures and then starts over, while the second one ends after cycling once. Can someone as ...