[FFmpeg-devel] [PATCH] avfilter/avfiltergraph: auto insert idet filters in case of supported formats after video sources
Michael Niedermayer
michaelni at gmx.at
Mon Jan 19 06:09:29 CET 2015
This should allow changing the default of scale filters to autodetect interlacing
Signed-off-by: Michael Niedermayer <michaelni at gmx.at>
---
libavfilter/avfiltergraph.c | 80 +++++++++++++++++++++++++++++++++++++++++++
1 file changed, 80 insertions(+)
diff --git a/libavfilter/avfiltergraph.c b/libavfilter/avfiltergraph.c
index a859ecb..679b23f 100644
--- a/libavfilter/avfiltergraph.c
+++ b/libavfilter/avfiltergraph.c
@@ -1089,6 +1089,84 @@ static int pick_formats(AVFilterGraph *graph)
return 0;
}
+static int inject_idets(AVFilterGraph *graph, AVClass *log_ctx)
+{
+ int i, j, k;
+ int idet_count = 0;
+ int ret;
+
+ for (i = 0; i < graph->nb_filters; i++) {
+ AVFilterContext *filter = graph->filters[i];
+ if (filter->nb_inputs || !filter->nb_outputs)
+ continue;
+
+ for (j = 0; j < filter->nb_outputs; j++) {
+ AVFilterLink *link = filter->outputs[j];
+ if (link->type != AVMEDIA_TYPE_VIDEO)
+ continue;
+ if (link->in_formats) {
+ int progressive = 1;
+
+ for (k = 0; k < link->in_formats->nb_formats; k++) {
+ switch (link->in_formats->formats[k]) {
+ case AV_PIX_FMT_YUV420P:
+ case AV_PIX_FMT_YUV422P:
+ case AV_PIX_FMT_YUV444P:
+ progressive = 0;
+ }
+ }
+ if (!progressive) {
+ AVFilterContext *detect;
+ AVFilter *filter;
+ AVFilterLink *inlink, *outlink;
+ char scale_args[256];
+ char inst_name[30];
+
+ if (!(filter = avfilter_get_by_name("idet"))) {
+ av_log(log_ctx, AV_LOG_ERROR, "'idet' filter "
+ "not present, cannot perform interlace detection.\n");
+ return AVERROR(EINVAL);
+ }
+
+ snprintf(inst_name, sizeof(inst_name), "auto-inserted idet %d",
+ idet_count++);
+
+ if ((ret = avfilter_graph_create_filter(&detect, filter,
+ inst_name, "analyze_interlaced_flag=10"/*graph->idet_opts*/, NULL,
+ graph)) < 0)
+ return ret;
+
+
+ if ((ret = avfilter_insert_filter(link, detect, 0, 0)) < 0)
+ return ret;
+
+ if ((ret = filter_query_formats(detect)) < 0)
+ return ret;
+
+ inlink = detect->inputs[0];
+ outlink = detect->outputs[0];
+ av_assert0( inlink-> in_formats->refcount > 0);
+ av_assert0( inlink->out_formats->refcount > 0);
+ av_assert0(outlink-> in_formats->refcount > 0);
+ av_assert0(outlink->out_formats->refcount > 0);
+ if (!ff_merge_formats( inlink->in_formats, inlink->out_formats, inlink->type) ||
+ !ff_merge_formats(outlink->in_formats, outlink->out_formats, outlink->type))
+ ret = AVERROR(ENOSYS);
+
+ if (ret < 0) {
+ av_log(log_ctx, AV_LOG_ERROR,
+ "Impossible to link in idet filter between "
+ "'%s' and the filter '%s'\n", link->src->name, link->dst->name);
+ return ret;
+ }
+ }
+ }
+ }
+ }
+
+ return 0;
+}
+
/**
* Configure the formats of all the links in the graph.
*/
@@ -1102,6 +1180,8 @@ static int graph_config_formats(AVFilterGraph *graph, AVClass *log_ctx)
if (ret < 0)
return ret;
+ inject_idets(graph, log_ctx);
+
/* Once everything is merged, it's possible that we'll still have
* multiple valid media format choices. We try to minimize the amount
* of format conversion inside filters */
--
1.7.9.5
More information about the ffmpeg-devel
mailing list