FFmpeg
Data Structures | Macros | Enumerations | Functions | Variables
vf_deshake.c File Reference
#include "avfilter.h"
#include "internal.h"
#include "transform.h"
#include "video.h"
#include "libavutil/common.h"
#include "libavutil/file_open.h"
#include "libavutil/mem.h"
#include "libavutil/opt.h"
#include "libavutil/pixdesc.h"
#include "libavutil/pixelutils.h"
#include "libavutil/qsort.h"

Go to the source code of this file.

Data Structures

struct  IntMotionVector
 
struct  MotionVector
 
struct  Transform
 
struct  DeshakeContext
 

Macros

#define MAX_R   64
 
#define OFFSET(x)   offsetof(DeshakeContext, x)
 
#define FLAGS   AV_OPT_FLAG_VIDEO_PARAM|AV_OPT_FLAG_FILTERING_PARAM
 
#define CMP(i, j)
 

Enumerations

enum  SearchMethod { EXHAUSTIVE, SMART_EXHAUSTIVE, SEARCH_COUNT }
 

Functions

 AVFILTER_DEFINE_CLASS (deshake)
 
static int cmp (const void *a, const void *b)
 
static double clean_mean (double *values, int count)
 Cleaned mean (cuts off 20% of values to remove outliers and then averages) More...
 
static void find_block_motion (DeshakeContext *deshake, uint8_t *src1, uint8_t *src2, int cx, int cy, int stride, IntMotionVector *mv)
 Find the most likely shift in motion between two frames for a given macroblock. More...
 
static int block_contrast (uint8_t *src, int x, int y, int stride, int blocksize)
 Find the contrast of a given block. More...
 
static double block_angle (int x, int y, int cx, int cy, IntMotionVector *shift)
 Find the rotation for a given block. More...
 
static void find_motion (DeshakeContext *deshake, uint8_t *src1, uint8_t *src2, int width, int height, int stride, Transform *t)
 Find the estimated global motion for a scene given the most likely shift for each block in the frame. More...
 
static int deshake_transform_c (AVFilterContext *ctx, int width, int height, int cw, int ch, const float *matrix_y, const float *matrix_uv, enum InterpolateMethod interpolate, enum FillMethod fill, AVFrame *in, AVFrame *out)
 
static av_cold int init (AVFilterContext *ctx)
 
static int config_props (AVFilterLink *link)
 
static av_cold void uninit (AVFilterContext *ctx)
 
static int filter_frame (AVFilterLink *link, AVFrame *in)
 

Variables

static const AVOption deshake_options []
 
static enum AVPixelFormat pix_fmts []
 
static const AVFilterPad deshake_inputs []
 
const AVFilter ff_vf_deshake
 

Detailed Description

fast deshake / depan video filter

SAD block-matching motion compensation to fix small changes in horizontal and/or vertical shift. This filter helps remove camera shake from hand-holding a camera, bumping a tripod, moving on a vehicle, etc.

Algorithm:

TODO:

Dark Shikari links to http://wiki.videolan.org/SoC_x264_2010#GPU_Motion_Estimation_2 for an algorithm similar to what could be used here to get the gmv It requires only a couple diamond searches + fast downscaling

Special thanks to Jason Kotenko for his help with the algorithm and my inability to see simple errors in C code.

Definition in file vf_deshake.c.

Macro Definition Documentation

◆ MAX_R

#define MAX_R   64

Definition at line 87 of file vf_deshake.c.

◆ OFFSET

#define OFFSET (   x)    offsetof(DeshakeContext, x)

Definition at line 117 of file vf_deshake.c.

◆ FLAGS

Definition at line 118 of file vf_deshake.c.

◆ CMP

#define CMP (   i,
 
)
Value:
deshake->sad(src1 + cy * stride + cx, stride,\
src2 + (j) * stride + (i), stride)

Enumeration Type Documentation

◆ SearchMethod

Enumerator
EXHAUSTIVE 

Search all possible positions.

SMART_EXHAUSTIVE 

Search most possible positions (faster)

SEARCH_COUNT 

Definition at line 65 of file vf_deshake.c.

Function Documentation

◆ AVFILTER_DEFINE_CLASS()

AVFILTER_DEFINE_CLASS ( deshake  )

◆ cmp()

static int cmp ( const void *  a,
const void *  b 
)
static

Definition at line 144 of file vf_deshake.c.

Referenced by clean_mean().

