这是关于图像加载的chrome中的错误吗?

时间:2017-10-18 15:10:21

标签: javascript google-chrome debugging web promise

我的目标是在html中使用style['background-image']加载一些图像,但是当我将代码放入Ajax时,出现了问题。
如果我使用 async ajax ,则图片加载顺序为反向;当我使用同步ajax 时,图片加载顺序正常。
特别是它发生在chrome中。在firefox中是正常的。

html结构非常简单,就像这样

<div class="container">
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
</div>

当我使用sync ajax时,JS代码就像这样

function Ajax(url) {
        let xhr = new XMLHttpRequest()
        xhr.onreadystatechange = () => {
            if (xhr.readyState === 4 && xhr.status === 200) {
                let slides = Array.from(document.querySelectorAll('.test'))
                for (let i = 1; i < 20; i++) {
                    slides[i].style['background-image'] = `url(/data/gallery/1125425/content/${i})`
                }
            }
        }
        xhr.open('get', url, false)
        xhr.setRequestHeader('Content-type', 'application/x-www-form-urlencoded')
        xhr.send()
    }
    Ajax('https://api.github.com')

结果就是enter image description here

我们可以发现它是正常的,就像我们认为的那样

然后,当将异步从false更改为true 时,结果就是这样。

为了显示网址并不重要,我使用github的公共API。 现在我们在网络面板中看到了结果 enter image description here

我们可以看到最后一张图片被加载,与我们第一次尝试相比只是一个相反的顺序。

事实上,这种现象在firefox中不会发生,所以我想这是Chrome中的一个错误?

我已将我的代码放入Codepen 更新: 我认为是由Promise引起的,之后我注意到它不是。所以我改变了标题

2 个答案:

答案 0 :(得分:2)

调试你的codepen,我发现任何类型的范围包装都会颠倒顺序。这一个:

  let slides = Array.from(document.querySelectorAll('.test'))
  for (let i = 0; i < slides.length; i++) {
   (() => slides[i].style['background-image'] = `url(/data/gallery/1125425/content/${i})`)();
  }

而且:

(() => {
  let slides = Array.from(document.querySelectorAll('.test'))
  for (let i = 0; i < slides.length; i++) {
   slides[i].style['background-image'] = `url(/data/gallery/1125425/content/${i})`
  }
})();

所以Promise与毫无关系,我想。

但我也会说正向顺序(在我的情况下)不是严格的前向顺序,它是错误的:0, 1, 2, 3, 4, 5, 10, 8, 7, 19, etc并且这个序列在会话期间不会不时改变。

答案 1 :(得分:0)

不,这本身并不是一个错误,即使仍然很奇怪。

这是因为浏览器不会在此for循环期间重新计算元素的样式,而是仅在js执行结束并且所有DOM更改完成之后。

接下来的步骤(样式重新计算 - >加载新资源)取决于实现。

如果你想要一个固定的订单(即使我不明白你为什么会这样做),你可以在每次循环迭代时强制重排:

(() => {
  let slides = Array.from(document.querySelectorAll('.test'))
  for (let i = 0; i < slides.length; i++) {
   slides[i].style['background-image'] = `url(/${i})`
   document.body.offsetWidth; // force reflow
  }
})();
console.log("check the 'Network Panel' of your dev-tools");
<div class="container">
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
    <div class="test"></div>
</div>