>
<div class="loader" v-show="state.isLoading">
<div class="loader-inner ball-clip-rotate">
<div></div>
</div>
</div>
</div>
<!-- 控制条 -->
<div class="control-bar" :style="{ visibility: state.controlBarShow ? 'visible' : 'hidden'}">
<span class="time">{{video.displayTime}}</span>
<span class="progress" ref="progress">
<img
class="progress-btn ignore"
:style="{transform: `translate3d(${video.progress.current}px, 0, 0)`}"
src="../../assets/video/content_ic_tutu.svg"
>
<span class="progress-loaded" :style="{ width: `${video.loaded}%`}"></span>
<!-- 设置手动移动的进度条 -->
<span
class="progress-move"
@touchmove.stop.prevent="moveIng($event)"
@touchstart.stop="moveStart($event)"
@touchend.stop="moveEnd($event)"
></span>
</span>
<span class="total-time">{{video.totalTime}}</span>
<span class="full-screen" @click="fullScreen">
<img src="../../assets/video/content_ic_increase.svg" alt>
</span>
</div>
</div>
<!-- 错误弹窗 -->
<div class="error" v-show="state.isError">
<p class="lose">视频加载失败</p>
<p class="retry" @click="retry">点击重试</p>
</div>
</div>
</template>
播放器初始化
这里有个坑点我就是当父元素隐藏即display:none时,getBoundingClientRect()是获取不到元素的尺寸数值的,后来查了MDN文档,按上面说的改了一下border也没有用,最后尝试设置元素visibility属性为hidden后发现就可以获取了.
getBoundingClientRect() : 返回元素的大小及其相对于视口的位置, 这个api在计算元素相对位置的时候挺好用的.
init() {
// 初始化video,获取video元素
this.$video = this.$el.getElementsByTagName("video")[0];
this.initPlayer();
},
// 初始化播放器容器, 获取video-player元素
// getBoundingClientRect()以client可视区的左上角为基点进行位置计算
initPlayer() {
const $player = this.$el;
const $progress = this.$el.getElementsByClassName("progress")[0];
// 播放器位置
this.player.$player = $player;
this.progressBar.$progress = $progress;
this.player.pos = $player.getBoundingClientRect();
this.progressBar.pos = $progress.getBoundingClientRect()
this.video.progress.width = Math.round($progress.getBoundingClientRect().width);
},播放 && 暂停点击
我这里把事件监听都放在只有满足正在播放视频才开始事件监听; 感觉原生监听和vue方式的监听混合在一起写有点别扭…emem…这里需要对this.$video.play()做一个异常处理,防止video刚开始加载的时候失败,如果视频链接出错,play方法调用不了会抛错,后面我也用了video的error事件去监听播放时的错误










