AngularJs - cancel route change event
Instead of $routeChangeStart
use $locationChangeStart
Here's the discussion about it from the angularjs guys: https://github.com/angular/angular.js/issues/2109
Edit 3/6/2018 You can find it in the docs: https://docs.angularjs.org/api/ng/service/$location#event-$locationChangeStart
Example:
$scope.$on('$locationChangeStart', function(event, next, current) {
if ($scope.form.$invalid) {
event.preventDefault();
}
});
AngularJS - Detecting, stalling, and cancelling route changes
You are listening to the wrong event, I did a bit of googling but couldn't find anything in the docs. A quick test of this:
$scope.$on("$locationChangeStart", function(event){
event.preventDefault();
})
In a global controller prevented the location from changing. AngularJs : Cancel route resolve without promise
To cancel a route change from a resolver function, use a throw statement:The problem is that I don't want to use $location.path() in the case of login fail, because it reloads the whole page while I simply need to stay on the route and simply cancel the route, as long as user login is wrong.
monApp.config(function ($routeProvider, $locationProvider){
var rsf = { // This function tells if user is logged or not
"check":function(stockeUtilisateur,$location,Notification){
u = stockeUtilisateur.getUtilisateur();
if(u.role=='admin'||u.role=='utilisateur'){
Notification.success("Youre logged");
}
else{
//$location.path('/accueil');
//Notification.error("bad password");
throw "bad bassword";
}
}
};
$routeProvider
.when('/accueil', {
templateUrl: 'vues/accueil.html',
controller: 'neutreCtrl'
})
.when('/compte', {
templateUrl: 'vues/compte.html',
controller: 'compteCtrl',
resolve:rsf
})
.otherwise({redirectTo: '/accueil'});
})
When a resolver function throws an error, the route change is prevented and a $routeChangeError
event is broadcast. How to watch for a route change in AngularJS?
Note: This is a proper answer for a legacy version of AngularJS. See this question for updated versions.
$scope.$on('$routeChangeStart', function($event, next, current) {
// ... you could trigger something here ...
});
The following events are also available (their callback functions take different arguments):- $routeChangeSuccess
- $routeChangeError
- $routeUpdate - if reloadOnSearch property has been set to false
There are two other undocumented events:
- $locationChangeStart
- $locationChangeSuccess
Detect route change in an Angular service
By using $routeChangeStart, you are listening to a broadcast sent by $routeProvider on every change of the route. I don't think you need to call it in multiple places ( controllers ), just to check this.
In your service:
angular.module('lmsApp')
.service('pageAuth', ['$location', function ($location) {
var canAccess = function(event,next,current){
var user = firebase.auth().currentUser;
//requireAuth is a custom route property
if (next.$$route.requireAuth && user == null ) {
event.preventDefault(); //prevents route change
alert("You must be logged in to access page!");
}
else {
console.log("allowed");
}
}
$rootScope.$on('$routeChangeStart',canAccess);
}]);
And then inject your service in the .run()
part of your application. This will ensure the check will be done automatically ( by the broadcast as mentioned earlier ).In you config part :
angular.module('lmsApp')
.run(function runApp(pageAuth){
//rest of your stuff
});
Route change events while trying to avoid using $rootScope
You missread that.
First of all, this event was added by Angular team - do you think they recommend not to use it?:D That article is about that you should not put everything to $rootScope, which seems to be an easy way for beginners.
Actually, using $rootScope
- for for global events is absolutely ok -- that is actual purpose of this service.
AngularJS confirm before route change
Demo: http://plnkr.co/edit/Aq8uYg
In the demo, if you change the value of input, you will be noticed when trying to go back.
Listen to $locationChangeStart
and use event.preventDefault()
to cancel the location change if changes not confirmed.
This method has one advantage over $route.reload()
: current controller and models will not be re-instantiated. thus all of your variables are kept the same as user click the "Back" button.
Related Topics
JavaScript Time Zone Is Wrong for Past Daylight Saving Time Transition Rules
How to Convert Numbers Between Different Bases in JavaScript
When Do I Need to Specify the JavaScript Protocol
Can't Require() Default Export Value in Babel 6.X
Understanding JavaScript Promises; Stacks and Chaining
Javascript: How to Detect If a Word Is Highlighted
How to Read the Correct Time/Duration Values from Google Spreadsheet
Execute an Exe File Using Node.Js
JSON Transfer of Bigint: 12000000000002539 Is Converted to 12000000000002540
How Do We Set Remote in Typeahead.Js
Why Do I Need to Await an Async Function When It Is Not Supposedly Returning a Promise
Check If an Object Implements an Interface at Runtime with Typescript
How to Calculate How Many Seconds Between Two Dates
Focus Next Element in Tab Index