我最近从ngRoute迁移到了ui-router。我有一个包含2个部分的页面。
右侧部分显示当前项目详细信息, 左侧部分显示与当前项目类似的项目。
一旦用户点击左侧列表中的类似项目,右侧部分将重新加载点击的项目ID,左侧部分将保持不变。
为了使左侧部分保持在用户项导航上,我将左侧部分定义为抽象状态,将右侧部分定义为子级状态。 (如果您不想查看某个项目,则无法查看类似的项目。)
左侧部分(listview)是父级,包含HTML中的ui-view以嵌入项目详细信息。
要在页面打开时加载类似的项目,我需要知道我的子状态正在加载哪个项目。但我不能为抽象状态和它的子状态定义相同的URL。 我试图在抽象状态下解决$ stateParams而没有机会。
我的状态配置在
之下app.config(['$stateProvider', function ($stateProvider) {
$stateProvider
.state('item', {
//url: '/items/:itemName/:itemID'
url: '/items',
abstract: true,
templateUrl: 'Scripts/app/item/ItemListTemplate.html',
controller: 'ItemListController as itemList'
}).state('item.itemDetails', {
url: '/:itemName/:itemID',
templateUrl: 'Scripts/app/item/ItemDetailTemplate.html',
controller: 'ItemDetailController as itemDetail'
});
如何从抽象状态(来自ItemListController)访问itemID?
答案 0 :(得分:2)
我使用角度范围变量解决了问题。 parent包含一个ui-view来显示子状态内容。因此,子状态和父状态共享相同的范围,因此我可以通知父关于所选项目ID,父母可以更新它的视图。
父州有像这样的范围函数
$scope.notifySelectedItem = function(selectedItemID){};
并且子状态可以从它的范围调用此函数
$scope.notifySelectedItem($stateParams.itemID);
答案 1 :(得分:0)
我会将其建模为具有两个命名视图的单个状态。您所在州的主题是单个项目和相关数据,因此您的州可能应该围绕这一点。您已经描述了两个视图,一个显示项目详细信息,另一个显示其他内容,但主要主题仍然是一个项目。
$stateProvider
.state('item', {
url: '/item/:itemID',
views: {
detail: {
templateUrl: 'Scripts/app/item/ItemDetailTemplate.html',
controller: 'ItemDetailController as itemDetail'
}, related: {
templateUrl: 'Scripts/app/item/ItemListTemplate.html',
controller: 'ItemListController as itemList'
}
}
});
在父视图中,添加两个命名的ui-views,其中上面定义的视图将插入:
<div ui-view="related"></div>
<div ui-view="detail"></div>
现在,您可以使用解析来增强此功能,以便在调用控制器之前预加载数据:
$stateProvider
.state('item', {
url: '/item/:itemID',
resolve: {
item: function($http, $stateParams) {
return $http.get('/item/' + $stateParams.itemID);
},
related: function($http, $stateParams) {
return $http.get('/item/' + $stateParams.itemID + "/related");
},
},
views: {
detail: {
templateUrl: 'Scripts/app/item/ItemDetailTemplate.html',
controller: 'ItemDetailController as itemDetail'
}, related: {
templateUrl: 'Scripts/app/item/ItemListTemplate.html',
controller: 'ItemListController as itemList'
}
}
});
app.controller("ItemListController", function($scope, related) { $scope.related = related.data; });
app.controller("ItemDetailController", function($scope, item) { $scope.item = item.data; });