0

Below element is within my mainController

<img src="loader.gif" ng-hide="done_ajax"/>

and I can't alter using $scope.done_ajax because my ajax is done in another controller. How can I communicate between mainController and my controller2?

app.service('finished_request', function(){

});

callAPI("getUser", {
            method: "GET"
        }).done(function (resp) {

            $scope.$apply(function () {

            });

});
Alice Xu
  • 533
  • 6
  • 20

1 Answers1

0

If you want to share data between two controllers, you can use Service. Service are singletons, so you can easily share your data.

However, you want to notify when you have changed your data, so to achieve this, you should use the $broadcast() and $on() method.

  • $broadcast : dispatches the event downwards to all child scopes

As there is no parent-child relation between your scopes, if your controllers are at the same level, you can inject $rootScope into the controller and broadcast the event to all child scopes.

EDIT

there is example by using Service and broadcast parameter.

So you can do :

Controller

(function(){

function Controller($scope, $rootScope, Service) {

  $scope.data = 1;

  $scope.set = function(n){
    $scope.data = n;
    Service.set($scope.data);
    $rootScope.$broadcast('set', $scope.data);
  }

}

angular
.module('app', [])
.controller('ctrl', Controller);

})();




(function(){

function Controller($scope, Service) {

  $scope.$on('set', function(e, data){
    $scope.data2 = Service.get();
    $scope.data3 = data;
  });

}

angular
.module('app')
.controller('ctrl2', Controller);

})();

Service

(function(){

  function Service(){

    var data;

    function get(){
      return data;
    }

    function set(value){
      data = value;
    }


    return {
      get: get,
      set: set
    };

  }

  angular
    .module('app')
    .factory('Service', Service);

})();

HTML

  <body ng-app='app'>

    <h3>Controller 1</h3>
    <div ng-controller="ctrl">
      <button ng-click="set(data)">change</button>
      <input type="text" ng-model="data">
    </div>

    <h3>Controller 2</h3>
    <div ng-controller="ctrl2">
      <p>Data from controller 1 : {{data2}}</p>
      <p>Data from controller 1 without service : {{data3}}</p>
    </div>

  </body>

Now, you will be able to communicate between differents controllers, and retrieve data by using Service.

You can see the Plunker

Just by using Service singleton

Controller

(function(){

function Controller($scope, Service) {

  $scope.data = 1;

  $scope.set = function(n){
    Service.set(n)
  }

}

angular
.module('app', [])
.controller('ctrl', Controller);

})();



(function(){

function Controller($scope, Service) {
  //Retrieve service instance
  $scope.data_service = Service;

}

angular
.module('app')
.controller('ctrl2', Controller);

})();

HTML

  <body ng-app='app'>

    <h3>Controller 1</h3>
    <div ng-controller="ctrl">
      <button ng-click="set(data)">change</button>
      <input type="text" ng-model="data">
    </div>

    <h3>Controller 2</h3>
    <div ng-controller="ctrl2">
      <p>Data from controller 1 : {{data_service.get()}}</p>
    </div>

  </body>

Here, we just share the instance of our Service.

You can see the Plunker with Service

Paul Boutes
  • 3,285
  • 2
  • 19
  • 22
  • it's also possible to use broadcast without a service. Correct? – Alice Xu Aug 31 '15 at 13:09
  • yes, you can pass data as second parameter of `$broadcast` method. – Paul Boutes Aug 31 '15 at 13:16
  • Can do u it without $broadcast? take a look my flow here http://stackoverflow.com/questions/32312018/angularjs-service-doesnt-work-in-my-case – Alice Xu Aug 31 '15 at 13:20
  • @AliceXu I've update the code and the plunker, now you can see two example, by using broadcast without parameter and Service, and just broadcast with parameter. – Paul Boutes Aug 31 '15 at 13:21
  • I'm following someone's tutorial with just using service, any I appreciate your effort. – Alice Xu Aug 31 '15 at 13:25
  • @AliceXu Ok, i've update the code, with what you want, just by using Service instance. – Paul Boutes Aug 31 '15 at 13:43
  • Why you don't use like app.service('service_name',function(){}); ? – Alice Xu Aug 31 '15 at 13:46
  • This is a habit. By wrapping your Angular module in an anonymous function, you prevent your code from conflicting with other code. – Paul Boutes Aug 31 '15 at 13:51
  • http://stackoverflow.com/questions/32312018/angularjs-service-doesnt-work-in-my-case/32312203?noredirect=1#comment52500416_32312203 look at here, why would he use $watch and you don't? – Alice Xu Aug 31 '15 at 13:53
  • This is the power of Service. I just wrap my service instance into the `$scope` of my second controller, and this is the same instance, services are singletons. So when i retrieve data from service in my view, you don't have to use `$watch`, because we are sharing instance, not just a variable – Paul Boutes Aug 31 '15 at 14:00
  • Good aproach but if u have multiple service your code look abit messy I think. Do you think I should use factory instead of service in this case? – Alice Xu Sep 01 '15 at 02:35
  • In your case it's not really important. In my example, you can use `Service` instead of `Factory`. In this case, it is not really important because they are all Singletons. Basically, function that you write in `Service` will be new-ed, while the function will be invoked in a `Factory`. – Paul Boutes Sep 01 '15 at 08:09
  • singleton means what? can u explain why factory isn't a singleton? – Alice Xu Sep 01 '15 at 09:55
  • 1
    Singleton means that there is **only one** instance of a given object. And i said that all angular Service are singleton – Paul Boutes Sep 01 '15 at 10:00