不是很漂亮,但工作解決方案是使用事件。好吧,也許這並不壞,至少它並不複雜。 https://plnkr.co/edit/SNRFhaudhsWLKUNMFos6?p=preview
angular.module('app',[
'ui.router'
])
.config(function($stateProvider) {
$stateProvider.state('parent', {
views:{
'parent':{
controller: 'parentCtrl',
template: '<div id="parent">'+
'<button ng-click="go(1)">1</button><br>'+
'<button ng-click="go(2)">2</button><br>'+
'<button ng-click="go(3)">3</button><br>'+
'</div>'
},
},
url: ''
});
$stateProvider.state('parent.child', {
views:{
'[email protected]':{
controller: 'childCtrl',
template:'<b>{{ id }}</b>'
}
},
url: '/:id/child',
resolve: {
detailResolver: function($http, $stateParams, $rootScope) {
return $http.get('file'+$stateParams.id+'.json')
.then(function(response) {
alert('response ' + response.data.id);
$rootScope.$broadcast('newData', response.data);
return response.data;
});
}
}
});
})
.controller('parentCtrl', function ($log, $scope, $state) {
$log.info('parentCtrl');
var notify = true;
$scope.go = function (id) {
$state.go('parent.child', {id: id}, {notify:notify});
notify = false;
};
})
.controller('childCtrl', function ($scope, $log, detailResolver, $interval) {
/*
* some stuff happens here
*/
$log.info('childCtrl detailResolver.id == ' + detailResolver);
$scope.$on('newData', function (event, detailResolver) {
$scope.id = detailResolver;
});
$scope.id = detailResolver;
$interval(function(){
console.log(detailResolver.id)
},1000)
})
;
編輯: 多一點點複雜的解決方案,這需要改變承諾的創造者功能分爲觀測,但工程: https://plnkr.co/edit/1j1BCGvUXjtv3WhYN84T?p=preview
angular.module('app', [
'ui.router'
])
.config(function($stateProvider) {
$stateProvider.state('parent', {
views: {
'parent': {
controller: 'parentCtrl',
template: '<div id="parent">' +
'<button ng-click="go(1)">1</button><br>' +
'<button ng-click="go(2)">2</button><br>' +
'<button ng-click="go(3)">3</button><br>' +
'</div>'
},
},
url: ''
});
$stateProvider.state('parent.child', {
views: {
'[email protected]': {
controller: 'childCtrl',
template: '<b>{{ id }}</b>'
}
},
url: '/:id/child',
resolve: {
detailResolver: turnToObservable(['$http', '$stateParams', function($http, $stateParams) { //Have to be decorated either be this or $inject
return $http.get('file' + $stateParams.id + '.json')
.then(function(response) {
alert('response ' + response.data.id);
return response.data;
});
}])
}
});
})
.controller('parentCtrl', function($log, $scope, $state) {
$log.info('parentCtrl');
var notify = true;
$scope.go = function(id) {
$state.go('parent.child', {id: id}, {notify: notify});
notify = false;
};
})
.controller('childCtrl', function($scope, $log, detailResolver, $interval) {
/*
* some stuff happens here
*/
$log.info('childCtrl detailResolver.id == ' + detailResolver);
detailResolver.addListener(function (id) {
$scope.id = id;
});
});
function turnToObservable(promiseMaker) {
var promiseFn = extractPromiseFn(promiseMaker);
var listeners = [];
function addListener(listener) {
listeners.push(listener);
return function() {
listeners = listeners.filter(function(other) {
other !== listener;
});
}
}
function fireListeners(result) {
listeners.forEach(function(listener) {
listener(result);
});
}
function createObservable() {
promiseFn.apply(null, arguments).then(fireListeners);
return {
addListener: addListener
};
}
createObservable.$inject = promiseFn.$inject;
return createObservable;
}
function extractPromiseFn(promiseMaker) {
if (angular.isFunction(promiseMaker)) {
return promiseMaker;
}
if (angular.isArray(promiseMaker)) {
var promiseFn = promiseMaker[promiseMaker.length - 1];
promiseFn.$inject = promiseMaker.slice(0, promiseMaker.length - 1);
return promiseFn;
}
}
當然,使用全局事件將工作。這將是我們的計劃-b。儘管如此,我希望能找到更優雅的靈魂。我會再等一會兒,希望有人能通過rootScope提供一個無垃圾郵件事件的解決方案。 – nilsK
@nilsK這是一個相當有趣的問題,所以我帶着其他解決方案來解決這個問題,它需要改變你的函數,返回承諾函數返回可觀察對象,但它的工作原理。雖然它取決於一些全球可用的功能,但如果您希望這樣做,您可能會將其篡改爲提供商。 – sielakos
這仍然是一個有點古怪,需要裝飾的功能,但這樣做很有趣。 – sielakos