UltraGrid
UltraGrid Low-Latency High-Resolution Transmission System
Loading...
Searching...
No Matches
resize_utils.cpp File Reference
#include <cstdlib>
#include <opencv2/imgproc.hpp>
#include <opencv2/imgproc/types_c.h>
#include "capture_filter/resize_utils.h"
#include "debug.h"
#include "utils/color_out.h"
#include "video.h"
Include dependency graph for resize_utils.cpp:

Go to the source code of this file.

Macros

#define DEFAULT_ALGO   INTER_LINEAR
 
#define MOD_NAME   "[resize] "
 

Functions

static int get_out_cv_data_type (codec_t pixfmt)
 
int resize_algo_from_string (const char *str)
 
static const char * resize_algo_to_string (int algo)
 
void resize_frame (char *indata, codec_t in_color, char *outdata, int width, int height, struct resize_param *resize_spec)
 
static void resize_frame_dimensions (char *indata, codec_t in_color, char *outdata, int width, int height, int target_width, int target_height, int algo)
 
static Mat ug_to_rgb_mat (codec_t codec, int width, int height, char *indata)
 

Variables

struct { 
 
   const char *   name 
 
   int   val 
 
} interp_map [] 
 

Detailed Description

Macro Definition Documentation

◆ DEFAULT_ALGO

#define DEFAULT_ALGO   INTER_LINEAR

Definition at line 69 of file resize_utils.cpp.

Referenced by resize_algo_from_string(), and resize_frame().

◆ MOD_NAME

#define MOD_NAME   "[resize] "

Definition at line 70 of file resize_utils.cpp.

Referenced by ug_to_rgb_mat().

Function Documentation

◆ get_out_cv_data_type()

static int get_out_cv_data_type ( codec_t pixfmt)
static

Definition at line 130 of file resize_utils.cpp.

131{
132 return get_bits_per_component(pixfmt) == DEPTH16 ? CV_16UC3 : CV_8UC3;
133}
@ DEPTH16
Definition types.h:129
int get_bits_per_component(codec_t codec)

References DEPTH16, and get_bits_per_component().

Referenced by resize_frame(), and resize_frame_dimensions().

Here is the call graph for this function:

◆ resize_algo_from_string()

int resize_algo_from_string ( const char * str)

Definition at line 224 of file resize_utils.cpp.

225{
226 if (strcmp(str, "help") == 0) {
227 color_printf("Available resize algorithms:\n");
228 for (auto const &i : interp_map) {
229 color_printf("\t" TBOLD("%s") "%s\n", i.name,
230 i.val == DEFAULT_ALGO ? " (default)" : "");
231 }
233 }
234 for (auto const &i : interp_map) {
235 if (strcmp(i.name, str) == 0) {
236 return i.val;
237 }
238 }
239 return RESIZE_ALGO_UNKN;
240}
int color_printf(const char *format,...)
#define TBOLD(x)
Definition color_out.h:70
#define DEFAULT_ALGO
static const struct @12 interp_map[]
#define RESIZE_ALGO_UNKN
#define RESIZE_ALGO_HELP_SHOWN

References color_printf(), DEFAULT_ALGO, interp_map, RESIZE_ALGO_HELP_SHOWN, RESIZE_ALGO_UNKN, and TBOLD.

Referenced by parse_fmt().

Here is the call graph for this function:

◆ resize_algo_to_string()

static const char * resize_algo_to_string ( int algo)
static

Definition at line 243 of file resize_utils.cpp.

244{
245 for (auto const &i : interp_map) {
246 if (i.val == algo) {
247 return i.name;
248 }
249 }
250 return "(unknown algo!)";
251}

References interp_map.

Referenced by resize_frame().

◆ resize_frame()

void resize_frame ( char * indata,
codec_t in_color,
char * outdata,
int width,
int height,
struct resize_param * resize_spec )

Definition at line 184 of file resize_utils.cpp.