◆ clean_mean()

static double clean_mean ( double values,
int  count 
)
static

Cleaned mean (cuts off 20% of values to remove outliers and then averages)

Definition at line 152 of file vf_deshake.c.

Referenced by find_motion().

◆ find_block_motion()

static void find_block_motion ( DeshakeContext deshake,
uint8_t *  src1,
uint8_t *  src2,
int  cx,
int  cy,
int  stride,
IntMotionVector mv 
)
static

Find the most likely shift in motion between two frames for a given macroblock.

Test each block against several shifts given by the rx and ry attributes. Searches using a simple matrix of those shifts and chooses the most likely shift by the smallest difference in blocks.

Definition at line 173 of file vf_deshake.c.

Referenced by find_motion().

◆ block_contrast()

static int block_contrast ( uint8_t *  src,
int  x,
int  y,
int  stride,
int  blocksize 
)
static

Find the contrast of a given block.

When searching for global motion we really only care about the high contrast blocks, so using this method we can actually skip blocks we don't care much about.

Definition at line 242 of file vf_deshake.c.

Referenced by find_motion().

◆ block_angle()

static double block_angle ( int  x,
int  y,
int  cx,
int  cy,
IntMotionVector shift 
)
static

Find the rotation for a given block.

Definition at line 266 of file vf_deshake.c.

Referenced by find_motion().

◆ find_motion()

static void find_motion ( DeshakeContext deshake,
uint8_t *  src1,
uint8_t *  src2,
int  width,
int  height,
int  stride,
Transform t 
)
static

Find the estimated global motion for a scene given the most likely shift for each block in the frame.

The global motion is estimated to be the same as the motion from most blocks in the frame, so if most blocks move one pixel to the right and two pixels down, this would yield a motion vector (1, -2).

Definition at line 287 of file vf_deshake.c.

Referenced by filter_frame().

◆ deshake_transform_c()

static int deshake_transform_c ( AVFilterContext ctx,
int  width,
int  height,
int  cw,
int  ch,
const float matrix_y,
const float matrix_uv,
enum InterpolateMethod  interpolate,
enum FillMethod  fill,
AVFrame in,
AVFrame out 
)
static

Definition at line 367 of file vf_deshake.c.

Referenced by init().

◆ init()

static av_cold int init ( AVFilterContext ctx)
static

Definition at line 394 of file vf_deshake.c.

◆ config_props()

static int config_props ( AVFilterLink link)
static

Definition at line 433 of file vf_deshake.c.

◆ uninit()

static av_cold void uninit ( AVFilterContext ctx)
static

Definition at line 446 of file vf_deshake.c.

◆ filter_frame()

static int filter_frame ( AVFilterLink link,
AVFrame in 
)
static

Definition at line 456 of file vf_deshake.c.

Variable Documentation

◆ deshake_options

