JW Player - 亚马逊网络服务CDN和高级Javascript调试

时间:2015-09-29 12:46:10

标签: javascript amazon-web-services jwplayer amazon-cloudfront jwplayer7

我在下一页中嵌入了自定义的JW Player 7 Pro:http://dev.sharepoint-videos.com/jw-player-self-hosted/

嵌入代码如下:

<!--Course Video, Scripts and Style-->
<div id="visualSPPlayer">Loading the player...</div>
<script type="text/javascript">
  var playerInstance = jwplayer("visualSPPlayer");
  playerInstance.setup({
    file: "http://dbt8c2ssdzlxg.cloudfront.net/Search2013.mp4",
    primary: "HTML5",
    image: "https://assets-jpcust.jwpsrv.com/thumbs/2kOAeo0k-320.jpg?1443200073230",
    width: "100%",
    aspectratio: "16:9",
    tracks: [
      {
        file: "http://dbt8c2ssdzlxg.cloudfront.net/captions/Search/Captions.srt",
        label: "English",
        kind: "captions",
      },
      {
        file: 'http://dbt8c2ssdzlxg.cloudfront.net/chapters/Search/Chapters.vtt',
        kind: 'chapters'
  
      },
      {
        file: "http://dbt8c2ssdzlxg.cloudfront.net/thumbnails/search_thumbnails.vtt",
        kind: "thumbnails"
      }
    ],
    skin: {
      name: "vapor",
      active: "#E16933",
      inactive: "#E16933",
      background: "#333333"
    }
  });
</script>
<script type="application/javascript" src="http://dev.sharepoint-videos.com/wp-content/themes/symplex-child/js/player.js"></script>
<link rel="stylesheet" href="http://dev.sharepoint-videos.com/wp-content/themes/symplex-child/css/player.css" type="text/css" media="screen"/>

player.js文件内容:

