Why do we use $rootScope.$broadcast in AngularJS?

156,087

Solution 1

  1. What does $rootScope.$broadcast do?

    $rootScope.$broadcast is sending an event through the application scope. Any children scope of that app can catch it using a simple: $scope.$on().

    It is especially useful to send events when you want to reach a scope that is not a direct parent (A branch of a parent for example)

    !!! One thing to not do however is to use $rootScope.$on from a controller. $rootScope is the application, when your controller is destroyed that event listener will still exist, and when your controller will be created again, it will just pile up more event listeners. (So one broadcast will be caught multiple times). Use $scope.$on() instead, and the listeners will also get destroyed.

  2. What is the difference between $rootScope.$broadcast & $rootScope.$broadcast.apply?

    Sometimes you have to use apply(), especially when working with directives and other JS libraries. However since I don't know that code base, I wouldn't be able to tell if that's the case here.

Solution 2

$rootScope basically functions as an event listener and dispatcher.

To answer the question of how it is used, it used in conjunction with rootScope.$on;

$rootScope.$broadcast("hi");

$rootScope.$on("hi", function(){
    //do something
});

However, it is a bad practice to use $rootScope as your own app's general event service, since you will quickly end up in a situation where every app depends on $rootScope, and you do not know what components are listening to what events.

The best practice is to create a service for each custom event you want to listen to or broadcast.

.service("hiEventService",function($rootScope) {
    this.broadcast = function() {$rootScope.$broadcast("hi")}
    this.listen = function(callback) {$rootScope.$on("hi",callback)}
})

Solution 3

$rootScope.$broadcast is a convenient way to raise a "global" event which all child scopes can listen for. You only need to use $rootScope to broadcast the message, since all the descendant scopes can listen for it.

The root scope broadcasts the event:

$rootScope.$broadcast("myEvent");

Any child Scope can listen for the event:

$scope.$on("myEvent",function () {console.log('my event occurred');} );

Why we use $rootScope.$broadcast? You can use $watch to listen for variable changes and execute functions when the variable state changes. However, in some cases, you simply want to raise an event that other parts of the application can listen for, regardless of any change in scope variable state. This is when $broadcast is helpful.

Solution 4

Passing data !!!

I wonder why no one mention that $broadcast accept a parameter where you can pass an Object

Example:

// the object to transfert
var obj = {
    status : 10
}

$rootScope.$broadcast('status_updated', obj);
$scope.$on('status_updated', function(event, obj){
    console.log(obj.status); // 10
})

Solution 5

What does $rootScope.$broadcast do?

It broadcasts the message to respective listeners all over the angular app, a very powerful means to transfer messages to scopes at different hierarchical level(be it parent , child or siblings)

Similarly, we have $rootScope.$emit, the only difference is the former is also caught by $scope.$on while the latter is caught by only $rootScope.$on .

refer for examples :- http://toddmotto.com/all-about-angulars-emit-broadcast-on-publish-subscribing/

Share:
156,087

Related videos on Youtube

Nexus23
Author by

Nexus23

A Developer.

Updated on July 08, 2022

Comments

  • Nexus23
    Nexus23 almost 2 years

    Tried to find some basic information for AngularJS $rootScope.$broadcast, But the AngularJS documentation doesn't help much. In easy words why do we use this?

    Also, inside John Papa's Hot Towel template there is a custom function in the common module named $broadcast:

    function $broadcast() {
        return $rootScope.$broadcast.apply($rootScope, arguments);
    }
    

    I did not understand what this is doing. So here are couple of basic questions:

    1) What does $rootScope.$broadcast do?

    2) What is the difference between $rootScope.$broadcast and $rootScope.$broadcast.apply?

  • Nexus23
    Nexus23 almost 10 years
    Thanks @itcouldevenbeabout isn't this line calling the same logic of attaching an event to global $rootScope? function() {$rootScope.$broadcast("hi")}, which you mentioned is a bad practice?
  • CoolTapes
    CoolTapes over 9 years
    Using a service to make the broadcasts and also attach the listeners for a specific event avoids the situation where you're not sure who is listening. It becomes clear which components have the event service as a dependency
  • tobi
    tobi about 9 years
    @itcouldevenbeaboat but if you want to see where it is used you have to search for the service name, but without it you can search for it using just event name? It doesn't give anything more or I overlooked something?
  • Chris Camaratta
    Chris Camaratta almost 9 years
    Agreed with the assessment this suggestion appears to be a superficial wrapper. Why is this considered a best practice? Thanks.
  • lawrence
    lawrence almost 9 years
    This makes refactoring and evolving the code easier. For example, if you wanted to change the event name (e.g. to avoid colliding with some 3rd-party code), or if you wanted to not depend on $rootScope, or if you wanted to add more sophisticated functionality, e.g. keeping track of listeners programmatically, or firing events to only some of them, or waiting for some asynchronous work... then you'd only have to change the service file, not all of its dependents.
  • Brondahl
    Brondahl almost 9 years
    Having just discovered the difference between $emit and $broadcast, I'd be inclined to say that it would be better to $emit the event - that way you the event polluting in the smallest possible set of scopes, (ideally the service would have it's own scope, but I don't think that's possible?)
  • Jadiel de Armas
    Jadiel de Armas over 8 years
    @Brondahl, that is a great suggestion, and I second it. It would be better to use $emit in this particular example.
  • alpha-mouse
    alpha-mouse over 8 years
    -1. I don't see, how isolation in a service is any better than simply broadcasting. Anyway, better use own private scope in the service. And better use $emit, and not $broadcast. Also your proposed service does not support event arguments. What's worse it doesn't support unsubscription; a mortal sin for $rootScope.
  • adamdport
    adamdport over 8 years
    @alpha-mouse, There is no private scope in a service.
  • adamdport
    adamdport over 8 years
    The lack of unsubscription ruins this answer for me. If you call hiEventService.listen(callback) from a controller, the listener will still exist even after the controller is destroyed. Memory leak! Binding to controller scope $scope.$on("hi",callback) comes with automatic cleanup.
  • adamdport
    adamdport over 8 years
    Great catch on the $rootScope.$on memory leak. This applies to the accepted answer too, as controllers are likely to call the hiEventService he created.
  • alpha-mouse
    alpha-mouse over 8 years
    @adamdport one can be created by calling $rootScope.$new. But this doesn't matter much, there are greater problems with the proposed service anyway.
  • Petr Peller
    Petr Peller almost 8 years
    Your implementation will cause memory leaks as listeners are never unregistered.
  • guest
    guest over 7 years
    What is an example where you would use $broadcast vs. $broadcast.apply()
  • Geert Bellemans
    Geert Bellemans about 7 years
    $rootScope.$broadcast sends the event to all listeners, not only listeners from children scopes. $scope.$broadcast limits the event to child scopes