| OLD | NEW |
| 1 // Copyright 2013 The Chromium Authors. All rights reserved. | 1 // Copyright 2013 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "media/video/capture/file_video_capture_device.h" | 5 #include "media/video/capture/file_video_capture_device.h" |
| 6 | 6 |
| 7 #include <string> | 7 #include <string> |
| 8 | 8 |
| 9 #include "base/bind.h" | 9 #include "base/bind.h" |
| 10 #include "base/command_line.h" | |
| 11 #include "base/memory/scoped_ptr.h" | 10 #include "base/memory/scoped_ptr.h" |
| 12 #include "base/strings/string_number_conversions.h" | 11 #include "base/strings/string_number_conversions.h" |
| 13 #include "base/strings/string_piece.h" | 12 #include "base/strings/string_piece.h" |
| 14 #include "base/strings/sys_string_conversions.h" | 13 #include "base/strings/sys_string_conversions.h" |
| 15 #include "media/base/media_switches.h" | |
| 16 | |
| 17 | 14 |
| 18 namespace media { | 15 namespace media { |
| 19 static const char kFileVideoCaptureDeviceName[] = | |
| 20 "/dev/placeholder-for-file-backed-fake-capture-device"; | |
| 21 | |
| 22 static const int kY4MHeaderMaxSize = 200; | 16 static const int kY4MHeaderMaxSize = 200; |
| 23 static const char kY4MSimpleFrameDelimiter[] = "FRAME"; | 17 static const char kY4MSimpleFrameDelimiter[] = "FRAME"; |
| 24 static const int kY4MSimpleFrameDelimiterSize = 6; | 18 static const int kY4MSimpleFrameDelimiterSize = 6; |
| 25 | 19 |
| 26 int ParseY4MInt(const base::StringPiece& token) { | 20 int ParseY4MInt(const base::StringPiece& token) { |
| 27 int temp_int; | 21 int temp_int; |
| 28 CHECK(base::StringToInt(token, &temp_int)) << token; | 22 CHECK(base::StringToInt(token, &temp_int)) << token; |
| 29 return temp_int; | 23 return temp_int; |
| 30 } | 24 } |
| 31 | 25 |
| (...skipping 71 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 103 index = blank_position + 1; | 97 index = blank_position + 1; |
| 104 } | 98 } |
| 105 // Last video format semantic correctness check before sending it back. | 99 // Last video format semantic correctness check before sending it back. |
| 106 CHECK(video_format->IsValid()); | 100 CHECK(video_format->IsValid()); |
| 107 } | 101 } |
| 108 | 102 |
| 109 // Reads and parses the header of a Y4M |file|, returning the collected pixel | 103 // Reads and parses the header of a Y4M |file|, returning the collected pixel |
| 110 // format in |video_format|. Returns the index of the first byte of the first | 104 // format in |video_format|. Returns the index of the first byte of the first |
| 111 // video frame. | 105 // video frame. |
| 112 // Restrictions: Only trivial per-frame headers are supported. | 106 // Restrictions: Only trivial per-frame headers are supported. |
| 113 int64 ParseFileAndExtractVideoFormat( | 107 // static |
| 108 int64 FileVideoCaptureDevice::ParseFileAndExtractVideoFormat( |
| 114 base::File* file, | 109 base::File* file, |
| 115 media::VideoCaptureFormat* video_format) { | 110 media::VideoCaptureFormat* video_format) { |
| 116 std::string header(kY4MHeaderMaxSize, 0); | 111 std::string header(kY4MHeaderMaxSize, 0); |
| 117 file->Read(0, &header[0], kY4MHeaderMaxSize - 1); | 112 file->Read(0, &header[0], kY4MHeaderMaxSize - 1); |
| 118 | 113 |
| 119 size_t header_end = header.find(kY4MSimpleFrameDelimiter); | 114 size_t header_end = header.find(kY4MSimpleFrameDelimiter); |
| 120 CHECK_NE(header_end, header.npos); | 115 CHECK_NE(header_end, header.npos); |
| 121 | 116 |
| 122 ParseY4MTags(header, video_format); | 117 ParseY4MTags(header, video_format); |
| 123 return header_end + kY4MSimpleFrameDelimiterSize; | 118 return header_end + kY4MSimpleFrameDelimiterSize; |
| 124 } | 119 } |
| 125 | 120 |
| 126 // Opens a given file for reading, and returns the file to the caller, who is | 121 // Opens a given file for reading, and returns the file to the caller, who is |
| 127 // responsible for closing it. | 122 // responsible for closing it. |
| 128 base::File OpenFileForRead(const base::FilePath& file_path) { | 123 // static |
| 124 base::File FileVideoCaptureDevice::OpenFileForRead( |
| 125 const base::FilePath& file_path) { |
| 129 base::File file(file_path, base::File::FLAG_OPEN | base::File::FLAG_READ); | 126 base::File file(file_path, base::File::FLAG_OPEN | base::File::FLAG_READ); |
| 130 CHECK(file.IsValid()) << file_path.value(); | 127 CHECK(file.IsValid()) << file_path.value(); |
| 131 return file.Pass(); | 128 return file.Pass(); |
| 132 } | 129 } |
| 133 | 130 |
| 134 // Inspects the command line and retrieves the file path parameter. | |
| 135 base::FilePath GetFilePathFromCommandLine() { | |
| 136 base::FilePath command_line_file_path = | |
| 137 CommandLine::ForCurrentProcess()->GetSwitchValuePath( | |
| 138 switches::kUseFileForFakeVideoCapture); | |
| 139 CHECK(!command_line_file_path.empty()); | |
| 140 return command_line_file_path; | |
| 141 } | |
| 142 | |
| 143 void FileVideoCaptureDevice::GetDeviceNames(Names* const device_names) { | |
| 144 DCHECK(device_names->empty()); | |
| 145 base::FilePath command_line_file_path = GetFilePathFromCommandLine(); | |
| 146 #if defined(OS_WIN) | |
| 147 device_names->push_back( | |
| 148 Name(base::SysWideToUTF8(command_line_file_path.value()), | |
| 149 kFileVideoCaptureDeviceName)); | |
| 150 #else | |
| 151 device_names->push_back(Name(command_line_file_path.value(), | |
| 152 kFileVideoCaptureDeviceName)); | |
| 153 #endif // OS_WIN | |
| 154 } | |
| 155 | |
| 156 void FileVideoCaptureDevice::GetDeviceSupportedFormats( | |
| 157 const Name& device, | |
| 158 VideoCaptureFormats* supported_formats) { | |
| 159 base::File file = OpenFileForRead(GetFilePathFromCommandLine()); | |
| 160 VideoCaptureFormat capture_format; | |
| 161 ParseFileAndExtractVideoFormat(&file, &capture_format); | |
| 162 supported_formats->push_back(capture_format); | |
| 163 } | |
| 164 | |
| 165 VideoCaptureDevice* FileVideoCaptureDevice::Create(const Name& device_name) { | |
| 166 #if defined(OS_WIN) | |
| 167 return new FileVideoCaptureDevice( | |
| 168 base::FilePath(base::SysUTF8ToWide(device_name.name()))); | |
| 169 #else | |
| 170 return new FileVideoCaptureDevice(base::FilePath(device_name.name())); | |
| 171 #endif // OS_WIN | |
| 172 } | |
| 173 | |
| 174 FileVideoCaptureDevice::FileVideoCaptureDevice(const base::FilePath& file_path) | 131 FileVideoCaptureDevice::FileVideoCaptureDevice(const base::FilePath& file_path) |
| 175 : capture_thread_("CaptureThread"), | 132 : capture_thread_("CaptureThread"), |
| 176 file_path_(file_path), | 133 file_path_(file_path), |
| 177 frame_size_(0), | 134 frame_size_(0), |
| 178 current_byte_index_(0), | 135 current_byte_index_(0), |
| 179 first_frame_byte_index_(0) {} | 136 first_frame_byte_index_(0) {} |
| 180 | 137 |
| 181 FileVideoCaptureDevice::~FileVideoCaptureDevice() { | 138 FileVideoCaptureDevice::~FileVideoCaptureDevice() { |
| 182 DCHECK(thread_checker_.CalledOnValidThread()); | 139 DCHECK(thread_checker_.CalledOnValidThread()); |
| 183 // Check if the thread is running. | 140 // Check if the thread is running. |
| (...skipping 97 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 281 base::TimeTicks::Now()); | 238 base::TimeTicks::Now()); |
| 282 // Reschedule next CaptureTask. | 239 // Reschedule next CaptureTask. |
| 283 base::MessageLoop::current()->PostDelayedTask( | 240 base::MessageLoop::current()->PostDelayedTask( |
| 284 FROM_HERE, | 241 FROM_HERE, |
| 285 base::Bind(&FileVideoCaptureDevice::OnCaptureTask, | 242 base::Bind(&FileVideoCaptureDevice::OnCaptureTask, |
| 286 base::Unretained(this)), | 243 base::Unretained(this)), |
| 287 base::TimeDelta::FromSeconds(1) / capture_format_.frame_rate); | 244 base::TimeDelta::FromSeconds(1) / capture_format_.frame_rate); |
| 288 } | 245 } |
| 289 | 246 |
| 290 } // namespace media | 247 } // namespace media |
| OLD | NEW |