// META: global=window,dedicatedworker
// META: script=/webcodecs/video-encoder-utils.js
// META: variant=?av1
// META: variant=?vp8
// META: variant=?vp9_p0
// META: variant=?vp9_p2
// META: variant=?h264_avc
// META: variant=?h264_annexb

var ENCODER_CONFIG = null;
promise_setup(async () => {
  const config = {
    '?av1': {codec: 'av01.0.04M.08'},
    '?vp8': {codec: 'vp8'},
    '?vp9_p0': {codec: 'vp09.00.10.08'},
    '?vp9_p2': {codec: 'vp09.02.10.10'},
    '?h264_avc': {codec: 'avc1.42001F', avc: {format: 'avc'}},
    '?h264_annexb': {codec: 'avc1.42001F', avc: {format: 'annexb'}}
  }[location.search];
  config.hardwareAcceleration = 'prefer-software';
  config.bitrateMode = "constant";
  config.scalabilityMode = "L1T2";
  config.framerate = 30;
  ENCODER_CONFIG = config;
});

promise_test(async t => {
  let original_w = 800;
  let original_h = 600;
  let original_bitrate = 3_000_000;

  let new_w = 640;
  let new_h = 480;
  let new_bitrate = 2_000_000;

  let next_ts = 0
  let reconf_ts = 0;
  let frames_to_encode = 16;
  let before_reconf_frames = 0;
  let after_reconf_frames = 0;

  let process_video_chunk = function (chunk, metadata) {
    let config = metadata.decoderConfig;
    var data = new Uint8Array(chunk.data);
    assert_greater_than_equal(data.length, 0);
    let after_reconf = (reconf_ts != 0) && (chunk.timestamp >= reconf_ts);
    if (after_reconf) {
      after_reconf_frames++;
      if (config) {
        assert_equals(config.codedWidth, new_w);
        assert_equals(config.codedHeight, new_h);
      }
    } else {
      before_reconf_frames++;
      if (config) {
        assert_equals(config.codedWidth, original_w);
        assert_equals(config.codedHeight, original_h);
      }
    }
  };

  const init = {
    output: (chunk, md) => {
      try {
        process_video_chunk(chunk, md);
      } catch (e) {
        assert_unreached(e.message);
      }
    },
    error: (e) => {
      assert_unreached(e.message);
    },
  };
  const params = {
    ...ENCODER_CONFIG,
    width: original_w,
    height: original_h,
    bitrate: original_bitrate,
  };
  await checkEncoderSupport(t, params);

  let encoder = new VideoEncoder(init);
  encoder.configure(params);

  // Remove this flush after crbug.com/1275789 is fixed
  await encoder.flush();

  // Encode |frames_to_encode| frames with original settings
  for (let i = 0; i < frames_to_encode; i++) {
    var frame = createFrame(original_w, original_h, next_ts++);
    encoder.encode(frame, {});
    frame.close();
  }

  params.width = new_w;
  params.height = new_h;
  params.bitrate = new_bitrate;

  // Reconfigure encoder and run |frames_to_encode| frames with new settings
  encoder.configure(params);
  reconf_ts = next_ts;

  for (let i = 0; i < frames_to_encode; i++) {
    var frame = createFrame(new_w, new_h, next_ts++);
    encoder.encode(frame, {});
    frame.close();
  }

  await encoder.flush();

  // Configure back to original config
  params.width = original_w;
  params.height = original_h;
  params.bitrate = original_bitrate;
  encoder.configure(params);
  await encoder.flush();

  encoder.close();
  assert_equals(before_reconf_frames, frames_to_encode);
  assert_equals(after_reconf_frames, frames_to_encode);
}, "Reconfiguring encoder");
