[FFmpeg-devel] Rotate video filter
Stefano Sabatini
stefano.sabatini-lala
Sun Oct 10 12:03:11 CEST 2010
On date Saturday 2010-10-09 22:29:53 +0200, Radek Polak encoded:
> Hi,
> i would like to write video converter which scales & rotates video. I found
> scale option but i havent found rotate option, so i assume it's missing in
> current ffmpeg.
>
> However i searched web and found SOC project of Vitor Sessak who implemented
> video filter that can be used for rotation [1].
>
> I have checked out the sources from svn://svn.ffmpeg.org/soc/libavfilter and did
> a patch (attached) against current ffmpeg for this video filter and for me it
> works good.
>
> Would it be possible to include such patch in ffmpeg upstream sources?
We're already discussing a rotate filter, but given that this is a
simpler variant I guess it makes sense to implement this functionality
as a separate filter.
> Thanks
>
> Radek
>
> [1] http://www.mail-archive.com/ffmpeg-soc at mplayerhq.hu/msg01688.html
> From 4a1f2f6ae45c90acbdf1e2e5bce97e1c05263f01 Mon Sep 17 00:00:00 2001
> From: Vitor Sessak <vitor1001 at gmail.com>
> Date: Sat, 9 Oct 2010 22:12:33 +0200
> Subject: [PATCH] Added transpose video filter
> MIME-Version: 1.0
> Content-Type: text/plain; charset=UTF-8
> Content-Transfer-Encoding: 8bit
>
> It can be used together with vflip to rotate videos:
>
> traspose + vflip == 90?ccw rotate
> vflip + transpose== 90? cw rotate
> ---
> libavfilter/vf_transpose.c | 134 ++++++++++++++++++++++++++++++++++++++++++++
> 1 files changed, 134 insertions(+), 0 deletions(-)
> create mode 100644 libavfilter/vf_transpose.c
>
> diff --git a/libavfilter/vf_transpose.c b/libavfilter/vf_transpose.c
> new file mode 100644
> index 0000000..c968283
> --- /dev/null
> +++ b/libavfilter/vf_transpose.c
> @@ -0,0 +1,134 @@
> +/*
> + * transpose (line => column) video filter
remove this line, file description goes in @file
> + * Copyright (c) 2008 Vitor Sessak
Nit: (c) => (C)
> + *
> + * This file is part of FFmpeg.
> + *
> + * FFmpeg is free software; you can redistribute it and/or
> + * modify it 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.
> + *
> + * FFmpeg is distributed in the hope that it 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 FFmpeg; if not, write to the Free Software
> + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
> + */
> +
> +/**
> + * @file
> + * Transposition filter
> + *
> + * @todo handle packed pixel formats
What about to fix this?
> + */
> +
> +#include "avfilter.h"
> +
> +typedef struct
> +{
nit: typedef struct {
> + int hsub, vsub;
> +} TransContext;
> +
> +static int config_props_input(AVFilterLink *link)
inlink for better readability.
> +{
> + TransContext *trans = link->dst->priv;
> +
> + avcodec_get_chroma_sub_sample(link->format, &trans->hsub, &trans->vsub);
This add a dependency on libavcodec. Use av_pix_fmt_descriptors.
> +
> + return 0;
> +}
> +
> +static int query_formats(AVFilterContext *ctx)
> +{
> + enum PixelFormat pix_fmts[] = {
> + PIX_FMT_YUV444P, PIX_FMT_YUV422P, PIX_FMT_YUV420P,
> + PIX_FMT_YUV411P, PIX_FMT_YUV410P,
> + PIX_FMT_YUVJ444P, PIX_FMT_YUVJ422P, PIX_FMT_YUVJ420P,
> + PIX_FMT_YUV440P, PIX_FMT_YUVJ440P,
> + PIX_FMT_NONE
> + };
> +
> + avfilter_set_common_formats(ctx, avfilter_make_format_list(pix_fmts));
> + return 0;
> +}
> +
> +static int config_props_output(AVFilterLink *link)
inlink
> +{
> + link->w = link->src->inputs[0]->h;
> + link->h = link->src->inputs[0]->w;
> +
> + return 0;
> +}
> +
> +static void end_frame(AVFilterLink *link)
> +{
inlink
> + TransContext *trans = link->dst->priv;
> + AVFilterBufferRef *in = link->cur_buf;
> + AVFilterBufferRef *out = link->dst->outputs[0]->out_buf;
> + AVFilterBufferRef *pic = link->cur_buf;
pic is redundant
> + AVFilterLink *output = link->dst->outputs[0];
> + int i, j, plane;
> +
> + /* luma plane */
> + for(i = 0; i < pic->video->h; i ++)
nit: for_( here and below
> + for(j = 0; j < pic->video->w; j ++)
> + *(out->data[0] + j *out->linesize[0] + i) =
> + *(in->data[0]+ i * in->linesize[0] + j);
> +
> + /* chroma planes */
> + for(plane = 1; plane < 3; plane ++) {
> + for(i = 0; i < pic->video->h >> trans->vsub; i++) {
> + for(j = 0; j < pic->video->w >> trans->hsub; j++)
> + *(out->data[plane] + j *out->linesize[plane] + i) =
> + *(in->data[plane]+ i * in->linesize[plane] + j);
> + }
> + }
> +
> + avfilter_unref_buffer(in);
> + avfilter_draw_slice(output, 0, out->video->h, 1);
> + avfilter_end_frame(output);
> + avfilter_unref_buffer(out);
> +}
> +
> +static void start_frame(AVFilterLink *link, AVFilterBufferRef *picref)
inlink
> +{
> + AVFilterLink *out = link->dst->outputs[0];
outlink
> +
> + out->out_buf = avfilter_get_video_buffer(out, AV_PERM_WRITE, out->w, out->h);
> + out->out_buf->pts = picref->pts;
> +
> + if (picref->video->pixel_aspect.num == 0) {
> + out->out_buf->video->pixel_aspect = picref->video->pixel_aspect;
> + } else {
> + out->out_buf->video->pixel_aspect.num = picref->video->pixel_aspect.den;
> + out->out_buf->video->pixel_aspect.den = picref->video->pixel_aspect.num;
> + }
> +
> + avfilter_start_frame(out, avfilter_ref_buffer(out->out_buf, ~0));
> +}
> +
> +AVFilter avfilter_vf_transpose =
> +{
nit: "avfilter_vf_transpose = {" on the same line
> + .name = "transpose",
> +
missing .description
> + .priv_size = sizeof(TransContext),
> +
> + .query_formats = query_formats,
> +
> + .inputs = (AVFilterPad[]) {{ .name = "default",
> + .type = AVMEDIA_TYPE_VIDEO,
> + .start_frame = start_frame,
> + .end_frame = end_frame,
> + .config_props = config_props_input,
> + .min_perms = AV_PERM_READ, },
> + { .name = NULL}},
> + .outputs = (AVFilterPad[]) {{ .name = "default",
> + .config_props = config_props_output,
> + .type = AVMEDIA_TYPE_VIDEO, },
> + { .name = NULL}},
> +};
Missing docs in doc/filters.texi.
--
FFmpeg = Faithful and Faithful Martial Portable Embarassing Gigant
More information about the ffmpeg-devel
mailing list