奇怪的 IE,Javascript 仅适用于开发模式 (F12)

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/31107364/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-10-28 13:17:27  来源:igfitidea点击:

Weird IE, Javascript only works in development mode (F12)

javascriptjqueryhtmlinternet-explorervideo

提问by user534498

Basically, I have two tags, one is hidden and one is shown.

基本上,我有两个标签,一个是隐藏的,一个是显示的。

The hidden one will load video at background, and when the front one is finished, I will swap the two by hiding the shown one.

隐藏的将在后台加载视频,当前面的完成后,我将通过隐藏显示的来交换两者。

I will also have a list of playable videos on server side, I will use ajax to get the list and decide which one to load next.

我还将在服务器端提供一个可播放视频列表,我将使用 ajax 获取列表并决定接下来加载哪个。

Anyway it is hard for you to try this because you need to have a video server, and I found it's hard to chop the code, so I will just show you the whole source code (with some comments), hope you can understand.

反正你很难尝试,因为你需要有一个视频服务器,而且我发现很难砍代码,所以我只给你展示完整的源代码(有一些注释),希望你能理解。

I used jquery and video.js. The source code is as follows,

我使用了 jquery 和 video.js。源代码如下,

HTML:

HTML:

<div class="container" id="video-container-1">
</div>
<div class="container" id="video-container-2">
</div>

Javascript:

Javascript:

//I am making a live video by chopping the video into MP4 files of 800ms each
//The play rate has to be adjustable or the local browser and live server will not sync
var play_rate = { 1.0:800, 1.01:790, 1.02:785, 1.03:777, 1.04:770, 1.05:762, 1.06:755, 1.07:748,
  1.08:741, 1.09:734, 1.1:727 };
var min_rate=1.0;
var max_rate=1.1;
var base_rate = 1.03;
var current_rate = base_rate;
var timer_value = play_rate[current_rate];

var key_to_play;
var timer_id;
var newest_key;
var video_server_address = "192.168.100.1:20001";


var current_play = 1;
var container = new Array();
var player = new Array;

function video_html(container_id, id) {
  return '<video id="video-js-' + container_id + '" class="video-js vjs-default-skin" ' +
  ' preload="auto" width="960" height="540"  crossorigin="anonymous" ' +
  'data-setup=\'{"example_option":true}\'>' +
  '\t<source src="http://' + video_server_address +'/live/' + id + '.mp4" type="video/mp4" /> \n' +
  '\t\t<track id="video-vtt" kind="subtitle" label="english" srclang="en" src="http://' + video_server_address + '/live/' + id + '.vtt" default></track>\n ' +
  '\t\t<p class="vjs-no-js">To view this video please enable JavaScript, and consider upgrading to a web browser that <a href="http://videojs.com/html5-video-support/" target="_blank">supports HTML5 video</a></p>\n' +
  '</video>';
}
function play_next()
{
  var next_play;
  if (current_play == 1)
    next_play = 2;
  else
    next_play = 1;

  player[next_play - 1].play();
  container[next_play - 1].show();
  container[current_play - 1].hide();
  if (player[current_play - 1])
    player[current_play - 1].dispose();

  key_to_play++;

  //switch current & next
  current_play = next_play;

  timer_id = setTimeout(function() {
    play_next();
  }, timer_value);

  //Assuming get list + load video < 700ms
  $.get("http://" + video_server_address + "/live/list", 
    function(list){
      keys = list["keys"];
      newest_key = keys[keys.length - 1];


      console.log("key_to_play: " + key_to_play + "  newest_key: " + newest_key);

      var next_play;
      if (current_play == 1)
        next_play = 2;
      else
        next_play = 1;
      //-----------------begin-------------------
      //not really useful to you because these are just 
      //to let the video play sync with video server, we can safely 
      //remove these but the video play will out of sync after some time    
      if (key_to_play > newest_key)
      {
        //too fast
        //make it slower?
        if (current_rate > min_rate)
        {
          current_rate = current_rate - 0.01;
          timer_value = play_rate[current_rate];
        }
        else
        {
          //it is already 1.0 (the slowest settings)
          //have to crop on the timer_value
          timer_value = play_rate[current_rate] + 5 * (key_to_play - newest_key);
        }
        //either wait or play again? just play again and test for stability first
        key_to_play = newest_key;
      }
      else if (key_to_play == newest_key || key_to_play == newest_key - 1)
      {
        //the best situation we got
        //don't change anything
      }
      else
      {
        //a little slow
        if (current_rate < max_rate)
        {
          current_rate = current_rate + 0.01;
          timer_value = play_rate[current_rate];
        }
        else
        {
          timer_value = play_rate[current_rate] - 5 * (newest_key - key_to_play);
        }

        //tooo slow, drop 4 * 800ms data
        if (newest_key - key_to_play > 5)
        {
          key_to_play = newest_key - 1;
        }
      }
      //-------------------end------------

      container[next_play - 1].html(video_html(next_play, key_to_play));
      player[next_play - 1] = videojs('video-js-' + next_play, {}, function(){
        // Player (this) is initialized and ready.
        //the following is only to make the browser show subtitle
        //without this, the FF will not show subtitle by default
        $('#video-container-' + next_play + " div.vjs-subtitles-button li.vjs-menu-item").eq(1).trigger('click');
      });
      player[next_play - 1].playbackRate(current_rate);



      console.log(timer_value);
    }
  );



}

