summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJim Bankoski <jimbankoski@google.com>2012-06-23 11:20:41 -0700
committerJim Bankoski <jimbankoski@google.com>2012-06-23 11:20:41 -0700
commit96b6b6bbf046c944b44a2ca96d4c6adb851fecf7 (patch)
tree25625440ce08d1ce32e73e2c74d9193802cace33
parent007486329fe79280f6b062a85fad9ba8720aaaea (diff)
downloadlibvpx-96b6b6bbf046c944b44a2ca96d4c6adb851fecf7.tar
libvpx-96b6b6bbf046c944b44a2ca96d4c6adb851fecf7.tar.gz
libvpx-96b6b6bbf046c944b44a2ca96d4c6adb851fecf7.tar.bz2
libvpx-96b6b6bbf046c944b44a2ca96d4c6adb851fecf7.zip
add auto keyframe unit test
To do so we add a framework for encoding a yv12 file.. Change-Id: I94a061eb916beaf6cde920cf1aaadb6eed10a717
-rw-r--r--test/encode_test_driver.cc3
-rw-r--r--test/i420_video_source.h117
-rw-r--r--test/keyframe_test.cc42
-rw-r--r--test/test-data.sha11
-rw-r--r--test/test.mk3
5 files changed, 155 insertions, 11 deletions
diff --git a/test/encode_test_driver.cc b/test/encode_test_driver.cc
index 0a188facf..d7aaf6b2a 100644
--- a/test/encode_test_driver.cc
+++ b/test/encode_test_driver.cc
@@ -105,8 +105,7 @@ void EncoderTest::RunLoop(VideoSource *video) {
Encoder encoder(cfg_, deadline_, &stats_);
bool again;
-
- for (video->Begin(), again = true; again; video->Next()) {
+ for (again = true, video->Begin(); again; video->Next()) {
again = video->img() != NULL;
PreEncodeFrameHook(video);
diff --git a/test/i420_video_source.h b/test/i420_video_source.h
new file mode 100644
index 000000000..f4717647b
--- /dev/null
+++ b/test/i420_video_source.h
@@ -0,0 +1,117 @@
+/*
+ * Copyright (c) 2012 The WebM project authors. All Rights Reserved.
+ *
+ * Use of this source code is governed by a BSD-style license
+ * that can be found in the LICENSE file in the root of the source
+ * tree. An additional intellectual property rights grant can be found
+ * in the file PATENTS. All contributing project authors may
+ * be found in the AUTHORS file in the root of the source tree.
+ */
+#ifndef TEST_I420_VIDEO_SOURCE_H_
+#define TEST_I420_VIDEO_SOURCE_H_
+#include <cstdio>
+#include <cstdlib>
+
+#include "test/video_source.h"
+
+namespace libvpx_test {
+
+// This class extends VideoSource to allow parsing of raw yv12
+// so that we can do actual file encodes.
+class I420VideoSource : public VideoSource {
+ public:
+ I420VideoSource(const std::string &file_name,
+ unsigned int width, unsigned int height,
+ int rate_numerator, int rate_denominator,
+ unsigned int start, int limit)
+ : file_name_(file_name),
+ img_(NULL),
+ start_(start),
+ limit_(limit),
+ framerate_numerator_(rate_numerator),
+ framerate_denominator_(rate_denominator) {
+
+ // This initializes raw_sz_, width_, height_ and allocates an img.
+ SetSize(width, height);
+ }
+
+ virtual ~I420VideoSource() {
+ vpx_img_free(img_);
+ if (input_file_)
+ fclose(input_file_);
+ }
+
+ virtual void Begin() {
+ std::string path_to_source = file_name_;
+ const char *kDataPath = getenv("LIBVPX_TEST_DATA_PATH");
+ if (kDataPath) {
+ path_to_source = kDataPath;
+ path_to_source += "/";
+ path_to_source += file_name_;
+ }
+
+ input_file_ = fopen(path_to_source.c_str(), "rb");
+ ASSERT_TRUE(input_file_) << "File open failed.";
+
+ if (start_) {
+ fseek(input_file_, raw_sz_ * start_, SEEK_SET);
+ }
+
+ frame_ = start_;
+ FillFrame();
+ }
+
+ virtual void Next() {
+ ++frame_;
+ FillFrame();
+ }
+
+ virtual vpx_image_t *img() const { return (frame_ < limit_) ? img_ : NULL; }
+
+ // Models a stream where Timebase = 1/FPS, so pts == frame.
+ virtual vpx_codec_pts_t pts() const { return frame_; }
+
+ virtual unsigned long duration() const { return 1; }
+
+ virtual vpx_rational_t timebase() const {
+ const vpx_rational_t t = { framerate_denominator_, framerate_numerator_ };
+ return t;
+ }
+
+ virtual unsigned int frame() const { return frame_; }
+
+ void SetSize(unsigned int width, unsigned int height) {
+ if (width != width_ || height != height_) {
+ vpx_img_free(img_);
+ img_ = vpx_img_alloc(NULL, VPX_IMG_FMT_VPXI420, width, height, 1);
+ ASSERT_TRUE(img_ != NULL);
+ width_ = width;
+ height_ = height;
+ raw_sz_ = width * height * 3 / 2;
+ }
+ }
+
+ virtual void FillFrame() {
+ // Read a frame from input_file.
+ if (fread(img_->img_data, raw_sz_, 1, input_file_) == 0) {
+ limit_ = frame_;
+ }
+ }
+
+ protected:
+ std::string file_name_;
+ FILE *input_file_;
+ vpx_image_t *img_;
+ size_t raw_sz_;
+ unsigned int start_;
+ unsigned int limit_;
+ unsigned int frame_;
+ unsigned int width_;
+ unsigned int height_;
+ unsigned int framerate_numerator_;
+ unsigned int framerate_denominator_;
+};
+
+} // namespace libvpx_test
+
+#endif // TEST_I420_VIDEO_SOURCE_H_
diff --git a/test/keyframe_test.cc b/test/keyframe_test.cc
index db18e5dab..aacccb1b8 100644
--- a/test/keyframe_test.cc
+++ b/test/keyframe_test.cc
@@ -10,13 +10,13 @@
#include <climits>
#include <vector>
#include "test/encode_test_driver.h"
-#include "test/video_source.h"
+#include "test/i420_video_source.h"
#include "third_party/googletest/src/include/gtest/gtest.h"
namespace {
class KeyframeTest : public ::libvpx_test::EncoderTest,
- public ::testing::TestWithParam<enum libvpx_test::TestMode> {
+ public ::testing::TestWithParam<enum libvpx_test::TestMode> {
protected:
virtual void SetUp() {
InitializeConfig();
@@ -46,7 +46,7 @@ class KeyframeTest : public ::libvpx_test::EncoderTest,
bool kf_do_force_kf_;
int kf_count_;
int kf_count_max_;
- std::vector< vpx_codec_pts_t > kf_pts_list_;
+ std::vector<vpx_codec_pts_t> kf_pts_list_;
};
TEST_P(KeyframeTest, TestRandomVideoSource) {
@@ -78,9 +78,8 @@ TEST_P(KeyframeTest, TestForceKeyframe) {
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
// verify that every third frame is a keyframe.
- for (std::vector<vpx_codec_pts_t>::iterator iter = kf_pts_list_.begin();
- iter != kf_pts_list_.end();
- ++iter) {
+ for (std::vector<vpx_codec_pts_t>::const_iterator iter = kf_pts_list_.begin();
+ iter != kf_pts_list_.end(); ++iter) {
ASSERT_EQ(0, *iter % 3) << "Unexpected keyframe at frame " << *iter;
}
}
@@ -92,12 +91,37 @@ TEST_P(KeyframeTest, TestKeyframeMaxDistance) {
ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
// verify that keyframe interval matches kf_max_dist
- for (std::vector<vpx_codec_pts_t>::iterator iter = kf_pts_list_.begin();
- iter != kf_pts_list_.end();
- iter++) {
+ for (std::vector<vpx_codec_pts_t>::const_iterator iter = kf_pts_list_.begin();
+ iter != kf_pts_list_.end(); ++iter) {
ASSERT_EQ(0, *iter % 25) << "Unexpected keyframe at frame " << *iter;
}
}
+TEST_P(KeyframeTest, TestAutoKeyframe) {
+ cfg_.kf_mode = VPX_KF_AUTO;
+ kf_do_force_kf_ = false;
+
+ // This clip has a cut scene every 30 frames -> Frame 0, 30, 60, 90, 120.
+ // I check only the first 40 frames to make sure there's a keyframe at frame
+ // 0 and 30.
+ ::libvpx_test::I420VideoSource video("hantro_collage_w352h288.yuv", 352, 288,
+ 30, 1, 0, 40);
+
+ ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
+
+ EXPECT_EQ(2u, kf_pts_list_.size()) << " Not the right number of keyframes ";
+
+ // Verify that keyframes match the file keyframes in the file.
+ for (std::vector<vpx_codec_pts_t>::const_iterator iter = kf_pts_list_.begin();
+ iter != kf_pts_list_.end(); ++iter) {
+
+ if (deadline_ == VPX_DL_REALTIME && *iter > 0)
+ EXPECT_EQ(0, (*iter - 1) % 30) << "Unexpected keyframe at frame "
+ << *iter;
+ else
+ EXPECT_EQ(0, *iter % 30) << "Unexpected keyframe at frame " << *iter;
+ }
+}
+
INSTANTIATE_TEST_CASE_P(AllModes, KeyframeTest, ALL_TEST_MODES);
} // namespace
diff --git a/test/test-data.sha1 b/test/test-data.sha1
new file mode 100644
index 000000000..8d40242b8
--- /dev/null
+++ b/test/test-data.sha1
@@ -0,0 +1 @@
+d5dfb0151c9051f8c85999255645d7a23916d3c0 hantro_collage_w352h288.yuv
diff --git a/test/test.mk b/test/test.mk
index d58beb41e..c68801db0 100644
--- a/test/test.mk
+++ b/test/test.mk
@@ -3,8 +3,11 @@ LIBVPX_TEST_SRCS-yes += boolcoder_test.cc
LIBVPX_TEST_SRCS-yes += config_test.cc
LIBVPX_TEST_SRCS-yes += encode_test_driver.cc
LIBVPX_TEST_SRCS-yes += encode_test_driver.h
+LIBVPX_TEST_SRCS-yes += i420_video_source.h
LIBVPX_TEST_SRCS-yes += idctllm_test.cc
LIBVPX_TEST_SRCS-yes += keyframe_test.cc
LIBVPX_TEST_SRCS-yes += resize_test.cc
LIBVPX_TEST_SRCS-yes += test_libvpx.cc
LIBVPX_TEST_SRCS-yes += video_source.h
+
+LIBVPX_TEST_DATA-yes += hantro_collage_w352h288.yuv \ No newline at end of file