w3c / webcodecs

WebCodecs is a flexible web API for encoding and decoding audio and video.
https://w3c.github.io/webcodecs/
Other
1.01k stars 137 forks source link

Support per-frame QP configuration by VideoEncoder #270

Closed daijh closed 1 year ago

daijh commented 3 years ago

Customize BRCs by applications, in addition to CBR/VBR provided by VideoEncoder.

Some applications prefer to implement its own BRC according to per-frame QP, to better response to network bandwidth estimation. One such per-frame QP BRC implement can be found: https://github.com/intel/libmebo/blob/master/explainer.md

dictionary VideoEncoderEncodeOptions {
  boolean keyFrame = false;

  // proposal
  unsigned long QP;
};
daijh commented 3 years ago

56 Refine encoder configuration of bitrate and/or quantization

chcunningham commented 3 years ago

Thanks for filing @daijh. Can you say more on why per-frame is important vs making this part of the config (affecting N frames). I'm surprised we would want to adjust it with every frame (e.g. 30 times a second).

daijh commented 3 years ago

@chcunningham The BRC is something intrinsic of the video encoder, and it usually cannot be much changed after platform shipped. Some developers would like to use their own BRC cross all platforms, instead of platform intrinsic BRC. Per-frame QP enables the developer to implement customized BRC, by set QP of every frame according to previous encoded frames size and bitrate budget, as mentioned in #56

Djuffin commented 2 years ago

As I see it we’ll need to make at least 3 following changes in the API. I'm curious to know what the community thinks

New bitrate mode.

It also might be a good idea to replace QP by a more generic term.

aboba commented 2 years ago

Some thoughts:

  1. For setting the QP value, it seems like option 1 (using encode()) is easier than option 2 (configure()).
  2. For the QP range, I have a mild preference for handling it on a per-codec basis (option 1).
chcunningham commented 2 years ago

Editors Call discussion w/ @aboba

Thanks @Djuffin for moving this along!

For bitrate mode: Could we just use "VBR" here? I like reasoning about both cases as "variable".

Related questions:

For range discovery:

For setting a QP value, I also prefer option 1. This is a per-frame config, so doing it per-frame feels right.

chcunningham commented 2 years ago

Chrome folks met just now. Notes:

For bitrate mode: Could we just use "VBR" here? I like reasoning about both cases as "variable".

Simplicity of just doing VBR is clear, but also this is modeled on AVCodec (Mac), which has a distinct "mode" for setting QP. No super strong opinions though.

should we define the behavior where setting per-frame QP comes to override any previously configured config.bitrate? (do underlying libraries support combining these things? My hunch is it's probably either-or).

@Djuffin assumed they would be exclusive. Combining is an error.

I also like 1 better. I wonder if we need to return a supported range, or if we can instead get by with a static codec specific range defined in each codec registration?

Some preference for codec-specific route w/ ranges in registry.

If range-support is impl specific, would you support throwing an error (rather than silent failure) for unsupported values.

Throw an unsupported error.

Do you know the semantic meaning of QP across codecs....

Seems like another good reason to consider codec specific route (w/ codec specific names if appropriate).

dalecurtis commented 2 years ago

I spoke with James Zern from the encoding team today:

Djuffin commented 1 year ago

API proposal: https://github.com/w3c/webcodecs/pull/633

This is PR introduces codec specific quantizer fields in VideoEncoderEncodeOptions dictionary.

dictionary VideoEncoderEncodeOptions {
  boolean keyFrame;
  VideoEncoderEncodeOptionsForVp9 vp9;
  VideoEncoderEncodeOptionsForAv1 av1;
};

dictionary VideoEncoderEncodeOptionsForVp9 {
 unsigned short? quantizer;
}
Djuffin commented 1 year ago

Alternative API https://github.com/w3c/webcodecs/pull/642

This is PR introduces a generic quantizer field in VideoEncoderEncodeOptions dictionary.

dictionary VideoEncoderEncodeOptions {
  boolean keyFrame;
  double? quantizer;
};
Djuffin commented 1 year ago

On March 7th w3c media working group decided that codec specific quantizer fields are preferred. API proposal: https://github.com/w3c/webcodecs/pull/633

Rationale:

  1. There might be codecs in the future that don't have the concept of QP
  2. Having qp values for different codecs in different places will prevent websites from accidentally using qp value from one codec for another codec.
aboba commented 1 year ago

@dalecurtis Can we close this issue?

dalecurtis commented 1 year ago

Now landed.