1 /*
2 * Copyright (C) 2012 Mark Himsley
3 *
4 * get_scene_score() Copyright (c) 2011 Stefano Sabatini
5 * taken from libavfilter/vf_select.c
6 *
7 * This file is part of FFmpeg.
8 *
9 * FFmpeg is free software; you can redistribute it and/or
10 * modify it under the terms of the GNU Lesser General Public
11 * License as published by the Free Software Foundation; either
12 * version 2.1 of the License, or (at your option) any later version.
13 *
14 * FFmpeg is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
17 * Lesser General Public License for more details.
18 *
19 * You should have received a copy of the GNU Lesser General Public
20 * License along with FFmpeg; if not, write to the Free Software
21 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
22 */
23
24 /**
25 * @file
26 * filter for upsampling or downsampling a progressive source
27 */
28
30
37
42
43 #define OFFSET(x) offsetof(FrameRateContext, x)
44 #define V AV_OPT_FLAG_VIDEO_PARAM
45 #define F AV_OPT_FLAG_FILTERING_PARAM
46 #define FRAMERATE_FLAG_SCD 01
47
50
51 {
"interp_start",
"point to start linear interpolation",
OFFSET(interp_start),
AV_OPT_TYPE_INT, {.i64=15}, 0, 255,
V|
F },
52 {
"interp_end",
"point to end linear interpolation",
OFFSET(interp_end),
AV_OPT_TYPE_INT, {.i64=240}, 0, 255,
V|
F },
54
58
60 };
61
63
65 const uint16_t *src2, ptrdiff_t stride2)
66 {
67 int sum = 0;
68 int x, y;
69
70 for (y = 0; y < 8; y++) {
71 for (x = 0; x < 8; x++)
72 sum +=
FFABS(src1[x] - src2[x]);
73 src1 += stride1;
74 src2 += stride2;
75 }
76 return sum;
77 }
78
80 {
81 int64_t sad;
82 int x, y;
83 for (sad = y = 0; y < height - 7; y += 8) {
84 for (x = 0; x < width - 7; x += 8) {
86 p1_linesize,
87 p2 + y * p2_linesize + x,
88 p2_linesize);
89 }
90 }
91 return sad;
92 }
93
95 {
96 int64_t sad;
97 int x, y;
98 for (sad = y = 0; y < height - 7; y += 8) {
99 for (x = 0; x < width - 7; x += 8) {
100 sad += s->
sad(p1 + y * p1_linesize + x,
101 p1_linesize,
102 p2 + y * p2_linesize + x,
103 p2_linesize);
104 }
105 }
106 emms_c();
107 return sad;
108 }
109
111 {
113 double ret = 0;
114
115 ff_dlog(ctx,
"get_scene_score()\n");
116
119 int64_t sad;
121
122 ff_dlog(ctx,
"get_scene_score() process\n");
125 else
127
130 ret = av_clipf(
FFMIN(mafd, diff), 0, 100.0);
132 }
133 ff_dlog(ctx,
"get_scene_score() result is:%f\n", ret);
134 return ret;
135 }
136
141
143 {
149
159 const int start = (cpy_src_h * job ) / nb_jobs;
160 const int end = (cpy_src_h * (job+1)) / nb_jobs;
161 cpy_src1_data += start * cpy_src1_line_size;
162 cpy_src2_data += start * cpy_src2_line_size;
163 cpy_dst_data += start * cpy_dst_line_size;
164
165 s->
blend(cpy_src1_data, cpy_src1_line_size,
166 cpy_src2_data, cpy_src2_line_size,
167 cpy_dst_data, cpy_dst_line_size,
168 cpy_line_width, end - start,
170 }
171
172 return 0;
173 }
174
176 {
179 double interpolate_scene_score = 0;
180
183 interpolate_scene_score = s->
score;
184 else
186 ff_dlog(ctx,
"blend_frames() interpolate scene score:%f\n", interpolate_scene_score);
187 }
188 // decide if the shot-change detection allows us to blend two frames
189 if (interpolate_scene_score < s->scene_score) {
195
196 // get work-space for output frame
200
202
203 ff_dlog(ctx,
"blend_frames() INTERPOLATE to create work frame\n");
205 return 1;
206 }
207 return 0;
208 }
209
211 {
213 int64_t work_pts;
215 int ret;
216
218 return 0;
220 return 0;
221
223
225 return 0;
226
229 } else {
231 return 0;
232
235 ff_dlog(ctx,
"process_work_frame() interpolate: %"PRId64
"/256\n", interpolate8);
238 } else if (interpolate <= 0 || interpolate8 < s->interp_start) {
240 } else {
242 if (ret < 0)
243 return ret;
244 if (ret == 0)
246 }
247 }
248
251
254
255 return 1;
256 }
257
259 {
262 return 0;
263 }
264
266 {
270 }
271
273 {
285 };
286
288 if (!fmts_list)
291 }
292
294 {
296 for (line = 0; line <
height; line++) {
297 for (pixel = 0; pixel <
width; pixel++)
299 src1 += src1_linesize;
300 src2 += src2_linesize;
301 dst += dst_linesize;
302 }
303 }
304
306 {
308 uint16_t *dstw = (uint16_t *)dst;
309 uint16_t *src1w = (uint16_t *)
src1;
310 uint16_t *src2w = (uint16_t *)src2;
312 src1_linesize /= 2;
313 src2_linesize /= 2;
314 dst_linesize /= 2;
315 for (line = 0; line <
height; line++) {
316 for (pixel = 0; pixel <
width; pixel++)
318 src1w += src1_linesize;
319 src2w += src2_linesize;
320 dstw += dst_linesize;
321 }
322 }
323
325 {
329 } else {
332 }
333 if (ARCH_X86)
335 }
336
338 {
343
344 for (plane = 0; plane < 4; plane++) {
346 plane);
347 }
348
351
355
357
359
360 return 0;
361 }
362
364 {
365 int ret;
369
372
375 return 0;
376 }
377
379 if (s->
f1 && pts == s->
pts1) {
381 return 0;
382 }
383
391
397 }
398
401
402 do {
404 if (ret <= 0)
405 return ret;
407 } while (ret >= 0);
408
409 return ret;
410 }
411
413 {
416 int exact;
417
418 ff_dlog(ctx,
"config_output()\n");
419
421 "config_output() input time base:%u/%u (%f)\n",
424
425 // make sure timebase is small enough to hold the framerate
426
431
433 "time base:%u/%u -> %u/%u exact:%d\n",
436 if (!exact) {
438 }
439
442
444 "config_output() output time base:%u/%u (%f) w:%d h:%d\n",
447 outlink->
w, outlink->
h);
448
449
450 av_log(ctx,
AV_LOG_INFO,
"fps -> fps:%u/%u scene score:%f interpolate start:%d end:%d\n",
453
454 return 0;
455 }
456
458 {
461 int ret;
462
463 ff_dlog(ctx,
"request_frame()\n");
464
469 if (ret < 0)
470 return ret;
472 }
473
474 ff_dlog(ctx,
"request_frame() source's request_frame() returned:%d\n", ret);
475 return ret;
476 }
477
479 {
484 },
486 };
487
489 {
494 },
496 };
497
500 .description =
NULL_IF_CONFIG_SMALL(
"Upsamples or downsamples progressive source between specified frame rates."),
502 .priv_class = &framerate_class,
506 .
inputs = framerate_inputs,
509 };
static int64_t scene_sad16(FrameRateContext *s, const uint16_t *p1, int p1_linesize, const uint16_t *p2, int p2_linesize, const int width, const int height)
int av_image_get_linesize(enum AVPixelFormat pix_fmt, int width, int plane)
Compute the size of an image line with format pix_fmt and width width for the plane plane...
static void blend_frames16_c(BLEND_FUNC_PARAMS)
const AVPixFmtDescriptor * av_pix_fmt_desc_get(enum AVPixelFormat pix_fmt)
This structure describes decoded (raw) audio or video data.
static int process_work_frame(AVFilterContext *ctx)
static av_cold void uninit(AVFilterContext *ctx)
double scene_score
score that denotes a scene change has happened
double score
scene change score (f0 to f1)
static int64_t scene_sad8(FrameRateContext *s, uint8_t *p1, int p1_linesize, uint8_t *p2, int p2_linesize, const int width, const int height)
planar YUV 4:4:4, 24bpp, (1 Cr & Cb sample per 1x1 Y samples)
#define AV_LOG_WARNING
Something somehow does not look correct.
Main libavfilter public API header.
int64_t pts0
last frame pts in dest_time_base
int h
agreed upon image height
static double get_scene_score(AVFilterContext *ctx, AVFrame *crnt, AVFrame *next)
#define AV_PIX_FMT_YUV420P12
AVFrame * ff_get_video_buffer(AVFilterLink *link, int w, int h)
Request a picture buffer with a specific set of permissions.
AVFILTER_DEFINE_CLASS(framerate)
int64_t pts1
current frame pts in dest_time_base
int interp_end
end of range to apply linear interpolation
const char * name
Pad name.
AVFilterLink ** inputs
array of pointers to input links
int ff_filter_frame(AVFilterLink *link, AVFrame *frame)
Send a frame of data to the next filter.
AVComponentDescriptor comp[4]
Parameters that describe how pixels are packed.
#define BLEND_FACTOR_DEPTH16
static av_cold int end(AVCodecContext *avctx)
AVRational dest_frame_rate
output frames per second
int64_t pts
Presentation timestamp in time_base units (time when frame should be shown to user).
static void interpolate(float *out, float v1, float v2, int size)
static double av_q2d(AVRational a)
Convert an AVRational to a double.
planar YUV 4:4:0 full scale (JPEG), deprecated in favor of AV_PIX_FMT_YUV440P and setting color_range...
planar YUV 4:2:2, 16bpp, full scale (JPEG), deprecated in favor of AV_PIX_FMT_YUV422P and setting col...
static int request_frame(AVFilterLink *outlink)
#define AVERROR_EOF
End of file.
int interlaced_frame
The content of the picture is interlaced.
int flags
flags affecting frame rate conversion algorithm
int av_reduce(int *dst_num, int *dst_den, int64_t num, int64_t den, int64_t max)
Reduce a fraction.
#define AV_PIX_FMT_YUV422P12
#define BLEND_FACTOR_DEPTH8
int line_size[4]
bytes of pixel data per line for each plane
A filter pad used for either input or output.
int64_t av_rescale_q(int64_t a, AVRational bq, AVRational cq)
Rescale a 64-bit integer by 2 rational numbers.
A link between two filters.
int64_t n
output frame counter
uint8_t log2_chroma_h
Amount to shift the luma height right to find the chroma height.
AVRational frame_rate
Frame rate of the stream on the link, or 1/0 if unknown or variable; if left to 0/0, will be automatically copied from the first input of the source filter if it exists.
int interp_start
start of range to apply linear interpolation
void av_frame_free(AVFrame **frame)
Free the frame and any dynamically allocated objects in it, e.g.
#define NULL_IF_CONFIG_SMALL(x)
Return NULL if CONFIG_SMALL is true, otherwise the argument without modification. ...
void * priv
private data for use by the filter
#define AVFILTER_FLAG_SLICE_THREADS
The filter supports multithreading by splitting frames into multiple parts and processing them concur...
AVRational time_base
Define the time base used by the PTS of the frames/samples which will pass through this link...
simple assert() macros that are a bit more flexible than ISO C assert().
#define FRAMERATE_FLAG_SCD
int64_t av_gcd(int64_t a, int64_t b)
Compute the greatest common divisor of two integer operands.
#define AV_PIX_FMT_YUV444P10
planar YUV 4:2:2, 16bpp, (1 Cr & Cb sample per 2x1 Y samples)
int w
agreed upon image width
common internal API header
static int blend_frames(AVFilterContext *ctx, int interpolate)
#define AV_PIX_FMT_YUV422P9
int ff_filter_get_nb_threads(AVFilterContext *ctx)
Get number of threads for current filter instance.
int64_t av_rescale(int64_t a, int64_t b, int64_t c)
Rescale a 64-bit integer with rounding to nearest.
planar YUV 4:2:0, 12bpp, full scale (JPEG), deprecated in favor of AV_PIX_FMT_YUV420P and setting col...
double prev_mafd
previous MAFD (scene detect only)
#define FFABS(a)
Absolute value, Note, INT_MIN / INT64_MIN result in undefined behavior as they are not representable ...
AVFilterContext * src
source filter
AVRational srce_time_base
timebase of source
static const AVFilterPad inputs[]
static av_always_inline int64_t sad_8x8_16(const uint16_t *src1, ptrdiff_t stride1, const uint16_t *src2, ptrdiff_t stride2)
#define AV_PIX_FMT_YUV444P9
AVFrame * av_frame_clone(const AVFrame *src)
Create a new frame that references the same data as src.
static const AVFilterPad outputs[]
int format
agreed upon media format
void ff_framerate_init_x86(FrameRateContext *s)
#define AV_LOG_INFO
Standard information.
static const AVFilterPad framerate_outputs[]
static int query_formats(AVFilterContext *ctx)
static int filter_slice(AVFilterContext *ctx, void *arg, int job, int nb_jobs)
int linesize[AV_NUM_DATA_POINTERS]
For video, size in bytes of each picture line.
Descriptor that unambiguously describes how the bits of a pixel are stored in the up to 4 data planes...
#define AV_PIX_FMT_YUV420P10
planar YUV 4:1:0, 9bpp, (1 Cr & Cb sample per 4x4 Y samples)
av_pixelutils_sad_fn av_pixelutils_get_sad_fn(int w_bits, int h_bits, int aligned, void *log_ctx)
Get a potentially optimized pointer to a Sum-of-absolute-differences function (see the av_pixelutils_...
AVRational dest_time_base
timebase of destination
offset must point to AVRational
const char * name
Filter name.
#define AV_PIX_FMT_YUV420P9
static av_cold int init(AVFilterContext *ctx)
AVFilterLink ** outputs
array of pointers to output links
static enum AVPixelFormat pix_fmts[]
void ff_framerate_init(FrameRateContext *s)
AVFilterInternal * internal
An opaque struct for libavfilter internal use.
#define AV_PIX_FMT_YUV422P10
#define AV_PIX_FMT_YUV444P12
uint8_t * data[AV_NUM_DATA_POINTERS]
pointer to the picture/channel planes.
#define BLEND_FUNC_PARAMS
static av_always_inline AVRational av_inv_q(AVRational q)
Invert a rational.
planar YUV 4:2:0, 12bpp, (1 Cr & Cb sample per 2x2 Y samples)
av_pixelutils_sad_fn sad
Sum of the absolute difference function (scene detect only)
static void blend_frames_c(BLEND_FUNC_PARAMS)
planar YUV 4:4:4, 24bpp, full scale (JPEG), deprecated in favor of AV_PIX_FMT_YUV444P and setting col...
planar YUV 4:1:1, 12bpp, (1 Cr & Cb sample per 4x1 Y samples)
avfilter_execute_func * execute
static int filter_frame(AVFilterLink *inlink, AVFrame *inpicref)
static av_always_inline int diff(const uint32_t a, const uint32_t b)
static const AVOption framerate_options[]
AVFilterContext * dst
dest filter
static int config_input(AVFilterLink *inlink)
planar YUV 4:1:1, 12bpp, (1 Cr & Cb sample per 4x1 Y samples) full scale (JPEG), deprecated in favor ...
static const AVFilterPad framerate_inputs[]
int64_t start_pts
pts of the first output frame
int flush
1 if the filter is being flushed
planar YUV 4:4:0 (1 Cr & Cb sample per 1x2 Y samples)
AVFrame * f1
current frame
int ff_request_frame(AVFilterLink *link)
Request an input frame from the filter at the other end of the link.
static int config_output(AVFilterLink *outlink)
int depth
Number of bits in the component.
AVPixelFormat
Pixel format.
int64_t delta
pts1 to pts0 delta
int av_frame_copy_props(AVFrame *dst, const AVFrame *src)
Copy only "metadata" fields from src to dst.
#define AV_NOPTS_VALUE
Undefined timestamp value.