web-dev-qa-db-fra.com

Attendre des données dans le contrôleur avant que la fonction de lien ne soit exécutée dans la directive AngularJS

Comment puis-je m'assurer que les données d'un contrôleur ont été chargées dans une directive avant l'exécution de la fonction de liaison?

En utilisant psuedo-code, j'aurais pu:

<my-map id="map-canvas" class="map-canvas"></my-map>

pour mon html.

Dans ma directive, je pourrais avoir quelque chose comme ça:

app.directive('myMap', [function() {



return{
    restrict: 'AE',
    template: '<div></div>',
    replace: true,
    controller: function ($scope, PathService) {

        $scope.paths = [];

        PathService.getPaths().then(function(data){
            $scope.paths = data;

        });

    },
    link: function(scope, element, attrs){
        console.log($scope.paths.length);

    }

}


}]);

Ce qui précède ne fonctionnera pas car console.log ($ scope.paths.length); sera appelé avant que le service n'ait renvoyé des données.

Je sais que je peux appeler le service à partir de la fonction de liaison mais souhaiterais savoir s’il existe un moyen d’attendre l’appel de service avant d’activer la fonction de liaison.

26
James Brunet

La solution la plus simple consisterait à utiliser ng-if puisque l'élément et la directive ne seraient rendus que lorsque le ng-if est résolu comme étant vrai

<my-map id="map-canvas" class="map-canvas" ng-if="dataHasLoaded"></my-map>

app.controller('MyCtrl', function($scope, service){
  $scope.dataHasLoaded = false;

  service.loadData().then(
    function (data) {
      //doSomethingAmazing
      $scope.dataHasLoaded = true
    }
  )
})

ou utiliser des promesses

return {
  restrict: 'AE',
  template: '<div></div>',
  replace: true,
  controller: function ($scope, PathService) {
    $scope.paths = [];
    $scope.servicePromise = PathService.getPaths()
  },
  link: function (scope, element, attrs) {
    scope.servicePromise.then(function (data) {
      scope.paths = data;
      console.log(scope.paths)
    });
  }
}
43
maurycy
app.directive('MyDirective', function() {
    return {
        controller: function() {
            this.$postLink = function() {
                // here will run after the link function and also after the binding came in
            };
        },
        controllerAs: 'vm'
    };
});

vérifier le angulaire 1.5 Les composants ont un cycle de vie bien défini et cela fonctionne sur les directives à 

0
Yitzchak Weingarten