programing

angularJS에서의 브로드캐스트이벤트 구독 해제 방법$on을 통해 등록된 기능을 삭제하는 방법

lastmemo 2023. 3. 22. 20:37
반응형

angularJS에서의 브로드캐스트이벤트 구독 해제 방법$on을 통해 등록된 기능을 삭제하는 방법

$on 기능을 사용하여 $broadcast 이벤트에 청취자를 등록했습니다.

$scope.$on("onViewUpdated", this.callMe);

특정 비즈니스 규칙에 따라 이 청취자의 등록을 취소합니다.단, 일단 등록이 되면 등록을 취소할 수 없는 것이 문제입니다.

Angular에 방법이 있습니까?특정 청취자의 등록을 취소하려면 , JS 를 선택합니다.이 이벤트를 등록 취소하는 $on과 같은 메서드는 $off일 수 있습니다.그래서 내가 말할 수 있는 비즈니스 논리에 근거해서

 $scope.$off("onViewUpdated", this.callMe);

누군가가 "onViewUpdated" 이벤트를 브로드캐스트하면 이 함수의 호출이 중지됩니다.

감사해요.

EDIT: 다른 기능에서 청취자의 등록을 취소합니다.등록하는 기능이 아닙니다.

이벤트 가입 해제를 위해서는 반환된 기능을 저장하고 호출해야 합니다.

var deregisterListener = $scope.$on("onViewUpdated", callMe);
deregisterListener (); // this will deregister that listener

이는 적어도 1.0.4에서는 소스 코드:)에 기재되어 있습니다.짧으니까 그냥 전체 코드를 올릴게요.

/**
  * @param {string} name Event name to listen on.
  * @param {function(event)} listener Function to call when the event is emitted.
  * @returns {function()} Returns a deregistration function for this listener.
  */
$on: function(name, listener) {
    var namedListeners = this.$$listeners[name];
    if (!namedListeners) {
      this.$$listeners[name] = namedListeners = [];
    }
    namedListeners.push(listener);

    return function() {
      namedListeners[indexOf(namedListeners, listener)] = null;
    };
},

, 메뉴얼도 참조해 주세요.

대부분의 답변을 보면 지나치게 복잡한 것 같다.Angular는 등록을 취소하는 메커니즘이 내장되어 있습니다.

에서 반환된 등록 해제 함수를 사용합니다.

// Register and get a handle to the listener
var listener = $scope.$on('someMessage', function () {
    $log.log("Message received");
});

// Unregister
$scope.$on('$destroy', function () {
    $log.log("Unregistering listener");
    listener();
});

이 코드는 유효합니다.

$rootScope.$$listeners.nameOfYourEvent=[];

편집: 올바른 방법은 @LiviuT의 답변에 있습니다!

Angular의 스코프를 언제든지 확장하여 다음과 같이 청취자를 제거할 수 있습니다.

//A little hack to add an $off() method to $scopes.
(function () {
  var injector = angular.injector(['ng']),
      rootScope = injector.get('$rootScope');
      rootScope.constructor.prototype.$off = function(eventName, fn) {
        if(this.$$listeners) {
          var eventArr = this.$$listeners[eventName];
          if(eventArr) {
            for(var i = 0; i < eventArr.length; i++) {
              if(eventArr[i] === fn) {
                eventArr.splice(i, 1);
              }
            }
          }
        }
      }
}());

작동 방식은 다음과 같습니다.

  function myEvent() {
    alert('test');
  }
  $scope.$on('test', myEvent);
  $scope.$broadcast('test');
  $scope.$off('test', myEvent);
  $scope.$broadcast('test');

그리고 여기 그 중 한 가지가 있다.

코드를 디버깅한 후 "blesh"의 답변과 같은 나만의 함수를 만들었습니다.그래서 내가 한 일은 했다.

MyModule = angular.module('FIT', [])
.run(function ($rootScope) {
        // Custom $off function to un-register the listener.
        $rootScope.$off = function (name, listener) {
            var namedListeners = this.$$listeners[name];
            if (namedListeners) {
                // Loop through the array of named listeners and remove them from the array.
                for (var i = 0; i < namedListeners.length; i++) {
                    if (namedListeners[i] === listener) {
                        return namedListeners.splice(i, 1);
                    }
                }
            }
        }
});

