7

I can see the event $routeChangeStart in my controller, but I don't see how to tell Angular to stay. I need to popup something like "Do you want to SAVE, DELETE, or CANCEL?" and stay on the current "page" if the user selects cancel. I don't see any events that allow listeners to cancel a route change.

Jim Cote
  • 1,746
  • 3
  • 15
  • 26

3 Answers3

16

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.

Mathew Berg
  • 28,625
  • 11
  • 69
  • 90
  • 3
    how to continue changing? For example - show message "Do you want change page?" - Yes - No. On Yes - continue, on "NO" stop. – Ihor Shubin Mar 11 '14 at 12:26
  • This is no good if you need access to the routing parameters. Really irritating that the route can't be canceled from the route change start event. – KingOfHypocrites Aug 30 '14 at 02:24
  • 1
    Nope. Does not cancel the route location change at all, AFAICT. The event.preventDefault() appears to do nothing. – see sharper Sep 17 '14 at 04:53
2

The documented way of doing this is to use the resolve property of the routes.

The '$route' service documentation says that a '$routeChangeError' event is fired if any of the 'resolve' promises are rejected.1 That means you can use the '$routeProvider' to specify a function which returns a promise that later gets rejected if you would like to prevent the route from changing.

One advantage of this method is that the promise can be resolved or rejected based on the results of asynchronous tasks.

tilgovi
  • 306
  • 2
  • 11
  • 2
    But even when rejected, browser url is changed. How to deal with that? – FelikZ May 18 '13 at 12:08
  • You can change the location back yourself with a service that watches the root scope for $locationChangeSuccess. This is what the $route service uses internally but I don't know if it's completely safe to rely on it staying public in the future. However, you could combine this with $routeChangeError for now to restore the old location. Perhaps it's worth asking the maintainers about. – tilgovi Jun 11 '13 at 03:04
  • 1
    @FelikZ FYI, the relevant Angular issue to watch is https://github.com/angular/angular.js/issues/2100 – Sam Oct 25 '13 at 07:05
0
$scope.$watch("$locationChangeStart", function(event){
    event.preventDefault(); 
});

You can do like this as well. Benefit of doing this way is that it doesn't trigger through if() statement with $on ...as you well see that below code will trigger no matter what the condition is:

if(condition){ //it doesn't matter what the condition is true or false
  $scope.$on("$locationChangeStart", function(event){ //this gets triggered
     event.preventDefault();  
  }); 
}
CodeOverRide
  • 4,431
  • 43
  • 36