const AVOption deshake_options[]
static
Initial value:
= {
{ "x", "set x for the rectangular search area", OFFSET(cx), AV_OPT_TYPE_INT, {.i64=-1}, -1, INT_MAX, .flags = FLAGS },
{ "y", "set y for the rectangular search area", OFFSET(cy), AV_OPT_TYPE_INT, {.i64=-1}, -1, INT_MAX, .flags = FLAGS },
{ "w", "set width for the rectangular search area", OFFSET(cw), AV_OPT_TYPE_INT, {.i64=-1}, -1, INT_MAX, .flags = FLAGS },
{ "h", "set height for the rectangular search area", OFFSET(ch), AV_OPT_TYPE_INT, {.i64=-1}, -1, INT_MAX, .flags = FLAGS },
{ "rx", "set x for the rectangular search area", OFFSET(rx), AV_OPT_TYPE_INT, {.i64=16}, 0, MAX_R, .flags = FLAGS },
{ "ry", "set y for the rectangular search area", OFFSET(ry), AV_OPT_TYPE_INT, {.i64=16}, 0, MAX_R, .flags = FLAGS },
{ "edge", "set edge mode", OFFSET(edge), AV_OPT_TYPE_INT, {.i64=FILL_MIRROR}, FILL_BLANK, FILL_COUNT-1, FLAGS, .unit = "edge"},
{ "blank", "fill zeroes at blank locations", 0, AV_OPT_TYPE_CONST, {.i64=FILL_BLANK}, INT_MIN, INT_MAX, FLAGS, .unit = "edge" },
{ "original", "original image at blank locations", 0, AV_OPT_TYPE_CONST, {.i64=FILL_ORIGINAL}, INT_MIN, INT_MAX, FLAGS, .unit = "edge" },
{ "clamp", "extruded edge value at blank locations", 0, AV_OPT_TYPE_CONST, {.i64=FILL_CLAMP}, INT_MIN, INT_MAX, FLAGS, .unit = "edge" },
{ "mirror", "mirrored edge at blank locations", 0, AV_OPT_TYPE_CONST, {.i64=FILL_MIRROR}, INT_MIN, INT_MAX, FLAGS, .unit = "edge" },
{ "blocksize", "set motion search blocksize", OFFSET(blocksize), AV_OPT_TYPE_INT, {.i64=8}, 4, 128, .flags = FLAGS },
{ "contrast", "set contrast threshold for blocks", OFFSET(contrast), AV_OPT_TYPE_INT, {.i64=125}, 1, 255, .flags = FLAGS },
{ "search", "set search strategy", OFFSET(search), AV_OPT_TYPE_INT, {.i64=EXHAUSTIVE}, EXHAUSTIVE, SEARCH_COUNT-1, FLAGS, .unit = "smode" },
{ "exhaustive", "exhaustive search", 0, AV_OPT_TYPE_CONST, {.i64=EXHAUSTIVE}, INT_MIN, INT_MAX, FLAGS, .unit = "smode" },
{ "less", "less exhaustive search", 0, AV_OPT_TYPE_CONST, {.i64=SMART_EXHAUSTIVE}, INT_MIN, INT_MAX, FLAGS, .unit = "smode" },
{ "filename", "set motion search detailed log file name", OFFSET(filename), AV_OPT_TYPE_STRING, {.str=NULL}, .flags = FLAGS },
{ "opencl", "ignored", OFFSET(opencl), AV_OPT_TYPE_BOOL, {.i64=0}, 0, 1, .flags = FLAGS },
{ NULL }
}

Definition at line 120 of file vf_deshake.c.

◆ pix_fmts

enum AVPixelFormat pix_fmts[]
static

◆ deshake_inputs

const AVFilterPad deshake_inputs[]
static
Initial value:
= {
{
.name = "default",
.filter_frame = filter_frame,
.config_props = config_props,
},
}

Definition at line 581 of file vf_deshake.c.

◆ ff_vf_deshake

const AVFilter ff_vf_deshake
Initial value:
= {
.name = "deshake",
.description = NULL_IF_CONFIG_SMALL("Stabilize shaky video."),
.priv_size = sizeof(DeshakeContext),
.init = init,
.priv_class = &deshake_class,
}

Definition at line 590 of file vf_deshake.c.

