1 // Copyright 2014 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
8 #include "base/memory/ref_counted.h"
9 #include "base/memory/scoped_ptr.h"
10 #include "media/base/video_frame.h"
11 #include "media/cast/cast_defines.h"
12 #include "media/cast/cast_environment.h"
13 #include "media/cast/sender/video_encoder_impl.h"
14 #include "media/cast/test/fake_single_thread_task_runner.h"
15 #include "media/cast/test/utility/default_config.h"
16 #include "media/cast/test/utility/video_utility.h"
17 #include "testing/gmock/include/gmock/gmock.h"
25 class TestVideoEncoderCallback
26 : public base::RefCountedThreadSafe<TestVideoEncoderCallback> {
28 explicit TestVideoEncoderCallback(bool multiple_buffer_mode)
29 : multiple_buffer_mode_(multiple_buffer_mode),
30 count_frames_delivered_(0) {}
32 int count_frames_delivered() const {
33 return count_frames_delivered_;
36 void SetExpectedResult(uint32 expected_frame_id,
37 uint32 expected_last_referenced_frame_id,
38 uint32 expected_rtp_timestamp,
39 const base::TimeTicks& expected_reference_time) {
40 expected_frame_id_ = expected_frame_id;
41 expected_last_referenced_frame_id_ = expected_last_referenced_frame_id;
42 expected_rtp_timestamp_ = expected_rtp_timestamp;
43 expected_reference_time_ = expected_reference_time;
46 void DeliverEncodedVideoFrame(
47 scoped_ptr<EncodedFrame> encoded_frame) {
48 if (expected_frame_id_ != expected_last_referenced_frame_id_) {
49 EXPECT_EQ(EncodedFrame::DEPENDENT, encoded_frame->dependency);
50 } else if (!multiple_buffer_mode_) {
51 EXPECT_EQ(EncodedFrame::KEY, encoded_frame->dependency);
53 EXPECT_EQ(expected_frame_id_, encoded_frame->frame_id);
54 EXPECT_EQ(expected_last_referenced_frame_id_,
55 encoded_frame->referenced_frame_id)
56 << "frame id: " << expected_frame_id_;
57 EXPECT_EQ(expected_rtp_timestamp_, encoded_frame->rtp_timestamp);
58 EXPECT_EQ(expected_reference_time_, encoded_frame->reference_time);
59 EXPECT_FALSE(encoded_frame->data.empty());
60 ++count_frames_delivered_;
64 friend class base::RefCountedThreadSafe<TestVideoEncoderCallback>;
65 virtual ~TestVideoEncoderCallback() {}
67 const bool multiple_buffer_mode_;
68 int count_frames_delivered_;
70 uint32 expected_frame_id_;
71 uint32 expected_last_referenced_frame_id_;
72 uint32 expected_rtp_timestamp_;
73 base::TimeTicks expected_reference_time_;
75 DISALLOW_COPY_AND_ASSIGN(TestVideoEncoderCallback);
79 class VideoEncoderImplTest : public ::testing::Test {
81 VideoEncoderImplTest() {
82 video_config_ = GetDefaultVideoSenderConfig();
83 video_config_.codec = CODEC_VIDEO_VP8;
84 gfx::Size size(video_config_.width, video_config_.height);
85 video_frame_ = media::VideoFrame::CreateFrame(
86 VideoFrame::I420, size, gfx::Rect(size), size, base::TimeDelta());
87 PopulateVideoFrame(video_frame_.get(), 123);
90 ~VideoEncoderImplTest() override {}
92 void SetUp() override {
93 testing_clock_ = new base::SimpleTestTickClock();
94 testing_clock_->Advance(base::TimeTicks::Now() - base::TimeTicks());
95 task_runner_ = new test::FakeSingleThreadTaskRunner(testing_clock_);
97 new CastEnvironment(scoped_ptr<base::TickClock>(testing_clock_).Pass(),
103 void TearDown() override {
104 video_encoder_.reset();
105 task_runner_->RunTasks();
108 void CreateEncoder() {
109 test_video_encoder_callback_ = new TestVideoEncoderCallback(
110 video_config_.max_number_of_video_buffers_used != 1);
111 video_encoder_.reset(
112 new VideoEncoderImpl(cast_environment_, video_config_));
115 void AdvanceClockAndVideoFrameTimestamp() {
116 testing_clock_->Advance(base::TimeDelta::FromMilliseconds(33));
117 video_frame_->set_timestamp(
118 video_frame_->timestamp() + base::TimeDelta::FromMilliseconds(33));
121 base::SimpleTestTickClock* testing_clock_; // Owned by CastEnvironment.
122 scoped_refptr<TestVideoEncoderCallback> test_video_encoder_callback_;
123 VideoSenderConfig video_config_;
124 scoped_refptr<test::FakeSingleThreadTaskRunner> task_runner_;
125 scoped_ptr<VideoEncoder> video_encoder_;
126 scoped_refptr<media::VideoFrame> video_frame_;
128 scoped_refptr<CastEnvironment> cast_environment_;
130 DISALLOW_COPY_AND_ASSIGN(VideoEncoderImplTest);
133 TEST_F(VideoEncoderImplTest, GeneratesKeyFrameThenOnlyDeltaFrames) {
136 VideoEncoder::FrameEncodedCallback frame_encoded_callback =
137 base::Bind(&TestVideoEncoderCallback::DeliverEncodedVideoFrame,
138 test_video_encoder_callback_.get());
140 EXPECT_EQ(0, test_video_encoder_callback_->count_frames_delivered());
142 test_video_encoder_callback_->SetExpectedResult(
143 0, 0, TimeDeltaToRtpDelta(video_frame_->timestamp(), kVideoFrequency),
144 testing_clock_->NowTicks());
145 EXPECT_TRUE(video_encoder_->EncodeVideoFrame(
146 video_frame_, testing_clock_->NowTicks(), frame_encoded_callback));
147 task_runner_->RunTasks();
149 for (uint32 frame_id = 1; frame_id < 10; ++frame_id) {
150 AdvanceClockAndVideoFrameTimestamp();
151 test_video_encoder_callback_->SetExpectedResult(
154 TimeDeltaToRtpDelta(video_frame_->timestamp(), kVideoFrequency),
155 testing_clock_->NowTicks());
156 EXPECT_TRUE(video_encoder_->EncodeVideoFrame(
157 video_frame_, testing_clock_->NowTicks(), frame_encoded_callback));
158 task_runner_->RunTasks();
161 EXPECT_EQ(10, test_video_encoder_callback_->count_frames_delivered());
164 TEST_F(VideoEncoderImplTest,
165 FramesDoNotDependOnUnackedFramesInMultiBufferMode) {
166 video_config_.max_number_of_video_buffers_used = 3;
169 VideoEncoder::FrameEncodedCallback frame_encoded_callback =
170 base::Bind(&TestVideoEncoderCallback::DeliverEncodedVideoFrame,
171 test_video_encoder_callback_.get());
173 EXPECT_EQ(0, test_video_encoder_callback_->count_frames_delivered());
175 test_video_encoder_callback_->SetExpectedResult(
176 0, 0, TimeDeltaToRtpDelta(video_frame_->timestamp(), kVideoFrequency),
177 testing_clock_->NowTicks());
178 EXPECT_TRUE(video_encoder_->EncodeVideoFrame(
179 video_frame_, testing_clock_->NowTicks(), frame_encoded_callback));
180 task_runner_->RunTasks();
182 AdvanceClockAndVideoFrameTimestamp();
183 video_encoder_->LatestFrameIdToReference(0);
184 test_video_encoder_callback_->SetExpectedResult(
185 1, 0, TimeDeltaToRtpDelta(video_frame_->timestamp(), kVideoFrequency),
186 testing_clock_->NowTicks());
187 EXPECT_TRUE(video_encoder_->EncodeVideoFrame(
188 video_frame_, testing_clock_->NowTicks(), frame_encoded_callback));
189 task_runner_->RunTasks();
191 AdvanceClockAndVideoFrameTimestamp();
192 video_encoder_->LatestFrameIdToReference(1);
193 test_video_encoder_callback_->SetExpectedResult(
194 2, 1, TimeDeltaToRtpDelta(video_frame_->timestamp(), kVideoFrequency),
195 testing_clock_->NowTicks());
196 EXPECT_TRUE(video_encoder_->EncodeVideoFrame(
197 video_frame_, testing_clock_->NowTicks(), frame_encoded_callback));
198 task_runner_->RunTasks();
200 video_encoder_->LatestFrameIdToReference(2);
202 for (uint32 frame_id = 3; frame_id < 10; ++frame_id) {
203 AdvanceClockAndVideoFrameTimestamp();
204 test_video_encoder_callback_->SetExpectedResult(
206 TimeDeltaToRtpDelta(video_frame_->timestamp(), kVideoFrequency),
207 testing_clock_->NowTicks());
208 EXPECT_TRUE(video_encoder_->EncodeVideoFrame(
209 video_frame_, testing_clock_->NowTicks(), frame_encoded_callback));
210 task_runner_->RunTasks();
213 EXPECT_EQ(10, test_video_encoder_callback_->count_frames_delivered());