xref: /aosp_15_r20/external/webrtc/test/testsupport/fixed_fps_video_frame_writer_adapter_test.cc (revision d9f758449e529ab9291ac668be2861e7a55c2422)
1 /*
2  *  Copyright (c) 2022 The WebRTC project authors. All Rights Reserved.
3  *
4  *  Use of this source code is governed by a BSD-style license
5  *  that can be found in the LICENSE file in the root of the source
6  *  tree. An additional intellectual property rights grant can be found
7  *  in the file PATENTS.  All contributing project authors may
8  *  be found in the AUTHORS file in the root of the source tree.
9  */
10 
11 #include "test/testsupport/fixed_fps_video_frame_writer_adapter.h"
12 
13 #include <memory>
14 #include <utility>
15 #include <vector>
16 
17 #include "api/units/time_delta.h"
18 #include "api/units/timestamp.h"
19 #include "api/video/i420_buffer.h"
20 #include "api/video/video_frame.h"
21 #include "rtc_base/synchronization/mutex.h"
22 #include "test/gmock.h"
23 #include "test/gtest.h"
24 #include "test/testsupport/video_frame_writer.h"
25 #include "test/time_controller/simulated_time_controller.h"
26 
27 namespace webrtc {
28 namespace test {
29 namespace {
30 
31 constexpr TimeDelta kOneSecond = TimeDelta::Seconds(1);
32 
33 using ::testing::ElementsAre;
34 
35 class InMemoryVideoWriter : public VideoFrameWriter {
36  public:
37   ~InMemoryVideoWriter() override = default;
38 
WriteFrame(const webrtc::VideoFrame & frame)39   bool WriteFrame(const webrtc::VideoFrame& frame) override {
40     MutexLock lock(&mutex_);
41     received_frames_.push_back(frame);
42     return true;
43   }
44 
Close()45   void Close() override {}
46 
received_frames() const47   std::vector<VideoFrame> received_frames() const {
48     MutexLock lock(&mutex_);
49     return received_frames_;
50   }
51 
52  private:
53   mutable Mutex mutex_;
54   std::vector<VideoFrame> received_frames_ RTC_GUARDED_BY(mutex_);
55 };
56 
EmptyFrameWithId(uint16_t frame_id)57 VideoFrame EmptyFrameWithId(uint16_t frame_id) {
58   return VideoFrame::Builder()
59       .set_video_frame_buffer(I420Buffer::Create(1, 1))
60       .set_id(frame_id)
61       .build();
62 }
63 
FrameIds(const std::vector<VideoFrame> & frames)64 std::vector<uint16_t> FrameIds(const std::vector<VideoFrame>& frames) {
65   std::vector<uint16_t> out;
66   for (const VideoFrame& frame : frames) {
67     out.push_back(frame.id());
68   }
69   return out;
70 }
71 
CreateSimulatedTimeController()72 std::unique_ptr<TimeController> CreateSimulatedTimeController() {
73   // Using an offset of 100000 to get nice fixed width and readable
74   // timestamps in typical test scenarios.
75   const Timestamp kSimulatedStartTime = Timestamp::Seconds(100000);
76   return std::make_unique<GlobalSimulatedTimeController>(kSimulatedStartTime);
77 }
78 
TEST(FixedFpsVideoFrameWriterAdapterTest,WhenWrittenWithSameFpsVideoIsCorrect)79 TEST(FixedFpsVideoFrameWriterAdapterTest,
80      WhenWrittenWithSameFpsVideoIsCorrect) {
81   auto time_controller = CreateSimulatedTimeController();
82   int fps = 25;
83 
84   auto inmemory_writer = std::make_unique<InMemoryVideoWriter>();
85   InMemoryVideoWriter* inmemory_writer_ref = inmemory_writer.get();
86 
87   FixedFpsVideoFrameWriterAdapter video_writer(fps, time_controller->GetClock(),
88                                                std::move(inmemory_writer));
89 
90   for (int i = 1; i <= 30; ++i) {
91     video_writer.WriteFrame(EmptyFrameWithId(i));
92     time_controller->AdvanceTime(kOneSecond / fps);
93   }
94   video_writer.Close();
95 
96   std::vector<VideoFrame> received_frames =
97       inmemory_writer_ref->received_frames();
98   EXPECT_THAT(
99       FrameIds(received_frames),
100       ElementsAre(1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18,
101                   19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30));
102 }
103 
TEST(FixedFpsVideoFrameWriterAdapterTest,FrameIsRepeatedWhenThereIsAFreeze)104 TEST(FixedFpsVideoFrameWriterAdapterTest, FrameIsRepeatedWhenThereIsAFreeze) {
105   auto time_controller = CreateSimulatedTimeController();
106   int fps = 25;
107 
108   auto inmemory_writer = std::make_unique<InMemoryVideoWriter>();
109   InMemoryVideoWriter* inmemory_writer_ref = inmemory_writer.get();
110 
111   FixedFpsVideoFrameWriterAdapter video_writer(fps, time_controller->GetClock(),
112                                                std::move(inmemory_writer));
113 
114   // Write 10 frames
115   for (int i = 1; i <= 10; ++i) {
116     video_writer.WriteFrame(EmptyFrameWithId(i));
117     time_controller->AdvanceTime(kOneSecond / fps);
118   }
119 
120   // Freeze for 4 frames
121   time_controller->AdvanceTime(4 * kOneSecond / fps);
122 
123   // Write 10 more frames
124   for (int i = 11; i <= 20; ++i) {
125     video_writer.WriteFrame(EmptyFrameWithId(i));
126     time_controller->AdvanceTime(kOneSecond / fps);
127   }
128   video_writer.Close();
129 
130   std::vector<VideoFrame> received_frames =
131       inmemory_writer_ref->received_frames();
132   EXPECT_THAT(FrameIds(received_frames),
133               ElementsAre(1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 10, 10, 10, 10, 11, 12,
134                           13, 14, 15, 16, 17, 18, 19, 20));
135 }
136 
TEST(FixedFpsVideoFrameWriterAdapterTest,NoFramesWritten)137 TEST(FixedFpsVideoFrameWriterAdapterTest, NoFramesWritten) {
138   auto time_controller = CreateSimulatedTimeController();
139   int fps = 25;
140 
141   auto inmemory_writer = std::make_unique<InMemoryVideoWriter>();
142   InMemoryVideoWriter* inmemory_writer_ref = inmemory_writer.get();
143 
144   FixedFpsVideoFrameWriterAdapter video_writer(fps, time_controller->GetClock(),
145                                                std::move(inmemory_writer));
146   time_controller->AdvanceTime(TimeDelta::Millis(100));
147   video_writer.Close();
148 
149   std::vector<VideoFrame> received_frames =
150       inmemory_writer_ref->received_frames();
151   ASSERT_TRUE(received_frames.empty());
152 }
153 
TEST(FixedFpsVideoFrameWriterAdapterTest,FreezeInTheMiddleAndNewFrameReceivedBeforeMiddleOfExpectedInterval)154 TEST(FixedFpsVideoFrameWriterAdapterTest,
155      FreezeInTheMiddleAndNewFrameReceivedBeforeMiddleOfExpectedInterval) {
156   auto time_controller = CreateSimulatedTimeController();
157   constexpr int kFps = 10;
158   constexpr TimeDelta kInterval = kOneSecond / kFps;
159 
160   auto inmemory_writer = std::make_unique<InMemoryVideoWriter>();
161   InMemoryVideoWriter* inmemory_writer_ref = inmemory_writer.get();
162 
163   FixedFpsVideoFrameWriterAdapter video_writer(
164       kFps, time_controller->GetClock(), std::move(inmemory_writer));
165   video_writer.WriteFrame(EmptyFrameWithId(1));
166   time_controller->AdvanceTime(2.3 * kInterval);
167   video_writer.WriteFrame(EmptyFrameWithId(2));
168   video_writer.Close();
169 
170   std::vector<VideoFrame> received_frames =
171       inmemory_writer_ref->received_frames();
172   EXPECT_THAT(FrameIds(received_frames), ElementsAre(1, 1, 2));
173 }
174 
TEST(FixedFpsVideoFrameWriterAdapterTest,FreezeInTheMiddleAndNewFrameReceivedAfterMiddleOfExpectedInterval)175 TEST(FixedFpsVideoFrameWriterAdapterTest,
176      FreezeInTheMiddleAndNewFrameReceivedAfterMiddleOfExpectedInterval) {
177   auto time_controller = CreateSimulatedTimeController();
178   constexpr int kFps = 10;
179   constexpr TimeDelta kInterval = kOneSecond / kFps;
180 
181   auto inmemory_writer = std::make_unique<InMemoryVideoWriter>();
182   InMemoryVideoWriter* inmemory_writer_ref = inmemory_writer.get();
183 
184   FixedFpsVideoFrameWriterAdapter video_writer(
185       kFps, time_controller->GetClock(), std::move(inmemory_writer));
186   video_writer.WriteFrame(EmptyFrameWithId(1));
187   time_controller->AdvanceTime(2.5 * kInterval);
188   video_writer.WriteFrame(EmptyFrameWithId(2));
189   video_writer.Close();
190 
191   std::vector<VideoFrame> received_frames =
192       inmemory_writer_ref->received_frames();
193   EXPECT_THAT(FrameIds(received_frames), ElementsAre(1, 1, 1, 2));
194 }
195 
TEST(FixedFpsVideoFrameWriterAdapterTest,NewFrameReceivedBeforeMiddleOfExpectedInterval)196 TEST(FixedFpsVideoFrameWriterAdapterTest,
197      NewFrameReceivedBeforeMiddleOfExpectedInterval) {
198   auto time_controller = CreateSimulatedTimeController();
199   constexpr int kFps = 10;
200   constexpr TimeDelta kInterval = kOneSecond / kFps;
201 
202   auto inmemory_writer = std::make_unique<InMemoryVideoWriter>();
203   InMemoryVideoWriter* inmemory_writer_ref = inmemory_writer.get();
204 
205   FixedFpsVideoFrameWriterAdapter video_writer(
206       kFps, time_controller->GetClock(), std::move(inmemory_writer));
207   video_writer.WriteFrame(EmptyFrameWithId(1));
208   time_controller->AdvanceTime(0.3 * kInterval);
209   video_writer.WriteFrame(EmptyFrameWithId(2));
210   video_writer.Close();
211 
212   std::vector<VideoFrame> received_frames =
213       inmemory_writer_ref->received_frames();
214   EXPECT_THAT(FrameIds(received_frames), ElementsAre(2));
215 }
216 
TEST(FixedFpsVideoFrameWriterAdapterTest,NewFrameReceivedAfterMiddleOfExpectedInterval)217 TEST(FixedFpsVideoFrameWriterAdapterTest,
218      NewFrameReceivedAfterMiddleOfExpectedInterval) {
219   auto time_controller = CreateSimulatedTimeController();
220   constexpr int kFps = 10;
221   constexpr TimeDelta kInterval = kOneSecond / kFps;
222 
223   auto inmemory_writer = std::make_unique<InMemoryVideoWriter>();
224   InMemoryVideoWriter* inmemory_writer_ref = inmemory_writer.get();
225 
226   FixedFpsVideoFrameWriterAdapter video_writer(
227       kFps, time_controller->GetClock(), std::move(inmemory_writer));
228   video_writer.WriteFrame(EmptyFrameWithId(1));
229   time_controller->AdvanceTime(0.5 * kInterval);
230   video_writer.WriteFrame(EmptyFrameWithId(2));
231   video_writer.Close();
232 
233   std::vector<VideoFrame> received_frames =
234       inmemory_writer_ref->received_frames();
235   EXPECT_THAT(FrameIds(received_frames), ElementsAre(1, 2));
236 }
237 
TEST(FixedFpsVideoFrameWriterAdapterTest,FreeezeAtTheEndAndDestroyBeforeMiddleOfExpectedInterval)238 TEST(FixedFpsVideoFrameWriterAdapterTest,
239      FreeezeAtTheEndAndDestroyBeforeMiddleOfExpectedInterval) {
240   auto time_controller = CreateSimulatedTimeController();
241   constexpr int kFps = 10;
242   constexpr TimeDelta kInterval = kOneSecond / kFps;
243 
244   auto inmemory_writer = std::make_unique<InMemoryVideoWriter>();
245   InMemoryVideoWriter* inmemory_writer_ref = inmemory_writer.get();
246 
247   FixedFpsVideoFrameWriterAdapter video_writer(
248       kFps, time_controller->GetClock(), std::move(inmemory_writer));
249   video_writer.WriteFrame(EmptyFrameWithId(1));
250   time_controller->AdvanceTime(2.3 * kInterval);
251   video_writer.Close();
252 
253   std::vector<VideoFrame> received_frames =
254       inmemory_writer_ref->received_frames();
255   EXPECT_THAT(FrameIds(received_frames), ElementsAre(1, 1, 1));
256 }
257 
TEST(FixedFpsVideoFrameWriterAdapterTest,FreeezeAtTheEndAndDestroyAfterMiddleOfExpectedInterval)258 TEST(FixedFpsVideoFrameWriterAdapterTest,
259      FreeezeAtTheEndAndDestroyAfterMiddleOfExpectedInterval) {
260   auto time_controller = CreateSimulatedTimeController();
261   constexpr int kFps = 10;
262   constexpr TimeDelta kInterval = kOneSecond / kFps;
263 
264   auto inmemory_writer = std::make_unique<InMemoryVideoWriter>();
265   InMemoryVideoWriter* inmemory_writer_ref = inmemory_writer.get();
266 
267   FixedFpsVideoFrameWriterAdapter video_writer(
268       kFps, time_controller->GetClock(), std::move(inmemory_writer));
269   video_writer.WriteFrame(EmptyFrameWithId(1));
270   time_controller->AdvanceTime(2.5 * kInterval);
271   video_writer.Close();
272 
273   std::vector<VideoFrame> received_frames =
274       inmemory_writer_ref->received_frames();
275   EXPECT_THAT(FrameIds(received_frames), ElementsAre(1, 1, 1));
276 }
277 
TEST(FixedFpsVideoFrameWriterAdapterTest,DestroyBeforeMiddleOfExpectedInterval)278 TEST(FixedFpsVideoFrameWriterAdapterTest,
279      DestroyBeforeMiddleOfExpectedInterval) {
280   auto time_controller = CreateSimulatedTimeController();
281   constexpr int kFps = 10;
282   constexpr TimeDelta kInterval = kOneSecond / kFps;
283 
284   auto inmemory_writer = std::make_unique<InMemoryVideoWriter>();
285   InMemoryVideoWriter* inmemory_writer_ref = inmemory_writer.get();
286 
287   FixedFpsVideoFrameWriterAdapter video_writer(
288       kFps, time_controller->GetClock(), std::move(inmemory_writer));
289   video_writer.WriteFrame(EmptyFrameWithId(1));
290   time_controller->AdvanceTime(0.3 * kInterval);
291   video_writer.Close();
292 
293   std::vector<VideoFrame> received_frames =
294       inmemory_writer_ref->received_frames();
295   EXPECT_THAT(FrameIds(received_frames), ElementsAre(1));
296 }
297 
TEST(FixedFpsVideoFrameWriterAdapterTest,DestroyAfterMiddleOfExpectedInterval)298 TEST(FixedFpsVideoFrameWriterAdapterTest,
299      DestroyAfterMiddleOfExpectedInterval) {
300   auto time_controller = CreateSimulatedTimeController();
301   constexpr int kFps = 10;
302   constexpr TimeDelta kInterval = kOneSecond / kFps;
303 
304   auto inmemory_writer = std::make_unique<InMemoryVideoWriter>();
305   InMemoryVideoWriter* inmemory_writer_ref = inmemory_writer.get();
306 
307   FixedFpsVideoFrameWriterAdapter video_writer(
308       kFps, time_controller->GetClock(), std::move(inmemory_writer));
309   video_writer.WriteFrame(EmptyFrameWithId(1));
310   time_controller->AdvanceTime(0.5 * kInterval);
311   video_writer.Close();
312 
313   std::vector<VideoFrame> received_frames =
314       inmemory_writer_ref->received_frames();
315   EXPECT_THAT(FrameIds(received_frames), ElementsAre(1));
316 }
317 
318 }  // namespace
319 }  // namespace test
320 }  // namespace webrtc
321