따라서 $rootscope에 기능을 연결하면 모든 컨트롤러에서 사용할 수 있게 됩니다.

그리고 내 코드로 나는 하고 있다.

$scope.$off("onViewUpdated", callMe);

감사해요.

편집: 각도JS의 방법은 @LiviuT의 답변에 있습니다!그러나 다른 범위에서 리스너를 등록 해제하고 동시에 등록 해제 함수의 참조를 유지하기 위한 로컬 변수 작성은 피해야 합니다.이것은 가능한 해결책입니다.

@LiviuT의 답변은 훌륭하지만, 많은 사람들이 다른 $scope나 함수에서 핸들러의 해체 기능에 어떻게 재접속해야 하는지 궁금해 하는 것 같다.@Рустем Мусабеков's answer works just great, but isn't very idiomatic. (And relies on what's supposed to be a private implementation detail, which could change any time.)그리고 거기서부터는 일이 더 복잡해져요

풀 수 있는 기능 function)을 것(Tear-down function)이라고합니다.offCallMeFn(이 예에서는) 핸들러 자체에서 어떤 조건에 따라 호출합니다.마syslog $ 、 syslogsyslog 、 arg 、 일일syslog 。따라서 핸들러는 언제든지 원하는 장소에서 스스로를 파괴할 수 있으며, 자신의 파괴의 씨앗을 가지고 다닐 수 있습니다.다음과 같이 합니다.

// Creation of our handler:
var tearDownFunc = $rootScope.$on('demo-event', function(event, booleanParam) {
    var selfDestruct = tearDownFunc;
    if (booleanParam === false) {
        console.log('This is the routine handler here. I can do your normal handling-type stuff.')
    }
    if (booleanParam === true) {
        console.log("5... 4... 3... 2... 1...")
        selfDestruct();
    }
});

// These two functions are purely for demonstration
window.trigger = function(booleanArg) {
    $scope.$emit('demo-event', booleanArg);
}
window.check = function() {
    // shows us where Angular is stashing our handlers, while they exist
    console.log($rootScope.$$listeners['demo-event'])
};

// Interactive Demo:

>> trigger(false);
// "This is the routine handler here. I can do your normal handling-type stuff."

>> check();
// [function] (So, there's a handler registered at this point.)  

>> trigger(true);
// "5... 4... 3... 2... 1..."

>> check();
// [null] (No more handler.)

>> trigger(false);
// undefined (He's dead, Jim.)

두 가지 생각:

  1. 이는 한 번 실행 핸들러에 적합한 공식입니다. 실행해 .selfDestruct자살 임무가 끝나는 대로요
  2. 당신이 닫힌 변수에 대한 참조를 가지고 있다는 것을 감안할 때 원래 스코프가 제대로 파괴되고 쓰레기가 수집될 수 있을지 궁금합니다.기억력에 문제가 되려면 수백만개를 써야 할 텐데 궁금하네요아시는 분 있으면 말씀해주세요.

컴포넌트가 삭제되면 후크를 등록하여 리스너 등록을 해제합니다.

$scope.$on('$destroy', function () {
   delete $rootScope.$$listeners["youreventname"];
});  

번 끌 경우, '듣다'로 수 .boolean

function switchListen(_switch) {
    if (_switch) {
      $scope.$on("onViewUpdated", this.callMe);
    } else {
      $rootScope.$$listeners.onViewUpdated = [];
    }
}

'$on' 자체는 등록 취소에 대한 함수를 반환합니다.

 var unregister=  $rootScope.$on('$stateChangeStart',
            function(event, toState, toParams, fromState, fromParams, options) { 
                alert('state changing'); 
            });

unregister() 함수를 호출하여 해당 청취자의 등록을 해제할 수 있습니다.

한 가지 방법은 일단 청자를 끝낸 후에 단순히 청자를 파괴하는 것이다.

var removeListener = $scope.$on('navBarRight-ready', function () {
        $rootScope.$broadcast('workerProfile-display', $scope.worker)
        removeListener(); //destroy the listener
    })

언급URL : https://stackoverflow.com/questions/14898296/how-to-unsubscribe-to-a-broadcast-event-in-angularjs-how-to-remove-function-reg

반응형