1 // libjingle 2 // Copyright 2004--2005, Google Inc. 3 // 4 // Redistribution and use in source and binary forms, with or without 5 // modification, are permitted provided that the following conditions are met: 6 // 7 // 1. Redistributions of source code must retain the above copyright notice, 8 // this list of conditions and the following disclaimer. 9 // 2. Redistributions in binary form must reproduce the above copyright notice, 10 // this list of conditions and the following disclaimer in the documentation 11 // and/or other materials provided with the distribution. 12 // 3. The name of the author may not be used to endorse or promote products 13 // derived from this software without specific prior written permission. 14 // 15 // THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED 16 // WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF 17 // MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO 18 // EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 19 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 20 // PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; 21 // OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, 22 // WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR 23 // OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF 24 // ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 25 // 26 // This file contains two classes, VideoRecorder and FileVideoCapturer. 27 // VideoRecorder records the captured frames into a file. The file stores a 28 // sequence of captured frames; each frame has a header defined in struct 29 // CapturedFrame, followed by the frame data. 30 // 31 // FileVideoCapturer, a subclass of VideoCapturer, is a simulated video capturer 32 // that periodically reads images from a previously recorded file. 33 34 #ifndef TALK_SESSION_PHONE_FILEVIDEOCAPTURER_H_ 35 #define TALK_SESSION_PHONE_FILEVIDEOCAPTURER_H_ 36 37 #include <string> 38 #include <vector> 39 40 #include "talk/base/stream.h" 41 #include "talk/session/phone/videocapturer.h" 42 43 namespace talk_base { 44 class FileStream; 45 } 46 47 namespace cricket { 48 49 // Utility class to record the frames captured by a video capturer into a file. 50 class VideoRecorder { 51 public: VideoRecorder()52 VideoRecorder() {} ~VideoRecorder()53 ~VideoRecorder() { Stop(); } 54 55 // Start the recorder by opening the specified file. Return true if the file 56 // is opened successfully. write_header should normally be true; false means 57 // write raw frame pixel data to file without any headers. 58 bool Start(const std::string& filename, bool write_header); 59 // Stop the recorder by closing the file. 60 void Stop(); 61 // Record a video frame to the file. Return true if the frame is written to 62 // the file successfully. This method needs to be called after Start() and 63 // before Stop(). 64 bool RecordFrame(const CapturedFrame& frame); 65 66 private: 67 talk_base::FileStream video_file_; 68 bool write_header_; 69 70 DISALLOW_COPY_AND_ASSIGN(VideoRecorder); 71 }; 72 73 // Simulated video capturer that periodically reads frames from a file. 74 class FileVideoCapturer : public VideoCapturer { 75 public: 76 FileVideoCapturer(); 77 virtual ~FileVideoCapturer(); 78 79 // Determines if the given device is actually a video file, to be captured 80 // with a FileVideoCapturer. IsFileVideoCapturerDevice(const Device & device)81 static bool IsFileVideoCapturerDevice(const Device& device) { 82 return device.id == kVideoFileDeviceName; 83 } 84 85 // Creates a fake device for the given filename. CreateFileVideoCapturerDevice(const std::string & filename)86 static Device CreateFileVideoCapturerDevice(const std::string& filename) { 87 return Device(filename, kVideoFileDeviceName); 88 } 89 90 // Set how many times to repeat reading the file. Repeat forever if the 91 // parameter is talk_base::kForever(-1); no repeat if the parameter is 0 or 92 // less than -1. set_repeat(int repeat)93 void set_repeat(int repeat) { repeat_ = repeat; } 94 95 // If ignore_framerate is true, file is read as quickly as possible. If 96 // false, read rate is controlled by the timestamps in the video file 97 // (thus simulating camera capture). Default value set to false. set_ignore_framerate(bool ignore_framerate)98 void set_ignore_framerate(bool ignore_framerate) { 99 ignore_framerate_ = ignore_framerate; 100 } 101 102 // Initializes the capturer with the given file. 103 bool Init(const std::string& filename); 104 105 // Initializes the capturer with the given device. This should only be used 106 // if IsFileVideoCapturerDevice returned true for the given device. 107 bool Init(const Device& device); 108 109 // Override virtual methods of parent class VideoCapturer. 110 virtual CaptureResult Start(const VideoFormat& capture_format); 111 virtual void Stop(); 112 virtual bool IsRunning(); 113 114 protected: 115 // Override virtual methods of parent class VideoCapturer. 116 virtual bool GetPreferredFourccs(std::vector<uint32>* fourccs); 117 118 // Read the frame header from the file stream, video_file_. 119 talk_base::StreamResult ReadFrameHeader(CapturedFrame* frame); 120 121 // Read a frame and determine how long to wait for the next frame. If the 122 // frame is read successfully, Set the output parameter, wait_time_ms and 123 // return true. Otherwise, do not change wait_time_ms and return false. 124 bool ReadFrame(bool first_frame, int* wait_time_ms); 125 126 // Return the CapturedFrame - useful for extracting contents after reading 127 // a frame. Should be used only while still reading a file (i.e. only while 128 // the CapturedFrame object still exists). frame()129 const CapturedFrame* frame() const { 130 return &captured_frame_; 131 } 132 133 private: 134 class FileReadThread; // Forward declaration, defined in .cc. 135 136 static const char* kVideoFileDeviceName; 137 talk_base::FileStream video_file_; 138 CapturedFrame captured_frame_; 139 // The number of bytes allocated buffer for captured_frame_.data. 140 uint32 frame_buffer_size_; 141 FileReadThread* file_read_thread_; 142 int repeat_; // How many times to repeat the file. 143 int64 start_time_ns_; // Time when the file video capturer starts. 144 int64 last_frame_timestamp_ns_; // Timestamp of last read frame. 145 bool ignore_framerate_; 146 147 DISALLOW_COPY_AND_ASSIGN(FileVideoCapturer); 148 }; 149 150 } // namespace cricket 151 152 #endif // TALK_SESSION_PHONE_FILEVIDEOCAPTURER_H_ 153