vue---Vue中引入Video.js视频播放器

5,933 阅读1分钟

产品开发培训内容,视频。

2020.04.16

videojs画中画小窗口播放问题?

目的:使用监听滚动条位置来触发,比如滚动到距离顶部600px左右进入触发画中画小窗口播放;代码如下:

$(window).scroll(function(){
    var s = $(window).scrollTop();
    if(s > 600){
      video.requestPictureInPicture();
    }esle{
      video.exitPictureInPicture();
    }
});

结果:失败,报错Uncaught (in promise) DOMException

原因:需要用户主动触发,不可以使用任何自动执行函数!

最终:隐藏掉改按钮

.vjs-picture-in-picture-control{
  display: none !important;
}

video标签隐藏右下角的三个点

```
var video = $('#qqq'); //console.log(video); //通过打印拿到所有的属性和方法
video[0]['disablePictureInPicture'] = true; //disablePictureInPicture的属性改为true
```

点击屏幕播放/暂停

video.js 默认效果是单击播放区域暂停

需求:要实现单击播放区禁止暂停功能

.video-js.vjs-playing .vjs-tech {
    pointer-events: auto !important;
}
  

暂停按钮显示在视频中间--css样式控制

常用选项

autoplay : true/false 播放器准备好之后,是否自动播放 【默认false】
controls : true/false 是否拥有控制条 【默认true】,如果设为false ,那么只能通过api进行控制了。也就是说界面上不会出现任何控制按钮
height: 视频容器的高度,字符串或数字 单位像素 比如: height:300 or height:‘300px‘
width: 视频容器的宽度, 字符串或数字 单位像素
loop : true/false 视频播放结束后,是否循环播放
muted : true/false 是否静音
poster: 播放前显示的视频画面,播放开始之后自动移除。通常传入一个URL
preload:预加载
‘auto‘ 自动
’metadata‘ 元数据信息 ,比如视频长度,尺寸等
‘none‘ 不预加载任何数据,直到用户开始播放才开始下载
children: Array | Object 可选子组件 从基础的Component组件继承而来的子组件,数组中的顺序将影响组件的创建顺序哦。

常用事件

播放 this.play()
停止 – video没有stop方法,可以用pause 暂停获得同样的效果
暂停 this.pause()
销毁 this.dispose()
监听 this.on(‘click‘,fn)
触发事件this.trigger(‘dispose‘)

