AngularJS: Clear $ watch


277

Tengo una función de reloj en mi aplicación AngularJS.

$scope.$watch('quartzCrystal', function () {
   ...
}

Sin embargo, después de alguna condición (en mi ejemplo, cambiar la página en mi aplicación de una sola página ) quiero detener ese reloj (como borrar el tiempo de espera).

¿Cómo puedo hacer eso?

Respuestas:


520

$watchdevuelve una función de desregistro. Llamarlo daría de baja el $watcher.

var listener = $scope.$watch("quartz", function () {});
// ...
listener(); // Would clear the watch

24
¿Sabe si es una buena práctica cancelar el registro de todos sus oyentes al final del ciclo de vida del controlador (como en un $on('$destroy')) o AngularJS se encargará de ellos? ¡Gracias!
— Yorch

81
Todos los observadores serán eliminados cuando se destruya el alcance, no es necesario administrarlos
— Umur Kontacı

66
Puede ver una discusión interesante aquí que explica el asunto: github.com/angular/angular.js/issues/4574 Básicamente, si asigna un oyente al $ rootScope, debe desasignarlo usted mismo, o persistirá $ cambios de alcance. Los observadores en $ scope se destruyen con el $ scope ($ scopes no son singletons en Angular, y se crean y destruyen cuando es necesario).
— Mladen Danic

3
Pero, ¿qué pasa si solo quiero que el observador verifique si el valor existe y luego, cuando existe, haga algunos cambios y luego me registre, ya lo intenté? Var listen = $ scope. $ Watch ('mvIdentity.currentUser', function (currentUser ) {prueba = 1; consola.log ("->" + $ scope.updateemail + "-" + prueba); listen ();});
— Harshit Laddha

44
@ UmurKontacı En realidad, el comentario de deadman es perfectamente válido ya que su comentario original no es correcto para todos los casos.
— GFoley83

49

scope. $ watch devuelve una función que puede llamar y que anulará el registro del reloj.

Algo como:

var unbindWatch = $scope.$watch("myvariable", function() {
    //...
});

setTimeout(function() {
    unbindWatch();
}, 1000);

14
Sí, puedes relajarte dentro de watchFn! Caso de uso simple: desea mirar y ejecutar watchFn solo una vez, luego dejar de mirar.
— Mike Rapadas

3
¿Puedo volver a vincular el reloj después de llamar a la función de desvinculación, como volver a llamarlo?
— Bruno Finger

Esto fue útil. Hacer unbindWatch en un tiempo de espera parece importante en mis pruebas.
— eeejay

En este caso, debe usar $ timeout, que también puede cancelar su registro.
— Ben Taliadoros

Lo mejor es evitar los tiempos de espera
— Davi Lima

25

También puede borrar el reloj dentro de la devolución de llamada si desea borrarlo justo después de que ocurra algo. De esa manera, su $ watch permanecerá activo hasta que se use.

Al igual que...

var clearWatch = $scope.$watch('quartzCrystal', function( crystal ){
  if( isQuartz( crystal )){
    // do something special and then stop watching!
    clearWatch();
  }else{
    // maybe do something special but keep watching!
  } 
}

4

En algún momento su $ watch está llamando dynamicallyy creará sus instancias, por lo que debe llamar a la función de desregistro antes de su $watchfunción

if(myWatchFun)
  myWatchFun(); // it will destroy your previous $watch if any exist
myWatchFun = $scope.$watch("abc", function () {});

4

Idealmente, cada reloj personalizado debe eliminarse cuando abandone el alcance.

Ayuda en una mejor gestión de la memoria y un mejor rendimiento de la aplicación.

// call to $watch will return a de-register function
var listener = $scope.$watch(someVariableToWatch, function(....));

$scope.$on('$destroy', function() {
    listener(); // call the de-register function on scope destroy
});

4

Si tiene demasiados observadores y necesita eliminarlos a todos, puede insertarlos en una matriz y destruirlos $watchen un bucle.

var watchers = [];
watchers.push( $scope.$watch('watch-xxx', function(newVal){
   //do something
}));    

for(var i = 0; i < watchers.length; ++i){
    if(typeof watchers[i] === 'function'){
        watchers[i]();
    }
}

watchers = [];

Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.