【问题标题】:JavaScript: how to force Image() not to use the browser cache?JavaScript:如何强制 Image() 不使用浏览器缓存?
【发布时间】:2010-09-14 23:33:18
【问题描述】:

如果我在浏览器中手动加载 nextimg URL,每次重新加载时它都会提供一张新图片。但是这段代码在draw() 的每次迭代中都显示了相同的图像。

如何强制 myimg 不被缓存?

<html>
  <head>
    <script type="text/javascript">
      function draw(){
        var canvas = document.getElementById('canv');
        var ctx = canvas.getContext('2d');
        var rx;
        var ry;
        var i;

        myimg = new Image();
        myimg.src = 'http://ohm:8080/cgi-bin/nextimg'

        rx=Math.floor(Math.random()*100)*10
        ry=Math.floor(Math.random()*100)*10
        ctx.drawImage(myimg,rx,ry);
        window.setTimeout('draw()',0);
      }
    </script>
  </head>
  <body onload="draw();">
    <canvas id="canv" width="1024" height="1024"></canvas>
  </body>
</html>

【问题讨论】:

    标签: javascript image caching


    【解决方案1】:

    这里实际上有 两个 缓存需要您绕过:一个是常规 HTTP 缓存,您可以通过在图像上使用正确的 HTTP 标头来避免。但是您还必须阻止浏览器重新使用图像的内存副本;如果它决定它可以做到这一点,它甚至永远不会到达查询其缓存的地步,因此 HTTP 标头将无济于事。

    为防止这种情况,您可以使用更改查询字符串或更改片段标识符。

    查看我的帖子here了解更多详情。

    【讨论】:

      【解决方案2】:

      最简单的方法是在末尾添加一个不断变化的查询字符串:

      var url = 'http://.../?' + escape(new Date())
      

      有些人更喜欢使用Math.random() 而不是escape(new Date())。但正确的方法可能是更改 Web 服务器发送的标头以禁止缓存。

      【讨论】:

      • 丹,有点老帖子,但我肯定欠你一杯啤酒。不完全是我的情况,但给了我很好的主意。谢谢!
      • 我不得不在没有结尾斜杠的情况下使用它:var url = 'http;//.../something.png'+'?'+Math.random(),但它工作正常! +1 标题咨询 :)
      • Cache-Control: no-cache 有帮助吗?虽然我很欣赏这个漂亮的解决方法,但我不禁想知道这是否是我们现在能做的最好的事情。当时我们在月球着陆器代码中使用了什么样的黑客?
      • escape 已弃用,请改用encodeURI。见w3schools.com/jsref/jsref_escape.asp
      【解决方案3】:

      这实际上听起来像是浏览器中的一个错误——如果它在 Safari 中,您可以在 http://bugs.webkit.org 或在 Firefox 中提交 https://bugzilla.mozilla.org/。为什么我说潜在的浏览器错误?因为浏览器意识到它不应该在重新加载时进行缓存,但是当您以编程方式请求它时,它确实会为您提供图像的缓存副本。

      也就是说你确定你真的在画什么吗? Canvas.drawImage API 不会等待图像加载,并且如果您尝试使用它时图像尚未完全加载,则指定不绘制。

      更好的做法是:

          var myimg = new Image();
          myimg.onload = function() {
              var rx=Math.floor(Math.random()*100)*10
              var ry=Math.floor(Math.random()*100)*10
              ctx.drawImage(myimg,rx,ry);
              window.setTimeout(draw,0);
          }
          myimg.src = 'http://ohm:8080/cgi-bin/nextimg'
      

      (您也可以将draw 作为参数传递给setTimeout,而不是使用字符串,这样可以省去一遍又一遍地重新解析和编译相同的字符串。)

      【讨论】:

        【解决方案4】:

        您无法阻止它在 Javascript 中完全缓存图像。但是,你可以玩弄图像的 src/address 来强制它重新缓存:

        [Image].src = 'image.png?' + (new Date()).getTime();
        

        您可能可以采用任何 Ajax 缓存解决方案并在此处应用它。

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 2021-06-18
          • 1970-01-01
          • 1970-01-01
          • 2011-10-11
          • 2010-09-12
          • 1970-01-01
          相关资源
          最近更新 更多