vue,uniapp,js获取视频第一帧图片作为封面图

需求:后端返回http视频线上地址数组,将视频的第一帧作为封面图展示,通过列表渲染页面,如下图

 

1、获取视频列表,这里需要Promise函数处理异步问题,跟据具体业务逻辑来处理

// 获取设备的视频列表
			function getVideoList() {
				return new Promise((resolve, reject) => {
					mui.ajax('你的接口地址', {
						data: {  // 你接口的参数
							code: pu_id,
							date: '2021-08-26'
						},
						dataType: 'json',
						type: 'get',
						success: function(data) {
							videoList = data.data
							resolve(videoList)
						}
					})
				})
			}

2.通过在script中创建video,canvas,标签进行对视频的处理

// 视频截图封面图
			    function getVideoCanvas() {
				var videoCanList = [] // 因为后端返回的视频数组,这里先定义一个空数组
				videoList.forEach((item, index) => {  // for循环获取到的视频数组
                    // 因为是循环处理,这里定义一个promise函数
					var promise = new Promise((reslove, reject) => {
                        // 在缓存中创建video标签
						var video = document.createElement("VIDEO")
                        // 通过setAttribute给video dom元素添加自动播放的属性,因为视频播放才        
                           能获取封面图
						video.setAttribute('autoplay', 'autoplay')
                        // 再添加一个静音的属性,否则自动播放会有声音
						video.setAttribute('muted', 'muted')
                        // 上面我们只是创建了video标签,视频播放需要内部的source的标签,scr为 
                           播放源
						video.innerHTML = '<source src=' + item + ' type="audio/mp4">'
                        // 再创建canvas画布标签
						var canvas = document.createElement('canvas');
						var ctx = canvas.getContext('2d');
                        // video注册canplay自动播放事件
						video.addEventListener('canplay', function() {
							// 创建画布的宽高属性节点,就是图片的大小,单位PX
							var anw = document.createAttribute("width");
							anw.nodeValue = 500;
							var anh = document.createAttribute("height");
							anh.nodeValue = 300;
							canvas.setAttributeNode(anw);
							canvas.setAttributeNode(anh);
                            // 画布渲染
							ctx.drawImage(video, 0, 0, 500, 300);
							// 生成图片
							var base64 = canvas.toDataURL('image/png') // 这就是封面图片的base64编码
                            // 视频结束播放的事件
							video.pause()
							console.log(base64) // 可打印看是不是base64编码图片
							curDateList.unshift({ // 这里是我自己的数据处理模块
								type: 'video',
								videoUrl: item,
								img: base64
							})
							reslove(base64)  // promise函数成功的回调
						}, false)
					})
					videoCanList.push(promise) // 这里将每一次promise函数成功回调的结果push进一开始定义的空数组
				})
                // 通过Promise.all方法等待上面的循环结束这里再执行业务逻辑
				Promise.all(videoCanList).then(res=>{
					console.log(videoCanList) // 这里就是每一张视频的封面图
					console.log(curDateList)
				})
			}

获取到视频的封面图就已经完成一大半了,注意需要跨域的视频可能会污染画布不生效,有更好的方法可以留言

  • 7
    点赞
  • 23
    收藏
    觉得还不错? 一键收藏
  • 10
    评论
uniapp中,可以使用uni-app官方提供的uni.media.chooseVideo API选择本地视频文件,并通过video标签播放视频。同时,我们可以通过video标签提供的canvas截取视频的第一帧作为图片。 具体实现步骤如下: 1. 使用uni.media.chooseVideo API选择本地视频文件,并通过video标签播放视频。 ```js uni.media.chooseVideo({ sourceType: ['album'], success: function(res) { var videoPath = res.tempFilePath; // 将视频路径绑定到video标签 uni.createVideoContext('myVideo').src = videoPath; } }) ``` 2. 在video标签的loadedmetadata事件中获取视频时长、宽高等信息,并将视频的第一帧渲染到canvas上。 ```html <template> <view> <video id="myVideo" :bindloadedmetadata="onLoadedMetadata"></video> <canvas id="myCanvas"></canvas> </view> </template> <script> export default { methods: { onLoadedMetadata(e) { // 获取视频时长、宽高 const duration = e.duration; const width = e.videoWidth; const height = e.videoHeight; // 将canvas的宽高设置为视频的宽高 const canvas = uni.createCanvasContext('myCanvas'); canvas.canvas.width = width; canvas.canvas.height = height; // 绘制视频的第一帧到canvas上 canvas.drawImage('myVideo', 0, 0, width, height); canvas.draw(); // 将canvas转换为图片 const that = this; setTimeout(function() { uni.canvasToTempFilePath({ canvasId: 'myCanvas', success: function(res) { const imagePath = res.tempFilePath; // 将图片路径保存到data中 that.imagePath = imagePath; } }) }, 1000) } } } </script> ``` 在上述代码中,我们通过video标签的loadedmetadata事件获取视频的宽高等信息,并将canvas的宽高设置为视频的宽高。接着,我们通过canvas的drawImage方法绘制视频的第一帧到canvas上,并将canvas转换为图片,最后将图片路径保存到data中。 需要注意的是,由于canvas绘是异步的,我们需要在setTimeout中等待一定时间,确保canvas已经绘制完成。同时,为了避免视频播放过程中截取到不正确的图片,我们可以在视频播放前暂停视频,并在canvas绘制完成后再播放视频

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 10
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值