jQuery(document).ready(function () {

  jQuery(function ($) {

    var playerInstance = jwplayer();
    var chapters = [];
    var captions = [];
    var toc = [];
    var caption = -1;
    var matches = [];
    var seekArr = [];
    var seekPos = [];
    var seePos;
    var query = "";
    var cycle = -1;

    var transcript = document.getElementById('courseTranscript');
    var search = document.getElementById('courseSearch');
    var match = document.getElementById('courseMatch');

    var caption_file;
    var chapter_file;

    playerInstance.onReady(function () {
      //Self-Hosted
      caption_file = playerInstance.getPlaylist()[0].tracks[0].file;
      chapter_file = playerInstance.getPlaylist()[0].tracks[1].file;

      if (playerInstance.getRenderingMode() == "flash") {
        return;
      }

      tag = document.querySelector('video');
      tag.defaultPlaybackRate = 1.0;
      tag.playbackRate = 1.0;

      playerInstance.addButton("http://dev.sharepoint-videos.com/wp-content/uploads/2015/09/hare.png", "1.5x", function () {
        playerInstance.seek(playerInstance.getPosition());
        tag.playbackRate = 1.5;
      }, "playerHighSpeed");

      playerInstance.addButton("http://dev.sharepoint-videos.com/wp-content/uploads/2015/09/normal.png", "1.0x", function () {
        playerInstance.seek(playerInstance.getPosition());
        tag.playbackRate = 1.0;
      }, "playerNormalSpeed");

      playerInstance.addButton("http://dev.sharepoint-videos.com/wp-content/uploads/2015/09/snail.png", "0.5x", function () {
        playerInstance.seek(playerInstance.getPosition());
        tag.playbackRate = 0.5;
      }, "playerSlowSpeed");
    });

    //Adds Player Focus on Playing
    playerInstance.on('play', function () {
      $('html, body').animate({
        scrollTop: $(".jwplayer").offset().top - 190
      }, 1000);
    });

    playerInstance.onReady(function () {
      $.get(caption_file, function (data) {
        data = data.trim();
        var t = data.split("\n\r\n");

        for (var i = 0; i < t.length; i++) {
          var c = parse(t[i]);
          chapters.push(c);
        }
        loadCaptions();
        loadChapters();
      });
      //
    });

    // Load chapters / captions
    function loadCaptions() {
      $.get(caption_file, function (data) {
        data = data.trim();
        var t = data.split("\n\r\n");
        t.pop();
        var h = "<p>";
        var s = 0;
        for (var i = 0; i < t.length; i++) {
          var c = parse(t[i]);
          
          if (s < chapters.length && c.begin > chapters[s].begin) {
            s++;
          }
          
          h += "<span id='caption" + i + "'>" + c.text + "</span>";
          captions.push(c);
        }
        transcript.innerHTML = h + "</p>";
      });
    };

    function parse(d) {
      var a = d.split("\n");
      //console.log(a[1]);
      var i = a[1].indexOf(' --> ');
      var t = a[2]; //Caption text

      if (a[3]) {
        t += " " + a[3];
      }
      
      t = t.replace(/&/g, '&amp;').replace(/</g, '&lt;').replace(/>/g, '&gt;');
      
      return {
        begin: seconds(a[1].substr(0, i)),
        btext: a[1].substr(3, i - 7),
        end: seconds(a[1].substr(i + 5)),
        text: t
      }
    };

    function seconds(s) {
      var a = s.split(':');
      secs = a[2].substring(0, a[2].indexOf(','));
      var r = Number(secs) + Number(a[a.length - 2]) * 60;

      if (a.length > 2) {
        r += Number(a[a.length - 3]) * 3600;
      }
      
      return r;
    };

    function toc_seconds(s) {
      var a = s.split(':');
      secs = a[2].substring(0, a[2].indexOf('.'));
      var r = Number(secs) + Number(a[a.length - 2]) * 60;
      
      if (a.length > 2) {
        r += Number(a[a.length - 3]) * 3600;
      }
      
      return r;
    };

    function toc_time(s) {
      var a = s.split(':');
      var ms = a[2].split(".");
      var h = a[0];

      if (h != "00") {
        var r = a[0] + ":" + a[1] + ":" + ms[0];
      } else {
        var r = a[1] + ":" + ms[0];
      }

      return r;
    };

    // Highlight current caption and chapter
    playerInstance.onTime(function (e) {
      var p = e.position;
      for (var j = 0; j < captions.length; j++) {
        if (captions[j].begin < p && captions[j].end > p) {
          if (j != caption) {
            var c = document.getElementById('caption' + j);
            if (caption > -1) {
              document.getElementById('caption' + caption).className = "";
            }
            c.className = "current";
            if (query == "") {
              transcript.scrollTop = c.offsetTop - transcript.offsetTop - 40;
            }
            caption = j;
          }
          break;
        }
      }
    });

    // Hook up interactivity
    transcript.addEventListener("click", function (e) {
      if (e.target.id.indexOf("caption") == 0) {
        var i = Number(e.target.id.replace("caption", ""));
        playerInstance.seek(captions[i].begin);
      }
    });
    /**/
    
    search.addEventListener('focus', function (e) {
      setTimeout(function () {
        search.select();
      }, 100);
      resetSearch();
      $("#prevMatchLink").hide();
      $("#nextMatchLink").hide();
    });
    
    search.addEventListener('keydown', function (e) {
      if (e.keyCode == 27) {
        resetSearch();
        $("#prevMatchLink").hide();
        $("#nextMatchLink").hide();
      } else if (e.keyCode == 13) {
        $("#prevMatchLink").show();
        $("#nextMatchLink").show();
        var q = this.value.toLowerCase();
        if (q.length > 0) {
          if (q == query) {
            if (cycle >= matches.length - 1) {
              cycleSearch(0);

            } else {

              cycleSearch(cycle + 1);
            }
          } else {
            resetSearch();
            searchTranscript(q);
          }
        } else {
          resetSearch();
        }
      } else if (e.keyCode == 37) {
        cycleSearch(cycle - 1);
      }
      else if (e.keyCode == 39) {
        cycleSearch(cycle + 1);
      }
    });

    $("#prevMatchLink").click(function (e) {
      e.preventDefault();
      cycleSearch(cycle - 1);
    });

    $("#nextMatchLink").click(function (e) {
      e.preventDefault();
      cycleSearch(cycle + 1);
    });

    // Execute search
    function searchTranscript(q) {
      matches = [];
      query = q;
      for (var i = 0; i < captions.length; i++) {
        var m = captions[i].text.toLowerCase().indexOf(q);
        if (m > -1) {
          document.getElementById('caption' + i).innerHTML =
            captions[i].text.substr(0, m) + "<em>" +
              captions[i].text.substr(m, q.length) + "</em>" +
              captions[i].text.substr(m + q.length);
          matches.push(i);
        }
      }
      
      if (matches.length) {
        cycleSearch(0);
      } else {
        resetSearch();
      }
    };

    function cycleSearch(i) {
      if (cycle > -1) {
        var o = document.getElementById('caption' + matches[cycle]);
        o.getElementsByTagName("em")[0].className = "";
      }
      var c = document.getElementById('caption' + matches[i]);
      c.getElementsByTagName("em")[0].className = "current";
      match.innerHTML = (i + 1) + " of " + matches.length;
      transcript.scrollTop = c.offsetTop - transcript.offsetTop - 40;
      cycle = i;
    };

    function resetSearch() {
      if (matches.length) {
        for (var i = 0; i < captions.length; i++) {
          document.getElementById('caption' + i).innerHTML = captions[i].text;
        }
      }
      query = "";
      matches = [];
      match.innerHTML = "0 of 0";
      cycle = -1;
      transcript.scrollTop = 0;
    };

    var videoTitle = $(".videoTitle").text();
    var hasPlayed = false;

    playerInstance.onBeforePlay(function (event) {
      if (hasPlayed == false) {
        ga('send', 'event', 'Video', 'Play', videoTitle);
        hasPlayed = true;
      }
    });

    //Can be used to trigger the Course to Marked Completed so the user doesn't have to
    playerInstance.on('complete', function () {

    });

    function loadChapters() {

      $.get(chapter_file, function (data) {
        data = data.trim();
        var c = data.split("\n\r\n");
        var d;

        for (var i = 0; i < c.length; i++) {
          d = c[i].split("\n");
          //pushes in Title for each chapter
          toc.push(d[0]);
          //pushes in the time intervals for each chapter
          seekArr.push(d[1]);
        };

        for (var a = 0; a < seekArr.length; a++) {
          //Splits the time interval and pushes the start interval for each chapter
          var tempPos = seekArr[a].split(" --> ");
          seekPos.push(tempPos[0]);
        };

        runTOC(seekPos);
        var toc_output = "";
        $.each(toc, function (i, v) {
          toc_output += "<li class=ch" + i + "><a href='#' onclick='jwplayer().seek(" + toc_seconds(seekPos[i]) + ");'>" + v + "</a> (" + toc_time(seekPos[i]) + ")</li>"
        });

        if (toc.length < 7) {
          toc_output += " <li class='blank'> </li><li class='blank'> </li>";
        }

        $(".courseTitles ul").html(toc_output);
      });
    };

    function runTOC(x) {
      playerInstance.onTime(function (event) {

        for (var i = 0; i < x.length; i++) {
          if (event.position > toc_seconds(x[i])) {
            $(".courseTitles ul li").removeClass("active");
            $(".courseTitles ul li.ch" + i).addClass('active');
          }
        };
      });
    }
  });
});

