vf_framestep.c

来自「君正早期ucos系统(只有早期的才不没有打包成库),MPLAYER,文件系统,图」· C语言 代码 · 共 193 行

C
193
字号
/* * vf_fstep.c - filter to ouput only 1 every n frame, or only the I (key) *              frame * * The parameters are: * *    [I] | [i]num * * if you call the filter with I (uppercase) as the parameter *    ... -vf framestep=I ... * then ONLY the keyframes are outputted. * For DVD it means, generally, one every 15 frames (IBBPBBPBBPBBPBB), for avi it means * every scene change or every keyint value (see -lavcopts). * * if you call the filter with the i (lowercase) *    ... -vf framestep=i ... * then a I! followed by a cr is printed when a key frame (eg Intra frame) is * found, leaving the current line of mplayer/mencoder, where you got the * time, in seconds, and frame of the key. Use this information to split the * AVI. * * After the i or alone you can put a positive number and only one frame every * x (the number you set) is passed on the filter chain, limiting the output * of the frame. * * Example *    ... -vf framestep=i20 ... * Dump one every 20 frames, printing on the console when a I-Frame is encounter. * *    ... -vf framestep=25 * Dump one every 25 frames. * * If you call the filter without parameter it does nothing (except using memory * and resource of your system,. of course). * * This filter doesn' t work like the option -sstep seconds. * * The -sstep seek to the new position, without decoding all frames but, * expecially on avi file coded whith mpeg4 (lavc or xvid or divx), the * seek is not always too much precise. * * This filter simply discard the unwanted frames, so you are very precise in * counting the frame but sometime you use a lot of CPU for nothing. * * As usual it depends on what you're doing. * *     Daniele Forghieri ( guru@digitalfantasy.it ) */#include <uclib.h>#include <uclib.h>#include <uclib.h>#include "config.h"#include "mp_msg.h"#include "help_mp.h"#include "cpudetect.h"#include "img_format.h"#include "mp_image.h"#include "vf.h"/* Uncomment if you want to print some info on the format */// #define DUMP_FORMAT_DATA/* Private data */struct vf_priv_s {    /* Current frame */    int  frame_cur;    /* Frame output step, 0 = all */    int  frame_step;    /* Only I-Frame (2), print on I-Frame (1) */    int  dump_iframe;};/* Filter handler */static int put_image(struct vf_instance_s* vf, mp_image_t *mpi, double pts){    mp_image_t        *dmpi;    struct vf_priv_s  *priv;    int               skip;    priv = vf->priv;    /* Print the 'I' if is a intra frame. The \n advance the current line so you got the     * current file time (in second) and the frame number on the console ;-)     */    if (priv->dump_iframe) {        if (mpi->pict_type == 1) {            mp_msg(MSGT_VFILTER, MSGL_INFO, "I!\n");        }    }    /* decide if frame must be shown */    if (priv->dump_iframe == 2) {        /* Only key frame */        skip = mpi->pict_type == 1 ? 0 : 1;    }    else {        /* Only 1 every frame_step */        skip = 0;        if ((priv->frame_step != 0) && ((priv->frame_cur % priv->frame_step) != 0)) {            skip = 1;        }    }    /* Increment current frame */    ++priv->frame_cur;    if (skip == 0) {	/* Get image, export type (we don't modify tghe image) */	dmpi=vf_get_image(vf->next, mpi->imgfmt,                      MP_IMGTYPE_EXPORT, 0,	              mpi->w, mpi->h);        /* Copy only the pointer ( MP_IMGTYPE_EXPORT ! ) */        dmpi->planes[0] = mpi->planes[0];        dmpi->planes[1] = mpi->planes[1];        dmpi->planes[2] = mpi->planes[2];        dmpi->stride[0] = mpi->stride[0];        dmpi->stride[1] = mpi->stride[1];        dmpi->stride[2] = mpi->stride[2];        dmpi->width     = mpi->width;        dmpi->height    = mpi->height;        /* Chain to next filter / output ... */        return vf_next_put_image(vf, dmpi, pts);    }    /* Skip the frame */    return 0;}static void uninit(struct vf_instance_s* vf){    /* Free private data */    free(vf->priv);}/* Main entry funct for the filter */static int open(vf_instance_t *vf, char* args){	struct vf_priv_s *p;        vf->put_image = put_image;	vf->uninit = uninit;	vf->default_reqs = VFCAP_ACCEPT_STRIDE;	vf->priv = p = calloc(1, sizeof(struct vf_priv_s));        if (p == NULL) {            return(0);        }        if (args != NULL) {#ifdef DUMP_FORMAT_DATA            if (*args == 'd') {                p->dump_iframe = 3;            }            else#endif            if (*args == 'I') {                /* Dump only KEY (ie INTRA) frame */                p->dump_iframe = 2;            }            else {                if (*args == 'i') {                    /* Print a 'I!' when a i-frame is encounter */                    p->dump_iframe = 1;                    ++args;                }                if (*args != '\0') {                    p->frame_step = atoi(args);                    if (p->frame_step <= 0) {                        mp_msg(MSGT_VFILTER, MSGL_WARN, MSGTR_MPCODECS_ErrorParsingArgument);                        return(0);                    }                }            }        }	return 1;}vf_info_t vf_info_framestep = {    "Dump one every n / key frames",    "framestep",    "Daniele Forghieri",    "",    open,    NULL};

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?