uni.chooseVideo 后h5端获取图片第一帧图片

uni.chooseVideo对于h5端很不友好,无法获取视频图片,网上说的用renderjs可以使用,不过我用的是canvas绘制

比较需要注意的是你绘制的要跟你canvas设置的宽高一致不然绘制的图片会不完整

1.html得写这个canvas元素

<canvas id="videoCanvas" canvas-id="videoCanvas"></canvas>

2.设置css样式(这个只能隐藏,你也可以放出来)

#videoCanvas {
		width: 228px;
		height: 228px;
		position: fixed;
		// top: -400px;
		z-index: 9;
		visibility: hidden;
	}

3.写个按钮然后上传图片

const chooseVideo = () => {

		uni.chooseVideo({
			sourceType: ['album', 'camera'],
			maxDuration: 300,
			success: res => {
				nextTick(() => {
					// 使用定时器等待组件挂载和渲染完成
					setTimeout(() => {
						attemptCaptureVideoFrame();
					}, 800); // 根据平台情况调整延迟时间
				});
				// uploadVideo(res.tempFilePath)
			},
			fail: err => {
				console.error('选择视频失败:', err)
			}
		})
	}

4.这一步是绘制

function attemptCaptureVideoFrame() {
		const canvasId = 'videoCanvas'; // 对应 <canvas canvas-id="videoCanvas">
		const isH5 = typeof window !== 'undefined' && window.document;

		if (isH5) {
			uni.createSelectorQuery()
				.select('#videoCanvas')
				.fields({
					node: true,
					size: true
				}, canvasRes => {
					if (!canvasRes || !canvasRes.node) {
						console.error('Canvas 元素无效');
						return;
					}
					const canvasNode = canvasRes.node;
					const ctx = canvasNode.getContext('2d');

					// 创建独立 video 元素用于截图
					const videoEl = document.createElement('video');
					videoEl.src = videoUrl.value;
					videoEl.crossOrigin = 'anonymous';
					videoEl.muted = true; // 静音避免自动播放限制

					// 设置目标截图时间点(单位:秒)
					const targetTime = 2; // 修改为合适的截图时间点,比如第 3 秒

					// 监听视频加载完成
					videoEl.onloadeddata = () => {
						// 设置视频跳转到指定时间点
						videoEl.currentTime = targetTime;
					};

					// 监听 seek 完成事件,确保跳转到目标时间点
					videoEl.onseeked = () => {
						// 确保 DOM 更新后再绘制
						setTimeout(() => {
							try {
								ctx.drawImage(videoEl, 0, 0, 228, 228);
								const tempFilePath = canvasNode.toDataURL('image/png');
								thumbnail.value = tempFilePath;
								console.log(`手动绘制第 ${targetTime} 秒帧图成功:`, tempFilePath);
							} catch (err) {
								console.error('绘制失败:', err);
							}
						}, 200); // 添加短延迟确保画面已渲染
					};

					// 超时保护
					setTimeout(() => {
						if (videoEl.readyState < 2) {
							console.warn('视频加载超时,无法绘制');
						}
					}, 5000);
				})
				.exec();
		} else {
			// 小程序平台处理逻辑(可选使用 uni.canvasToTempFilePath 或服务端生成)
			const ctx = uni.createCanvasContext(canvasId);

			setTimeout(() => {
				ctx.draw(false, () => {
					uni.canvasToTempFilePath({
						canvasId: canvasId,
						success: res => {
							thumbnail.value = res.tempFilePath;
							console.log('小程序生成首帧图成功:', res.tempFilePath);
						},
						fail: err => {
							console.error('canvasToTempFilePath 失败:', err);
						}
					});
				})
			}, 800);
		}
	}

然后thumbnail.value 就是绘制的图片

效果图如下

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值