我们使用带有Cloudfront的Amazon Web Services托管视频和章节/字幕VTT文件。

我们已经包含了字幕中的交互式文字记录以及视频准备播放后要加载的动态视频章节。

我注意到的一件事是,章节和脚本并不总是加载并要求页面刷新几次,所以我想这可能是AWS方面的缓存问题。

我使用了谷歌浏览器,当章节和成绩单没有加载时,开发者控制台中没有错误。

应该注意的是,当使用JW平台云托管解决方案时,此功能正在完美运行,因此它似乎是AWS / Cloudfront CDN的一个因素。

      function load_jwp_scripts() { 
   		
	  wp_enqueue_script('jwplayer-js', plugins_url( "/js/jwplayer.js", __FILE__), array(), '1.0', false);
	  wp_enqueue_script('jwplayer-license-js', plugins_url( "/js/jwplayer_license.js", __FILE__), array(), '1.0', false);
	  wp_enqueue_script('jwplayer-player-js', plugins_url( "/js/player.js", __FILE__), array('jquery'), '1.0', true);
	  
      }
  
     add_action('wp_enqueue_scripts', 'load_jwp_scripts');

1 个答案:

答案 0 :(得分:1)

我能够找到解决问题的可行方案。

问题是使用$(document).ready声明。它与jwplayer.on不兼容(&#34; ready&#34;)。

删除它并再次正确渲染。