How to re-render a directive template and link function?
-
21-12-2019 - |
Question
I am creating a navigation "tree" that basically allows you to navigate to parent views like so
Home > Planner > Contacts > john.smith@hotmail.com
This list is just a normal <ul>
that should get changed each time the view is changed and allow the user to click on any of the above links to navigate. I am using ui-router
's $stateChangeStart
event to build up my list of links, the problem is that my directive does not "re-build" this list every time the page change.
Is there a way to force the directive to re-render every time I change my state?
TreeNav directive
app.directive('treeNav', ['$rootScope', function ($rootScope) {
return {
replace: true,
restrict: 'E',
template: '<ul>\
<li ng-repeat="item in treeNavs">\
<a ui-sref="{{ item.state }}">{{ item.name }}</a>\
<span> > </span>\
</li>\
</ul>',
link: function (scope, elem, attrs) {
scope.treeNavs = $rootScope.treeNav.reverse();
scope.$watch('$rootScope.treeNav', function (newVal, oldVal) {
scope.treeNavs = newVal.reverse();
});
}
}
}]);
Solution
I believe you aren't setting up your $watch
statement correctly.
You should also be careful with your use of .reverse
. reverse()
reverses the entries in an array in place, which is probably not what you want to do, since it would modify the array on the $rootScope
.
You can use splice()
to create a new copy and then reverse that:
scope.treeNavs = $rootScope.treeNavs.splice().reverse();
$rootScope.$watch('treeNav', function(newVal) {
scope.treeNavs = newVal.splice().reverse();
});