AngularJS $location not updated properly when using $routeProvider
-
20-12-2019 - |
Question
I have an Angular JS application with a defaultController
which controls the header of the app. Then I have some other controllers one for each view. The views are loaded in the <main>
. I load the views using the $routeProvider
with this code:
myapp.config(['$routeProvider',
function($routeProvider) {
$routeProvider.
when('/login', {
templateUrl: 'templates/login.html',
controller: 'loginController'
}).
when('/dashboard', {
templateUrl: 'templates/dashboard.html',
controller: 'dashboardController'
}).
...
I am trying to display a LOGOUT button inside the header when the loaded view is the dashboard and hide it if the loaded view is the login view. In order to do that I have on the defaultController
the $location
object and I properly add and remove classes from the LOGOUT button with ng-class
.
There is only one problem: $location gives me the correct path the first time I load the page, but after I change the view (changed by the $routeProvider
) that variable is not updated anymore, so when I am actually on /#/dashboard
, the $location.url
is still on /login
. Here the controller code:
controllers.controller('defaultController', ['$scope', 'ipCookie', '$location', function($scope, ipCookie, $location) {
$scope.url = $location.url();
...
I also tried with $window.location.hash
with the same result.
Any idea?
EDIT: after the accepted answer this is what I ve added on the defaultController
in order to make it work
$scope.$on("$locationChangeSuccess", function() {
$scope.url = $location.url();
});
Solution
The location is probably updated in the service after your default controller is loaded.
You can either inject the $location
service into the scope and make decisions in your template based on it (then it will automatically be watched and re-evaluated) or you could listen for the $locationChangeSuccess
event.
When injecting, you can simply $scope.location = $location
and then use something like <a ng-hide="location.path() != '/something'">
.
$location
broadcasts the $locationChangeSuccess
on the root scope, so you should be able to listen for it on whichever scope you have available: $scope.$on( "$locationChangeSuccess", function() { /* do something */ } );