186{
187 if (resize_spec->algo == RESIZE_ALGO_DFL) {
188 resize_spec->algo = DEFAULT_ALGO;
189 MSG(NOTICE, "using resize algorithm: %s\n",
191 }
192
193 DEBUG_TIMER_START(resize);
194 if (resize_spec->mode == resize_param::USE_FRACTION) {
195 const double factor = resize_spec->factor;
196 Mat rgb = ug_to_rgb_mat(in_color, (int) width, (int) height, indata);
197 Mat out((int) (height * factor), (int) (width * factor),
198 get_out_cv_data_type(in_color), outdata);
199 resize(rgb, out, Size(0, 0), factor, factor, resize_spec->algo);
200 } else if (resize_spec->mode == resize_param::USE_DIMENSIONS) {
201 resize_frame_dimensions(indata, in_color, outdata, width, height,
202 resize_spec->target_width,
203 resize_spec->target_height, resize_spec->algo);
204 } else {
205 abort();
206 }
207 DEBUG_TIMER_STOP(resize);
208}
#define DEBUG_TIMER_START(name)
Definition debug.h:324
#define DEBUG_TIMER_STOP(name)
Definition debug.h:325
#define MSG(l, fmt,...)
Definition debug.h:96
static const char * resize_algo_to_string(int algo)
static Mat ug_to_rgb_mat(codec_t codec, int width, int height, char *indata)
static void resize_frame_dimensions(char *indata, codec_t in_color, char *outdata, int width, int height, int target_width, int target_height, int algo)
static int get_out_cv_data_type(codec_t pixfmt)
#define RESIZE_ALGO_DFL
enum resize_param::resize_mode mode

References resize_param::algo, DEBUG_TIMER_START, DEBUG_TIMER_STOP, DEFAULT_ALGO, resize_param::factor, get_out_cv_data_type(), resize_param::mode, MSG, RESIZE_ALGO_DFL, resize_algo_to_string(), resize_frame_dimensions(), resize_param::target_height, resize_param::target_width, ug_to_rgb_mat(), resize_param::USE_DIMENSIONS, and resize_param::USE_FRACTION.

Referenced by filter().

Here is the call graph for this function:

◆ resize_frame_dimensions()

static void resize_frame_dimensions ( char * indata,
codec_t in_color,
char * outdata,
int width,
int height,
int target_width,
int target_height,
int algo )
static

Definition at line 136 of file resize_utils.cpp.

139{
140 const codec_t out_color =
141 get_bits_per_component(in_color) == 16 ? RG48 : RGB;
142 Mat rgb = ug_to_rgb_mat(in_color, (int) width, (int) height, indata);
143
144 double in_aspect = (double) width / height;
145 double out_aspect = (double) target_width / target_height;
146 Rect r;
147 if (in_aspect == out_aspect) {
148 r.x = 0;
149 r.y = 0;
150 r.width = target_width;
151 r.height = target_height;
152 } else if (in_aspect > out_aspect) {
153 r.x = 0;
154 r.width = target_width;
155 r.height = (int) (target_width / in_aspect);
156 r.y = (target_height - r.height) / 2;
157 // clear top and bottom margin
158 size_t linesize = vc_get_linesize(target_width, out_color);
159 size_t top_margin_size = r.y * linesize;
160 size_t bottom_margin_size = (target_height - r.y - r.height) * linesize;
161 memset(outdata, 0, top_margin_size);
162 memset(outdata + linesize * target_height - bottom_margin_size, 0, bottom_margin_size);
163 } else {
164 r.y = 0;
165 r.height = target_height;
166 r.width = (int) (target_height * in_aspect);
167 r.x = (target_width - r.width) / 2;
168 // clear left and right margins
169 size_t linesize = vc_get_linesize(target_width, out_color);
170 size_t left_margin_size = vc_get_linesize(r.x, out_color);
171 size_t right_margin_size = vc_get_linesize(target_width - r.x - r.width, out_color);
172 for (int i = 0; i < target_height; ++i) {
173 memset(outdata + i * linesize, 0, left_margin_size);
174 memset(outdata + (i + 1) * linesize - right_margin_size, 0, right_margin_size);
175 }
176 }
177
178 Mat out((int) target_height, (int) target_width,
179 get_out_cv_data_type(in_color), outdata);
180 resize(rgb, out(r), r.size(), 0, 0, algo);
181}
int vc_get_linesize(unsigned int width, codec_t codec)
codec_t
Definition types.h:65
@ RGB
RGB 8-bit (packed into 24-bit word)
Definition types.h:80
@ RG48
16-bit RGB little-endian (RlRhGl...)
Definition types.h:95

References get_bits_per_component(), get_out_cv_data_type(), RG48, RGB, ug_to_rgb_mat(), and vc_get_linesize().

Referenced by resize_frame().

Here is the call graph for this function:

◆ ug_to_rgb_mat()

static Mat ug_to_rgb_mat ( codec_t codec,
int width,
int height,
char * indata )
static

Definition at line 85 of file resize_utils.cpp.

85 {
86 Mat yuv;
87 Mat rgb;
88 int pix_fmt = CV_8UC2;
89 int cv_color = 0;
90 int num = 1;
91 int den = 1;
92
93 switch (codec) {
94 case RG48:
95 rgb.create(height, width, CV_16UC3);
96 rgb.data = (uchar*)indata;
97 return rgb;
98 case RGB:
99 rgb.create(height, width, CV_8UC3);
100 rgb.data = (uchar*)indata;
101 return rgb;
102 case RGBA:
103 cv_color = CV_RGBA2RGB;
104 pix_fmt = CV_8UC4;
105 break;
106 case I420:
107 pix_fmt = CV_8U;
108 num = 3;
109 den = 2;
110 cv_color = CV_YUV2RGB_I420;
111 break;
112 case UYVY:
113 cv_color = CV_YUV2RGB_UYVY;
114 break;
115 case YUYV:
116 cv_color = CV_YUV2RGB_YUYV;
117 break;
118 default:
119 LOG(LOG_LEVEL_ERROR) << MOD_NAME "Unsupported codec: " << codec << "\n";
120 abort();
121 }
122 yuv.create(height * num / den, width, pix_fmt);
123 yuv.data = (uchar*)indata;
124 cvtColor(yuv, rgb, cv_color);
125
126 return rgb;
127}
#define LOG_LEVEL_ERROR
general errors
Definition debug.h:59
#define LOG(level)
Definition debug.h:313
#define MOD_NAME
@ YUYV
YCbCr 422 8-bit - Y0 Cb Y1 Cr.
Definition types.h:72
@ UYVY
YCbCr 422 8-bit - Cb Y0 Cr Y1.
Definition types.h:71
@ I420
planar YCbCr 4:2:0
Definition types.h:97
@ RGBA
RGBA 8-bit, big-endian.
Definition types.h:70

References I420, LOG, LOG_LEVEL_ERROR, MOD_NAME, RG48, RGB, RGBA, UYVY, and YUYV.

Referenced by resize_frame(), and resize_frame_dimensions().

Variable Documentation

◆ [struct]

const struct { ... } interp_map[]
Initial value:
= {
{INTER_NEAREST, "nearest" },
{ INTER_LINEAR, "linear" },
{ INTER_CUBIC, "cubic" },
{ INTER_AREA, "area" },
{ INTER_LANCZOS4, "lanczos4" },
}

Referenced by resize_algo_from_string(), and resize_algo_to_string().

◆ name

const char* name

Definition at line 212 of file resize_utils.cpp.

◆ val

int val

Definition at line 211 of file resize_utils.cpp.