Commit 30d40c9e authored by Clément Bœsch's avatar Clément Bœsch

lavfi/drawtext: add generic timeline interface and deprecate "draw".

parent 493ebbd7
...@@ -3239,16 +3239,6 @@ Either a string (e.g. "yellow") or in 0xRRGGBB[AA] format ...@@ -3239,16 +3239,6 @@ Either a string (e.g. "yellow") or in 0xRRGGBB[AA] format
(e.g. "0xff00ff"), possibly followed by an alpha specifier. (e.g. "0xff00ff"), possibly followed by an alpha specifier.
The default value of @var{boxcolor} is "white". The default value of @var{boxcolor} is "white".
@item draw
Set an expression which specifies if the text should be drawn. If the
expression evaluates to 0, the text is not drawn. This is useful for
specifying that the text should be drawn only when specific conditions
are met.
Default value is "1".
See below for the list of accepted constants and functions.
@item expansion @item expansion
Select how the @var{text} is expanded. Can be either @code{none}, Select how the @var{text} is expanded. Can be either @code{none},
@code{strftime} (deprecated) or @code{strftime} (deprecated) or
...@@ -3548,7 +3538,7 @@ drawtext="fontsize=60:fontfile=FreeSerif.ttf:fontcolor=green:text=g:x=(w-max_gly ...@@ -3548,7 +3538,7 @@ drawtext="fontsize=60:fontfile=FreeSerif.ttf:fontcolor=green:text=g:x=(w-max_gly
@item @item
Show text for 1 second every 3 seconds: Show text for 1 second every 3 seconds:
@example @example
drawtext="fontfile=FreeSerif.ttf:fontcolor=white:x=100:y=x/dar:draw=lt(mod(t\,3)\,1):text='blink'" drawtext="fontfile=FreeSerif.ttf:fontcolor=white:x=100:y=x/dar:enable=lt(mod(t\,3)\,1):text='blink'"
@end example @end example
@item @item
......
...@@ -31,7 +31,7 @@ ...@@ -31,7 +31,7 @@
#define LIBAVFILTER_VERSION_MAJOR 3 #define LIBAVFILTER_VERSION_MAJOR 3
#define LIBAVFILTER_VERSION_MINOR 83 #define LIBAVFILTER_VERSION_MINOR 83
#define LIBAVFILTER_VERSION_MICRO 101 #define LIBAVFILTER_VERSION_MICRO 102
#define LIBAVFILTER_VERSION_INT AV_VERSION_INT(LIBAVFILTER_VERSION_MAJOR, \ #define LIBAVFILTER_VERSION_INT AV_VERSION_INT(LIBAVFILTER_VERSION_MAJOR, \
LIBAVFILTER_VERSION_MINOR, \ LIBAVFILTER_VERSION_MINOR, \
...@@ -82,5 +82,8 @@ ...@@ -82,5 +82,8 @@
#ifndef FF_API_OLD_GRAPH_PARSE #ifndef FF_API_OLD_GRAPH_PARSE
#define FF_API_OLD_GRAPH_PARSE (LIBAVFILTER_VERSION_MAJOR < 4) #define FF_API_OLD_GRAPH_PARSE (LIBAVFILTER_VERSION_MAJOR < 4)
#endif #endif
#ifndef FF_API_DRAWTEXT_OLD_TIMELINE
#define FF_API_DRAWTEXT_OLD_TIMELINE (LIBAVFILTER_VERSION_MAJOR < 4)
#endif
#endif /* AVFILTER_VERSION_H */ #endif /* AVFILTER_VERSION_H */
...@@ -155,9 +155,11 @@ typedef struct { ...@@ -155,9 +155,11 @@ typedef struct {
AVExpr *x_pexpr, *y_pexpr; ///< parsed expressions for x and y AVExpr *x_pexpr, *y_pexpr; ///< parsed expressions for x and y
int64_t basetime; ///< base pts time in the real world for display int64_t basetime; ///< base pts time in the real world for display
double var_values[VAR_VARS_NB]; double var_values[VAR_VARS_NB];
#if FF_API_DRAWTEXT_OLD_TIMELINE
char *draw_expr; ///< expression for draw char *draw_expr; ///< expression for draw
AVExpr *draw_pexpr; ///< parsed expression for draw AVExpr *draw_pexpr; ///< parsed expression for draw
int draw; ///< set to zero to prevent drawing int draw; ///< set to zero to prevent drawing
#endif
AVLFG prng; ///< random AVLFG prng; ///< random
char *tc_opt_string; ///< specified timecode option string char *tc_opt_string; ///< specified timecode option string
AVRational tc_rate; ///< frame rate for timecode AVRational tc_rate; ///< frame rate for timecode
...@@ -186,7 +188,9 @@ static const AVOption drawtext_options[]= { ...@@ -186,7 +188,9 @@ static const AVOption drawtext_options[]= {
{"shadowy", "set y", OFFSET(shadowy), AV_OPT_TYPE_INT, {.i64=0}, INT_MIN, INT_MAX , FLAGS}, {"shadowy", "set y", OFFSET(shadowy), AV_OPT_TYPE_INT, {.i64=0}, INT_MIN, INT_MAX , FLAGS},
{"tabsize", "set tab size", OFFSET(tabsize), AV_OPT_TYPE_INT, {.i64=4}, 0, INT_MAX , FLAGS}, {"tabsize", "set tab size", OFFSET(tabsize), AV_OPT_TYPE_INT, {.i64=4}, 0, INT_MAX , FLAGS},
{"basetime", "set base time", OFFSET(basetime), AV_OPT_TYPE_INT64, {.i64=AV_NOPTS_VALUE}, INT64_MIN, INT64_MAX , FLAGS}, {"basetime", "set base time", OFFSET(basetime), AV_OPT_TYPE_INT64, {.i64=AV_NOPTS_VALUE}, INT64_MIN, INT64_MAX , FLAGS},
{"draw", "if false do not draw", OFFSET(draw_expr), AV_OPT_TYPE_STRING, {.str="1"}, CHAR_MIN, CHAR_MAX, FLAGS}, #if FF_API_DRAWTEXT_OLD_TIMELINE
{"draw", "if false do not draw (deprecated)", OFFSET(draw_expr), AV_OPT_TYPE_STRING, {.str=NULL}, CHAR_MIN, CHAR_MAX, FLAGS},
#endif
{"expansion", "set the expansion mode", OFFSET(exp_mode), AV_OPT_TYPE_INT, {.i64=EXP_NORMAL}, 0, 2, FLAGS, "expansion"}, {"expansion", "set the expansion mode", OFFSET(exp_mode), AV_OPT_TYPE_INT, {.i64=EXP_NORMAL}, 0, 2, FLAGS, "expansion"},
{"none", "set no expansion", OFFSET(exp_mode), AV_OPT_TYPE_CONST, {.i64=EXP_NONE}, 0, 0, FLAGS, "expansion"}, {"none", "set no expansion", OFFSET(exp_mode), AV_OPT_TYPE_CONST, {.i64=EXP_NONE}, 0, 0, FLAGS, "expansion"},
...@@ -423,6 +427,12 @@ static av_cold int init(AVFilterContext *ctx) ...@@ -423,6 +427,12 @@ static av_cold int init(AVFilterContext *ctx)
DrawTextContext *s = ctx->priv; DrawTextContext *s = ctx->priv;
Glyph *glyph; Glyph *glyph;
#if FF_API_DRAWTEXT_OLD_TIMELINE
if (s->draw_expr)
av_log(ctx, AV_LOG_WARNING, "'draw' option is deprecated and will be removed soon, "
"you are encouraged to use the generic timeline support through the 'enable' option\n");
#endif
if (!s->fontfile && !CONFIG_FONTCONFIG) { if (!s->fontfile && !CONFIG_FONTCONFIG) {
av_log(ctx, AV_LOG_ERROR, "No font filename provided\n"); av_log(ctx, AV_LOG_ERROR, "No font filename provided\n");
return AVERROR(EINVAL); return AVERROR(EINVAL);
...@@ -518,8 +528,10 @@ static av_cold void uninit(AVFilterContext *ctx) ...@@ -518,8 +528,10 @@ static av_cold void uninit(AVFilterContext *ctx)
av_expr_free(s->x_pexpr); av_expr_free(s->x_pexpr);
av_expr_free(s->y_pexpr); av_expr_free(s->y_pexpr);
#if FF_API_DRAWTEXT_OLD_TIMELINE
av_expr_free(s->draw_pexpr); av_expr_free(s->draw_pexpr);
s->x_pexpr = s->y_pexpr = s->draw_pexpr = NULL; s->x_pexpr = s->y_pexpr = s->draw_pexpr = NULL;
#endif
av_freep(&s->positions); av_freep(&s->positions);
s->nb_positions = 0; s->nb_positions = 0;
...@@ -564,16 +576,25 @@ static int config_input(AVFilterLink *inlink) ...@@ -564,16 +576,25 @@ static int config_input(AVFilterLink *inlink)
av_expr_free(s->x_pexpr); av_expr_free(s->x_pexpr);
av_expr_free(s->y_pexpr); av_expr_free(s->y_pexpr);
#if FF_API_DRAWTEXT_OLD_TIMELINE
av_expr_free(s->draw_pexpr); av_expr_free(s->draw_pexpr);
s->x_pexpr = s->y_pexpr = s->draw_pexpr = NULL; s->x_pexpr = s->y_pexpr = s->draw_pexpr = NULL;
#else
s->x_pexpr = s->y_pexpr = NULL;
#endif
if ((ret = av_expr_parse(&s->x_pexpr, s->x_expr, var_names, if ((ret = av_expr_parse(&s->x_pexpr, s->x_expr, var_names,
NULL, NULL, fun2_names, fun2, 0, ctx)) < 0 || NULL, NULL, fun2_names, fun2, 0, ctx)) < 0 ||
(ret = av_expr_parse(&s->y_pexpr, s->y_expr, var_names, (ret = av_expr_parse(&s->y_pexpr, s->y_expr, var_names,
NULL, NULL, fun2_names, fun2, 0, ctx)) < 0 ||
(ret = av_expr_parse(&s->draw_pexpr, s->draw_expr, var_names,
NULL, NULL, fun2_names, fun2, 0, ctx)) < 0) NULL, NULL, fun2_names, fun2, 0, ctx)) < 0)
return AVERROR(EINVAL); return AVERROR(EINVAL);
#if FF_API_DRAWTEXT_OLD_TIMELINE
if (s->draw_expr &&
(ret = av_expr_parse(&s->draw_pexpr, s->draw_expr, var_names,
NULL, NULL, fun2_names, fun2, 0, ctx)) < 0)
return ret;
#endif
return 0; return 0;
} }
...@@ -955,10 +976,16 @@ static int draw_text(AVFilterContext *ctx, AVFrame *frame, ...@@ -955,10 +976,16 @@ static int draw_text(AVFilterContext *ctx, AVFrame *frame,
s->x = s->var_values[VAR_X] = av_expr_eval(s->x_pexpr, s->var_values, &s->prng); s->x = s->var_values[VAR_X] = av_expr_eval(s->x_pexpr, s->var_values, &s->prng);
s->y = s->var_values[VAR_Y] = av_expr_eval(s->y_pexpr, s->var_values, &s->prng); s->y = s->var_values[VAR_Y] = av_expr_eval(s->y_pexpr, s->var_values, &s->prng);
s->x = s->var_values[VAR_X] = av_expr_eval(s->x_pexpr, s->var_values, &s->prng); s->x = s->var_values[VAR_X] = av_expr_eval(s->x_pexpr, s->var_values, &s->prng);
#if FF_API_DRAWTEXT_OLD_TIMELINE
if (s->draw_pexpr){
s->draw = av_expr_eval(s->draw_pexpr, s->var_values, &s->prng); s->draw = av_expr_eval(s->draw_pexpr, s->var_values, &s->prng);
if(!s->draw) if(!s->draw)
return 0; return 0;
}
if (ctx->is_disabled)
return 0;
#endif
box_w = FFMIN(width - 1 , max_text_line_w); box_w = FFMIN(width - 1 , max_text_line_w);
box_h = FFMIN(height - 1, y + s->max_glyph_h); box_h = FFMIN(height - 1, y + s->max_glyph_h);
...@@ -1042,4 +1069,9 @@ AVFilter avfilter_vf_drawtext = { ...@@ -1042,4 +1069,9 @@ AVFilter avfilter_vf_drawtext = {
.inputs = avfilter_vf_drawtext_inputs, .inputs = avfilter_vf_drawtext_inputs,
.outputs = avfilter_vf_drawtext_outputs, .outputs = avfilter_vf_drawtext_outputs,
.process_command = command, .process_command = command,
#if FF_API_DRAWTEXT_OLD_TIMELINE
.flags = AVFILTER_FLAG_SUPPORT_TIMELINE_INTERNAL,
#else
.flags = AVFILTER_FLAG_SUPPORT_TIMELINE_GENERIC,
#endif
}; };
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment