Reputation: 755
I'm monitoring a CSS style and updating a variable in the scope that's based on that CSS style's value. It works the first time around but when the browser is resized, the scope gets updated but ng-style does not update with the new scope parameter.
JS:
.directive('monitorStyle', function() {
return {
link: function(scope, element, attrs) {
scope[attrs.updateVariable] = $(element).css(attrs.monitorStyle);
angular.element(window).on('resize', function() {
scope[attrs.updateVariable] = $(element).css(attrs.monitorStyle);
});
}
}
})
HTML:
<p class="text" monitor-style="font-size" update-variable="textHeight">Press "<img class="mini up" src="img/select-arrow.png" src="Up" ng-style="{'height': textHeight}">
I'm trying to do this outside of the controller because that's what people recommend. Why is ng-style not updating when the scope gets updated?
Upvotes: 1
Views: 3954
Reputation: 755
Yo, I made this sick solution.
So if you want to watch styles (even an array of them on a particular element) and then send their values to the $scope you can use this JS:
.directive('monitorStyle', function($timeout) {
return {
link: function(scope, element, attrs) {
function addToScope() {
var updateVariable = attrs.updateVariable.split(',');
var monitorStyle = attrs.monitorStyle.split(',');
for (var i = 0; i < updateVariable.length; i++) {
scope[updateVariable[i]] = $(element).css(monitorStyle[i]);
}
}
addToScope();
angular.element(window).on('resize', function() {
addToScope();
scope.$apply();
});
}
}
})
And apply it like this:
<h2 monitor-style="font-size,line-height" update-variable="headerHeight,headerLineHeight">
This will update the $scope on initialization and on window resizes. You can of course modify it to your own purpose.
Each time the $scope changes you can update other styles like this:
<div ng-style="{'height': headerHeight, 'line-height': headerLineHeight}">
Upvotes: 0
Reputation: 4093
The window event isn't an angular event, so angular don't know he have to update the model/scope. You have to add scope.$apply() to tell angular to refresh it :
angular.element(window).on('resize', function() {
scope[attrs.updateVariable] = $(element).css(attrs.monitorStyle);
scope.$apply();
});
Data bindig only works when your model is updated with angular event like $http, $timeout, ng-click, ...
A great article about it : http://jimhoskins.com/2012/12/17/angularjs-and-apply.html
Upvotes: 4