xref: /aosp_15_r20/external/webrtc/test/testsupport/frame_reader.h (revision d9f758449e529ab9291ac668be2861e7a55c2422)
1 /*
2  *  Copyright (c) 2011 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 #ifndef TEST_TESTSUPPORT_FRAME_READER_H_
12 #define TEST_TESTSUPPORT_FRAME_READER_H_
13 
14 #include <stdio.h>
15 
16 #include <string>
17 
18 #include "absl/types/optional.h"
19 #include "api/scoped_refptr.h"
20 
21 namespace webrtc {
22 class I420Buffer;
23 namespace test {
24 
25 // Handles reading of I420 frames from video files.
26 class FrameReader {
27  public:
~FrameReader()28   virtual ~FrameReader() {}
29 
30   // Initializes the frame reader, i.e. opens the input file.
31   // This must be called before reading of frames has started.
32   // Returns false if an error has occurred, in addition to printing to stderr.
33   virtual bool Init() = 0;
34 
35   // Reads a frame from the input file. On success, returns the frame.
36   // Returns nullptr if encountering end of file or a read error.
37   virtual rtc::scoped_refptr<I420Buffer> ReadFrame() = 0;
38 
39   // Closes the input file if open. Essentially makes this class impossible
40   // to use anymore. Will also be invoked by the destructor.
41   virtual void Close() = 0;
42 
43   // Frame length in bytes of a single frame image.
44   virtual size_t FrameLength() = 0;
45   // Total number of frames in the input video source.
46   virtual int NumberOfFrames() = 0;
47 };
48 
49 class YuvFrameReaderImpl : public FrameReader {
50  public:
51   enum class RepeatMode { kSingle, kRepeat, kPingPong };
52   class DropperUtil {
53    public:
54     DropperUtil(int source_fps, int target_fps);
55 
56     enum class DropDecision { kDropframe, kKeepFrame };
57     DropDecision UpdateLevel();
58 
59    private:
60     const double frame_size_buckets_;
61     double bucket_level_;
62   };
63 
64   // Creates a file handler. The input file is assumed to exist and be readable.
65   // Parameters:
66   //   input_filename          The file to read from.
67   //   width, height           Size of each frame to read.
68   YuvFrameReaderImpl(std::string input_filename, int width, int height);
69   YuvFrameReaderImpl(std::string input_filename,
70                      int input_width,
71                      int input_height,
72                      int desired_width,
73                      int desired_height,
74                      RepeatMode repeat_mode,
75                      absl::optional<int> clip_fps,
76                      int target_fps);
77   ~YuvFrameReaderImpl() override;
78   bool Init() override;
79   rtc::scoped_refptr<I420Buffer> ReadFrame() override;
80   void Close() override;
81   size_t FrameLength() override;
82   int NumberOfFrames() override;
83 
84  protected:
85   const std::string input_filename_;
86   // It is not const, so subclasses will be able to add frame header size.
87   size_t frame_length_in_bytes_;
88   const int input_width_;
89   const int input_height_;
90   const int desired_width_;
91   const int desired_height_;
92   const size_t frame_size_bytes_;
93   const RepeatMode repeat_mode_;
94   int number_of_frames_;
95   int current_frame_index_;
96   std::unique_ptr<DropperUtil> dropper_;
97   FILE* input_file_;
98 };
99 
100 class Y4mFrameReaderImpl : public YuvFrameReaderImpl {
101  public:
102   // Creates a file handler. The input file is assumed to exist and be readable.
103   // Parameters:
104   //   input_filename          The file to read from.
105   //   width, height           Size of each frame to read.
106   Y4mFrameReaderImpl(std::string input_filename, int width, int height);
107   ~Y4mFrameReaderImpl() override;
108   bool Init() override;
109   rtc::scoped_refptr<I420Buffer> ReadFrame() override;
110 
111  private:
112   // Buffer that is used to read file and frame headers.
113   char* buffer_;
114 };
115 
116 }  // namespace test
117 }  // namespace webrtc
118 
119 #endif  // TEST_TESTSUPPORT_FRAME_READER_H_
120