Add custom quality factors and quantizer bitrate mode (#448)

* Add custom quality factors and quantizer bitrate mode (closes #327)

* Fix quantizer mode fallback and per-frame quantizer edge cases

* Clean up quantizer mode tests

* Quantizer implementation

* Add quality tests

* Improve conversion codec error message, make test more lenient

* Add quantizer support blog post

---------

Co-authored-by: Vanilagy <[email protected]>
This commit is contained in:
Don Carignan
2026-07-30 17:24:59 +02:00
committed by GitHub
co-authored by Vanilagy
parent 1a99b0371d
commit c3df2a24e5
48 changed files with 1372 additions and 371 deletions
+11 -8
View File
@@ -165,7 +165,7 @@ type ConversionVideoOptions = {
crop?: { left: number; top: number; width: number; height: number };
frameRate?: number;
codec?: VideoCodec;
bitrate?: number | Quality;
quality?: Quality;
alpha?: 'discard' | 'keep'; // Defaults to 'discard'
hardwareAcceleration?: 'no-preference' | 'prefer-hardware' | 'prefer-software';
keyFrameInterval?: number;
@@ -233,7 +233,7 @@ The `frameRate` property can be used to set the frame rate of the output video i
Use the `codec` property to control the codec of the output track. This should be set to a [codec](./supported-formats-and-codecs#video-codecs) supported by the output file, or else the track will be [discarded](#discarded-tracks).
Use the `bitrate` property to control the bitrate of the output video. For example, you can use this field to compress the video track. Accepted values are the number of bits per second or a [subjective quality](./media-sources#subjective-qualities). If this property is set, transcoding will always happen. If this property is not set but transcoding is still required, `QUALITY_HIGH` will be used as the value.
Use the `quality` property to control the quality of the output video. For example, you can use this field to compress the video track. See [Encoding quality](./media-sources#encoding-quality) for more. If this property is set, transcoding will always happen. If this property is not set but transcoding is still required, `new Quality('high')` will be used as the value.
Use the `keyFrameInterval` property to control the maximum interval in seconds between key frames in the output video. Setting this fields forces a transcode.
If you want to prevent direct copying of media data and force a transcoding step, use `forceTranscode: true`.
@@ -280,7 +280,7 @@ You can set the `audio` property in the conversion options to configure the conv
type ConversionAudioOptions = {
discard?: boolean;
codec?: AudioCodec;
bitrate?: number | Quality;
quality?: Quality;
numberOfChannels?: number;
sampleRate?: number;
sampleFormat?: 'u8' | 's16' | 's32' | 'f32';
@@ -325,7 +325,7 @@ The `sampleRate` property controls the sample rate in Hz (e.g., 44100, 48000). I
Use the `codec` property to control the codec of the output track. This should be set to a [codec](./supported-formats-and-codecs#audio-codecs) supported by the output file, or else the track will be [discarded](#discarded-tracks).
Use the `bitrate` property to control the bitrate of the output audio. For example, you can use this field to compress the audio track. Accepted values are the number of bits per second or a [subjective quality](./media-sources#subjective-qualities). If this property is set, transcoding will always happen. If this property is not set but transcoding is still required, `QUALITY_HIGH` will be used as the value.
Use the `quality` property to control the quality of the output audio. For example, you can use this field to compress the audio track. See [Encoding quality](./media-sources#encoding-quality) for more. If this property is set, transcoding will always happen. If this property is not set but transcoding is still required, `new Quality('high')` will be used as the value.
If you want to prevent direct copying of media data and force a transcoding step, use `forceTranscode: true`.
@@ -387,9 +387,9 @@ const conversion = await Conversion.init({
input,
output,
video: [
{ height: 1080, bitrate: QUALITY_HIGH },
{ height: 720, bitrate: QUALITY_MEDIUM },
{ height: 480, bitrate: QUALITY_LOW },
{ height: 1080, quality: new Quality('high') },
{ height: 720, quality: new Quality('medium') },
{ height: 480, quality: new Quality('low') },
],
});
```
@@ -576,7 +576,10 @@ const conversion = await Conversion.init({
});
// Add our own audio track directly
const audioSource = new AudioBufferSource({ codec: 'aac', bitrate: 128e3 });
const audioSource = new AudioBufferSource({
codec: 'aac',
quality: new Quality({ bitrate: 128e3 }),
});
output.addAudioTrack(audioSource);
// Start the output