diff options
Diffstat (limited to 'TOOLS')
-rwxr-xr-x | TOOLS/osxbundle.py | 13 | ||||
-rw-r--r-- | TOOLS/uncrustify.cfg | 7 | ||||
-rw-r--r-- | TOOLS/vf_dlopen/Makefile | 4 | ||||
-rw-r--r-- | TOOLS/vf_dlopen/framestep.c | 104 | ||||
-rw-r--r-- | TOOLS/vf_dlopen/ildetect.c | 296 | ||||
-rwxr-xr-x | TOOLS/vf_dlopen/ildetect.sh | 84 |
6 files changed, 504 insertions, 4 deletions
diff --git a/TOOLS/osxbundle.py b/TOOLS/osxbundle.py index e0f240797f..6cd2a227c5 100755 --- a/TOOLS/osxbundle.py +++ b/TOOLS/osxbundle.py @@ -5,6 +5,7 @@ import re import shutil import sys from optparse import OptionParser +from textwrap import dedent def sh(command): return os.popen(command).read() @@ -69,8 +70,16 @@ def cp_dylibs(target_file, dest_dir): try: shutil.copy(dylib_path, dylib_dest_path) except IOError: - sys.exit("%s uses library %s which is not available anymore" % \ - (target_file, dylib_path) ) + if re.match("dylib$", target_file): + reinstall_what = target_file + else: + reinstall_what = dylib_path + + sys.exit(dedent("""\ + %s uses library %s which is not available anymore. + This is most likely because you uninstalled %s. + Please reinstall %s to fix it's dependencies.""" % \ + (target_file, dylib_path, dylib_path, reinstall_what) )) os.chmod(dylib_dest_path, 0o755) cp_dylibs(dylib_dest_path, dest_dir) diff --git a/TOOLS/uncrustify.cfg b/TOOLS/uncrustify.cfg index b5133be203..837d9a1770 100644 --- a/TOOLS/uncrustify.cfg +++ b/TOOLS/uncrustify.cfg @@ -1,3 +1,10 @@ +# Usage: +# uncrustify -l C -c TOOLS/uncrustify.cfg --no-backup --replace file.c +# +# Keep in mind that this uncrustify configuration still produces some +# bad/broken formatting. +# + code_width=80 indent_align_string=false indent_braces=false diff --git a/TOOLS/vf_dlopen/Makefile b/TOOLS/vf_dlopen/Makefile index 332c890821..8057676d57 100644 --- a/TOOLS/vf_dlopen/Makefile +++ b/TOOLS/vf_dlopen/Makefile @@ -19,7 +19,7 @@ # 02110-1301 USA # -FILTERS = showqscale telecine tile rectangle +FILTERS = showqscale telecine tile rectangle framestep ildetect COMMON = filterutils.o OBJECTS = $(patsubst %,%.o,$(FILTERS)) $(COMMON) @@ -28,7 +28,7 @@ OUT = $(patsubst %,%.so,$(FILTERS)) CFLAGS ?= -Wall -Wextra -O3 -march=native -mtune=native -ffast-math -CPPFLAGS += -I../../libmpcodecs +CPPFLAGS += -I../../video/filter CFLAGS += -fPIC LDFLAGS += -shared -fPIC diff --git a/TOOLS/vf_dlopen/framestep.c b/TOOLS/vf_dlopen/framestep.c new file mode 100644 index 0000000000..531d11b018 --- /dev/null +++ b/TOOLS/vf_dlopen/framestep.c @@ -0,0 +1,104 @@ +/* + * Copyright (c) 2012 Rudolf Polzer <divVerent@xonotic.org> + * + * This file is part of mpv's vf_dlopen examples. + * + * mpv's vf_dlopen examples are free software; you can redistribute them and/or + * modify them under the terms of the GNU Lesser General Public License as + * published by the Free Software Foundation; either version 2.1 of the + * License, or (at your option) any later version. + * + * mpv's vf_dlopen examples are distributed in the hope that they will be + * useful, but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser + * General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with mpv's vf_dlopen examples; if not, write to the Free + * Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA + * 02110-1301 USA + */ + +#include <assert.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> + +#include "vf_dlopen.h" +#include "filterutils.h" + +#define MIN(a,b) ((a)<(b)?(a):(b)) + +/* + * frame stepping filter + * + * usage: -vf dlopen=./framestep.so:5 + * + * outputs every 5th frame + * + * usage: -vf dlopen=./framestep.so:5:3 + * + * outputs every 5th frame, starting with frame index 3 (default: 0) + */ + +typedef struct { + int step, pos; +} framestep_data_t; + +static int framestep_put_image(struct vf_dlopen_context *ctx) +{ + framestep_data_t *framestep = ctx->priv; + + // stepping + if (framestep->pos < 0) + return 0; + --framestep->pos; + if (framestep->pos >= 0) + return 0; + framestep->pos += framestep->step; + + // copying + assert(ctx->inpic.planes == ctx->outpic[0].planes); + int np = ctx->inpic.planes; + int p; + for (p = 0; p < np; ++p) { + assert(ctx->inpic.planewidth[p] == ctx->outpic->planewidth[p]); + assert(ctx->inpic.planeheight[p] == ctx->outpic->planeheight[p]); + copy_plane( + ctx->outpic->plane[p], + ctx->outpic->planestride[p], + ctx->inpic.plane[p], + ctx->inpic.planestride[p], + MIN(ctx->inpic.planestride[p], ctx->outpic->planestride[p]), + ctx->inpic.planeheight[p] + ); + } + ctx->outpic->pts = ctx->inpic.pts; + + return 1; +} + +void framestep_uninit(struct vf_dlopen_context *ctx) +{ + free(ctx->priv); +} + +int vf_dlopen_getcontext(struct vf_dlopen_context *ctx, int argc, const char **argv) +{ + VF_DLOPEN_CHECK_VERSION(ctx); + + if (argc != 1 && argc != 2) + return -1; + + framestep_data_t *framestep = malloc(sizeof(framestep_data_t)); + memset(framestep, 0, sizeof(*framestep)); + + framestep->step = atoi(argv[0]); + framestep->pos = (argc >= 2) ? atoi(argv[1]) : 0; + + ctx->priv = framestep; + ctx->put_image = framestep_put_image; + ctx->uninit = framestep_uninit; + + return 1; +} diff --git a/TOOLS/vf_dlopen/ildetect.c b/TOOLS/vf_dlopen/ildetect.c new file mode 100644 index 0000000000..1ac1c08946 --- /dev/null +++ b/TOOLS/vf_dlopen/ildetect.c @@ -0,0 +1,296 @@ +/* + * Copyright (c) 2012 Rudolf Polzer <divVerent@xonotic.org> + * + * This file is part of mpv's vf_dlopen examples. + * + * mpv's vf_dlopen examples are free software; you can redistribute them and/or + * modify them under the terms of the GNU Lesser General Public License as + * published by the Free Software Foundation; either version 2.1 of the + * License, or (at your option) any later version. + * + * mpv's vf_dlopen examples are distributed in the hope that they will be + * useful, but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser + * General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with mpv's vf_dlopen examples; if not, write to the Free + * Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA + * 02110-1301 USA + */ + +#include <assert.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <math.h> + +#include "vf_dlopen.h" + +#include "filterutils.h" + +/* + * interlacing detector + * + * usage: -vf dlopen=./ildetect.so:<method>:<threshold> + * + * outputs an interlacing detection report at the end + * + * methods: + * 0 = transcode 32detect (default) + * 1 = decomb IsCombed + * 2 = IsCombedTIVTC + * 3 = simple average + * + * threshold: + * normalized at 1 + */ + +typedef struct { + int method; + double combing_threshold; + double motion_threshold; + double motion_amount; + double yes_threshold; + double no_threshold; + double total_yes_threshold; + double total_no_threshold; + double tc_threshold; + double decision_threshold; + double tc_decision_threshold; + double lastcombed; + int numtotalframes; + int numdecidedframes; + int totalcombedframes; + int numjumpingadjacentframes; + int numdecidedadjacentframes; + unsigned char *buffer_data; + size_t buffer_size; +} ildetect_data_t; + +static int il_config(struct vf_dlopen_context *ctx) +{ + ctx->out_height -= 4; + ctx->out_d_height = ctx->out_height; + return 1; +} + +static int il_decision(struct vf_dlopen_context *ctx, + int p0, int p1, int p2, int p3, int p4) +{ + ildetect_data_t *il = ctx->priv; + + // model for threshold: p0, p2, p4 = 0; p1, p3 = t + switch (il->method) { + case 0: { // diff-diff (transcode 32detect) + int d12 = p1 - p2; // t + int d13 = p1 - p3; // 0 + if (abs(d12) > 15 * il->combing_threshold && + abs(d13) < 10 * il->combing_threshold) + return 1; + // true for t > 15 + break; + } + case 1: { // multiply (decomb IsCombed) + int d12 = p1 - p2; // t + int d32 = p3 - p2; // t + if (d12 * d32 > pow(il->combing_threshold, 2) * (25*25)) + return 1; + // true for t > 21 + break; + } + case 2: { // blur-blur (IsCombedTIVTC) + int b024 = p0 + 6 * p2 + p4; // 0 + int b13 = 4 * p1 + 4 * p3; // 8t + if (abs(b024 - b13) > il->combing_threshold * 8 * 20) + return 1; + // true for t > 20 + break; + } + case 3: { // average-average + int d123 = p1 + p3 - 2 * p2; // 2t + int d024 = p0 + p4 - 2 * p2; // 0 + if ((abs(d123) - abs(d024)) > il->combing_threshold * 30) + return 1; + // true for t > 15 + break; + } + } + return 0; +} + +static int il_put_image(struct vf_dlopen_context *ctx) +{ + ildetect_data_t *il = ctx->priv; + unsigned int x, y; + int first_frame = 0; + + size_t sz = ctx->inpic.planestride[0] * ctx->inpic.planeheight[0]; + if (sz != il->buffer_size) { + il->buffer_data = realloc(il->buffer_data, sz); + il->buffer_size = sz; + first_frame = 1; + } + + assert(ctx->inpic.planes == 1); + assert(ctx->outpic[0].planes == 1); + + assert(ctx->inpic.planewidth[0] == ctx->outpic[0].planewidth[0]); + assert(ctx->inpic.planeheight[0] == ctx->outpic[0].planeheight[0] + 4); + + if (first_frame) { + printf("First frame\n"); + il->lastcombed = -1; + } else { + // detect interlacing + // for each row of 5 pixels, compare: + // p2 vs (p1 + p3) / 2 + // p2 vs (p0 + p4) / 2 + unsigned int totalcombedframes = 0; // add 255 per combed pixel + unsigned int totalpixels = 0; + for (y = 0; y < ctx->inpic.planeheight[0] - 4; ++y) { + unsigned char *in_line = + &ctx->inpic.plane[0][ctx->inpic.planestride[0] * y]; + unsigned char *buf_line = + &il->buffer_data[ctx->inpic.planestride[0] * y]; + unsigned char *out_line = + &ctx->outpic->plane[0][ctx->outpic->planestride[0] * y]; + for (x = 0; x < ctx->inpic.planewidth[0]; ++x) { + int b2 = buf_line[x + ctx->inpic.planestride[0] * 2]; + int p0 = in_line[x]; + int p1 = in_line[x + ctx->inpic.planestride[0]]; + int p2 = in_line[x + ctx->inpic.planestride[0] * 2]; + int p3 = in_line[x + ctx->inpic.planestride[0] * 3]; + int p4 = in_line[x + ctx->inpic.planestride[0] * 4]; + int is_moving = abs(b2 - p2) > il->motion_threshold; + + if (!is_moving) { + out_line[x] = 128; + continue; + } + + ++totalpixels; + + int combed = il_decision(ctx, p0, p1, p2, p3, p4); + totalcombedframes += combed; + out_line[x] = 255 * combed; + } + } + + double avgpixels = totalpixels / (double) + ((ctx->inpic.planeheight[0] - 4) * ctx->inpic.planewidth[0]); + + if (avgpixels > il->motion_amount) { + double avgcombed = totalcombedframes / (double) totalpixels; + + if (il->lastcombed >= 0) { + if (il->lastcombed < il->no_threshold || + il->lastcombed > il->yes_threshold) + if (avgcombed < il->no_threshold || + avgcombed > il->yes_threshold) + ++il->numdecidedadjacentframes; + if (il->lastcombed > il->yes_threshold && + avgcombed < il->no_threshold) + ++il->numjumpingadjacentframes; + if (il->lastcombed < il->no_threshold && + avgcombed > il->yes_threshold) + ++il->numjumpingadjacentframes; + } + + il->lastcombed = avgcombed; + + if (avgcombed > il->yes_threshold) { + ++il->numdecidedframes; + ++il->totalcombedframes; + } else if (avgcombed < il->no_threshold) { + ++il->numdecidedframes; + } + } else + il->lastcombed = -1; + } + + ++il->numtotalframes; + + copy_plane( + il->buffer_data, ctx->inpic.planestride[0], + ctx->inpic.plane[0], ctx->inpic.planestride[0], + ctx->inpic.planewidth[0], + ctx->inpic.planeheight[0]); + + ctx->outpic[0].pts = ctx->inpic.pts; + return 1; +} + +void il_uninit(struct vf_dlopen_context *ctx) +{ + ildetect_data_t *il = ctx->priv; + + double avgdecided = il->numtotalframes + ? il->numdecidedframes / (double) il->numtotalframes : -1; + double avgadjacent = il->numdecidedframes + ? il->numdecidedadjacentframes / (double) il->numdecidedframes : -1; + double avgscore = il->numdecidedframes + ? il->totalcombedframes / (double) il->numdecidedframes : -1; + double avgjumps = il->numdecidedadjacentframes + ? il->numjumpingadjacentframes / (double) il->numdecidedadjacentframes : -1; + + printf("ildetect: Avg decided: %f\n", avgdecided); + printf("ildetect: Avg adjacent decided: %f\n", avgadjacent); + printf("ildetect: Avg interlaced decided: %f\n", avgscore); + printf("ildetect: Avg interlaced/progressive adjacent decided: %f\n", avgjumps); + + if (avgdecided < il->decision_threshold) + avgadjacent = avgscore = avgjumps = -1; + + if (avgadjacent < il->tc_decision_threshold) + avgadjacent = avgjumps = -1; + + if (avgscore < 0) + printf("ildetect: Content is probably: undecided\n"); + else if (avgscore < il->total_no_threshold) + printf("ildetect: Content is probably: PROGRESSIVE\n"); + else if (avgscore > il->total_yes_threshold && avgjumps < 0) + printf("ildetect: Content is probably: INTERLACED (possibly telecined)\n"); + else if (avgjumps > il->tc_threshold) + printf("ildetect: Content is probably: TELECINED\n"); + else if (avgscore > il->total_yes_threshold) + printf("ildetect: Content is probably: INTERLACED\n"); + else + printf("ildetect: Content is probably: unknown\n"); + + free(ctx->priv); +} + +int vf_dlopen_getcontext(struct vf_dlopen_context *ctx, int argc, const char **argv) +{ + VF_DLOPEN_CHECK_VERSION(ctx); + (void) argc; + (void) argv; + + ildetect_data_t *il = malloc(sizeof(ildetect_data_t)); + memset(il, 0, sizeof(*il)); + +#define A(i,d) ((argc>(i) && *argv[i]) ? atof(argv[i]) : (d)) + il->method = A(0, 0); + il->combing_threshold = A(1, 1); + il->motion_threshold = A(2, 6); + il->motion_amount = A(3, 0.1); + il->yes_threshold = A(4, 0.1); + il->no_threshold = A(5, 0.05); + il->total_yes_threshold = A(6, 0.1); + il->total_no_threshold = A(7, 0.05); + il->tc_threshold = A(8, 0.1); + il->decision_threshold = A(9, 0.2); + il->tc_decision_threshold = A(10, 0.2); + + static struct vf_dlopen_formatpair map[] = { + { "y8", "y8" }, + { NULL, NULL } + }; + ctx->format_mapping = map; + ctx->config = il_config; + ctx->put_image = il_put_image; + ctx->uninit = il_uninit; + ctx->priv = il; + return 1; +} diff --git a/TOOLS/vf_dlopen/ildetect.sh b/TOOLS/vf_dlopen/ildetect.sh new file mode 100755 index 0000000000..6fd924e224 --- /dev/null +++ b/TOOLS/vf_dlopen/ildetect.sh @@ -0,0 +1,84 @@ +#!/bin/sh + +case "$0" in + */*) + MYDIR=${0%/*} + ;; + *) + MYDIR=. + ;; +esac + +: ${MPV:=mpv} +: ${ILDETECT_MPV:=$MPV} +: ${ILDETECT_MPV:=$MPV} +: ${ILDETECT_MPVFLAGS:=--start=35% --length=35} +: ${ILDETECT_DRY_RUN:=} +: ${ILDETECT_QUIET:=} +: ${ILDETECT_RUN_INTERLACED_ONLY:=} +: ${MAKE:=make} + +# exit status: +# 0 progressive +# 1 telecine +# 2 interlaced +# 8 unknown +# 15 compile fail +# 16 detect fail +# 17+ mpv's status | 16 + +$MAKE -C "$MYDIR" ildetect.so || exit 15 + +testfun() +{ + $ILDETECT_MPV "$@" \ + --vf=dlopen="$MYDIR/ildetect.so" \ + --o= --vo=null --no-audio --untimed \ + $ILDETECT_MPVFLAGS \ + | { if [ -n "$ILDETECT_QUIET" ]; then cat; else tee /dev/stderr; fi } \ + | grep "^ildetect:" +} + +out=`testfun "$@"` +case "$out" in + *"probably: PROGRESSIVE"*) + [ -n "$ILDETECT_DRY_RUN" ] || \ + [ -n "$ILDETECT_RUN_INTERLACED_ONLY" ] || \ + $ILDETECT_MPV "$@" + r=$? + [ $r -eq 0 ] || exit $(($r | 16)) + exit 0 + ;; + *"probably: TELECINED"*) + out2=`ILDETECT_MPVFLAGS="$ILDETECT_MPVFLAGS --vf-pre=pullup,scale" testfun "$@"` + case "$out2" in + *"probably: TELECINED"*|*"probably: INTERLACED"*) + [ -n "$ILDETECT_DRY_RUN" ] || \ + $ILDETECT_MPV "$@" -vf-pre yadif + r=$? + [ $r -eq 0 ] || exit $(($r | 16)) + exit 2 + ;; + *) + [ -n "$ILDETECT_DRY_RUN" ] || \ + $ILDETECT_MPV "$@" -vf-pre pullup + r=$? + [ $r -eq 0 ] || exit $(($r | 16)) + exit 1 + ;; + esac + ;; + *"probably: INTERLACED"*) + [ -n "$ILDETECT_DRY_RUN" ] || \ + $ILDETECT_MPV "$@" -vf-pre yadif + r=$? + [ $r -eq 0 ] || exit $(($r | 16)) + exit 2 + ;; + *"probably: "*) + exit 8 + ;; + *) + exit 16 + ;; +esac |