以下是我在Safari中遇到的错误的最小模型。
预期的行为:代码应该显示占位符,而另一个图像会加载,然后在删除占位符时淡入该图像。
placeholder -> fading in loaded image
实际行为 在Chrome和Mozilla中按预期工作,但 在Safari 中失败,从而产生以下效果:
placeholder -> white screen -> loaded image
有人可以帮我弄清楚为什么会在Safari中发生这种情况吗? (尝试在chrome或mozilla vs safari中以下示例运行以查找自己。)
const image = new Image();
image.onload = () => {
document.getElementById('placeholder').remove();
const el = document.createElement('img');
el.setAttribute('src', 'http://deelay.me/1000/https://cdn.pixabay.com/photo/2014/06/03/19/38/board-361516_1280.jpg');
el.setAttribute('width', '150');
el.setAttribute('height', '150');
el.style = `
animation-name: testAnimation;
animation-duration: 0.3s;
animation-iteration-count: 1;
animation-timing-function: ease-in;
background: red;
`;
document.body.appendChild(el);
}
image.src = 'http://deelay.me/1000/https://cdn.pixabay.com/photo/2014/06/03/19/38/board-361516_1280.jpg';
#placeholder {
background: #eee;
}
@-webkit-keyframes testAnimation {
0% {
opacity: 0.25;
}
50% {
opacity: 0.5;
}
100% {
opacity: 1;
}
}
<img id="placeholder" src="data:image/svg+xml;charset=utf-8,%3Csvg xmlns%3D'http%3A%2F%2Fwww.w3.org%2F2000%2Fsvg' width%3D'200' height%3D'300' viewBox%3D'0 0 200 300'%2F%3E" width="150" height="150">
(适用
另一个奇怪的行为是,如果animation-duration
增加到3-4秒左右,那么图像会淡入,但白屏仍然存在,即
placeholder -> white screen -> fading in loaded image
)
在使用img的背景颜色后,似乎在Safari中动画开始生效约1秒,然后图像才开始渲染到屏幕上。
在Chrome和Mozilla中,动画似乎与图像完全同步。
运行更新的代码以便自己查看
(它似乎也只发生在<img>
,我用其他一些元素(仍然在image.onload中)测试了它们,它们按预期工作。)
答案 0 :(得分:1)
这是通过在 图像元素 上添加另一个init(from:)
事件而不是在显式 图像对象>上添加的em> 并将onload
侦听器置于其中。
这似乎表明,在Safari中,只要image.onload
被添加到DOM中,动画和样式就会被应用 - 在它完全加载之前(它的<img>
事件被调用。)
这可以通过给onload
一个背景颜色进行测试,并在元素添加到DOM后立即看到它与动画一起显示,并且看到它需要额外的秒,直到图像本身变得可见
只需给<img>
一个背景色
(Safari中的错误? 我的Safari版本:版本11.0.2(13604.4.7.1.3))
编辑:实际上这个问题似乎是由缓存引起的,Safari似乎没有缓存预加载的代理图像,而其他浏览器会缓存它。当Safari渲染到屏幕时,Safari似乎会触发另一个请求 - 因此在查看实际图像之前样式是可见的,因为图像仍然被下载。
编辑2:经过进一步调查,似乎Safari实际上是这三种浏览器中唯一一种表现符合预期的浏览器 - 这是因为图像的HTTP响应包含<img>
标头明确指示浏览器不缓存图像。
Cache-Control: no-cache, must-revalidate
&#13;
const image = new Image();
const el = document.createElement('img');
el.setAttribute('src', 'http://deelay.me/500/https://cdn.pixabay.com/photo/2014/06/03/19/38/board-361516_1280.jpg');
el.setAttribute('width', '150');
el.setAttribute('height', '150');
el.style = `
animation-name: testAnimation;
animation-duration: 1s;
animation-iteration-count: 1;
animation-timing-function: ease-in;
background-color: red;
`;
el.onload = () => {
image.onload = () => {
document.getElementById('placeholder').remove();
document.body.appendChild(el);
}
}
image.src = 'http://deelay.me/500/https://cdn.pixabay.com/photo/2014/06/03/19/38/board-361516_1280.jpg';
&#13;
#placeholder {
background: #eee;
}
@-webkit-keyframes testAnimation {
0% {
opacity: 0.25;
}
50% {
opacity: 0.5;
}
100% {
opacity: 1;
}
}
&#13;
答案 1 :(得分:0)
这似乎与您使用的特定服务器/映像有关。我尝试仅更改图像URL(仅限于wikimedia.org上的内容,仅用于测试目的),动画在Safari 11.0.2(13604.4.7.1.6)中按预期开始工作。
预加载图像可能会有所帮助......甚至更好(假设您拥有正确的使用权限,所有这一切),您可以尝试将图像复制到Web服务器,以便可以在本地加载。从本质上讲,您只是通过Safari从远程服务器加载图像时完成运行动画的事实。您也可以尝试使用window.onload而不是image.onload来强制所有外部资源在运行之前加载。