$( document ).ready(function() {
  $.get("http://" + video_server_address + "/live/list", function(list){
    keys = list["keys"];
    key_to_play = keys[keys.length - 2];
    newest_key = keys[keys.length - 1];

    container[0] = $("div#video-container-1");
    container[1] = $("div#video-container-2");
    container[0].hide();

    container[1].html(video_html(2, key_to_play));
    player[0] = null;
    player[1] = videojs("video-js-2",{}, function(){
      // Player (this) is initialized and ready.
      console.log($("#video-container-2 div.vjs-subtitles-button li.vjs-menu-item").eq(1).text());
      $("#video-container-2 div.vjs-subtitles-button li.vjs-menu-item").eq(1).trigger('click');
    });
    player[1].playbackRate(current_rate);

    play_next();
  });
});
</script>

This code works good on chrome and FF, however, when trying on IE11, the new videos will not load, it will switch between two videos (say video 1 and 2) every 800ms, and I think it will load the latter ones (3, 4, 5 and so one), but it will not play, it is just keep playing 1 and 2 and 1 and 2.

这段代码在 chrome 和 FF 上运行良好,但是,在 IE11 上尝试时,新视频不会加载,它会每 800 毫秒在两个视频(比如视频 1 和 2)之间切换,我认为它会加载后一个(3 , 4, 5 等等),但它不会播放,它只是继续播放 1 和 2 和 1 和 2。

When I try to debug it, I open IE11 development tools, then when development tools is ready, IE11 will work well.

当我尝试调试它时,我打开IE11开发工具,然后当开发工具准备好时,IE11将运行良好。

As long as I close the development tools, IE11 will suck.

只要我关闭开发工具,IE11 就会很烂。

I am thinking maybe IE11 made some optimization and optimized some of the codes away? How can I check that?

我在想也许IE11做了一些优化并优化了一些代码?我该如何检查?

Thanks.

谢谢。

回答by Equalsk

Taken from the comments on the original question:

摘自对原始问题的评论:

Why does JavaScript only work after opening developer tools in IE once?

为什么 JavaScript 只能在 IE 中打开开发者工具一次后才能工作?

For OP it was the caching of his Ajax request causing the issue. Solved by disabling the cache:

对于 OP,是因为他的 Ajax 请求的缓存导致了这个问题。通过禁用缓存解决:

$.ajax({cache: false, ...})

回答by SMT

As you are using the below code

当您使用以下代码时

console.log("key_to_play: " + key_to_play + "  newest_key: " + newest_key);

Here you should check if the console object exists or not, when you press F12, it automatically creates console object, you should write it like this

这里你应该检查console对象是否存在,当你按F12时,它会自动创建console对象,你应该这样写

if (typeof console == "object") {
    console.log("key_to_play: " + key_to_play + "  newest_key: " + newest_key);
}
else{
    //do nothing`enter code here`
}

回答by Ricardo Vila

This answer is for the same behaviour in IE (caching ajkax calls) but with AngularJS not JQuery. I'll post it here so it can help another one like me.

此答案适用于 IE 中的相同行为(缓存 ajkax 调用),但使用的是 AngularJS 而不是 JQuery。我会把它贴在这里,以便它可以帮助像我这样的另一个人。

We found that IE didn't worked well in some pages unless DevTools (F12) where active for the first time. Finally thanks to this question whe noticed that IE was caching JS GET calls. So, when working with angular, in order to avoid that behaviour you should do this:

我们发现 IE 在某些页面上运行不佳,除非 DevTools (F12) 首次处于活动状态。最后感谢这个问题,他注意到 IE 正在缓存 JS GET 调用。因此,在使用 angular 时,为了避免这种行为,您应该这样做:

$httpProvider.defaults.headers.common['If-Modified-Since'] = '0';