videojs 销毁重新初始化

 mounted() { 
    this.initVideo();
},
methods: {
   initVideo() {
    //初始化视频方法
      let myPlayer = this.$video(myVideo, {
         
      });
      this.myvideo = myPlayer;
  },
changeVideo(){
    console.log('changeVideo');
    
    this.myvideo.reset(); //重置 video
    this.myvideo.src([
        {
            type: 'video/mp4',
            src:'//vjs.zencdn.net/v/oceans.mp4'
        },
    ]);
    this.myvideo.load();
    this.myvideo.play();
}

代码

<template>
  <div class="coreTraining">
    <video id="myVideo" 
          class="video-js vjs-big-play-centered vjs-fluid"
          webkit-playsinline="true"
          playsinline="true"
    >
        <source
            src="//vjs.zencdn.net/v/oceans.mp4"
            type="video/mp4"
        ></source>
    </video>

    <button @click="changeVideo">切换视频</button>
  </div>
</template>

<script>
export default {
    name: 'coreTraining',
    //引用的组件
    components: {},
    data() {
      return{
        myvideo:null
      }
    },
     mounted() { 
        this.initVideo();
    },
    methods: {
       initVideo() {

        //初始化视频方法
          let myPlayer = this.$video(myVideo, {
              controls: true,//确定播放器是否具有用户可以与之交互的控件。没有控件,启动视频播放的唯一方法是使用autoplay属性或通过Player API。
              // autoplay: "muted",//自动播放属性,muted:静音播放
              preload: "auto", //预加载 auto 自动
              fluid: true, // 自适应宽高
              language: 'zh-CN', // 设置语言
              poster:require("@/assets/images/train/1.png"),//播放前显示的视频画面,播放开始之后自动移除。通常传入一个URL
              // inactivityTimeout: false,//显示时间
              // width:'100%',
              // height:'210px'
              controlBar:{
                /* 使用children的形式可以控制每一个控件的位置,以及显示与否 */
                children: [
                  {name: 'playToggle'}, // 播放按钮
                  {name: 'currentTimeDisplay'}, // 当前已播放时间
                  {name: 'progressControl'}, // 播放进度条
                  {name: 'durationDisplay'}, // 总时间
                  // { // 倍数播放
                  //   name: 'playbackRateMenuButton',
                  //   'playbackRates': [0.5, 1, 1.5, 2, 2.5]
                  // },
                  {
                    name: 'volumePanel', // 音量控制
                    inline: false, // 不使用水平方式
                  },
                  {name: 'FullscreenToggle'} // 全屏
                ]
              }

          },function onPlayerReady() {
             console.log('播放器已经准备好了!onPlayerReady');
              // In this context, `this` is the player that was created by Video.js.<br>  // 注意,这个地方的上下文, `this` 指向的是Video.js的实例对像player
              setTimeout(() => {
                this.play();
              }, 1000);
            
              // 如何使用事件监听?
              this.on('ended', function() {
                console.log('播放结束了!');
              });

              this.on('pause',function () {//暂停
                console.log('pause');
              })
          });
          this.myvideo = myPlayer;
      },
      changeVideo(){
        console.log('changeVideo');
        
        this.myvideo.reset(); //重置 video
        this.myvideo.src([
            {
                type: 'video/mp4',
                src:'//vjs.zencdn.net/v/oceans.mp4'
            },
        ]);
        this.myvideo.load();
        this.myvideo.play();
      }
      
    }
   
  
    
}
</script>

<style lang="scss">
 @import "@/assets/styles/mixin.scss";

.video-js{ /* 给.video-js设置字体大小以统一各浏览器样式表现,因为video.js采用的是em单位 */
  // font-size: 14px;
}
.video-js button{
  outline: none;
}
.vjs-paused .vjs-big-play-button,
.vjs-paused.vjs-has-started .vjs-big-play-button {
    display: block;
}

.video-js.vjs-fluid,
.video-js.vjs-16-9,
.video-js.vjs-4-3{ /* 视频占满容器高度 */
  height: 210px;
  background-color: #161616;
}
.vjs-poster{
  background-color: #161616;
}

.video-js .vjs-big-play-button{/* 中间大的播放按钮 */
    //  font-size: 2.5em;
    // line-height: 2.3em;
    // height: 2.5em;
    // width: 2.5em;
    font-size: 2.3em;
    line-height: 2.1em;
    height: 2.3em;
    width: 2.3em;
    border-radius: 2.5em;
    background-color: #73859f;
    background-color: rgba(115,133,159,.5);
    border-width: 0.1em;
    // margin-top: -1.25em;
    // margin-left: -1.75em;
    transform: translate(-50%, -50%);
    margin-top: 0;
    margin-left: 0;
}
/* 中间的播放箭头 */
.vjs-big-play-button .vjs-icon-placeholder {
    font-size: 1.4em;
}
/* 加载圆圈 */
.vjs-loading-spinner {
    font-size: 2.5em;
    width: 2em;
    height: 2em;
    border-radius: 1em;
    // margin-top: -1em;
    // margin-left: -1.5em;
}

.video-js.vjs-playing .vjs-tech {
    pointer-events: auto !important;
}
.video-js .vjs-time-control{display:block;}
.video-js .vjs-remaining-time{display: none;}

.vjs-picture-in-picture-control{
  display: none !important;
}

.h5-video{
  width: 100%;
  height: 210px;
}

</style>

最终样式

参考链接:

video.js小技巧

1 初始化 Video.js初始化有两种方式。

1.1 标签方式

一种是在标签里面加上class="video-js"和data-setup='{}'属性。

注意,两者缺一不可。

刚开始的时候我觉得后面的值为空对象{},不放也行,

导致播放器加载不出来,后来加上来就可以了。

1.2 JS方式

另外一种初始化 video.js 的方法是通过JS,格式:

var player = videojs('my-player'); 这样有个要求,就是不能配置data-setup,并且需要传入的id。

当然,如果不想一个个初始化,可以这样:

(function(){
    var videos = document.getElementsByTagName('video');
    for(i=0; i<videos.length; i++) {
        var video = videos[i];
        if(video.className.indexOf('video-js') > -1) {
            videojs(video.id).ready(function(){
            });
        }
    }
})();

2 播放按钮居中

video.js默认的播放按钮在左上角,应该是 video.js 开发人员认为放中间会遮挡内容,所以没放中间。

不过我们常见的一般都在中间,比较符合习惯。

这是可以通过参数修改的,在标签中加入vjs-big-play-centered类,就可以了。

像这样:

class="video-js vjs-big-play-centered"

3 支持音乐标签

video.js 4.9开始支持标签,与video不同的是:播放audio时封面不会消失。

但是上面的播放框还是一直在的,配置方式和标签一样,也必须要配置data-setup参数。

4 禁止在iPhone safari中自动全屏

方法如下,在标签中加入playsinline参数,

<video playsinline ></video>

注意,在iOS10之前用的是webkit-playsinline。

5 暂停时显示播放按钮

video.js 在未播放时,会显示一个大的播放按钮,上面我们提到如何让他居中。

那么,如何在视频暂停时也显示这个播放按钮呢?

有很多用JS的解决办法,感觉都挺麻烦的。

其实用CSS就可以搞定了:

.vjs-paused .vjs-big-play-button,
.vjs-paused.vjs-has-started .vjs-big-play-button {
    display: block;
}

是不是很轻便很简单 :)

