【问题标题】:HTML video source switching via JavaScript matchMedia通过 JavaScript matchMedia 切换 HTML 视频源
【发布时间】:2019-05-11 00:38:33
【问题描述】:

我正在通过 HTML 标记 <video> 显示视频。我想根据用户屏幕的分辨率提供一个小视频和一个大视频。一个小屏幕应该只下载小视频。不再可以直接在 HTML 中使用 media 属性执行此操作。我尝试的基于matchMedia 的JavaScript 解决方案不起作用。

我使用我在 Google 的视频 (https://youtu.be/j5fYOYrsocs?t=356) 中找到的 matchMedia 尝试了以下 JavaScript 代码:

HTML:

<video>
</video>

JavaScript:

var mq = window.matchMedia('(min-width: 480px)');
if (mq.matches) {
video.src = 'http://techslides.com/demos/sample-videos/small.mp4';
}
else {
video.src = 'http://media.w3.org/2010/05/sintel/trailer.mp4';
}

不过,这段代码只会产生一个空白页。看到这支笔:https://codepen.io/blueslobster/pen/ROQjOv

【问题讨论】:

    标签: javascript html html5-video


    【解决方案1】:

    Offbeatmammal 是正确的,因为 OP 似乎忽略了引用视频标签。除了正确引用所述视频之外,如果我们打算在调整窗口大小时调整视频,我们应该“监听”视口的变化。此外,应将 OP 中的视频反转,请考虑以下事项:

     ... const mQL = window.matchMedia("(min-width: 481px)");
    

    传递给matchMedia()方法的媒体查询意味着:

    “当视口宽度为481px或更大时,应用以下规则、表达式、语句等

    所以当这个条件为TRUE时,应该加载较大的视频,否则应该加载较小的视频:

    if mQL.matches then较大的视频分配给vid.src else 分配较小的视频vid.src

    注意:第一个匹配mQL(最小宽度:481px)的视频(560x278)是TRUE。第二个视频从一个巨大的视频(854x438,这也是真的)变成了一个适当大小的视频:(480x318)。另请注意:原始媒体查询为 480 像素并更改为 481 像素,因为我拥有 ATM 的最佳替换视频具有 480 像素的自然宽度。 更多详细信息在 Demo 和 Pen 中进行了评论(全页模式下的 Demo 似乎不起作用,但在 CodePen,将窗口拖动到 481px 宽度以下即可看到魔法)

    演示1

    两个视频使用.addListener()

    /*
    Create a mediaQueryList Object (mQL)
    https://developer.mozilla.org/en-US/docs/Web/API/MediaQueryList
    */
    const mQL = window.matchMedia("(min-width: 481px)");
    
    /*
    Bind a listener to mQL -- triggers when window changes and calls vidSec callback function
    https://developer.mozilla.org/en-US/docs/Web/API/MediaQueryList/addListener
    */
    mQL.addListener(vidSrc);
    
    /*
    Call vidSrc() and pass mQL once to set the video src to the initial viewport. This insures
    that the correct video is loaded should the viewport be less than 481px wide. Moreover
    it's bad UX to start the page with an empty video tag.
    */
    vidSrc(mQL);
    
    /*
    Callback function passes the mQL...
    Reference the video tag...
    Ternary: url is the result of [=] 
             if mQL .matches property* is [?]
             equal to or greater than 481px [TRUE]
             "http://techslides.com/demos/sample-videos/small.mp4" 
             [:] else [FALSE]
             "https://html5demos.com/assets/dizzy.mp4" 
    Assign url to video .src property...
    load() video
    */
    /* [*] .matches Property: 
    https://developer.mozilla.org/en-US/docs/Web/API/MediaQueryList/matches
    */
    function vidSrc(mQL) {
      const vid = document.querySelector("video");
      let url = mQL.matches ? "http://techslides.com/demos/sample-videos/small.mp4" : "https://html5demos.com/assets/dizzy.mp4";
      vid.src = url;
      vid.load();
    }
    &lt;video&gt;&lt;/video&gt;

    演示2

    Pen

    三个视频——一个数组中的多个 mediaQueryLists

    const mQLs = [
      window.matchMedia(`(max-width: 854px)`),
      window.matchMedia(`(max-width: 481px)`)
    ];
    
    function vidSrc(mQL) {
      const vid = document.querySelector("video");
      let url;
      if (mQLs[0].matches) {
        url = "http://techslides.com/demos/sample-videos/small.mp4";
      }
      if (mQLs[1].matches) {
        url = "https://html5demos.com/assets/dizzy.mp4";
      }
      if (!mQLs[0].matches && !mQLs[1].matches) {
        url = "http://media.w3.org/2010/05/sintel/trailer.mp4";
      }
      vid.src = url;
      vid.load();
    }
    
    
    for (let i = 0; i < mQLs.length; i++) {
      vidSrc(mQLs[i]);
    }
    &lt;video&gt;&lt;/video&gt;

    【讨论】:

    • 我删除了监听线mQL.addListener(vidSrc);,因为这条线可能会在智能手机上出现问题:当我通过 Chrome DevTools 检查网络活动时,将智能手机从纵向模式切换到横向模式触发了更大视频的下载即使已经下载了较小的视频。看到这支笔:codepen.io/pen 额外问题:提供只能在 1080 像素及以上屏幕上播放的第三个(并且非常大)视频的最佳代码是什么?
    • 查看更新 -- 演示 2。数组中的多个 mQL 和函数 vidSrc() 被循环。
    【解决方案2】:

    您不能简单地将视频引用为video,因为在 javascript 中该变量尚未分配给任何东西。如果您定义了要更改的元素,那么它应该可以工作:

    <video id="vid"></video>
    <script>
    var mq = window.matchMedia('(min-width: 480px)');
    var vid = document.getElementById("vid")
    if (mq.matches) {
        vid.src = 'http://techslides.com/demos/sample-videos/small.mp4';
    } else {
        vid.src = 'http://media.w3.org/2010/05/sintel/trailer.mp4';
    } 
    </script>
    

    请注意,vid 的赋值必须在 DOM 构建之后发生,因此要么在 HTML 元素之后放置脚本,要么只在您知道该元素已创建以便可以引用它的位置触发(例如页面的 body onloaded 事件)

    【讨论】:

      【解决方案3】:

      您可以简单地使用 window.screen 对象的 widthheight 属性来获取屏幕的分辨率。

      <video id="video"></video>
      

      尝试使用:

      var video = document.getElementById("video");
      if (window.screen.width > 480) {
          //video source for resolution greater than 480p
          video.src = 'http://techslides.com/demos/sample-videos/small.mp4';
      }else {
          //video source for resolution less than 480p
          video.src = 'http://media.w3.org/2010/05/sintel/trailer.mp4';
      }
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2017-08-16
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2014-12-09
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多