angularjs recebendo rota anterior

{{header}}

{{back.text}}

Na minha configuração de módulo

  $routeProvider. when('/', { controller:HomeCtrl, templateUrl:'home.html' }). when('/menu', { controller:MenuCtrl, templateUrl:'menu.html' }). when('/items', { controller:ItemsCtrl, templateUrl:'items.html' }). otherwise({ redirectto:'/' }); 

Controladores

 function HomeCtrl($scope, $rootScope){ $rootScope.header = "Home"; $rootScope.back = {url:'#/menu', text:'Menu'}; } function MenuCtrl($scope, $rootScope){ $rootScope.header = "Menu"; $rootScope.back = {url:'#/', text:'Back'}; } function ItemsCtrl($scope, $rootScope){ $rootScope.header = "Items"; $rootScope.back = {url:'#/', text:'Back'}; } 

Como você pode ver nos meus controllers, eu codifiquei o URL do botão de retorno e o texto (na verdade, não preciso do texto como uma imagem). Dessa forma, encontrei o botão Voltar navegando incorretamente em alguns casos. Não consigo usar history.back() porque meu botão Voltar é alterado para um link de menu na visualização inicial.

Então, minha pergunta é como obter o caminho de rota anterior em controladores ou é melhor maneira de conseguir isso?

Eu criei uma demonstração de Plunker do meu problema. Por favor, verifique isso.

Essa alternativa também fornece uma function de retorno.

O modelo:

 Back 

O módulo:

 myModule.run(function ($rootScope, $location) { var history = []; $rootScope.$on('$routeChangeSuccess', function() { history.push($location.$$path); }); $rootScope.back = function () { var prevUrl = history.length > 1 ? history.splice(-2)[0] : "/"; $location.path(prevUrl); }; }); 

Use os events $ locationChangeStart ou $ locationChangeSuccess , 3º parâmetro:

 $scope.$on('$locationChangeStart',function(evt, absNewUrl, absOldUrl) { console.log('start', evt, absNewUrl, absOldUrl); }); $scope.$on('$locationChangeSuccess',function(evt, absNewUrl, absOldUrl) { console.log('success', evt, absNewUrl, absOldUrl); }); 

No seu html:

 Go Back 

No seu controlador principal:

 $scope.go_back = function() { $window.history.back(); }; 

Quando o usuário clica no link Go Back, a function do controlador é chamada e volta para a rota anterior.

@andresh Para mim locationChangeSuccess funcionou em vez de routeChangeSuccess.

 //Go back to the previous stage with this back() call var history = []; $rootScope.$on('$locationChangeSuccess', function() { history.push($location.$$path); }); $rootScope.back = function () { var prevUrl = history.length > 1 ? history.splice(-2)[0] : "/"; $location.path(prevUrl); history = []; //Delete history array after going back }; 

É assim que eu atualmente armazeno uma referência ao caminho anterior no $rootScope :

 run(['$rootScope', function($rootScope) { $rootScope.$on('$locationChangeStart', function() { $rootScope.previousPage = location.pathname; }); }]); 

Você precisará acoplar o listener de events ao $ rootScope em Angular 1.x, mas provavelmente você deve testar seu código um pouco ao não armazenar o valor do local anterior em $ rootScope. Um lugar melhor para armazenar o valor seria um serviço:

 var app = angular.module('myApp', []) .service('locationHistoryService', function(){ return { previousLocation: null, store: function(location){ this.previousLocation = location; }, get: function(){ return this.previousLocation; } }) .run(['$rootScope', 'locationHistoryService', function($location, locationHistoryService){ $rootScope.$on('$locationChangeSuccess', function(e, newLocation, oldLocation){ locationHistoryService.store(oldLocation); }); }]); 

Apenas para documentar:

O argumento de retorno de chamada previousRoute está tendo uma propriedade chamada $route que é muito semelhante ao serviço $route . Infelizmente argumento currentRoute , não está tendo muita informação sobre a rota atual.

Para superar isso eu tentei algo assim.

 $routeProvider. when('/', { controller:..., templateUrl:'...', routeName:"Home" }). when('/menu', { controller:..., templateUrl:'...', routeName:"Site Menu" }) 

Observe que na configuração de rotas acima, uma propriedade personalizada chamada routeName é adicionada.

 app.run(function($rootScope, $route){ //Bind the `$routeChangeSuccess` event on the rootScope, so that we dont need to //bind in induvidual controllers. $rootScope.$on('$routeChangeSuccess', function(currentRoute, previousRoute) { //This will give the custom property that we have defined while configuring the routes. console.log($route.current.routeName) }) }) 

modificação para o código acima:

 $scope.$on('$locationChangeStart',function(evt, absNewUrl, absOldUrl) { console.log('prev path: ' + absOldUrl.$$route.originalPath); });