2015-03-17 6 views
0

Я пытаюсь создать resusable сервис оповещения, который я назвал бы где-нибудь в моем приложении только с:AngularJs обновить директиву после вызова метода службы

alertService.showAlert('warning', 'something went wrong!'); 

Например, после Ajax вызова бэкэнд API. Сейчас я использую фабрику и директиву, но кажется, что я делаю что-то неправильно, потому что директива не обновляется после вызова метода showAlert. Сейчас у меня есть что-то вроде этого:

var srv = angular.module('srv', []); 
srv. factory('alertService', ['$timeout', function($timeout){ 
    var alertService = this; 
     alertService.alertNeeded = false; 
     alertService.alertClass = ''; 
     alertService.alertMessage = ''; 
     alertService.setAlertNeeded = function(){ 
      alertService.alertNeeded = true 
     }; 
     alertService.setAlertClass = function(type){ 
      if(type === 'warning') 
       alertService.alertClass = 'alert-warning'; 
      if(type === 'success') 
       alertService.alertClass = 'alert-success'; 
      if(type === 'info') 
       alertService.alertClass = 'alert-info'; 
      if(type === 'danger') 
       alertService.alertClass = 'alert-danger'; 
     }; 
     alertService.setAlertMessage = function(message){ 
      alertService.alertMessage = message; 
     }; 

     return { 
      showAlert: function(class, msg){ 
       alertService.setAlertNeeded(); 
       alertService.setAlertClass(class); 
       alertService.setAlertMessage(msg); 
      } 
     }; 
}]). 
directive('myAlerts', ['alertService', function(alertService){ 
     return { 
      restrict: 'A', 
      template: '<div ng-class="alertClass" ng-show="alertNeeded">{{alertMessage}}</div>', 
      link: function(scope){     
        scope.alertNeeded = alertService.alertNeeded; 
        scope.alertMessage = alertService.alertMessage; 
        scope.alertClass = alertService.alertClass; 
      } 
     } 
    }]). 
controller('alertShowingController', ['$scope', 'alertService', function($scope, alertService){ 
    alertService.showAlert('warning', 'Warning alert!!!') 
}]); 

Мой код не выглядит точно так же, но я просто хотел показать, что я пытаюсь сделать: я хочу, чтобы позвонить alertService.showAlert(...) из другого контроллера в другом модуле (который зависит от модуля srv), и таким образом обновите переменные в директиве myAlerts, чтобы показать правильное предупреждение.

Вещь после вызова метода showAlert Значения установлены, но внутри кода директивы я получаю alertService.alertNeeded как undefined.

Я совершенно не знаком с AngularJs, поэтому, возможно, я что-то ошибаюсь, но я провел целый вечер, чтобы заставить его работать, и я до сих пор не знаю, что является правильным решением для этого.

Пожалуйста, помогите!

+0

В принципе, ваш 'scope.alertMessage' должен быть функцией, которая возвращает' alertService.alertMessage'. Затем в шаблоне используйте '{{alertMessage()}}'. Таким образом, отображаемое сообщение будет обновляться каждый цикл дайджеста. –

+0

На самом деле, я был неправ. Объект, возвращаемый фабрикой 'alertService', должен предоставить эти методы. Отвечая сейчас. –

ответ

0

Ваш код имеет два разных значения для alertService. Внутри заводского определения это относится к самой фабрике. В другом месте это относится к объекту, возвращаемому фабрикой. Самый простой способ, чтобы двигаться вперед можно было бы добавить несколько недостающих методов объекта, возвращенного на заводе:

return { 
    showAlert: function(cssClass, msg){ 
     alertService.setAlertNeeded(); 
     alertService.setAlertClass(cssClass); 
     alertService.setAlertMessage(msg); 
    }, 

    alertClass: function() { return alertService.alertClass; },  
    alertMessage: function() { return alertService.alertMessage; }, 
    alertNeeded: function() { return alertService.alertNeeded; } 
}; 

Затем изменить шаблон директивы так, что она вызывает эти функции на каждом переваривать цикл:

directive('myAlerts', ['alertService', function(alertService){ 
     return { 
      restrict: 'A', 
      template: '<div ng-class="alertClass()"' + 
         '  ng-show="alertNeeded()">' + 
         ' {{alertMessage()}}' + 
         '</div>', 
      link: function(scope){     
       scope.alertNeeded = alertService.alertNeeded; 
       scope.alertMessage = alertService.alertMessage; 
       scope.alertClass = alertService.alertClass; 
      } 
     } 
}]) 

Затем вы должны увидеть свое предупреждающее сообщение. Try it in a fiddle.

+0

Омг, ты спасатель! Конечно, это было :) Спасибо :) – bbbb

+0

Пожалуйста, просмотрите ответ @ appdJava для другого подхода. Мой ответ был быстрым. Это демонстрирует образец мышления, который может быть действительно полезен позже. –

2

Вот образец, который я использовал однажды

var srv = angular.module('srv', []); 
srv.factory('alertService', ['$timeout', function($timeout){ 
    var alertListeners = []; 

    this.register = function (listener) { 
     alertListeners.push(listener); 
    }; 

    this.notifyAll = function (data) { 
     for (// each listener in array) { 
      var listenerObject = alertListeners[i]; 
      try { // do not allow exceptions in individual listeners to corrupt other listener processing 
       listenerObject.notify(data); 
      } catch(e) { 
        console.log(e); 
      } 
     } 
    }; 
}]). 
directive('myAlerts', ['alertService', function(alertService){ 

    var alertDirectiveObserver = function($scope, alertService) { 

     this.notify = function(data) { 
      /* 
      * TO DO - use data to show alert 
      */ 
     }; 

     alertService.register(this); 
    }; 


    return { 
    restrict: 'A', 
    template: '<div ng-class="alertClass" ng-show="alertNeeded">{{alertMessage}}</div>', 
    controller: ['$scope', 'alertService', alertDirectiveObserver], 
    link: function(scope){ 
    } 
    } 
}]). 
controller('alertShowingController', ['$scope', 'alertService', function($scope, alertService){ 
    alertService.notifyAll({'warning', 'Warning alert!!!'}) 
]); 

Конечно, вы должны также очистки путем регистрации функции для удаления объектов по размаху уничтожению.

например

element.on('$destroy', function() { 
    alertService.unregister(// some listener id); 
}); 
+0

Да, хорошее место. спасибо – Yeager

+0

Спасибо за ваш ответ. Думаю, я тоже попробую ваше решение :) – bbbb

Смежные вопросы