Reputation: 687
I've built an app with angularjs and created menu directives which get applied based on the view being loaded.
This is the structure of my menu directives:
angular.module('myApp')
.directive('ogSection1Nav', function() {
return {
restrict: 'E',
replace: true,
templateUrl: '../scripts/directives/section1_nav.html',
controller: function($scope, $location) {
$scope.getClass = function(path) {
var cur_path = $location.path().substr(0, path.length);
if (cur_path === path) {
if($location.path().substr(0).length > 1 && path.length === 1 )
return "";
else
return "currentNav";
} else {
return "";
}
}
}
};
});
Template
<section class="adminMenu">
<nav class="side-nav">
<ul>
<li ng-class="getClass('/section1_summary')"><a href="#/section1_summary"><img title="Summary" src="images/summary.svg" title="Summary" height="25" /><span class="navText">Summary</span></a></li>
<li ng-class="getClass('/section1_spot_list')"><a href="#/section1_spot_list"><img title="Spot List" src="images/postList.svg" title="" height="25" /><span class="navText">Spot List</span></a></li>
<li ng-class="getClass('/section1_volume')"><a href="#/section1_volume"><img title="Volume" src="images/volumeHour.svg" title="" height="25" /><span class="navText">Volume</span></a></li>
<li ng-class="getClass('/section1_location')"><a href="#/section1_location"><img title="Location" src="images/geography.svg" title="" height="25" /><span class="navText">Location</span></a></li>
<li ng-class="getClass('/section1_media_type')"><a href="#/section1_media_type"><img title="Media Type" src="images/mediaType.svg" title="" height="25" /><span class="navText">Media Type</span></a></li>
</ul>
</nav>
</section>
The getClass function checks the current location and compares it to the path as defined in ng-class="getClass('/section1_volume')" on the li elements and attaches the currentNav class to the current page.
Now I have a whole bunch of these menu directives and don't want to always duplicate the same function in every directive so I set up a service as follows:
angular.module('myApp')
.service('MenuState', function($location) {
this.getClass = function(path) {
var cur_path = $location.path().substr(0, path.length);
if (cur_path === path) {
if($location.path().substr(0).length > 1 && path.length === 1 )
return "";
else
return "currentNav";
} else {
return "";
}
};
});
I then call the getClass function in my directives as follows:
angular.module('portalDashboardApp')
.directive('ogAdvertisingMediatracNav', function() {
return {
restrict: 'E',
replace: true,
templateUrl: '../scripts/directives/advertising_mediatrac_nav.html',
controller: function($scope, MenuState) {
$scope.getClass = MenuState.getClass();
}
};
});
However I get the following error: TypeError: Cannot read property 'length' of undefined
I take it this is because the path variable is not being passed to my service but I am unsure of how to get this service to pull in my path by going through the various ng-class="getClass('/path_name')"> sections of my menu templates
Upvotes: 0
Views: 94
Reputation: 1051
@appdJava has proposed a good answer. Alternately, you could also do the following (need not call the getClass of MenuState, so remove parenthesis):
angular.module('portalDashboardApp')
.directive('ogAdvertisingMediatracNav', function() {
return {
restrict: 'E',
replace: true,
templateUrl: '../scripts/directives/advertising_mediatrac_nav.html',
controller: function($scope, MenuState) {
$scope.getClass = MenuState.getClass;
}
}
};
});
Upvotes: 1
Reputation: 1519
This might work for you by delegating the call as:
angular.module('portalDashboardApp')
.directive('ogAdvertisingMediatracNav', function() {
return {
restrict: 'E',
replace: true,
templateUrl: '../scripts/directives/advertising_mediatrac_nav.html',
controller: function($scope, MenuState) {
$scope.getClass = function(path) {
return MenuState.getClass(path);
}
}
};
});
Upvotes: 2
Reputation: 2727
I do think the problem is in your service:
this.getClass = function(path) {
var cur_path = $location.path().substr(0, path.length);
if (cur_path === path) {
if($location.path().substr(0).length > 1 && path.length === 1 )
return "";
else
return "currentNav";
} else {
return "";
}
};
Your function getClass
needs a variable 'path' and you don't apply this variable in your function call $scope.getClass = MenuState.getClass();
Upvotes: 0