FILL_CLAMP
@ FILL_CLAMP
Definition: transform.h:54
src1
const pixel * src1
Definition: h264pred_template.c:421
FILTER_PIXFMTS_ARRAY
#define FILTER_PIXFMTS_ARRAY(array)
Definition: internal.h:162
AV_PIX_FMT_YUV440P
@ AV_PIX_FMT_YUV440P
planar YUV 4:4:0 (1 Cr & Cb sample per 1x2 Y samples)
Definition: pixfmt.h:106
deshake_inputs
static const AVFilterPad deshake_inputs[]
Definition: vf_deshake.c:581
FLAGS
#define FLAGS
Definition: vf_deshake.c:118
FILL_ORIGINAL
@ FILL_ORIGINAL
Definition: transform.h:53
FILL_BLANK
@ FILL_BLANK
Definition: transform.h:52
init
static av_cold int init(AVFilterContext *ctx)
Definition: vf_deshake.c:394
OFFSET
#define OFFSET(x)
Definition: vf_deshake.c:117
ff_video_default_filterpad
const AVFilterPad ff_video_default_filterpad[1]
An AVFilterPad array whose only entry has name "default" and is of type AVMEDIA_TYPE_VIDEO.
Definition: video.c:37
AV_PIX_FMT_YUVJ422P
@ AV_PIX_FMT_YUVJ422P
planar YUV 4:2:2, 16bpp, full scale (JPEG), deprecated in favor of AV_PIX_FMT_YUV422P and setting col...
Definition: pixfmt.h:86
FILL_COUNT
@ FILL_COUNT
Definition: transform.h:56
AV_PIX_FMT_YUV420P
@ AV_PIX_FMT_YUV420P
planar YUV 4:2:0, 12bpp, (1 Cr & Cb sample per 2x2 Y samples)
Definition: pixfmt.h:73
FILTER_INPUTS
#define FILTER_INPUTS(array)
Definition: internal.h:182
AV_PIX_FMT_YUVJ444P
@ AV_PIX_FMT_YUVJ444P
planar YUV 4:4:4, 24bpp, full scale (JPEG), deprecated in favor of AV_PIX_FMT_YUV444P and setting col...
Definition: pixfmt.h:87
NULL
#define NULL
Definition: coverity.c:32
AV_PIX_FMT_YUVJ420P
@ AV_PIX_FMT_YUVJ420P
planar YUV 4:2:0, 12bpp, full scale (JPEG), deprecated in favor of AV_PIX_FMT_YUV420P and setting col...
Definition: pixfmt.h:85
SMART_EXHAUSTIVE
@ SMART_EXHAUSTIVE
Search most possible positions (faster)
Definition: vf_deshake.c:67
pix_fmts
static enum AVPixelFormat pix_fmts[]
Definition: vf_deshake.c:427
NULL_IF_CONFIG_SMALL
#define NULL_IF_CONFIG_SMALL(x)
Return NULL if CONFIG_SMALL is true, otherwise the argument without modification.
Definition: internal.h:106
EXHAUSTIVE
@ EXHAUSTIVE
Search all possible positions.
Definition: vf_deshake.c:66
FILL_MIRROR
@ FILL_MIRROR
Definition: transform.h:55
SEARCH_COUNT
@ SEARCH_COUNT
Definition: vf_deshake.c:68
MAX_R
#define MAX_R
Definition: vf_deshake.c:87
filter_frame
static int filter_frame(AVFilterLink *link, AVFrame *in)
Definition: vf_deshake.c:456
config_props
static int config_props(AVFilterLink *link)
Definition: vf_deshake.c:433
i
#define i(width, name, range_min, range_max)
Definition: cbs_h2645.c:255
src2
const pixel * src2
Definition: h264pred_template.c:422
AV_PIX_FMT_YUVJ440P
@ AV_PIX_FMT_YUVJ440P
planar YUV 4:4:0 full scale (JPEG), deprecated in favor of AV_PIX_FMT_YUV440P and setting color_range
Definition: pixfmt.h:107
stride
#define stride
Definition: h264pred_template.c:537
search
static float search(FOCContext *foc, int pass, int maxpass, int xmin, int xmax, int ymin, int ymax, int *best_x, int *best_y, float best_score)
Definition: vf_find_rect.c:147
uninit
static av_cold void uninit(AVFilterContext *ctx)
Definition: vf_deshake.c:446
AV_PIX_FMT_NONE
@ AV_PIX_FMT_NONE
Definition: pixfmt.h:72
AV_OPT_TYPE_INT
@ AV_OPT_TYPE_INT
Definition: opt.h:235
AV_PIX_FMT_YUV444P
@ AV_PIX_FMT_YUV444P
planar YUV 4:4:4, 24bpp, (1 Cr & Cb sample per 1x1 Y samples)
Definition: pixfmt.h:78
AVMEDIA_TYPE_VIDEO
@ AVMEDIA_TYPE_VIDEO
Definition: avutil.h:201
AV_PIX_FMT_YUV422P
@ AV_PIX_FMT_YUV422P
planar YUV 4:2:2, 16bpp, (1 Cr & Cb sample per 2x1 Y samples)
Definition: pixfmt.h:77
AV_OPT_TYPE_BOOL
@ AV_OPT_TYPE_BOOL
Definition: opt.h:251
FILTER_OUTPUTS
#define FILTER_OUTPUTS(array)
Definition: internal.h:183
AV_PIX_FMT_YUV411P
@ AV_PIX_FMT_YUV411P
planar YUV 4:1:1, 12bpp, (1 Cr & Cb sample per 4x1 Y samples)
Definition: pixfmt.h:80
DeshakeContext
Definition: vf_deshake.c:89
AV_PIX_FMT_YUV410P
@ AV_PIX_FMT_YUV410P
planar YUV 4:1:0, 9bpp, (1 Cr & Cb sample per 4x4 Y samples)
Definition: pixfmt.h:79
AV_OPT_TYPE_STRING
@ AV_OPT_TYPE_STRING
Definition: opt.h:239
AV_OPT_TYPE_CONST
@ AV_OPT_TYPE_CONST
Definition: opt.h:244