Transparent video read/write support (#145)

* Add support for reading transparent Matroska and implement alpha side data & decode

* Few fixes

* Implement alpha encoding

* Gracefully handle inability to acquire WebGL context, properly clean up WebGL contexts

* Improve touch device detection

* Test test

* Test test #2

* Test test 3

* Test test 4

* Test test 5

* Test test 6

* Test test 7

* Test test 8

* Test test 9

* Test test 10

* Test test 11

* Test test 12

* Test test 13

* Test test 14

* Test test 15

* Test test 16

* Test test 17

* Test test 18

* Test test 19

* Test test 20

* Fix type errors, improve MetadataTags docs

* Do a bunch of docs work

* Test test?

* "Unexpected only modifier 🤓"

* Add InputVideoTrack.canBeTransparent()

* Some clean-up

* Adjust CI to be less spammy in PRs

* Fix broken license headers
This commit is contained in:
David P.
2025-09-24 21:20:14 +02:00
committed by GitHub
parent 0878dd2ca9
commit fa4e064345
34 changed files with 1537 additions and 181 deletions
+4
View File
@@ -47,6 +47,7 @@ All video sources that handle encoding internally require you to specify a `Vide
type VideoEncodingConfig = {
codec: VideoCodec;
bitrate: number | Quality;
alpha?: 'discard' | 'keep';
bitrateMode?: 'constant' | 'variable';
latencyMode?: 'quality' | 'realtime';
keyFrameInterval?: number;
@@ -67,6 +68,9 @@ type VideoEncodingConfig = {
```
- `codec`: The [video codec](./supported-formats-and-codecs#video-codecs) used for encoding.
- `bitrate`: The target number of bits per second. Alternatively, this can be a [subjective quality](#subjective-qualities).
- `alpha`: What to do with alpha data contained in the video samples.
- `'discard'` (default): Only the samples' color data is kept; the video is opaque.
- `'keep'`: The samples' alpha data is also encoded as side data. Make sure to pair this mode with a container format that supports transparency (such as WebM or Matroska).
- `bitrateMode`: Can be used to control constant vs. variable bitrate.
- `latencyMode`: The latency mode as specified by the WebCodecs API. Browsers default to `quality`. Media stream-driven video sources will automatically use the `realtime` setting.
- `keyFrameInterval`: The maximum interval in seconds between two adjacent key frames. Defaults to 5 seconds. More frequent key frames improve seeking behavior but increase file size. When using multiple video tracks, this value should be set to the same value for all tracks.
+36
View File
@@ -397,6 +397,42 @@ await output.finalize();
- This is basically [`MediaRecorder`](https://developer.mozilla.org/en-US/docs/Web/API/MediaRecorder), but less sucky.
:::
## Creating transparent video
```ts
import {
Output,
WebMOutputFormat,
BufferTarget,
CanvasSource,
QUALITY_MEDIUM,
} from 'mediabunny';
const output = new Output({
// Use a format that supports transparency:
format: new WebMOutputFormat(),
target: new BufferTarget(),
});
const canvas = new OffscreenCanvas(1280, 720);
const context = canvas.getContext('2d', { alpha: true })!;
const source = new CanvasSource(canvas, {
codec: 'vp9',
quality: QUALITY_MEDIUM,
alpha: 'keep', // => Also encode alpha data
});
output.addVideoTrack(source);
await output.start();
// Add data...
await source.add(0, 1 / 30);
// ...
await output.finalize();
```
## Check encoding support
```ts