更新跨不同状态的ui-router解析数据

时间:2016-01-19 07:05:48

标签: javascript angularjs angular-ui-router

我正在使用ui-router来管理我网站的各种状态。我使用resolve将数据传递给headerhome控制器,如下面的代码所示。现在我需要更新HomeController中已解决数据的值,此更改也应反映到HeaderController

var myapp = angular.module('myapp', ["ui.router"]);

myapp.service("DataService", [function() {
  var data = { title: 'Some Title' };

  this.get = function() {
    return data;
  };

}]);

myapp.controller("HeaderController", ["data", function(data) {
  var vm = this;

  vm.title = data.title;
}]);

myapp.controller("HomeController", ["data", function(data) {
  var vm = this;

  vm.title = data.title;

  vm.updateTitle = function() {

    // update the resolved data here so the header and home view 
    // updates with new data.title

    data = { title: "Another title" };

    // i know i can do vm.title = data.title; to update home view. 
    // But would be nice to globally update and reflect that change 
    // on all controllers sharing the same resolved data
  };
}]);

myapp.config(function($stateProvider){
$stateProvider
    .state({
        name: "root",
        abstract: true,
        views: {
            "header": {
                templateUrl: "header.html",
                controller: 'HeaderController as vm'
            }
        },
        resolve: {
          data: ['DataService', function(DataService) {
            return DataService.get();
          }]
        }
    })
    .state({
        name: "root.home",
        url: "",
        views: {
            "content@": {
                templateUrl: "home.html",
                controller: "HomeController as vm"
            }
        }
    })
});

PS: 在研究resolve之前,我是直接向控制器注入服务所以请不要建议这样做。

编辑:更新了Plunkr,现在按预期工作。

以下是plunkr

的链接

经验教训:

Angular仅监视分配给作用域的对象,并保持对象的单独引用。我的意思是:

data = { title: 'some title' };
vm.data = data;
vm.title = data.title;

data.title = 'another title';

{{vm.title}} // some title

/////////////////

data = { title: 'some title' };
vm.data = data;

data.title = 'another title';

{{vm.data.title}} // another title

1 个答案:

答案 0 :(得分:2)

您应该利用变量引用,将HeaderController数据绑定到vm.data = data

另一个不正确的事情是data = { title: "Another title" };会创建一个带有新引用的数据对象,并且服务对象的引用将丢失。而不是你应该做data.title = 'Another title';

<强> header.html中

{{vm.data.title}}

<强> HeaderController

myapp.controller("HeaderController", ["data", function(data) {
  var vm = this;
  vm.data = data;
}]);

将updateTitle方法代码更新到下面。

vm.updateTitle = function() {

  // update the resolved data here so the header updates with new data.title
  vm.data.title =  "Another title";
};

Demo here

我要说的是,你不应该使用实际的对象引用,而应该在工厂内部使用setTitle函数,从updateTitle你将调用将更新标题的setter方法。但在这种情况下,您需要再次在两个控制器上添加服务引用。如果它的静态数据那么就没有必要通过解析函数来传递它们。我喜欢在我的控制器中注入服务,然后通过其getter&amp; amp;设定器。

首选方法Plunkr