在 Chrome/Mac 上强制 DOM 重绘/刷新

新手上路,请多包涵

每隔一段时间,Chrome 就会错误地或根本不渲染完全有效的 HTML/CSS。通过 DOM 检查器进行挖掘通常足以让它意识到其方式的错误并正确重绘,因此可以证明标记是好的。在我正在处理的项目中,这种情况经常发生(并且可以预见),我已经将代码放在适当的位置以在某些情况下强制重绘。

这适用于大多数浏览器/操作系统组合:

    el.style.cssText += ';-webkit-transform:rotateZ(0deg)'
    el.offsetHeight
    el.style.cssText += ';-webkit-transform:none'

例如,调整一些未使用的 CSS 属性,然后询问一些强制重绘的信息,然后取消调整该属性。不幸的是,Mac 版 Chrome 背后的聪明团队似乎找到了一种无需重绘即可获得 offsetHeight 的方法。从而杀死一个其他有用的黑客。

到目前为止,我想出的在 Chrome/Mac 上获得相同效果的最好方法是这个丑陋的东西:

    $(el).css("border", "solid 1px transparent");
    setTimeout(function()
    {
        $(el).css("border", "solid 0px transparent");
    }, 1000);

例如,实际上强制元素跳跃一点,然后冷却一秒钟并将其跳回。更糟糕的是,如果你将超时时间降低到 500 毫秒以下(到它不太明显的地方),它通常不会产生预期的效果,因为浏览器在恢复到原始状态之前不会进行重绘。

有人愿意提供适用于 Chrome/Mac 的更好版本的重绘/刷新黑客(最好基于上面的第一个示例)吗?

原文由 Jason Kester 发布,翻译遵循 CC BY-SA 4.0 许可协议

阅读 1.4k
1 个回答

不确定你到底想达到什么目的,但这是我过去使用过的一种成功强制浏览器重绘的方法,也许它对你有用。

 // in jquery
$('#parentOfElementToBeRedrawn').hide().show(0);

// in plain js
document.getElementById('parentOfElementToBeRedrawn').style.display = 'none';
document.getElementById('parentOfElementToBeRedrawn').style.display = 'block';

如果这个简单的重绘不起作用,您可以试试这个。它将一个空文本节点插入到保证重绘的元素中。

 var forceRedraw = function(element){

    if (!element) { return; }

    var n = document.createTextNode(' ');
    var disp = element.style.display;  // don't worry about previous display style

    element.appendChild(n);
    element.style.display = 'none';

    setTimeout(function(){
        element.style.display = disp;
        n.parentNode.removeChild(n);
    },20); // you can play with this timeout to make it as short as possible
}

编辑:作为对Šime Vidas 的回应,我们在这里实现的是强制回流。您可以从大师本人那里了解更多信息 http://paulirish.com/2011/dom-html5-css3-performance/

原文由 Juank 发布,翻译遵循 CC BY-SA 3.0 许可协议

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题