Reputation: 2312
In ie8 if elements don't 'repaint' with the associated css when you change the classname, how can you force the browser to refresh and not kill ie8 performance?
This post (How can I force WebKit to redraw/repaint to propagate style changes?) suggested calling offsetHeight which forces a repaint.
This post (http://www.tek-tips.com/viewthread.cfm?qid=1688809) had a comment that suggested adding and removing a class from body element.
Both of these approaches killed ie8 performance and the first had side-effects on my layout.
What's the best approach?
Upvotes: 20
Views: 16248
Reputation: 405
I had a lot of difficulty and tried everything to no avail...until I tried this for IE8
function toggleCheck(name) {
el = document.getElementById(name);
if( hasClass(el, 'checked') ) {
el.className = el.className.replace(/checked/,'unchecked');
} else if( hasClass(el, 'unchecked') ) {
el.className = el.className.replace(/unchecked/,'checked');
}
document.body.className = document.body.className;
}
function hasClass(element, cls) {
return (' ' + element.className + ' ').indexOf(' ' + cls + ' ') > -1;
}
And now my CSS changes for my checkboxes work beautifully for IE8, Chrome, and Firefox!
Upvotes: 0
Reputation: 4521
Ridiculously, this works:
function ie8Repaint(element) {
element.html(element.html().replace('>', '>'));
}
Nothing actually changes in the DOM so it won't affect any other browsers.
Upvotes: 6
Reputation: 31345
This expands on the other answers here. You need to both add a new class (Doug's answer) and ensure the class has a different content value (Adam's answer). Changing the class alone may not be enough. The content change is needed to force IE8 to repaint. Here is a related blog post.
Here is the JQuery to change add the new class:
$(".my-css-class").addClass("my-css-class2");
Here is CSS with the 2nd class having a slightly different content value:
.my-css-class:before {content: "\e014";}
.my-css-class2:before {content: "\e014 ";}
Upvotes: 1
Reputation: 55623
The correct answer to this question is that you need to actually change the content
rule.
.black-element:before { content:"Hey!"; color: #000;}
.red-element:before { content:"Hey! "; color: #f00;}
Notice the extra space I added after Hey!
on .red-element
Upvotes: 9
Reputation: 2841
Fire a move or resize event on it.
var ie8 = whateverYouUseToDetectIE();
var element = document.getElementById("my-element");
element.className += " new-class";
if (ie8) {
element.fireEvent("resize");
}
Upvotes: 2
Reputation: 2312
The solution I came up with for my ie8 issue was to add/remove a class on a near parent of the element i'm changing. Since I'm using modernizer, I check for ie8 and then do this add/remove dance to get the new css to paint.
$uicontext.addClass('new-ui-look');
if ($('html').is('.ie8')) {
// IE8: ui does not repaint when css class changes
$uicontext.parents('li').addClass('z').removeClass('z');
}
Upvotes: 24