Adds support for frame rate control in FrameGeneratorCapturer.
Bug: webrtc:9510
Change-Id: Idb062978a856ead994fce7e72402effcd8c719cf
Reviewed-on: https://webrtc-review.googlesource.com/95148
Reviewed-by: Erik Språng <sprang@webrtc.org>
Commit-Queue: Sebastian Jansson <srte@webrtc.org>
Cr-Commit-Position: refs/heads/master@{#24499}
diff --git a/test/frame_generator_capturer.cc b/test/frame_generator_capturer.cc
index 6a58a3f..87e9bb3 100644
--- a/test/frame_generator_capturer.cc
+++ b/test/frame_generator_capturer.cc
@@ -143,7 +143,8 @@
sink_(nullptr),
sink_wants_observer_(nullptr),
frame_generator_(std::move(frame_generator)),
- target_fps_(target_fps),
+ source_fps_(target_fps),
+ target_capture_fps_(target_fps),
first_frame_capture_time_(-1),
task_queue_("FrameGenCapQ", rtc::TaskQueue::Priority::HIGH) {
RTC_DCHECK(frame_generator_);
@@ -178,6 +179,12 @@
rtc::CritScope cs(&lock_);
if (sending_) {
VideoFrame* frame = frame_generator_->NextFrame();
+ // TODO(srte): Use more advanced frame rate control to allow arbritrary
+ // fractions.
+ int decimation =
+ std::round(static_cast<double>(source_fps_) / target_capture_fps_);
+ for (int i = 1; i < decimation; ++i)
+ frame = frame_generator_->NextFrame();
frame->set_timestamp_us(clock_->TimeInMicroseconds());
frame->set_ntp_time_ms(clock_->CurrentNtpInMilliseconds());
frame->set_rotation(fake_rotation_);
@@ -208,6 +215,24 @@
frame_generator_->ChangeResolution(width, height);
}
+void FrameGeneratorCapturer::ChangeFramerate(int target_framerate) {
+ rtc::CritScope cs(&lock_);
+ RTC_CHECK(target_capture_fps_ > 0);
+ if (target_framerate > source_fps_)
+ RTC_LOG(LS_WARNING) << "Target framerate clamped from " << target_framerate
+ << " to " << source_fps_;
+ if (source_fps_ % target_capture_fps_ != 0) {
+ int decimation =
+ std::round(static_cast<double>(source_fps_) / target_capture_fps_);
+ int effective_rate = target_capture_fps_ / decimation;
+ RTC_LOG(LS_WARNING) << "Target framerate, " << target_framerate
+ << ", is an uneven fraction of the source rate, "
+ << source_fps_
+ << ". The framerate will be :" << effective_rate;
+ }
+ target_capture_fps_ = std::min(source_fps_, target_framerate);
+}
+
void FrameGeneratorCapturer::SetSinkWantsObserver(SinkWantsObserver* observer) {
rtc::CritScope cs(&lock_);
RTC_DCHECK(!sink_wants_observer_);
@@ -230,7 +255,7 @@
TestVideoCapturer::AddOrUpdateSink(sink, resolution_wants);
// Ignore any requests for framerate higher than initially configured.
- if (wants.max_framerate_fps < target_fps_) {
+ if (wants.max_framerate_fps < target_capture_fps_) {
wanted_fps_.emplace(wants.max_framerate_fps);
} else {
wanted_fps_.reset();
@@ -253,9 +278,9 @@
int FrameGeneratorCapturer::GetCurrentConfiguredFramerate() {
rtc::CritScope cs(&lock_);
- if (wanted_fps_ && *wanted_fps_ < target_fps_)
+ if (wanted_fps_ && *wanted_fps_ < target_capture_fps_)
return *wanted_fps_;
- return target_fps_;
+ return target_capture_fps_;
}
} // namespace test
diff --git a/test/frame_generator_capturer.h b/test/frame_generator_capturer.h
index ac32fa4..6b2ed69 100644
--- a/test/frame_generator_capturer.h
+++ b/test/frame_generator_capturer.h
@@ -64,6 +64,7 @@
void Start() override;
void Stop() override;
void ChangeResolution(size_t width, size_t height);
+ void ChangeFramerate(int target_framerate);
void SetSinkWantsObserver(SinkWantsObserver* observer);
@@ -96,7 +97,8 @@
rtc::CriticalSection lock_;
std::unique_ptr<FrameGenerator> frame_generator_;
- int target_fps_ RTC_GUARDED_BY(&lock_);
+ int source_fps_ RTC_GUARDED_BY(&lock_);
+ int target_capture_fps_ RTC_GUARDED_BY(&lock_);
absl::optional<int> wanted_fps_ RTC_GUARDED_BY(&lock_);
VideoRotation fake_rotation_ = kVideoRotation_0;