Webkitanimation将垃圾像素留在屏幕上

以下代码在屏幕上放置一个白色框。 如果你在iPad上运行它(你也可以调整像素以在iPhone上运行),当你触摸盒子的时候,它会从屏幕上滑下来,沿着它的底边留下一些白色像素。

<!DOCTYPE HTML> <html> <head> <meta http-equiv="content-type" content="text/html; charset=utf-8" /> <meta name="viewport" content="width=device-height, user-scalable=no, maximum-scale=1, minimum-scale=1" /> <title>Line Bug Demo</title> <style> body { background: black; } .panel { background: white; position: absolute; z-index: 2; width: 1000px; height: 500px; top: 34px; left: 12px; -webkit-border-radius: 20px; -webkit-transition: left 0.333s ease-in-out; } .panel.hide { left: -1000px; } </style> </head> <body> <div class="panel" onclick="this.setAttribute('class', 'panel hide')"></div> </body> </html> 

获取bug的关键是使用边框半径,并进行animation。 如果你只是从屏幕上popup它,没有踪迹。 如果没有边界半径,没有踪迹。

以下是我迄今发现的解决方法:

 .panel.hide { -webkit-border-radius: 0; } 

丑陋的,对于我的应用程序来说并不实际,因为我将面板的内部和外部都设置为animation,并且在屏幕上时我真的很想要圆angular。

另一个:

 .panel { -webkit-transform: translateZ(0); } 

这将面板放入硬件pipe道中,正确地进行合成。 虽然这与这个简单的演示一起工作,但是在真实的web应用程序中使用硬件pipe道会导致内存不足的错误。 (剧烈,巨大,直接的变化)

任何其他的想法,我可以摆脱这个痕迹?

解决scheme

 box-shadow: 0 0 1px rgba(0, 0, 0, 0.05); 

如果您觉得太明显,可以使用箱子的背景颜色作为box-shadow颜色。

或者,根据Chrome上类似问题的回答 (感谢Sebastian在评论中的提示),您可能需要尝试:

 outline: 1px solid transparent; 

这是怎么回事?

我在其他地方给出了一个相当长的解释 ,但这里是简短的版本。 出于性能考虑,WebKit只会重新绘制它认为可能已经改变的那部分页面。 但是,iOS(pre-7)Safari实现的边框半径除了计算出的盒子尺寸之外还有几个像素。 由于WebKit不知道这些像素,因此不会重绘; 相反,他们被留下,并build立在每个animation帧。

通常的解决scheme,正如我在其他答案中所build议的那样,是强制这个元素需要硬件加速,以便将其绘制为单独的图层。 然而,太多的小元素或一些大的元素将导致大量的图块被推到GPU上,这会带来明显的性能影响。

使用box-shadow可以更直接地解决问题:它扩展了盒子的重绘尺寸,迫使WebKit重新绘制额外的像素。 移动浏览器中已知的box-shadow性能影响与所使用的模糊半径直接相关,因此一个像素阴影应该具有很小的影响。

我会做什么:

  • -webkit-backface-visibility: hidden
  • -webkit-transform:translateX(left value here)animation-webkit-transform:translateX(left value here) //或者translate-3d(x,y,z)左边应该是禁用的 [*]

请务必检查在父级上启用硬件加速是否有所作为。

也有简单的方法来强制重绘 – 让我知道你是否也需要关于他们的信息。

依靠3d转换是一种黑客攻击,应谨慎使用,这是GPU和内存之间的折衷,在某些情况下,它可能会导致animation混乱或内存问题(思考 – 移动,迫使GPU在大面积加速)。

CSS will-change属性将是一个正确的地方来标记可以提前优化的属性。