mirror of
https://github.com/FFmpeg/FFmpeg.git
synced 2024-11-26 19:01:44 +02:00
avcodec/me_cmp: add median SAD compare function
Signed-off-by: Michael Niedermayer <michael@niedermayer.cc>
This commit is contained in:
parent
dcfd24b10c
commit
4edd74bd7c
@ -2108,6 +2108,7 @@ typedef struct AVCodecContext {
|
||||
#define FF_CMP_W97 12
|
||||
#define FF_CMP_DCTMAX 13
|
||||
#define FF_CMP_DCT264 14
|
||||
#define FF_CMP_MEDIAN_SAD 15
|
||||
#define FF_CMP_CHROMA 256
|
||||
|
||||
/**
|
||||
|
@ -139,6 +139,45 @@ static inline int pix_abs16_c(MpegEncContext *v, uint8_t *pix1, uint8_t *pix2,
|
||||
return s;
|
||||
}
|
||||
|
||||
static inline int pix_median_abs16_c(MpegEncContext *v, uint8_t *pix1, uint8_t *pix2,
|
||||
ptrdiff_t stride, int h)
|
||||
{
|
||||
int s = 0, i, j;
|
||||
|
||||
#define V(x) (pix1[x] - pix2[x])
|
||||
|
||||
s += abs(V(0));
|
||||
s += abs(V(1) - V(0));
|
||||
s += abs(V(2) - V(1));
|
||||
s += abs(V(3) - V(2));
|
||||
s += abs(V(4) - V(3));
|
||||
s += abs(V(5) - V(4));
|
||||
s += abs(V(6) - V(5));
|
||||
s += abs(V(7) - V(6));
|
||||
s += abs(V(8) - V(7));
|
||||
s += abs(V(9) - V(8));
|
||||
s += abs(V(10) - V(9));
|
||||
s += abs(V(11) - V(10));
|
||||
s += abs(V(12) - V(11));
|
||||
s += abs(V(13) - V(12));
|
||||
s += abs(V(14) - V(13));
|
||||
s += abs(V(15) - V(14));
|
||||
|
||||
pix1 += stride;
|
||||
pix2 += stride;
|
||||
|
||||
for (i = 1; i < h; i++) {
|
||||
s += abs(V(0) - V(-stride));
|
||||
for (j = 1; j < 16; j++)
|
||||
s += abs(V(j) - mid_pred(V(j-stride), V(j-1), V(j-stride) + V(j-1) - V(j-stride-1)));
|
||||
pix1 += stride;
|
||||
pix2 += stride;
|
||||
|
||||
}
|
||||
#undef V
|
||||
return s;
|
||||
}
|
||||
|
||||
static int pix_abs16_x2_c(MpegEncContext *v, uint8_t *pix1, uint8_t *pix2,
|
||||
ptrdiff_t stride, int h)
|
||||
{
|
||||
@ -247,6 +286,37 @@ static inline int pix_abs8_c(MpegEncContext *v, uint8_t *pix1, uint8_t *pix2,
|
||||
return s;
|
||||
}
|
||||
|
||||
static inline int pix_median_abs8_c(MpegEncContext *v, uint8_t *pix1, uint8_t *pix2,
|
||||
ptrdiff_t stride, int h)
|
||||
{
|
||||
int s = 0, i, j;
|
||||
|
||||
#define V(x) (pix1[x] - pix2[x])
|
||||
|
||||
s += abs(V(0));
|
||||
s += abs(V(1) - V(0));
|
||||
s += abs(V(2) - V(1));
|
||||
s += abs(V(3) - V(2));
|
||||
s += abs(V(4) - V(3));
|
||||
s += abs(V(5) - V(4));
|
||||
s += abs(V(6) - V(5));
|
||||
s += abs(V(7) - V(6));
|
||||
|
||||
pix1 += stride;
|
||||
pix2 += stride;
|
||||
|
||||
for (i = 1; i < h; i++) {
|
||||
s += abs(V(0) - V(-stride));
|
||||
for (j = 1; j < 8; j++)
|
||||
s += abs(V(j) - mid_pred(V(j-stride), V(j-1), V(j-stride) + V(j-1) - V(j-stride-1)));
|
||||
pix1 += stride;
|
||||
pix2 += stride;
|
||||
|
||||
}
|
||||
#undef V
|
||||
return s;
|
||||
}
|
||||
|
||||
static int pix_abs8_x2_c(MpegEncContext *v, uint8_t *pix1, uint8_t *pix2,
|
||||
ptrdiff_t stride, int h)
|
||||
{
|
||||
@ -378,6 +448,9 @@ void ff_set_cmp(MECmpContext *c, me_cmp_func *cmp, int type)
|
||||
case FF_CMP_SAD:
|
||||
cmp[i] = c->sad[i];
|
||||
break;
|
||||
case FF_CMP_MEDIAN_SAD:
|
||||
cmp[i] = c->median_sad[i];
|
||||
break;
|
||||
case FF_CMP_SATD:
|
||||
cmp[i] = c->hadamard8_diff[i];
|
||||
break;
|
||||
@ -993,4 +1066,7 @@ av_cold void ff_me_cmp_init(MECmpContext *c, AVCodecContext *avctx)
|
||||
ff_me_cmp_init_x86(c, avctx);
|
||||
if (ARCH_MIPS)
|
||||
ff_me_cmp_init_mips(c, avctx);
|
||||
|
||||
c->median_sad[0] = pix_median_abs16_c;
|
||||
c->median_sad[1] = pix_median_abs8_c;
|
||||
}
|
||||
|
@ -76,6 +76,7 @@ typedef struct MECmpContext {
|
||||
me_cmp_func frame_skip_cmp[6]; // only width 8 used
|
||||
|
||||
me_cmp_func pix_abs[2][4];
|
||||
me_cmp_func median_sad[2];
|
||||
} MECmpContext;
|
||||
|
||||
void ff_me_cmp_init_static(void);
|
||||
|
@ -897,6 +897,7 @@ static inline int get_penalty_factor(int lambda, int lambda2, int type){
|
||||
case FF_CMP_NSSE:
|
||||
return lambda2>>FF_LAMBDA_SHIFT;
|
||||
case FF_CMP_BIT:
|
||||
case FF_CMP_MEDIAN_SAD:
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
@ -594,7 +594,8 @@ enum rc_strategy {
|
||||
{ "nsse", "Noise preserving sum of squared differences", 0, AV_OPT_TYPE_CONST, {.i64 = FF_CMP_NSSE }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS, "cmp_func" }, \
|
||||
{ "dct264", NULL, 0, AV_OPT_TYPE_CONST, {.i64 = FF_CMP_DCT264 }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS, "cmp_func" }, \
|
||||
{ "dctmax", NULL, 0, AV_OPT_TYPE_CONST, {.i64 = FF_CMP_DCTMAX }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS, "cmp_func" }, \
|
||||
{ "chroma", NULL, 0, AV_OPT_TYPE_CONST, {.i64 = FF_CMP_CHROMA }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS, "cmp_func" }
|
||||
{ "chroma", NULL, 0, AV_OPT_TYPE_CONST, {.i64 = FF_CMP_CHROMA }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS, "cmp_func" }, \
|
||||
{ "msad", "Sum of absolute differences, median predicted", 0, AV_OPT_TYPE_CONST, {.i64 = FF_CMP_MEDIAN_SAD }, INT_MIN, INT_MAX, FF_MPV_OPT_FLAGS, "cmp_func" }
|
||||
|
||||
#ifndef FF_MPV_OFFSET
|
||||
#define FF_MPV_OFFSET(x) offsetof(MpegEncContext, x)
|
||||
|
@ -312,6 +312,7 @@ static const AVOption avcodec_options[] = {
|
||||
#endif
|
||||
{"dctmax", NULL, 0, AV_OPT_TYPE_CONST, {.i64 = FF_CMP_DCTMAX }, INT_MIN, INT_MAX, V|E, "cmp_func"},
|
||||
{"chroma", NULL, 0, AV_OPT_TYPE_CONST, {.i64 = FF_CMP_CHROMA }, INT_MIN, INT_MAX, V|E, "cmp_func"},
|
||||
{"msad", "sum of absolute differences, median predicted", 0, AV_OPT_TYPE_CONST, {.i64 = FF_CMP_MEDIAN_SAD }, INT_MIN, INT_MAX, V|E, "cmp_func"},
|
||||
{"pre_dia_size", "diamond type & size for motion estimation pre-pass", OFFSET(pre_dia_size), AV_OPT_TYPE_INT, {.i64 = DEFAULT }, INT_MIN, INT_MAX, V|E},
|
||||
{"subq", "sub-pel motion estimation quality", OFFSET(me_subpel_quality), AV_OPT_TYPE_INT, {.i64 = 8 }, INT_MIN, INT_MAX, V|E},
|
||||
#if FF_API_AFD
|
||||
|
Loading…
Reference in New Issue
Block a user