Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How do I bind to a custom event in an angularjs directive?

I am having trouble catching an event which is sent like this:

document.body.dispatchEvent(event);

The directive below is on a div, inside the body:

.directive('myDirective',function(){
  return {
    restrict: 'A',
    link: function(scope, element, attrs, pageCtrl){

      element.bind('myEvent', function(){
        console.log('caught my event!');
      });
    }
  };
});

This works if the event is sent with triggerHandler on the div.

event = new Event('myEvent');
elem.triggerHandler(event);

How can I catch a custom event on the document body inside a directive?

Update: This is for use in a Cordova app, with an existing plugin, which dispatches events on document.body. So is there another way I can catch those events in a directive on a div?

like image 491
AgDude Avatar asked May 06 '14 23:05

AgDude


1 Answers

The problem is that events bubble, meaning when you dispatch the event from document.body, it propagates up through its ancestors. Since it doesn't travel down through its descendants, your directive's event listener is never fired.

You can, however, catch the event on body and fire to your div using Angular's internal event system.

Create two directives

One to decorate the body element with the following behavior:

  • catches the Cordova event, then...
  • broadcasts an Angular-internal event from rootScope

.directive('bodyDirective',function($rootScope){
  return {
    restrict: 'A',
    link: function(scope, element, attrs){
      element.bind('myEvent', function(){
        $rootScope.$broadcast('cordovaEvent');
      });
    }
  };
})

... and another to decorate the div with behavior that will catch the Angular event:

.directive('divDirective', function(){
  return {
    restrict: 'A',
    link: function(scope, element, attrs) {
      scope.$on('cordovaEvent', function(){
        // do something here
      }); 
    }
  } 
})

Plunker (you must view the preview in a separate window and watch console there)

like image 128
Marc Kline Avatar answered Oct 20 '22 22:10

Marc Kline