lavfi/drawtext: add fontcolor_expr option
authorAndrey Utkin <andrey.krieger.utkin@gmail.com>
Fri, 4 Jul 2014 18:54:53 +0000 (21:54 +0300)
committerStefano Sabatini <stefasab@gmail.com>
Thu, 17 Jul 2014 10:42:56 +0000 (12:42 +0200)
Allow to dynamically evaluate the font color.

Signed-off-by: Stefano Sabatini <stefasab@gmail.com>
doc/filters.texi
libavfilter/version.h
libavfilter/vf_drawtext.c

index 6bea105..54d6549 100644 (file)
@@ -3698,6 +3698,11 @@ the "Color" section in the ffmpeg-utils manual.
 
 The default value of @var{fontcolor} is "black".
 
 
 The default value of @var{fontcolor} is "black".
 
+@item fontcolor_expr
+String which is expanded the same way as @var{text} to obtain dynamic
+@var{fontcolor} value. By default this option has empty value and is not
+processed. When this option is set, it overrides @var{fontcolor} option.
+
 @item font
 The font family to be used for drawing text. By default Sans.
 
 @item font
 The font family to be used for drawing text. By default Sans.
 
@@ -4019,6 +4024,17 @@ Print the date of a real-time encoding (see strftime(3)):
 drawtext='fontfile=FreeSans.ttf:text=%@{localtime:%a %b %d %Y@}'
 @end example
 
 drawtext='fontfile=FreeSans.ttf:text=%@{localtime:%a %b %d %Y@}'
 @end example
 
+@item
+Shwo text fading in and out (appearing/disappearing):
+@example
+#!/bin/sh
+DS=1.0 # display start
+DE=10.0 # display end
+FID=1.5 # fade in duration
+FOD=5 # fade out duration
+ffplay -f lavfi "color,drawtext=text=TEST:fontsize=50:fontfile=FreeSerif.ttf:fontcolor_expr=ff0000%@{eif\\\\: max(0\\, min(255\\, 255*(1*between(t\\, $DS + $FID\\, $DE - $FOD) + ((t - $DS)/$FID)*between(t\\, $DS\\, $DS + $FID) + (-(t - $DE)/$FOD)*between(t\\, $DE - $FOD\\, $DE) ) )) \\\\: x\\\\: 2 @}"
+@end example
+
 @end itemize
 
 For more information about libfreetype, check:
 @end itemize
 
 For more information about libfreetype, check:
index 8f47a96..9f2c364 100644 (file)
@@ -31,7 +31,7 @@
 
 #define LIBAVFILTER_VERSION_MAJOR   4
 #define LIBAVFILTER_VERSION_MINOR  11
 
 #define LIBAVFILTER_VERSION_MAJOR   4
 #define LIBAVFILTER_VERSION_MINOR  11
-#define LIBAVFILTER_VERSION_MICRO 101
+#define LIBAVFILTER_VERSION_MICRO 102
 
 #define LIBAVFILTER_VERSION_INT AV_VERSION_INT(LIBAVFILTER_VERSION_MAJOR, \
                                                LIBAVFILTER_VERSION_MINOR, \
 
 #define LIBAVFILTER_VERSION_INT AV_VERSION_INT(LIBAVFILTER_VERSION_MAJOR, \
                                                LIBAVFILTER_VERSION_MINOR, \
