• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * libjingle
3  * Copyright 2004 Google Inc.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions are met:
7  *
8  *  1. Redistributions of source code must retain the above copyright notice,
9  *     this list of conditions and the following disclaimer.
10  *  2. Redistributions in binary form must reproduce the above copyright notice,
11  *     this list of conditions and the following disclaimer in the documentation
12  *     and/or other materials provided with the distribution.
13  *  3. The name of the author may not be used to endorse or promote products
14  *     derived from this software without specific prior written permission.
15  *
16  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED
17  * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
18  * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO
19  * EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
20  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
21  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
22  * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
23  * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
24  * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
25  * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26  */
27 
28 #include <stdio.h>
29 
30 #include <string>
31 #include <vector>
32 
33 #include "talk/media/base/testutils.h"
34 #include "talk/media/devices/filevideocapturer.h"
35 #include "webrtc/base/gunit.h"
36 #include "webrtc/base/logging.h"
37 #include "webrtc/base/thread.h"
38 
39 namespace {
40 
41 class FileVideoCapturerTest : public testing::Test {
42  public:
SetUp()43   virtual void SetUp() {
44     capturer_.reset(new cricket::FileVideoCapturer);
45   }
46 
OpenFile(const std::string & filename)47   bool OpenFile(const std::string& filename) {
48     return capturer_->Init(cricket::GetTestFilePath(filename));
49   }
50 
51  protected:
52   class VideoCapturerListener : public sigslot::has_slots<> {
53    public:
VideoCapturerListener()54     VideoCapturerListener()
55         : frame_count_(0),
56           frame_width_(0),
57           frame_height_(0),
58           resolution_changed_(false) {
59     }
60 
OnFrameCaptured(cricket::VideoCapturer * capturer,const cricket::CapturedFrame * frame)61     void OnFrameCaptured(cricket::VideoCapturer* capturer,
62                          const cricket::CapturedFrame* frame) {
63       ++frame_count_;
64       if (1 == frame_count_) {
65         frame_width_ = frame->width;
66         frame_height_ = frame->height;
67       } else if (frame_width_ != frame->width ||
68           frame_height_ != frame->height) {
69         resolution_changed_ = true;
70       }
71     }
72 
frame_count() const73     int frame_count() const { return frame_count_; }
frame_width() const74     int frame_width() const { return frame_width_; }
frame_height() const75     int frame_height() const { return frame_height_; }
resolution_changed() const76     bool resolution_changed() const { return resolution_changed_; }
77 
78    private:
79     int frame_count_;
80     int frame_width_;
81     int frame_height_;
82     bool resolution_changed_;
83   };
84 
85   rtc::scoped_ptr<cricket::FileVideoCapturer> capturer_;
86   cricket::VideoFormat capture_format_;
87 };
88 
TEST_F(FileVideoCapturerTest,TestNotOpened)89 TEST_F(FileVideoCapturerTest, TestNotOpened) {
90   EXPECT_EQ("", capturer_->GetId());
91   EXPECT_TRUE(capturer_->GetSupportedFormats()->empty());
92   EXPECT_EQ(NULL, capturer_->GetCaptureFormat());
93   EXPECT_FALSE(capturer_->IsRunning());
94 }
95 
TEST_F(FileVideoCapturerTest,TestInvalidOpen)96 TEST_F(FileVideoCapturerTest, TestInvalidOpen) {
97   EXPECT_FALSE(OpenFile("NotmeNotme"));
98 }
99 
TEST_F(FileVideoCapturerTest,TestOpen)100 TEST_F(FileVideoCapturerTest, TestOpen) {
101   EXPECT_TRUE(OpenFile("captured-320x240-2s-48.frames"));
102   EXPECT_NE("", capturer_->GetId());
103   EXPECT_TRUE(NULL != capturer_->GetSupportedFormats());
104   EXPECT_EQ(1U, capturer_->GetSupportedFormats()->size());
105   EXPECT_EQ(NULL, capturer_->GetCaptureFormat());  // not started yet
106   EXPECT_FALSE(capturer_->IsRunning());
107 }
108 
TEST_F(FileVideoCapturerTest,TestLargeSmallDesiredFormat)109 TEST_F(FileVideoCapturerTest, TestLargeSmallDesiredFormat) {
110   EXPECT_TRUE(OpenFile("captured-320x240-2s-48.frames"));
111   // desired format with large resolution.
112   cricket::VideoFormat desired(
113       3200, 2400, cricket::VideoFormat::FpsToInterval(30), cricket::FOURCC_ANY);
114   EXPECT_TRUE(capturer_->GetBestCaptureFormat(desired, &capture_format_));
115   EXPECT_EQ(320, capture_format_.width);
116   EXPECT_EQ(240, capture_format_.height);
117 
118   // Desired format with small resolution.
119   desired.width = 0;
120   desired.height = 0;
121   EXPECT_TRUE(capturer_->GetBestCaptureFormat(desired, &capture_format_));
122   EXPECT_EQ(320, capture_format_.width);
123   EXPECT_EQ(240, capture_format_.height);
124 }
125 
TEST_F(FileVideoCapturerTest,TestSupportedAsDesiredFormat)126 TEST_F(FileVideoCapturerTest, TestSupportedAsDesiredFormat) {
127   EXPECT_TRUE(OpenFile("captured-320x240-2s-48.frames"));
128   // desired format same as the capture format supported by the file
129   cricket::VideoFormat desired = capturer_->GetSupportedFormats()->at(0);
130   EXPECT_TRUE(capturer_->GetBestCaptureFormat(desired, &capture_format_));
131   EXPECT_TRUE(desired == capture_format_);
132 
133   // desired format same as the supported capture format except the fourcc
134   desired.fourcc = cricket::FOURCC_ANY;
135   EXPECT_TRUE(capturer_->GetBestCaptureFormat(desired, &capture_format_));
136   EXPECT_NE(capture_format_.fourcc, desired.fourcc);
137 
138   // desired format with minimum interval
139   desired.interval = cricket::VideoFormat::kMinimumInterval;
140   EXPECT_TRUE(capturer_->GetBestCaptureFormat(desired, &capture_format_));
141 }
142 
TEST_F(FileVideoCapturerTest,TestNoRepeat)143 TEST_F(FileVideoCapturerTest, TestNoRepeat) {
144   EXPECT_TRUE(OpenFile("captured-320x240-2s-48.frames"));
145   VideoCapturerListener listener;
146   capturer_->SignalFrameCaptured.connect(
147       &listener, &VideoCapturerListener::OnFrameCaptured);
148   capturer_->set_repeat(0);
149   capture_format_ = capturer_->GetSupportedFormats()->at(0);
150   EXPECT_EQ(cricket::CS_RUNNING, capturer_->Start(capture_format_));
151   EXPECT_TRUE_WAIT(!capturer_->IsRunning(), 20000);
152   EXPECT_EQ(48, listener.frame_count());
153 }
154 
TEST_F(FileVideoCapturerTest,TestRepeatForever)155 TEST_F(FileVideoCapturerTest, TestRepeatForever) {
156   // Start the capturer_ with 50 fps and read no less than 150 frames.
157   EXPECT_TRUE(OpenFile("captured-320x240-2s-48.frames"));
158   VideoCapturerListener listener;
159   capturer_->SignalFrameCaptured.connect(
160       &listener, &VideoCapturerListener::OnFrameCaptured);
161   capturer_->set_repeat(cricket::FileVideoCapturer::kForever);
162   capture_format_ = capturer_->GetSupportedFormats()->at(0);
163   capture_format_.interval = cricket::VideoFormat::FpsToInterval(50);
164   EXPECT_EQ(cricket::CS_RUNNING, capturer_->Start(capture_format_));
165   EXPECT_TRUE(NULL != capturer_->GetCaptureFormat());
166   EXPECT_TRUE(capture_format_ == *capturer_->GetCaptureFormat());
167   EXPECT_TRUE_WAIT(!capturer_->IsRunning() ||
168                    listener.frame_count() >= 150, 20000);
169   capturer_->Stop();
170   EXPECT_FALSE(capturer_->IsRunning());
171   EXPECT_GE(listener.frame_count(), 150);
172   EXPECT_FALSE(listener.resolution_changed());
173   EXPECT_EQ(listener.frame_width(), capture_format_.width);
174   EXPECT_EQ(listener.frame_height(), capture_format_.height);
175 }
176 
177 // See: https://code.google.com/p/webrtc/issues/detail?id=2409
TEST_F(FileVideoCapturerTest,DISABLED_TestPartialFrameHeader)178 TEST_F(FileVideoCapturerTest, DISABLED_TestPartialFrameHeader) {
179   EXPECT_TRUE(OpenFile("1.frame_plus_1.byte"));
180   VideoCapturerListener listener;
181   capturer_->SignalFrameCaptured.connect(
182       &listener, &VideoCapturerListener::OnFrameCaptured);
183   capturer_->set_repeat(0);
184   capture_format_ = capturer_->GetSupportedFormats()->at(0);
185   EXPECT_EQ(cricket::CS_RUNNING, capturer_->Start(capture_format_));
186   EXPECT_TRUE_WAIT(!capturer_->IsRunning(), 1000);
187   EXPECT_EQ(1, listener.frame_count());
188 }
189 
TEST_F(FileVideoCapturerTest,TestFileDevices)190 TEST_F(FileVideoCapturerTest, TestFileDevices) {
191   cricket::Device not_a_file("I'm a camera", "with an id");
192   EXPECT_FALSE(
193       cricket::FileVideoCapturer::IsFileVideoCapturerDevice(not_a_file));
194   const std::string test_file =
195       cricket::GetTestFilePath("captured-320x240-2s-48.frames");
196   cricket::Device file_device =
197       cricket::FileVideoCapturer::CreateFileVideoCapturerDevice(test_file);
198   EXPECT_TRUE(
199       cricket::FileVideoCapturer::IsFileVideoCapturerDevice(file_device));
200   EXPECT_TRUE(capturer_->Init(file_device));
201   EXPECT_EQ(file_device.id, capturer_->GetId());
202 }
203 
204 }  // unnamed namespace
205