最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

javascript - Angular filter doesn't update when service property changes - Stack Overflow

programmeradmin2浏览0评论

Perhaps this is a fundamental misunderstanding of Angular scope, but here goes.

I have a service that handles changing a language preference:

languageService.js

function languageService() {
  var language = "en";

  var service = {
    getLanguage: getLanguage,
    setLanguage: setLanguage

  };

  function getLanguage () {
    return language;
  }

  function setLanguage (newLang) {
   language = newLang;
  }

  return service;
}

I also have a filter that formats something:

someFilter.js

function myFilter(languageService) {
  return function(num) {
    var french = languageService.getLanguage() === 'fr';

    if (french) {
      return "is french!"
    } else {
      return "is other."
    }
  }      
}

I try to use this filter in some HTML: Blah blah {{ 'test' | someFilter }}.

It works, but only on load; if I call setLanguage('en'), the binding doesn't change.

Perhaps this is a fundamental misunderstanding of Angular scope, but here goes.

I have a service that handles changing a language preference:

languageService.js

function languageService() {
  var language = "en";

  var service = {
    getLanguage: getLanguage,
    setLanguage: setLanguage

  };

  function getLanguage () {
    return language;
  }

  function setLanguage (newLang) {
   language = newLang;
  }

  return service;
}

I also have a filter that formats something:

someFilter.js

function myFilter(languageService) {
  return function(num) {
    var french = languageService.getLanguage() === 'fr';

    if (french) {
      return "is french!"
    } else {
      return "is other."
    }
  }      
}

I try to use this filter in some HTML: Blah blah {{ 'test' | someFilter }}.

It works, but only on load; if I call setLanguage('en'), the binding doesn't change.

Share Improve this question edited Mar 15, 2016 at 18:20 opticon asked Mar 15, 2016 at 17:59 opticonopticon 3,6145 gold badges41 silver badges68 bronze badges 2
  • 1 You need to return 'service' from languageService.js. Also, in your filter make sure you're actually calling the getLanguage method () when you declare var french. – Matthew Clise Commented Mar 15, 2016 at 18:18
  • Yeah, sorry, I cut out some boilerplate for brevity's sake. I'll add it in. – opticon Commented Mar 15, 2016 at 18:19
Add a ment  | 

1 Answer 1

Reset to default 7

There are actually two issues with your code.

First, in the service you should fire a digest when your var changes. So it would be

myApp.factory('languageService', ['$rootScope', function ($rootScope) {
  var language = "en";

  var service = {
    getLanguage: getLanguage,
    setLanguage: setLanguage

  };

  function getLanguage () {
    return language;
  }

  function setLanguage (newLang) {
   language = newLang;
   $rootScope.digest();
  }

  return service;
}]);

Second and more subtle one. In angular, filters get updated only if the value you pass them in the markup changes (in your case is 'test'), for any other change to the scope your filter will be pletely ignored.

The solution is to force angular to parse that particular filter on any digest.

myApp.filter('someFilter', ['localeService', function (localeService) {
  function filter (value) {
    var french = languageService.getLanguage === 'fr';

    if (french) {
      return "is french!"
    } else {
      return "is other."
    }
  }

  filter.$stateful = true; // This line does the trick

  return filter;
}]);

You can get more info on the Angular Docs

发布评论

评论列表(0)

  1. 暂无评论