Add resolution query support for MediaCapabilities Bug: chromium:505034803 Change-Id: Ic8a61b90a68f29c641e354e8879a53e6e29ec6b6 Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/466180 Reviewed-by: Johannes Kron <kron@webrtc.org> Commit-Queue: Johannes Kron <kron@webrtc.org> Reviewed-by: Evan Shrubsole <eshr@webrtc.org> Reviewed-by: Erik Språng <sprang@webrtc.org> Cr-Commit-Position: refs/heads/main@{#47587}
diff --git a/api/video_codecs/BUILD.gn b/api/video_codecs/BUILD.gn index 51da74c..07d343d 100644 --- a/api/video_codecs/BUILD.gn +++ b/api/video_codecs/BUILD.gn
@@ -155,6 +155,7 @@ "../../media:rtc_simulcast_encoder_adapter", "../../rtc_base/system:rtc_export", "../environment", + "../video:resolution", ] } @@ -168,6 +169,7 @@ ":video_codecs_api", "../../modules/video_coding/svc:scalability_mode_util", "../environment", + "../video:resolution", "//third_party/abseil-cpp/absl/algorithm:container", ] }
diff --git a/api/video_codecs/builtin_video_encoder_factory.cc b/api/video_codecs/builtin_video_encoder_factory.cc index bd4bad6..109444f 100644 --- a/api/video_codecs/builtin_video_encoder_factory.cc +++ b/api/video_codecs/builtin_video_encoder_factory.cc
@@ -16,6 +16,7 @@ #include <vector> #include "api/environment/environment.h" +#include "api/video/resolution.h" #include "api/video_codecs/sdp_video_format.h" #include "api/video_codecs/video_encoder.h" #include "api/video_codecs/video_encoder_factory.h" @@ -54,9 +55,10 @@ CodecSupport QueryCodecSupport( const SdpVideoFormat& format, - std::optional<std::string> scalability_mode) const override { - return internal_encoder_factory_->QueryCodecSupport(format, - scalability_mode); + std::optional<std::string> scalability_mode, + std::optional<Resolution> resolution) const override { + return internal_encoder_factory_->QueryCodecSupport( + format, scalability_mode, resolution); } private:
diff --git a/api/video_codecs/test/video_encoder_factory_template_tests.cc b/api/video_codecs/test/video_encoder_factory_template_tests.cc index 9860104..733ef30 100644 --- a/api/video_codecs/test/video_encoder_factory_template_tests.cc +++ b/api/video_codecs/test/video_encoder_factory_template_tests.cc
@@ -90,13 +90,14 @@ TEST(VideoEncoderFactoryTemplate, OneTemplateAdapterCodecSupport) { VideoEncoderFactoryTemplate<FooEncoderTemplateAdapter> factory; - EXPECT_THAT(factory.QueryCodecSupport(kFooSdp, std::nullopt), + EXPECT_THAT(factory.QueryCodecSupport(kFooSdp, std::nullopt, std::nullopt), Field(&CodecSupport::is_supported, true)); - EXPECT_THAT(factory.QueryCodecSupport(kFooSdp, "L1T2"), + EXPECT_THAT(factory.QueryCodecSupport(kFooSdp, "L1T2", std::nullopt), Field(&CodecSupport::is_supported, true)); - EXPECT_THAT(factory.QueryCodecSupport(kFooSdp, "S3T3"), + EXPECT_THAT(factory.QueryCodecSupport(kFooSdp, "S3T3", std::nullopt), Field(&CodecSupport::is_supported, false)); - EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat("FooX"), std::nullopt), + EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat("FooX"), std::nullopt, + std::nullopt), Field(&CodecSupport::is_supported, false)); } @@ -125,19 +126,20 @@ VideoEncoderFactoryTemplate<FooEncoderTemplateAdapter, BarEncoderTemplateAdapter> factory; - EXPECT_THAT(factory.QueryCodecSupport(kFooSdp, std::nullopt), + EXPECT_THAT(factory.QueryCodecSupport(kFooSdp, std::nullopt, std::nullopt), Field(&CodecSupport::is_supported, true)); - EXPECT_THAT(factory.QueryCodecSupport(kFooSdp, "L1T2"), + EXPECT_THAT(factory.QueryCodecSupport(kFooSdp, "L1T2", std::nullopt), Field(&CodecSupport::is_supported, true)); - EXPECT_THAT(factory.QueryCodecSupport(kFooSdp, "S3T3"), + EXPECT_THAT(factory.QueryCodecSupport(kFooSdp, "S3T3", std::nullopt), Field(&CodecSupport::is_supported, false)); - EXPECT_THAT(factory.QueryCodecSupport(kBarLowSdp, std::nullopt), + EXPECT_THAT(factory.QueryCodecSupport(kBarLowSdp, std::nullopt, std::nullopt), Field(&CodecSupport::is_supported, true)); - EXPECT_THAT(factory.QueryCodecSupport(kBarHighSdp, std::nullopt), + EXPECT_THAT( + factory.QueryCodecSupport(kBarHighSdp, std::nullopt, std::nullopt), + Field(&CodecSupport::is_supported, true)); + EXPECT_THAT(factory.QueryCodecSupport(kBarLowSdp, "S2T1", std::nullopt), Field(&CodecSupport::is_supported, true)); - EXPECT_THAT(factory.QueryCodecSupport(kBarLowSdp, "S2T1"), - Field(&CodecSupport::is_supported, true)); - EXPECT_THAT(factory.QueryCodecSupport(kBarHighSdp, "S3T2"), + EXPECT_THAT(factory.QueryCodecSupport(kBarHighSdp, "S3T2", std::nullopt), Field(&CodecSupport::is_supported, false)); }
diff --git a/api/video_codecs/test/video_encoder_factory_unittest.cc b/api/video_codecs/test/video_encoder_factory_unittest.cc index 2480b56..94c8f55 100644 --- a/api/video_codecs/test/video_encoder_factory_unittest.cc +++ b/api/video_codecs/test/video_encoder_factory_unittest.cc
@@ -60,50 +60,57 @@ TEST(VideoEncoderFactoryTest, QueryCodecSupportNoScalabilityMode) { TestVideoEncoderFactory factory({SdpVideoFormat("VP8")}); - EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat("VP8"), std::nullopt), + EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat("VP8"), std::nullopt, + std::nullopt), SupportIs(kSupported)); } TEST(VideoEncoderFactoryTest, QueryCodecSupportUnsupportedFormat) { TestVideoEncoderFactory factory({SdpVideoFormat("VP8")}); - EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat("H264"), std::nullopt), + EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat("H264"), std::nullopt, + std::nullopt), SupportIs(kUnsupported)); } TEST(VideoEncoderFactoryTest, QueryCodecSupportWithScalabilityModeAndEmptyModeList) { TestVideoEncoderFactory factory({SdpVideoFormat("VP8")}); - EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat("VP8"), "L1T2"), - SupportIs(kUnsupported)); + EXPECT_THAT( + factory.QueryCodecSupport(SdpVideoFormat("VP8"), "L1T2", std::nullopt), + SupportIs(kUnsupported)); } TEST(VideoEncoderFactoryTest, QueryCodecSupportWithMatchingScalabilityMode) { SdpVideoFormat format("VP8", {}, {ScalabilityMode::kL1T2}); TestVideoEncoderFactory factory({format}); - EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat("VP8"), "L1T2"), - SupportIs(kSupported)); + EXPECT_THAT( + factory.QueryCodecSupport(SdpVideoFormat("VP8"), "L1T2", std::nullopt), + SupportIs(kSupported)); } TEST(VideoEncoderFactoryTest, QueryCodecSupportWithNonMatchingScalabilityMode) { SdpVideoFormat format("VP8", {}, {ScalabilityMode::kL1T2}); TestVideoEncoderFactory factory({format}); - EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat("VP8"), "L3T3"), - SupportIs(kUnsupported)); + EXPECT_THAT( + factory.QueryCodecSupport(SdpVideoFormat("VP8"), "L3T3", std::nullopt), + SupportIs(kUnsupported)); } TEST(VideoEncoderFactoryTest, QueryCodecSupportWithInvalidScalabilityMode) { SdpVideoFormat format("VP8", {}, {ScalabilityMode::kL1T2}); TestVideoEncoderFactory factory({format}); - EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat("VP8"), "INVALID"), - SupportIs(kUnsupported)); + EXPECT_THAT( + factory.QueryCodecSupport(SdpVideoFormat("VP8"), "INVALID", std::nullopt), + SupportIs(kUnsupported)); } TEST(VideoEncoderFactoryTest, QueryCodecSupportScalabilityModeUnsupportedFormat) { SdpVideoFormat format("VP8", {}, {ScalabilityMode::kL1T2}); TestVideoEncoderFactory factory({format}); - EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat("H264"), "L1T2"), - SupportIs(kUnsupported)); + EXPECT_THAT( + factory.QueryCodecSupport(SdpVideoFormat("H264"), "L1T2", std::nullopt), + SupportIs(kUnsupported)); } TEST(VideoEncoderFactoryTest, @@ -115,10 +122,12 @@ TestVideoEncoderFactory factory({vp9_profile0, vp9_profile2}); EXPECT_THAT(factory.QueryCodecSupport( - SdpVideoFormat("VP9", {{kVP9FmtpProfileId, "0"}}), "L3T3"), + SdpVideoFormat("VP9", {{kVP9FmtpProfileId, "0"}}), "L3T3", + std::nullopt), SupportIs(kSupported)); EXPECT_THAT(factory.QueryCodecSupport( - SdpVideoFormat("VP9", {{kVP9FmtpProfileId, "2"}}), "L3T3"), + SdpVideoFormat("VP9", {{kVP9FmtpProfileId, "2"}}), "L3T3", + std::nullopt), SupportIs(kUnsupported)); }
diff --git a/api/video_codecs/video_decoder_factory.cc b/api/video_codecs/video_decoder_factory.cc index 20e9fff..c0fc1b2 100644 --- a/api/video_codecs/video_decoder_factory.cc +++ b/api/video_codecs/video_decoder_factory.cc
@@ -10,13 +10,17 @@ #include "api/video_codecs/video_decoder_factory.h" +#include <optional> + +#include "api/video/resolution.h" #include "api/video_codecs/sdp_video_format.h" namespace webrtc { VideoDecoderFactory::CodecSupport VideoDecoderFactory::QueryCodecSupport( const SdpVideoFormat& format, - bool reference_scaling) const { + bool reference_scaling, + std::optional<Resolution> resolution) const { // Default implementation, query for supported formats and check if the // specified format is supported. Returns false if `reference_scaling` is // true.
diff --git a/api/video_codecs/video_decoder_factory.h b/api/video_codecs/video_decoder_factory.h index 89433e0..4c9c44d 100644 --- a/api/video_codecs/video_decoder_factory.h +++ b/api/video_codecs/video_decoder_factory.h
@@ -12,9 +12,11 @@ #define API_VIDEO_CODECS_VIDEO_DECODER_FACTORY_H_ #include <memory> +#include <optional> #include <vector> #include "api/environment/environment.h" +#include "api/video/resolution.h" #include "api/video_codecs/sdp_video_format.h" #include "api/video_codecs/video_decoder.h" #include "rtc_base/system/rtc_export.h" @@ -36,6 +38,13 @@ // for signaling etc. virtual std::vector<SdpVideoFormat> GetSupportedFormats() const = 0; + // TODO(crbug.com/505034803): Deprecate once all clients are switched. + // [[deprecated("Use the 3-parameter version instead")]] + virtual CodecSupport QueryCodecSupport(const SdpVideoFormat& format, + bool reference_scaling) const { + return QueryCodecSupport(format, reference_scaling, std::nullopt); + } + // Query whether the specifed format is supported or not and if it will be // power efficient, which is currently interpreted as if there is support for // hardware acceleration. @@ -44,10 +53,16 @@ // needed is if the video stream is produced with a scalability mode that has // a dependency between the spatial layers. See // https://w3c.github.io/webrtc-svc/#scalabilitymodes* for a specification of - // different scalabilty modes. NOTE: QueryCodecSupport is currently an - // experimental feature that is subject to change without notice. - virtual CodecSupport QueryCodecSupport(const SdpVideoFormat& format, - bool reference_scaling) const; + // different scalabilty modes. + // The parameter `resolution` may optionally be provided to require the format + // has decoding support up to the provided resolution to mark it as supported. + // + // NOTE: QueryCodecSupport is currently an experimental feature that is + // subject to change without notice. + virtual CodecSupport QueryCodecSupport( + const SdpVideoFormat& format, + bool reference_scaling, + std::optional<Resolution> resolution) const; // Creates a VideoDecoder for the specified `format`. virtual std::unique_ptr<VideoDecoder> Create(
diff --git a/api/video_codecs/video_encoder_factory.cc b/api/video_codecs/video_encoder_factory.cc index bee7ae2..e351323 100644 --- a/api/video_codecs/video_encoder_factory.cc +++ b/api/video_codecs/video_encoder_factory.cc
@@ -14,6 +14,7 @@ #include <string> #include "absl/algorithm/container.h" +#include "api/video/resolution.h" #include "api/video_codecs/scalability_mode.h" #include "api/video_codecs/sdp_video_format.h" @@ -21,7 +22,8 @@ VideoEncoderFactory::CodecSupport VideoEncoderFactory::QueryCodecSupport( const SdpVideoFormat& format, - std::optional<std::string> scalability_mode) const { + std::optional<std::string> scalability_mode, + std::optional<Resolution> resolution) const { // Default implementation, query for supported formats and check if the // specified format is supported. If a scalability mode is specified, check // that it is present in the matching format's scalability_modes list.
diff --git a/api/video_codecs/video_encoder_factory.h b/api/video_codecs/video_encoder_factory.h index a5cf3db..a86911c 100644 --- a/api/video_codecs/video_encoder_factory.h +++ b/api/video_codecs/video_encoder_factory.h
@@ -20,6 +20,7 @@ #include "api/ref_counted_base.h" #include "api/units/data_rate.h" #include "api/video/render_resolution.h" +#include "api/video/resolution.h" #include "api/video_codecs/sdp_video_format.h" #include "api/video_codecs/video_encoder.h" #include "rtc_base/system/rtc_export.h" @@ -81,16 +82,28 @@ return GetSupportedFormats(); } + // TODO(crbug.com/505034803): Deprecate once all clients are switched. + // [[deprecated("Use the 3-parameter version instead")]] + virtual CodecSupport QueryCodecSupport( + const SdpVideoFormat& format, + std::optional<std::string> scalability_mode) const { + return QueryCodecSupport(format, scalability_mode, std::nullopt); + } + // Query whether the specifed format is supported or not and if it will be // power efficient, which is currently interpreted as if there is support for // hardware acceleration. // See https://w3c.github.io/webrtc-svc/#scalabilitymodes* for a specification // of valid values for `scalability_mode`. + // The parameter `resolution` may optionally be provided to require the format + // has encoding support up to the provided resolution to mark it as supported. + // // NOTE: QueryCodecSupport is currently an experimental feature that is // subject to change without notice. virtual CodecSupport QueryCodecSupport( const SdpVideoFormat& format, - std::optional<std::string> scalability_mode) const; + std::optional<std::string> scalability_mode, + std::optional<Resolution> resolution) const; // Creates a VideoEncoder for the specified format. virtual std::unique_ptr<VideoEncoder> Create(
diff --git a/api/video_codecs/video_encoder_factory_template.h b/api/video_codecs/video_encoder_factory_template.h index 938a73b..037cf7e 100644 --- a/api/video_codecs/video_encoder_factory_template.h +++ b/api/video_codecs/video_encoder_factory_template.h
@@ -19,6 +19,7 @@ #include "absl/algorithm/container.h" #include "api/environment/environment.h" +#include "api/video/resolution.h" #include "api/video_codecs/scalability_mode.h" #include "api/video_codecs/sdp_video_format.h" #include "api/video_codecs/video_encoder.h" @@ -50,6 +51,7 @@ template <typename... Ts> class VideoEncoderFactoryTemplate : public VideoEncoderFactory { public: + using VideoEncoderFactory::QueryCodecSupport; std::vector<SdpVideoFormat> GetSupportedFormats() const override { return GetSupportedFormatsInternal<Ts...>(); } @@ -70,8 +72,10 @@ CodecSupport QueryCodecSupport( const SdpVideoFormat& format, - std::optional<std::string> scalability_mode) const override { - return QueryCodecSupportInternal<Ts...>(format, scalability_mode); + std::optional<std::string> scalability_mode, + std::optional<Resolution> resolution) const override { + return QueryCodecSupportInternal<Ts...>(format, scalability_mode, + resolution); } private: @@ -130,13 +134,15 @@ template <typename V, typename... Vs> CodecSupport QueryCodecSupportInternal( const SdpVideoFormat& format, - const std::optional<std::string>& scalability_mode) const { + const std::optional<std::string>& scalability_mode, + const std::optional<Resolution>& resolution) const { if (IsFormatInList(format, V::SupportedFormats())) { return {.is_supported = IsScalabilityModeSupported<V>(scalability_mode)}; } if constexpr (sizeof...(Vs) > 0) { - return QueryCodecSupportInternal<Vs...>(format, scalability_mode); + return QueryCodecSupportInternal<Vs...>(format, scalability_mode, + resolution); } return {.is_supported = false};
diff --git a/media/BUILD.gn b/media/BUILD.gn index dcdb269..785318b 100644 --- a/media/BUILD.gn +++ b/media/BUILD.gn
@@ -533,6 +533,7 @@ ":rtc_simulcast_encoder_adapter", "../api/environment", "../api/video:encoded_image", + "../api/video:resolution", "../api/video:video_bitrate_allocation", "../api/video:video_frame", "../api/video:video_rtp_headers", @@ -847,6 +848,7 @@ "../api/units:timestamp", "../api/video:encoded_image", "../api/video:recordable_encoded_frame", + "../api/video:resolution", "../api/video:video_bitrate_allocation", "../api/video:video_bitrate_allocator_factory", "../api/video:video_frame",
diff --git a/media/engine/fake_webrtc_video_engine.cc b/media/engine/fake_webrtc_video_engine.cc index c240915..2ba4217 100644 --- a/media/engine/fake_webrtc_video_engine.cc +++ b/media/engine/fake_webrtc_video_engine.cc
@@ -21,6 +21,7 @@ #include "api/fec_controller_override.h" #include "api/units/time_delta.h" #include "api/video/encoded_image.h" +#include "api/video/resolution.h" #include "api/video/video_frame.h" #include "api/video/video_frame_type.h" #include "api/video_codecs/scalability_mode.h" @@ -239,7 +240,8 @@ VideoEncoderFactory::CodecSupport FakeWebRtcVideoEncoderFactory::QueryCodecSupport( const SdpVideoFormat& format, - std::optional<std::string> scalability_mode) const { + std::optional<std::string> scalability_mode, + std::optional<Resolution> resolution) const { std::vector<SdpVideoFormat> supported_formats; for (const auto& f : formats_) { if (format.IsSameCodec(f))
diff --git a/media/engine/fake_webrtc_video_engine.h b/media/engine/fake_webrtc_video_engine.h index ea5995d..fb344a3 100644 --- a/media/engine/fake_webrtc_video_engine.h +++ b/media/engine/fake_webrtc_video_engine.h
@@ -22,6 +22,7 @@ #include "api/environment/environment.h" #include "api/fec_controller_override.h" #include "api/video/encoded_image.h" +#include "api/video/resolution.h" #include "api/video/video_frame.h" #include "api/video/video_frame_type.h" #include "api/video_codecs/scalability_mode.h" @@ -114,10 +115,12 @@ public: FakeWebRtcVideoEncoderFactory(); + using VideoEncoderFactory::QueryCodecSupport; std::vector<SdpVideoFormat> GetSupportedFormats() const override; VideoEncoderFactory::CodecSupport QueryCodecSupport( const SdpVideoFormat& format, - std::optional<std::string> scalability_mode) const override; + std::optional<std::string> scalability_mode, + std::optional<Resolution> resolution) const override; std::unique_ptr<VideoEncoder> Create(const Environment& env, const SdpVideoFormat& format) override;
diff --git a/media/engine/internal_decoder_factory.cc b/media/engine/internal_decoder_factory.cc index ed05e71..111ca43 100644 --- a/media/engine/internal_decoder_factory.cc +++ b/media/engine/internal_decoder_factory.cc
@@ -11,10 +11,12 @@ #include "media/engine/internal_decoder_factory.h" #include <memory> +#include <optional> #include <vector> #include "absl/strings/match.h" #include "api/environment/environment.h" +#include "api/video/resolution.h" #include "api/video/video_codec_type.h" #include "api/video_codecs/h264_profile_level_id.h" #include "api/video_codecs/sdp_video_format.h" @@ -65,7 +67,8 @@ VideoDecoderFactory::CodecSupport InternalDecoderFactory::QueryCodecSupport( const SdpVideoFormat& format, - bool reference_scaling) const { + bool reference_scaling, + std::optional<Resolution> resolution) const { // Query for supported formats and check if the specified format is supported. // Return unsupported if an invalid combination of format and // reference_scaling is specified. @@ -98,7 +101,7 @@ std::unique_ptr<VideoDecoder> InternalDecoderFactory::Create( const Environment& env, const SdpVideoFormat& format) { - if (!QueryCodecSupport(format, false).is_supported) { + if (!QueryCodecSupport(format, false, std::nullopt).is_supported) { RTC_LOG(LS_WARNING) << "Trying to create decoder for unsupported format. " << format.ToString(); return nullptr;
diff --git a/media/engine/internal_decoder_factory.h b/media/engine/internal_decoder_factory.h index a2cd362..ab07c21 100644 --- a/media/engine/internal_decoder_factory.h +++ b/media/engine/internal_decoder_factory.h
@@ -12,9 +12,11 @@ #define MEDIA_ENGINE_INTERNAL_DECODER_FACTORY_H_ #include <memory> +#include <optional> #include <vector> #include "api/environment/environment.h" +#include "api/video/resolution.h" #include "api/video_codecs/sdp_video_format.h" #include "api/video_codecs/video_decoder.h" #include "api/video_codecs/video_decoder_factory.h" @@ -24,9 +26,12 @@ class RTC_EXPORT InternalDecoderFactory : public VideoDecoderFactory { public: + using VideoDecoderFactory::QueryCodecSupport; std::vector<SdpVideoFormat> GetSupportedFormats() const override; - CodecSupport QueryCodecSupport(const SdpVideoFormat& format, - bool reference_scaling) const override; + CodecSupport QueryCodecSupport( + const SdpVideoFormat& format, + bool reference_scaling, + std::optional<Resolution> resolution) const override; std::unique_ptr<VideoDecoder> Create(const Environment& env, const SdpVideoFormat& format) override; };
diff --git a/media/engine/internal_decoder_factory_unittest.cc b/media/engine/internal_decoder_factory_unittest.cc index b10cc47..6f4a55f 100644 --- a/media/engine/internal_decoder_factory_unittest.cc +++ b/media/engine/internal_decoder_factory_unittest.cc
@@ -11,6 +11,7 @@ #include "media/engine/internal_decoder_factory.h" #include <memory> +#include <optional> #include "api/environment/environment.h" #include "api/environment/environment_factory.h" @@ -129,21 +130,26 @@ TEST(InternalDecoderFactoryTest, QueryCodecSupportNoReferenceScaling) { InternalDecoderFactory factory; EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat::VP8(), - /*reference_scaling=*/false), + /*reference_scaling=*/false, + /*resolution=*/std::nullopt), Support(kSupported)); EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat::VP9Profile0(), - /*reference_scaling=*/false), + /*reference_scaling=*/false, + /*resolution=*/std::nullopt), Support(kVp9Enabled ? kSupported : kUnsupported)); EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat::VP9Profile1(), - /*reference_scaling=*/false), + /*reference_scaling=*/false, + /*resolution=*/std::nullopt), Support(kVp9Enabled ? kSupported : kUnsupported)); #if defined(RTC_DAV1D_IN_INTERNAL_DECODER_FACTORY) EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat::AV1Profile0(), - /*reference_scaling=*/false), + /*reference_scaling=*/false, + /*resolution=*/std::nullopt), Support(kSupported)); EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat::AV1Profile1(), - /*reference_scaling=*/false), + /*reference_scaling=*/false, + /*resolution=*/std::nullopt), Support(kSupported)); #endif @@ -159,34 +165,40 @@ // subsets of High Predictive 4:4:4. EXPECT_THAT( factory.QueryCodecSupport( - SdpVideoFormat("H264", {{"profile-level-id", "42e01f"}}), false), + SdpVideoFormat("H264", {{"profile-level-id", "42e01f"}}), false, + /*resolution=*/std::nullopt), Support(h264_support)); EXPECT_THAT( factory.QueryCodecSupport( - SdpVideoFormat("H264", {{"profile-level-id", "42001f"}}), false), + SdpVideoFormat("H264", {{"profile-level-id", "42001f"}}), false, + /*resolution=*/std::nullopt), Support(h264_support)); EXPECT_THAT( factory.QueryCodecSupport( - SdpVideoFormat("H264", {{"profile-level-id", "4d001f"}}), false), + SdpVideoFormat("H264", {{"profile-level-id", "4d001f"}}), false, + /*resolution=*/std::nullopt), Support(h264_support)); EXPECT_THAT( factory.QueryCodecSupport( - SdpVideoFormat("H264", {{"profile-level-id", "640c1f"}}), false), + SdpVideoFormat("H264", {{"profile-level-id", "640c1f"}}), false, + /*resolution=*/std::nullopt), Support(h264_support)); EXPECT_THAT( factory.QueryCodecSupport( - SdpVideoFormat("H264", {{"profile-level-id", "64001f"}}), false), + SdpVideoFormat("H264", {{"profile-level-id", "64001f"}}), false, + /*resolution=*/std::nullopt), Support(h264_support)); EXPECT_THAT( factory.QueryCodecSupport( - SdpVideoFormat("H264", {{"profile-level-id", "ff0000"}}), false), + SdpVideoFormat("H264", {{"profile-level-id", "ff0000"}}), false, + /*resolution=*/std::nullopt), Support(kUnsupported)); EXPECT_THAT(factory.QueryCodecSupport( SdpVideoFormat("H264", {{"profile-level-id", "42e01f"}, {"packetization-mode", "2"}}), - false), + false, /*resolution=*/std::nullopt), Support(kUnsupported)); } @@ -194,20 +206,24 @@ InternalDecoderFactory factory; // VP9 and AV1 support for spatial layers. EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat::VP9Profile0(), - /*reference_scaling=*/true), + /*reference_scaling=*/true, + /*resolution=*/std::nullopt), Support(kVp9Enabled ? kSupported : kUnsupported)); #if defined(RTC_DAV1D_IN_INTERNAL_DECODER_FACTORY) EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat::AV1Profile0(), - /*reference_scaling=*/true), + /*reference_scaling=*/true, + /*resolution=*/std::nullopt), Support(kSupported)); #endif // Invalid config even though VP8 and H264 are supported. EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat::H264(), - /*reference_scaling=*/true), + /*reference_scaling=*/true, + /*resolution=*/std::nullopt), Support(kUnsupported)); EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat::VP8(), - /*reference_scaling=*/true), + /*reference_scaling=*/true, + /*resolution=*/std::nullopt), Support(kUnsupported)); }
diff --git a/media/engine/internal_encoder_factory.cc b/media/engine/internal_encoder_factory.cc index 43992b3..acf38e7 100644 --- a/media/engine/internal_encoder_factory.cc +++ b/media/engine/internal_encoder_factory.cc
@@ -16,6 +16,7 @@ #include <vector> #include "api/environment/environment.h" +#include "api/video/resolution.h" #include "api/video_codecs/sdp_video_format.h" #include "api/video_codecs/video_encoder.h" #include "api/video_codecs/video_encoder_factory.h" @@ -57,11 +58,13 @@ VideoEncoderFactory::CodecSupport InternalEncoderFactory::QueryCodecSupport( const SdpVideoFormat& format, - std::optional<std::string> scalability_mode) const { + std::optional<std::string> scalability_mode, + std::optional<Resolution> resolution) const { auto original_format = FuzzyMatchSdpVideoFormat(Factory().GetSupportedFormats(), format); return original_format - ? Factory().QueryCodecSupport(*original_format, scalability_mode) + ? Factory().QueryCodecSupport(*original_format, scalability_mode, + resolution) : VideoEncoderFactory::CodecSupport{.is_supported = false}; }
diff --git a/media/engine/internal_encoder_factory.h b/media/engine/internal_encoder_factory.h index 01c5ef7..dfe69cc 100644 --- a/media/engine/internal_encoder_factory.h +++ b/media/engine/internal_encoder_factory.h
@@ -17,6 +17,7 @@ #include <vector> #include "api/environment/environment.h" +#include "api/video/resolution.h" #include "api/video_codecs/sdp_video_format.h" #include "api/video_codecs/video_encoder.h" #include "api/video_codecs/video_encoder_factory.h" @@ -25,10 +26,12 @@ namespace webrtc { class RTC_EXPORT InternalEncoderFactory : public VideoEncoderFactory { public: + using VideoEncoderFactory::QueryCodecSupport; std::vector<SdpVideoFormat> GetSupportedFormats() const override; CodecSupport QueryCodecSupport( const SdpVideoFormat& format, - std::optional<std::string> scalability_mode) const override; + std::optional<std::string> scalability_mode, + std::optional<Resolution> resolution) const override; std::unique_ptr<VideoEncoder> Create(const Environment& env, const SdpVideoFormat& format) override; };
diff --git a/media/engine/internal_encoder_factory_unittest.cc b/media/engine/internal_encoder_factory_unittest.cc index e70419a..dbe8a49 100644 --- a/media/engine/internal_encoder_factory_unittest.cc +++ b/media/engine/internal_encoder_factory_unittest.cc
@@ -95,20 +95,25 @@ TEST(InternalEncoderFactoryTest, QueryCodecSupportWithScalabilityMode) { InternalEncoderFactory factory; // VP8 and VP9 supported for singles spatial layers. - EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat::VP8(), "L1T2"), - Support(kSupported)); - EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat::VP9Profile0(), "L1T3"), + EXPECT_THAT( + factory.QueryCodecSupport(SdpVideoFormat::VP8(), "L1T2", std::nullopt), + Support(kSupported)); + EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat::VP9Profile0(), "L1T3", + std::nullopt), Support(kVp9Enabled ? kSupported : kUnsupported)); // VP9 support for spatial layers. - EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat::VP9Profile0(), "L3T3"), + EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat::VP9Profile0(), "L3T3", + std::nullopt), Support(kVp9Enabled ? kSupported : kUnsupported)); // Invalid scalability modes even though VP8 and H264 are supported. - EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat::H264(), "L2T2"), - Support(kUnsupported)); - EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat::VP8(), "L3T3"), - Support(kUnsupported)); + EXPECT_THAT( + factory.QueryCodecSupport(SdpVideoFormat::H264(), "L2T2", std::nullopt), + Support(kUnsupported)); + EXPECT_THAT( + factory.QueryCodecSupport(SdpVideoFormat::VP8(), "L3T3", std::nullopt), + Support(kUnsupported)); } #if defined(RTC_USE_LIBAOM_AV1_ENCODER) @@ -123,23 +128,27 @@ TEST(InternalEncoderFactoryTest, QueryCodecSupportNoScalabilityModeAv1) { InternalEncoderFactory factory; EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat::AV1Profile0(), - /*scalability_mode=*/std::nullopt), + /*scalability_mode=*/std::nullopt, + std::nullopt), Support(kSupported)); } TEST(InternalEncoderFactoryTest, QueryCodecSupportNoScalabilityMode) { InternalEncoderFactory factory; EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat::VP8(), - /*scalability_mode=*/std::nullopt), + /*scalability_mode=*/std::nullopt, + std::nullopt), Support(kSupported)); EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat::VP9Profile0(), - /*scalability_mode=*/std::nullopt), + /*scalability_mode=*/std::nullopt, + std::nullopt), Support(kVp9Enabled ? kSupported : kUnsupported)); } TEST(InternalEncoderFactoryTest, QueryCodecSupportWithScalabilityModeAv1) { InternalEncoderFactory factory; - EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat::AV1Profile0(), "L2T1"), + EXPECT_THAT(factory.QueryCodecSupport(SdpVideoFormat::AV1Profile0(), "L2T1", + std::nullopt), Support(kSupported)); } #endif // defined(RTC_USE_LIBAOM_AV1_ENCODER)
diff --git a/media/engine/webrtc_video_engine.cc b/media/engine/webrtc_video_engine.cc index 1b81101..9ae3524 100644 --- a/media/engine/webrtc_video_engine.cc +++ b/media/engine/webrtc_video_engine.cc
@@ -495,7 +495,7 @@ const VideoSendStream::Config& config) { return config.encoder_settings.encoder_factory ->QueryCodecSupport(SdpVideoFormat(codec.name, codec.params), - scalability_mode) + scalability_mode, std::nullopt) .is_supported; }
diff --git a/modules/video_coding/codecs/test/video_codec_test.cc b/modules/video_coding/codecs/test/video_codec_test.cc index 9cbfd71..e020caf 100644 --- a/modules/video_coding/codecs/test/video_codec_test.cc +++ b/modules/video_coding/codecs/test/video_codec_test.cc
@@ -204,7 +204,8 @@ CreateEncoderFactory(encoder_impl); if (!encoder_factory ->QueryCodecSupport(sdp_video_format, - /*scalability_mode=*/std::nullopt) + /*scalability_mode=*/std::nullopt, + /*resolution=*/std::nullopt) .is_supported) { RTC_LOG(LS_WARNING) << "No " << encoder_impl << " encoder for video format " << sdp_video_format.ToString(); @@ -215,7 +216,8 @@ CreateDecoderFactory(decoder_impl); if (!decoder_factory ->QueryCodecSupport(sdp_video_format, - /*reference_scaling=*/false) + /*reference_scaling=*/false, + /*resolution=*/std::nullopt) .is_supported) { RTC_LOG(LS_WARNING) << "No " << decoder_impl << " decoder for video format " << sdp_video_format.ToString() @@ -225,7 +227,8 @@ decoder_factory = CreateDecoderFactory("builtin"); if (!decoder_factory ->QueryCodecSupport(sdp_video_format, - /*reference_scaling=*/false) + /*reference_scaling=*/false, + /*resolution=*/std::nullopt) .is_supported) { RTC_LOG(LS_WARNING) << "No " << decoder_impl << " decoder for video format " @@ -275,7 +278,8 @@ CreateEncoderFactory(encoder_impl); if (!encoder_factory ->QueryCodecSupport(sdp_video_format, - /*scalability_mode=*/std::nullopt) + /*scalability_mode=*/std::nullopt, + /*resolution=*/std::nullopt) .is_supported) { RTC_LOG(LS_WARNING) << "No encoder for video format " << sdp_video_format.ToString();
diff --git a/pc/test/peer_connection_test_wrapper.cc b/pc/test/peer_connection_test_wrapper.cc index 0b9a404..0360f4a 100644 --- a/pc/test/peer_connection_test_wrapper.cc +++ b/pc/test/peer_connection_test_wrapper.cc
@@ -97,10 +97,12 @@ return nullptr; } + using VideoEncoderFactory::QueryCodecSupport; CodecSupport QueryCodecSupport( const SdpVideoFormat& format, - std::optional<std::string> scalability_mode) const override { - return factory_.QueryCodecSupport(format, scalability_mode); + std::optional<std::string> scalability_mode, + std::optional<Resolution> resolution) const override { + return factory_.QueryCodecSupport(format, scalability_mode, resolution); } private:
diff --git a/rtc_tools/video_encoder/video_encoder.cc b/rtc_tools/video_encoder/video_encoder.cc index fbcb84f..91cb8bd 100644 --- a/rtc_tools/video_encoder/video_encoder.cc +++ b/rtc_tools/video_encoder/video_encoder.cc
@@ -392,7 +392,8 @@ // VP9 profile2 is not implemented at this moment. VideoEncoderFactory::CodecSupport support = builtin_video_encoder_factory_->QueryCodecSupport( - SdpVideoFormat(video_codec_string), scalability_mode_string); + SdpVideoFormat(video_codec_string), scalability_mode_string, + /*resolution=*/std::nullopt); return support.is_supported; }
diff --git a/sdk/objc/native/src/objc_video_encoder_factory.h b/sdk/objc/native/src/objc_video_encoder_factory.h index a42f758..39c7571 100644 --- a/sdk/objc/native/src/objc_video_encoder_factory.h +++ b/sdk/objc/native/src/objc_video_encoder_factory.h
@@ -33,11 +33,13 @@ id<RTC_OBJC_TYPE(RTCVideoEncoderFactory)> wrapped_encoder_factory() const; + using VideoEncoderFactory::QueryCodecSupport; std::vector<SdpVideoFormat> GetSupportedFormats() const override; std::vector<SdpVideoFormat> GetImplementations() const override; CodecSupport QueryCodecSupport( const SdpVideoFormat& format, - std::optional<std::string> scalability_mode) const override; + std::optional<std::string> scalability_mode, + std::optional<Resolution> resolution) const override; std::unique_ptr<VideoEncoder> Create(const Environment& env, const SdpVideoFormat& format) override; std::unique_ptr<EncoderSelectorInterface> GetEncoderSelector() const override;
diff --git a/sdk/objc/native/src/objc_video_encoder_factory.mm b/sdk/objc/native/src/objc_video_encoder_factory.mm index a8ba2db..ba2c5b0 100644 --- a/sdk/objc/native/src/objc_video_encoder_factory.mm +++ b/sdk/objc/native/src/objc_video_encoder_factory.mm
@@ -212,7 +212,8 @@ VideoEncoderFactory::CodecSupport ObjCVideoEncoderFactory::QueryCodecSupport( const SdpVideoFormat &format, - std::optional<std::string> scalability_mode) const { + std::optional<std::string> scalability_mode, + std::optional<Resolution> resolution) const { if ([encoder_factory_ respondsToSelector:@selector(queryCodecSupport: scalabilityMode:)]) { RTC_OBJC_TYPE(RTCVideoCodecInfo) *info = [[RTC_OBJC_TYPE(RTCVideoCodecInfo) @@ -229,7 +230,8 @@ } // Use default implementation. - return VideoEncoderFactory::QueryCodecSupport(format, scalability_mode); + return VideoEncoderFactory::QueryCodecSupport( + format, scalability_mode, resolution); } std::unique_ptr<VideoEncoder> ObjCVideoEncoderFactory::Create(
diff --git a/test/pc/e2e/analyzer/video/BUILD.gn b/test/pc/e2e/analyzer/video/BUILD.gn index c830de2..96b5faf 100644 --- a/test/pc/e2e/analyzer/video/BUILD.gn +++ b/test/pc/e2e/analyzer/video/BUILD.gn
@@ -161,6 +161,7 @@ "../../../../../api/environment", "../../../../../api/test/pclf:media_configuration", "../../../../../api/video:encoded_image", + "../../../../../api/video:resolution", "../../../../../api/video:video_bitrate_allocation", "../../../../../api/video:video_codec_constants", "../../../../../api/video:video_frame",
diff --git a/test/pc/e2e/analyzer/video/quality_analyzing_video_encoder.cc b/test/pc/e2e/analyzer/video/quality_analyzing_video_encoder.cc index 4b82660..9c26b0b 100644 --- a/test/pc/e2e/analyzer/video/quality_analyzing_video_encoder.cc +++ b/test/pc/e2e/analyzer/video/quality_analyzing_video_encoder.cc
@@ -26,6 +26,7 @@ #include "api/fec_controller_override.h" #include "api/test/video_quality_analyzer_interface.h" #include "api/video/encoded_image.h" +#include "api/video/resolution.h" #include "api/video/video_bitrate_allocation.h" #include "api/video/video_codec_constants.h" #include "api/video/video_codec_type.h" @@ -422,8 +423,9 @@ VideoEncoderFactory::CodecSupport QualityAnalyzingVideoEncoderFactory::QueryCodecSupport( const SdpVideoFormat& format, - std::optional<std::string> scalability_mode) const { - return delegate_->QueryCodecSupport(format, scalability_mode); + std::optional<std::string> scalability_mode, + std::optional<Resolution> resolution) const { + return delegate_->QueryCodecSupport(format, scalability_mode, resolution); } std::unique_ptr<VideoEncoder> QualityAnalyzingVideoEncoderFactory::Create(
diff --git a/test/pc/e2e/analyzer/video/quality_analyzing_video_encoder.h b/test/pc/e2e/analyzer/video/quality_analyzing_video_encoder.h index 0094d22..e797b6a 100644 --- a/test/pc/e2e/analyzer/video/quality_analyzing_video_encoder.h +++ b/test/pc/e2e/analyzer/video/quality_analyzing_video_encoder.h
@@ -26,6 +26,7 @@ #include "api/test/pclf/media_configuration.h" #include "api/test/video_quality_analyzer_interface.h" #include "api/video/encoded_image.h" +#include "api/video/resolution.h" #include "api/video/video_bitrate_allocation.h" #include "api/video/video_frame.h" #include "api/video/video_frame_type.h" @@ -184,10 +185,12 @@ ~QualityAnalyzingVideoEncoderFactory() override; // Methods of VideoEncoderFactory interface. + using VideoEncoderFactory::QueryCodecSupport; std::vector<SdpVideoFormat> GetSupportedFormats() const override; VideoEncoderFactory::CodecSupport QueryCodecSupport( const SdpVideoFormat& format, - std::optional<std::string> scalability_mode) const override; + std::optional<std::string> scalability_mode, + std::optional<Resolution> resolution) const override; std::unique_ptr<VideoEncoder> Create(const Environment& env, const SdpVideoFormat& format) override;