[FFmpeg-devel] [PATCH 2/2] Extend color syntax, make it accept an alpha component specifier.

Stefano Sabatini stefano.sabatini-lala
Mon Jun 21 22:43:24 CEST 2010


On date Wednesday 2010-06-16 20:34:12 +0200, Stefano Sabatini encoded:
> On date Saturday 2010-06-12 00:54:05 +0200, Stefano Sabatini encoded:
> > On date Friday 2010-06-11 09:39:11 +0200, Benoit Fouet encoded:
> > > Hi,
> > > 
> > > On Fri, 11 Jun 2010 00:34:21 +0200 Stefano Sabatini wrote:
> > > > ---
> > > >  libavfilter/parseutils.h |    8 ++++++-
> > > > 
> > > > diff --git a/libavfilter/parseutils.h b/libavfilter/parseutils.h
> > > > index b5b494e..fc0c784 100644
> > > > --- a/libavfilter/parseutils.h
> > > > +++ b/libavfilter/parseutils.h
> > > > @@ -46,7 +46,13 @@ char *av_get_token(const char **buf, const char *term);
> > > >   * Puts the RGBA values that correspond to color_string in rgba_color.
> > > >   *
> > > >   * @param color_string a string specifying a color. It can be the name of
> > > > - * a color (case insensitive match) or a 0xRRGGBB[AA] sequence.
> > > > + * a color (case insensitive match) eventually followed by "@" and a
> > > > + * string representing the alpha component, or a 0xRRGGBB[AA]
> > > > + * sequence.
> > > 
> > > s/eventually/possibly/
> > > 
> > > > + * The alpha component may be a string composed by "0x" followed by an
> > > > + * hexadecimal number or a base-10 number between 0 and 255, or a
> > > > + * decimal number between 0.0 and 1.0, which represents the opacity
> > > > + * value. If the alpha component is not specified then 255 is assumed.
> > > 
> > > maybe add a hint for user to know that 255 (or 0xff, or 1.0) is opaque.
> > 
> > Updated, result of the test is now:
> > 
> > Testing av_parse_color()
> > bikeshed -> R(154) G(134) B(238) A(43)
> > RaNdOm -> R(51) G(54) B(196) A(23)
> > Cannot find color 'foo'
> > red -> R(255) G(0) B(0) A(255)
> > Cannot find color 'Red '
> > RED -> R(255) G(0) B(0) A(255)
> > Violet -> R(238) G(130) B(238) A(255)
> > Yellow -> R(255) G(255) B(0) A(255)
> > Red -> R(255) G(0) B(0) A(255)
> > 0x000000 -> R(0) G(0) B(0) A(255)
> > Invalid 0xRRGGBB[AA] color string: '0x0000000'
> > 0xff000000 -> R(255) G(0) B(0) A(0)
> > 0x3e34ff -> R(62) G(52) B(255) A(255)
> > 0x3e34ffaa -> R(62) G(52) B(255) A(170)
> > Invalid 0xRRGGBB[AA] color string: '0xffXXee'
> > Invalid 0xRRGGBB[AA] color string: '0xfoobar'
> > Invalid 0xRRGGBB[AA] color string: '0xffffeeeeeeee'
> > Invalid alpha value specifier 'foo' in 'red at foo'
> > random at 10 -> R(204) G(35) B(199) A(10)
> > 0xff0000 at 1.0 -> R(255) G(0) B(0) A(255)
> > Invalid alpha value specifier '' in 'red@'
> > Invalid alpha value specifier '0xfff' in 'red at 0xfff'
> > red at 0xf -> R(255) G(0) B(0) A(15)
> > red at 2 -> R(255) G(0) B(0) A(2)
> > red at 0.1 -> R(255) G(0) B(0) A(25)
> > Invalid alpha value specifier '-1' in 'red at -1'
> > red at 0.5 -> R(255) G(0) B(0) A(127)
> > red at 1.0 -> R(255) G(0) B(0) A(255)
> > Invalid alpha value specifier '256' in 'red at 256'
> > Invalid alpha value specifier '10foo' in 'red at 10foo'
> > Invalid alpha value specifier '-1.0' in 'red at -1.0'
> > red at -0.0 -> R(255) G(0) B(0) A(0)
> > 
> > Regards.
> > -- 
> > FFmpeg = Foolish and Fundamental Magic Peaceful Ecstatic Gymnast
> 
> > From 6a16a573a5cb47cc4f58f1ae22f4bdb6b86cbbe8 Mon Sep 17 00:00:00 2001
> > From: Stefano Sabatini <stefano.sabatini-lala at poste.it>
> > Date: Thu, 10 Jun 2010 20:24:01 +0200
> > Subject: [PATCH 2/3] Extend color syntax, make it accept an alpha component specifier.
> > 
> > ---
> >  libavfilter/parseutils.c |   62 ++++++++++++++++++++++++++++++++++++++++------
> >  libavfilter/parseutils.h |   10 ++++++-
> >  2 files changed, 63 insertions(+), 9 deletions(-)
> > 
> > diff --git a/libavfilter/parseutils.c b/libavfilter/parseutils.c
> > index 9ac61d8..4501b48 100644
> > --- a/libavfilter/parseutils.c
> > +++ b/libavfilter/parseutils.c
> > @@ -24,6 +24,7 @@
> >  
> >  #include <strings.h>
> >  #include "libavutil/avutil.h"
> > +#include "libavutil/avstring.h"
> >  #include "libavutil/random_seed.h"
> >  #include "parseutils.h"
> >  
> > @@ -215,22 +216,31 @@ static int color_table_compare(const void *lhs, const void *rhs)
> >      return strcasecmp(lhs, ((const ColorEntry *)rhs)->name);
> >  }
> >  
> > +#define ALPHA_SEP '@'
> > +
> >  int av_parse_color(uint8_t *rgba_color, const char *color_string, void *log_ctx)
> >  {
> > -    if (!strcasecmp(color_string, "random") || !strcasecmp(color_string, "bikeshed")) {
> > +    char *tail, color_string2[128];
> > +    const ColorEntry *entry;
> > +    av_strlcpy(color_string2, color_string, sizeof(color_string2));
> > +    if ((tail = strchr(color_string2, ALPHA_SEP)))
> > +        *tail++ = 0;
> > +    rgba_color[3] = 255;
> > +
> > +    if (!strcasecmp(color_string2, "random") || !strcasecmp(color_string2, "bikeshed")) {
> >          int rgba = av_get_random_seed();
> >          rgba_color[0] = rgba >> 24;
> >          rgba_color[1] = rgba >> 16;
> >          rgba_color[2] = rgba >> 8;
> >          rgba_color[3] = rgba;
> >      } else
> > -    if (!strncmp(color_string, "0x", 2)) {
> > +    if (!strncmp(color_string2, "0x", 2)) {
> >          char *tail;
> > -        int len = strlen(color_string);
> > -        unsigned int rgba = strtoul(color_string, &tail, 16);
> > +        int len = strlen(color_string2);
> > +        unsigned int rgba = strtoul(color_string2, &tail, 16);
> >  
> >          if (*tail || (len != 8 && len != 10)) {
> > -            av_log(log_ctx, AV_LOG_ERROR, "Invalid 0xRRGGBB[AA] color string: '%s'\n", color_string);
> > +            av_log(log_ctx, AV_LOG_ERROR, "Invalid 0xRRGGBB[AA] color string: '%s'\n", color_string2);
> >              return AVERROR(EINVAL);
> >          }
> >          if (len == 10) {
> > @@ -241,16 +251,37 @@ int av_parse_color(uint8_t *rgba_color, const char *color_string, void *log_ctx)
> >          rgba_color[1] = rgba >> 8;
> >          rgba_color[2] = rgba;
> >      } else {
> > -        const ColorEntry *entry = bsearch(color_string,
> > +        entry = bsearch(color_string2,
> >                                            color_table,
> >                                            FF_ARRAY_ELEMS(color_table),
> >                                            sizeof(ColorEntry),
> >                                            color_table_compare);
> >          if (!entry) {
> > -            av_log(log_ctx, AV_LOG_ERROR, "Cannot find color '%s'\n", color_string);
> > +            av_log(log_ctx, AV_LOG_ERROR, "Cannot find color '%s'\n", color_string2);
> > +            return AVERROR(EINVAL);
> > +        }
> > +        memcpy(rgba_color, entry->rgba_color, 3);
> > +    }
> > +
> > +    if (tail) {
> > +        unsigned long int alpha;
> > +        const char *alpha_string = tail;
> > +        if (!strncmp(alpha_string, "0x", 2)) {
> > +            alpha = strtoul(alpha_string, &tail, 16);
> > +        } else {
> > +            alpha = strtoul(alpha_string, &tail, 10);
> > +            if (*tail) {
> > +                double d = strtod(alpha_string, &tail);
> > +                alpha = d * 255;
> > +            }
> > +        }
> > +
> > +        if (tail == alpha_string || *tail || alpha > 255) {
> > +            av_log(log_ctx, AV_LOG_ERROR, "Invalid alpha value specifier '%s' in '%s'\n",
> > +                   alpha_string, color_string);
> >              return AVERROR(EINVAL);
> >          }
> > -        memcpy(rgba_color, entry->rgba_color, 4);
> > +        rgba_color[3] = alpha;
> >      }
> >  
> >      return 0;
> > @@ -420,6 +451,21 @@ int main(void)
> >              "0xffXXee",
> >              "0xfoobar",
> >              "0xffffeeeeeeee",
> > +            "red at foo",
> > +            "random at 10",
> > +            "0xff0000 at 1.0",
> > +            "red@",
> > +            "red at 0xfff",
> > +            "red at 0xf",
> > +            "red at 2",
> > +            "red at 0.1",
> > +            "red at -1",
> > +            "red at 0.5",
> > +            "red at 1.0",
> > +            "red at 256",
> > +            "red at 10foo",
> > +            "red at -1.0",
> > +            "red at -0.0",
> >          };
> >  
> >          av_log_set_level(AV_LOG_DEBUG);
> > diff --git a/libavfilter/parseutils.h b/libavfilter/parseutils.h
> > index b5b494e..fb930b7 100644
> > --- a/libavfilter/parseutils.h
> > +++ b/libavfilter/parseutils.h
> > @@ -46,7 +46,15 @@ char *av_get_token(const char **buf, const char *term);
> >   * Puts the RGBA values that correspond to color_string in rgba_color.
> >   *
> >   * @param color_string a string specifying a color. It can be the name of
> > - * a color (case insensitive match) or a 0xRRGGBB[AA] sequence.
> > + * a color (case insensitive match) or a 0xRRGGBB[AA] sequence,
> > + * possibly followed by "@" and a string representing the alpha
> > + * component.
> > + * The alpha component may be a string composed by "0x" followed by an
> > + * hexadecimal number or a base-10 number between 0 and 255, or a
> > + * decimal number between 0.0 and 1.0, which represents the opacity
> > + * value (0 means completely transparent, 255/0xff/1.0 completely
> > + * opaque).
> > + * If the alpha component is not specified then 255 is assumed.
> >   * The string "random" will result in a random color.
> >   * @return >= 0 in case of success, a negative value in case of
> >   * failure (for example if color_string cannot be parsed).
> 
> Ping.

I'll apply in three days if there are no objections.

Regards.
-- 
FFmpeg = Fast & Frightening Meaningful Perennial Erudite God



More information about the ffmpeg-devel mailing list