index 3336eb2..c744d93 100644 (file)
@@ -143,6 +143,8 @@ typedef struct DrawTextContext {
     uint8_t *fontfile;              ///< font to be used
     uint8_t *text;                  ///< text to be drawn
     AVBPrint expanded_text;         ///< used to contain the expanded text
     uint8_t *fontfile;              ///< font to be used
     uint8_t *text;                  ///< text to be drawn
     AVBPrint expanded_text;         ///< used to contain the expanded text
+    uint8_t *fontcolor_expr;        ///< fontcolor expression to evaluate
+    AVBPrint expanded_fontcolor;    ///< used to contain the expanded fontcolor spec
     int ft_load_flags;              ///< flags used for loading fonts, see FT_LOAD_*
     FT_Vector *positions;           ///< positions for each element in the text
     size_t nb_positions;            ///< number of elements of positions array
     int ft_load_flags;              ///< flags used for loading fonts, see FT_LOAD_*
     FT_Vector *positions;           ///< positions for each element in the text
     size_t nb_positions;            ///< number of elements of positions array
@@ -201,6 +203,7 @@ static const AVOption drawtext_options[]= {
     {"text",        "set text",             OFFSET(text),               AV_OPT_TYPE_STRING, {.str=NULL},  CHAR_MIN, CHAR_MAX, FLAGS},
     {"textfile",    "set text file",        OFFSET(textfile),           AV_OPT_TYPE_STRING, {.str=NULL},  CHAR_MIN, CHAR_MAX, FLAGS},
     {"fontcolor",   "set foreground color", OFFSET(fontcolor.rgba),     AV_OPT_TYPE_COLOR,  {.str="black"}, CHAR_MIN, CHAR_MAX, FLAGS},
     {"text",        "set text",             OFFSET(text),               AV_OPT_TYPE_STRING, {.str=NULL},  CHAR_MIN, CHAR_MAX, FLAGS},
     {"textfile",    "set text file",        OFFSET(textfile),           AV_OPT_TYPE_STRING, {.str=NULL},  CHAR_MIN, CHAR_MAX, FLAGS},
     {"fontcolor",   "set foreground color", OFFSET(fontcolor.rgba),     AV_OPT_TYPE_COLOR,  {.str="black"}, CHAR_MIN, CHAR_MAX, FLAGS},
+    {"fontcolor_expr", "set foreground color expression", OFFSET(fontcolor_expr), AV_OPT_TYPE_STRING, {.str=""}, CHAR_MIN, CHAR_MAX, FLAGS},
     {"boxcolor",    "set box color",        OFFSET(boxcolor.rgba),      AV_OPT_TYPE_COLOR,  {.str="white"}, CHAR_MIN, CHAR_MAX, FLAGS},
     {"bordercolor", "set border color",     OFFSET(bordercolor.rgba),   AV_OPT_TYPE_COLOR,  {.str="black"}, CHAR_MIN, CHAR_MAX, FLAGS},
     {"shadowcolor", "set shadow color",     OFFSET(shadowcolor.rgba),   AV_OPT_TYPE_COLOR,  {.str="black"}, CHAR_MIN, CHAR_MAX, FLAGS},
     {"boxcolor",    "set box color",        OFFSET(boxcolor.rgba),      AV_OPT_TYPE_COLOR,  {.str="white"}, CHAR_MIN, CHAR_MAX, FLAGS},
     {"bordercolor", "set border color",     OFFSET(bordercolor.rgba),   AV_OPT_TYPE_COLOR,  {.str="black"}, CHAR_MIN, CHAR_MAX, FLAGS},
     {"shadowcolor", "set shadow color",     OFFSET(shadowcolor.rgba),   AV_OPT_TYPE_COLOR,  {.str="black"}, CHAR_MIN, CHAR_MAX, FLAGS},
@@ -683,6 +686,7 @@ static av_cold int init(AVFilterContext *ctx)
         av_log(ctx, AV_LOG_WARNING, "expansion=strftime is deprecated.\n");
 
     av_bprint_init(&s->expanded_text, 0, AV_BPRINT_SIZE_UNLIMITED);
         av_log(ctx, AV_LOG_WARNING, "expansion=strftime is deprecated.\n");
 
     av_bprint_init(&s->expanded_text, 0, AV_BPRINT_SIZE_UNLIMITED);
+    av_bprint_init(&s->expanded_fontcolor, 0, AV_BPRINT_SIZE_UNLIMITED);
 
     return 0;
 }
 
     return 0;
 }
@@ -726,6 +730,7 @@ static av_cold void uninit(AVFilterContext *ctx)
     FT_Done_FreeType(s->library);
 
     av_bprint_finalize(&s->expanded_text, NULL);
     FT_Done_FreeType(s->library);
 
     av_bprint_finalize(&s->expanded_text, NULL);
+    av_bprint_finalize(&s->expanded_fontcolor, NULL);
 }
 
 static int config_input(AVFilterLink *inlink)
 }
 
 static int config_input(AVFilterLink *inlink)
@@ -1054,11 +1059,8 @@ end:
     return ret;
 }
 
     return ret;
 }
 
-static int expand_text(AVFilterContext *ctx)
+static int expand_text(AVFilterContext *ctx, char *text, AVBPrint *bp)
 {
 {
-    DrawTextContext *s = ctx->priv;
-    char *text = s->text;
-    AVBPrint *bp = &s->expanded_text;
     int ret;
 
     av_bprint_clear(bp);
     int ret;
 
     av_bprint_clear(bp);
@@ -1154,7 +1156,7 @@ static int draw_text(AVFilterContext *ctx, AVFrame *frame,
         av_bprintf(bp, "%s", s->text);
         break;
     case EXP_NORMAL:
         av_bprintf(bp, "%s", s->text);
         break;
     case EXP_NORMAL:
-        if ((ret = expand_text(ctx)) < 0)
+        if ((ret = expand_text(ctx, s->text, &s->expanded_text)) < 0)
             return ret;
         break;
     case EXP_STRFTIME:
             return ret;
         break;
     case EXP_STRFTIME:
@@ -1180,6 +1182,20 @@ static int draw_text(AVFilterContext *ctx, AVFrame *frame,
         s->nb_positions = len;
     }
 
         s->nb_positions = len;
     }
 
+    if (s->fontcolor_expr[0]) {
+        /* If expression is set, evaluate and replace the static value */
+        av_bprint_clear(&s->expanded_fontcolor);
+        if ((ret = expand_text(ctx, s->fontcolor_expr, &s->expanded_fontcolor)) < 0)
+            return ret;
+        if (!av_bprint_is_complete(&s->expanded_fontcolor))
+            return AVERROR(ENOMEM);
+        av_log(s, AV_LOG_DEBUG, "Evaluated fontcolor is '%s'\n", s->expanded_fontcolor.str);
+        ret = av_parse_color(s->fontcolor.rgba, s->expanded_fontcolor.str, -1, s);
+        if (ret)
+            return ret;
+        ff_draw_color(&s->dc, &s->fontcolor, s->fontcolor.rgba);
+    }
+
     x = 0;
     y = 0;
 
     x = 0;
     y = 0;