6 播放按钮变○圆形

video.js 默认的播放按钮是圆角矩形,

我们一般更熟悉播放按钮为圆形的:

那么怎么改呢?还是用CSS来解决。

.video-js .vjs-big-play-button{
    font-size: 2.5em;
    line-height: 2.3em;
    height: 2.5em;
    width: 2.5em;
    -webkit-border-radius: 2.5em;
    -moz-border-radius: 2.5em;
    border-radius: 2.5em;
    background-color: #73859f;
    background-color: rgba(115,133,159,.5);
    border-width: 0.15em;
    margin-top: -1.25em;
    margin-left: -1.75em;
}
/* 中间的播放箭头 */
.vjs-big-play-button .vjs-icon-placeholder {
    font-size: 1.63em;
}
/* 加载圆圈 */
.vjs-loading-spinner {
    font-size: 2.5em;
    width: 2em;
    height: 2em;
    border-radius: 1em;
    margin-top: -1em;
    margin-left: -1.5em;
}

因为原来居中的时候宽度和高度改变了,所以margin的值也要相应改变

7 点击屏幕播放/暂停

这个是视频播放的时候用得较多的功能,解决方法如下。

.video-js.vjs-playing .vjs-tech {
    pointer-events: auto;
}

pointer-events是CSS的一个属性,用来控制鼠标的动作,具体可参考《CSS里的pointer-events属性》。

8 重载视频文件

总有那么一些情形,我们需要 video.js 重新载入视频文件。

比如,立即播放刚上传的文件。

例如这样的标签:

<video id="example_video">
    <source id="videoMP4" src="1.mp4" />
</video>
<button id="reload">重载</button>

在video.js中,用现成的js方法就可以实现:

var video = document.getElementById('example_video');
var source = document.getElementById('videoMP4');
$("#reload").click(function() {
    video.pause()
    source.setAttribute('src', '2.mp4');
    video.load();
    video.play();
});

或者:

var video = document.getElementById('example_video');
$("#reload").click(function() {
    video.pause()
    video.setAttribute('src', '2.mp4');
    video.load();
    video.play();
});

9 进度显示当前播放时间

video.js 默认倒序显示时间,也就是视频播放的剩余时间。

要显示当前的播放时间,以及总共视频时长,加2行CSS解决:

.video-js .vjs-time-control{display:block;}
.video-js .vjs-remaining-time{display: none;}