我想了解如何为多个控制器设计单个ajax方法,这也会影响用户界面(例如,加载动画)。
理念是(没有承诺):
var myApp = angular.module('myApp', []);
myApp.controller('myCtrl',
function myCtrl($scope, myFactory){
$scope.loading = false;
$scope.someStuff = myFactory.getStuff(params);
});
myApp.factory('myFactory', function(myService){
return{
getStuff: function(params){
return myService.ajax(params);
}
}
});
myApp.service('myService', function($http) {
this.ajax = function(params){
// switch $scope.loading = true;
// make request
// return $http result
// switch $scope.loading = false;
};
});
据我所知,我需要使用$ scope进行UI更改,并且应该将ajax-method用于自定义服务。 Angularjs中的服务不适用于$ scope,我不知道如何解决这个问题。
我认为,必须有一系列承诺服务。 怎么设计?
更新:我希望,随着文档更加完整和清晰。但角度用户社区已经很棒了。感谢。
答案 0 :(得分:0)
在我的项目中,我定义了一个名为appState
的服务,该服务包含({1}}和showGlobalSpinner
等方法,用于修改hideGlobalSpinner
上的变量。
基本上:
$rootScope
我接下来要做的是使用(…)
.factory('appState', ['$rootScope', function ($rootScope) {
return {
showGlobalSpinner: function () {
++$rootScope.loadingInProgress;
},
hideGlobalSpinner: function () {
if ($rootScope.loadingInProgress > 0) {
--$rootScope.loadingInProgress
}
}
};
}]);
指令在我需要的地方显示微调器:
ng-show
在每个AJAX之前,我只需致电<div class="spinner" ng-show="loadingInProgress"></div>
,在成功/错误之后,我致电AppState.showGlobalSpinner()
答案 1 :(得分:0)
您可以将此method添加到任何控制器:
.controller('HeaderCtrl',['$scope','httpRequestTracker', function($scope,httpRequestTracker) {
$scope.hasPendingRequests = function () {
return httpRequestTracker.hasPendingRequests();
};
}]);
angular.module('services.httpRequestTracker', []);
angular.module('services.httpRequestTracker').factory('httpRequestTracker', ['$http', function($http){
var httpRequestTracker = {};
httpRequestTracker.hasPendingRequests = function() {
return $http.pendingRequests.length > 0;
};
return httpRequestTracker;
}]);
答案 2 :(得分:0)
您可以使用HTTP拦截器,一些事件和指令来尝试更通用的方法:
<强>的Javascript 强>
app.factory('myHttpInterceptor', function($q, $rootScope) {
return function(promise) {
$rootScope.$broadcast('RequestStarted');
var success = function(response) {
$rootScope.$broadcast('RequestFinished', true);
};
var error = function(response) {
$rootScope.$broadcast('RequestFinished', false);
return $q.reject(response);
};
promise.then(success, error);
return promise;
}
})
.config(function($httpProvider) {
$httpProvider.responseInterceptors.push('myHttpInterceptor');
})
.directive('loading', function() {
return {
restrict: 'E',
transclude: true,
template: '<div ng-show="visible" ng-transclude></div>',
controller: function($scope) {
$scope.visible = false;
$scope.$on('RequestStarted', function() {
$scope.visible = true;
});
$scope.$on('RequestFinished', function() {
$scope.visible = false;
});
}
};
});
<强> HTML 强>
...
<loading><h1>Loading...</h1></loading>
...
您可以看到有效的演示here。
通过使用HTTP拦截器,您将能够跟踪Angular应用程序中$http
服务(包括$resource
)所做的每个HTTP请求,并相应地显示加载动画。