摘要:大家好,很高兴又见面了,我是"高级前端进阶",由我带着大家一起关注前端前沿、深入前端底层技术,大家一起进步,也欢迎大家关注、点赞、收藏、转发,您的支持是我不断创作的动力。
大家好,很高兴又见面了,我是"高级前端进阶",由我带着大家一起关注前端前沿、深入前端底层技术,大家一起进步,也欢迎大家关注、点赞、收藏、转发,您的支持是我不断创作的动力。
Mediabunny 是一个 JavaScript 库,用于直接在浏览器中读取、写入和转换媒体文件,例如: Mp4、webm、MP。其旨在成为一套完整的 Web 高性能媒体操作工具包,完全用 TypeScript 编写,零依赖,性能卓越,并且支持 tree-shakable。
Pure TypeScript media toolkit for reading, writing, and converting video and audio files, directly in the browser.
开发者可以将其视为 FFmpeg,但其是专为 Web 平台而生的。Mediabunny 核心功能包括:
广泛格式支持:读写 MP4、MOV、WebM、MKV、WAVE、MP3、Ogg、ADTS、FLAC丰富的内置编码和解码:支持 25 多种视频、音频和字幕编解码器,并使用 WebCodecs API 进行硬件加速高精度支持:细粒度、微秒级的读写操作支持丰富的转换 API:易于使用的 API,提供转码、转码、调整大小、旋转、裁剪、重采样、修剪等功能从零开始且专为 Web 开发: Mediabunny 100% 使用 TypeScript 实现,零依赖,其 API 经过精心设计通用 I/O:支持从内存、磁盘或网络读取和写入文件,包括从画布、网络摄像头、屏幕、麦克风、音频缓冲区、自己的编码堆栈或其他任何来源注入媒体数据。同时支持通过高效的流式处理处理任意大小的文件可摇树优化:开发者可以仅打包使用的代码,压缩后体积最小 5 kB零依赖且跨平台:使用高性能 TypeScript 实现,可在浏览器和 Node.js 上运行目前 Mediabunny 在 Github 通过 MPL-2.0 协议开源,短短几周已经有超过 3.5k 的 star,是一个值得关注的前端开源项目。
Mediabunny 让开发者可以高效地读取任何视频或音频文件的数据,无论其大小、时长、分辨率、旋转、轨道、编解码器和其他元数据,以及文件中任何位置的原始或解码媒体数据。开发者只需加载需要的内容即可:
const input = new Input({source: new UrlSource("./bigbuckbunny.mp4"),formats: ALL_FORMATS,// 支持格式 .mp4, .webm, .wav, ...});const duration = await input.computeDuration;const videoTrack = await input.getPrimaryVideoTrack;const {displayWidth, displayHeight, rotation} = videoTrack;const audioTrack = await input.getPrimaryAudioTrack;const {sampleRate, numberOfChannels} = audioTrack;// 获取视频中途的帧const sink = new VideoSampleSink(videoTrack);const frame = await sink.getSample(duration / 2);// 遍历视频中所有的帧for await (const frame of sink.samples) {// ...}开发者可以直接在客户端生成新媒体文件(例如 MP4 或 WebM),速度以硬件允许的速度为准。支持添加多个视频、音频或字幕轨道,并实现精确到微秒级的控制。
const output = new Output({format: new Mp4OutputFormat,// .mp4target: new BufferTarget,// 内存});// 添加视频,由画布驱动const videoSource = new CanvasSource(canvas, {codec: "av1",bitrate: QUALITY_HIGH,});output.addVideoTrack(videoSource);// 添加音频,由音频缓冲区驱动const audioSource = new AudioBufferSource({codec: "opus",bitrate: QUALITY_HIGH,});output.addAudioTrack(audioSource);await output.start;// Add media data here...await output.finalize;const {buffer} = output.target;// 最终文件开发者可以使用转换 API 将任何媒体文件转换为任何其他媒体文件:执行转码、转码、调整大小、旋转、音频重采样、修剪等操作。
const input = new Input({source: new BlobSource(file),// 从硬盘读取文件formats: ALL_FORMATS,});const output = new Output({format: new WebMOutputFormat,// 转化成为. webmtarget: new StreamTarget(writableStream),// 写入硬盘});const conversion = await Conversion.init({input, output});await conversion.execute;// Done!开发可以通过下面代码快速提取视频缩略图:
import {Input, ALL_FORMATS, BlobSource, CanvasSink} from "mediabunny";const input = new Input({formats: ALL_FORMATS,source: new BlobSource(file),});const videoTrack = await input.getPrimaryVideoTrack;if (videoTrack) {const decodable = await videoTrack.canDecode;if (decodable) {const sink = new CanvasSink(videoTrack, {width: 320,// 自动 resize 缩略图});// Get the thumbnail at timestamp 10sconst result = await sink.getCanvas(10);result.canvas; // HTMLCanvasElement | OffscreenCanvasresult.timestamp; // in secondsresult.duration; // in seconds// Generate five equally-spaced thumbnails through the videoconst startTimestamp = await videoTrack.getFirstTimestamp;const endTimestamp = await videoTrack.computeDuration;const timestamps = [0, 0.2, 0.4, 0.6, 0.8].map((t) => startTimestamp + t * (endTimestamp - startTimestamp));// Loop over these timestampsfor await (const result of sink.canvasesAtTimestamps(timestamps)) {// ...}}}录制现场媒体也非常实用,而且实用起来也非常简单,例如:
import { Output, BufferTarget, WebMOutputFormat, MediaStreamVideoTrackSource, MediaStreamAudioTrackSource, QUALITY_MEDIUM} from 'mediabunny';const userMedia = await navigator.mediaDevices.getUserMedia({ video: true, audio: true,});const videoTrack = userMedia.getVideoTracks[0];const audioTrack = userMedia.getAudioTracks[0];const output = new Output({ format: new WebMOutputFormat, target: new BufferTarget,});if (videoTrack) { const source = new MediaStreamVideoTrackSource(videoTrack, { codec: 'vp9', bitrate: QUALITY_MEDIUM, }); output.addVideoTrack(source);}if (audioTrack) { const source = new MediaStreamAudioTrackSource(audioTrack, { codec: 'opus', bitrate: QUALITY_MEDIUM, }); output.addAudioTrack(source);}await output.start;await output.finalize;更多关于 mediabunny 的用法和示例可以参考文末资料,本文不再过多展开。
来源:有趣的科技君