Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(15)

Side by Side Diff: webrtc/tools/frame_analyzer/reference_less_video_analysis_lib.cc

Issue 2515253004: Added tool for reference less video analysis (Closed)
Patch Set: Added newline character Created 4 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
(Empty)
1 /*
2 * Copyright (c) 2016 The WebRTC project authors. All Rights Reserved.
3 *
4 * Use of this source code is governed by a BSD-style license
5 * that can be found in the LICENSE file in the root of the source
6 * tree. An additional intellectual property rights grant can be found
7 * in the file PATENTS. All contributing project authors may
8 * be found in the AUTHORS file in the root of the source tree.
9 */
10 #include <stdio.h>
11 #include <stdlib.h>
12 #include <string.h>
13 #include <iostream>
14 #include <numeric>
15 #include <vector>
16
17 #include "webrtc/tools/frame_analyzer/reference_less_video_analysis_lib.h"
18 #include "webrtc/tools/frame_analyzer/video_quality_analysis.h"
19 #include "third_party/libvpx/source/libvpx/y4minput.h"
20
21 #define PSNR_FREEZE_THRESHOLD 47
22 #define SSIM_FREEZE_THRESHOLD .999
23
24 void get_height_width_fps(int *height, int *width, int *fps,
25 const std::string& video_file) {
26 FILE* input_file = fopen(video_file.c_str(), "rb");
27 y4m_input y4m;
28 y4m_input_open(&y4m, input_file, NULL, 0, 0);
29 *width = y4m.pic_w;
30 *height = y4m.pic_h;
31 *fps = y4m.fps_n;
32 fclose(input_file);
33
34 printf("Height: %d Width: %d fps:%d \n", *height, *width, *fps);
35 }
36
37 bool frozen_frame(std::vector<double> psnr_per_frame,
38 std::vector<double> ssim_per_frame, size_t frame) {
39 if (psnr_per_frame[frame] >= PSNR_FREEZE_THRESHOLD ||
40 ssim_per_frame[frame] >= SSIM_FREEZE_THRESHOLD)
41 return true;
42 return false;
43 }
44
45 std::vector<int> find_frame_clusters(const std::vector<double>& psnr_per_frame,
46 const std::vector<double>& ssim_per_frame) {
47 std::vector<int> identical_frame_clusters;
48 int num_frozen = 0;
49 size_t total_no_of_frames = psnr_per_frame.size();
50
51 for (size_t each_frame = 0; each_frame < total_no_of_frames; each_frame++) {
52 if (frozen_frame(psnr_per_frame, ssim_per_frame, each_frame)) {
53 num_frozen++;
54 } else if (num_frozen > 0) {
55 // Not frozen anymore.
56 identical_frame_clusters.push_back(num_frozen);
57 num_frozen = 0;
58 }
59 }
60 return identical_frame_clusters;
61 }
62
63 void print_freezing_metrics(const std::vector<double>& psnr_per_frame,
64 const std::vector<double>& ssim_per_frame) {
65 /*
66 * Prints the different metrics mainly:
67 * 1) Identical frame number, PSNR and SSIM values.
68 * 2) Length of continuous frozen frames.
69 * 3) Max length of continuous freezed frames.
70 * 4) No of unique frames found.
71 * 5) Total different identical frames found.
72 *
73 * Sample output:
74 * Printing metrics for file: /src/webrtc/tools/test_3.y4m
75 =============================
76 Total number of frames received: 74
77 Total identical frames: 5
78 Number of unique frames: 69
79 Printing Identical Frames:
80 Frame Number: 29 PSNR: 48.000000 SSIM: 0.999618
81 Frame Number: 30 PSNR: 48.000000 SSIM: 0.999898
82 Frame Number: 60 PSNR: 48.000000 SSIM: 0.999564
83 Frame Number: 64 PSNR: 48.000000 SSIM: 0.999651
84 Frame Number: 69 PSNR: 48.000000 SSIM: 0.999684
85 Print identical frame which appears in clusters :
86 2 1 1 1
87 *
88 */
89 size_t total_no_of_frames = psnr_per_frame.size();
90 std::vector<int> identical_frame_clusters = find_frame_clusters(
91 psnr_per_frame, ssim_per_frame);
92 int total_identical_frames = std::accumulate(
93 identical_frame_clusters.begin(), identical_frame_clusters.end(), 0);
94 size_t unique_frames = total_no_of_frames - total_identical_frames;
95
96 printf("Total number of frames received: %zu\n", total_no_of_frames);
97 printf("Total identical frames: %d\n", total_identical_frames);
98 printf("Number of unique frames: %zu\n", unique_frames);
99
100 printf("Printing Identical Frames: \n");
101 for (size_t frame = 0; frame < total_no_of_frames; frame++) {
102 if (frozen_frame(psnr_per_frame, ssim_per_frame, frame)) {
103 printf(" Frame Number: %zu PSNR: %f SSIM: %f \n", frame,
104 psnr_per_frame[frame], ssim_per_frame[frame]);
105 }
106 }
107
108 printf("Print identical frame which appears in clusters : \n");
109 for (int cluster = 0;
110 cluster < static_cast<int>(identical_frame_clusters.size()); cluster++)
111 printf("%d ", identical_frame_clusters[cluster]);
112 printf("\n");
113 }
114
115 void compute_metrics(const std::string& video_file_name,
116 std::vector<double>* psnr_per_frame,
117 std::vector<double>* ssim_per_frame) {
118 int height = 0, width = 0, fps = 0;
119 get_height_width_fps(&height, &width, &fps, video_file_name);
120
121 int no_of_frames = 0;
122 int size = webrtc::test::GetI420FrameSize(width, height);
123
124 // Allocate buffers for test and reference frames.
125 uint8_t* current_frame = new uint8_t[size];
126 uint8_t* next_frame = new uint8_t[size];
127
128 while (true) {
129 if (!(webrtc::test::ExtractFrameFromY4mFile (video_file_name.c_str(),
130 width, height,
131 no_of_frames,
132 current_frame))) {
133 break;
134 }
135
136 if (!(webrtc::test::ExtractFrameFromY4mFile (video_file_name.c_str(),
137 width, height,
138 no_of_frames + 1,
139 next_frame))) {
140 break;
141 }
142
143 double result_psnr = webrtc::test::CalculateMetrics(webrtc::test::kPSNR,
144 current_frame,
145 next_frame,
146 width, height);
147 double result_ssim = webrtc::test::CalculateMetrics(webrtc::test::kSSIM,
148 current_frame,
149 next_frame,
150 width, height);
151
152 psnr_per_frame->push_back(result_psnr);
153 ssim_per_frame->push_back(result_ssim);
154 no_of_frames++;
155 }
156 // Cleanup.
157 delete[] current_frame;
158 delete[] next_frame;
159 }
160
161 bool check_file_extension(const std::string& video_file_name) {
162 if (video_file_name.substr(video_file_name.length()-3, 3) != "y4m") {
163 printf("Only y4m video file format is supported. Given: %s\n",
164 video_file_name.c_str());
165 return false;
166 }
167 return true;
168 }
169
170 int run_analysis(const std::string& video_file) {
171 std::vector<double> psnr_per_frame;
172 std::vector<double> ssim_per_frame;
173 if (check_file_extension(video_file)) {
174 compute_metrics(video_file, &psnr_per_frame, &ssim_per_frame);
175 } else {
176 return -1;
177 }
178 printf("=============================\n");
179 printf("Printing metrics for file: %s\n", video_file.c_str());
180 printf("=============================\n");
181 print_freezing_metrics(psnr_per_frame, ssim_per_frame);
182 return 0;
183 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698