From 76b0459fdd7a2498d7a9233683f055b6c616f9c0 Mon Sep 17 00:00:00 2001 From: John Bowler Date: Wed, 16 Nov 2011 13:44:42 -0600 Subject: [PATCH] [libpng15] Updated contrib/sRGBtables code --- contrib/sRGBtables/cvtcolor.c | 181 ++++++++++++++++++++++++++++++++++ contrib/sRGBtables/makesRGB.c | 32 +----- contrib/sRGBtables/sRGB.h | 7 +- 3 files changed, 187 insertions(+), 33 deletions(-) create mode 100644 contrib/sRGBtables/cvtcolor.c diff --git a/contrib/sRGBtables/cvtcolor.c b/contrib/sRGBtables/cvtcolor.c new file mode 100644 index 000000000..26afe6dc9 --- /dev/null +++ b/contrib/sRGBtables/cvtcolor.c @@ -0,0 +1,181 @@ +/*- + * convert.c + * + * Convert 8-bit sRGB or 16-bit linear values to another format. + */ +#define _ISOC99_SOURCE 1 + +#include +#include +#include +#include + +#include + +#include "sRGB.h" + +static void +usage(const char *prog) +{ + fprintf(stderr, + "%s: usage: %s [-linear|-sRGB] [-gray|-color] component{1,4}\n", + prog, prog); + exit(1); +} + +unsigned long +component(const char *prog, const char *arg, int issRGB) +{ + char *ep; + unsigned long c = strtoul(arg, &ep, 0); + + if (ep <= arg || *ep || c > 65535 || (issRGB && c > 255)) + { + fprintf(stderr, "%s: %s: invalid component value (%lu)\n", prog, arg, c); + usage(prog); + } + + return c; +} + +int +main(int argc, const char **argv) +{ + const char *prog = *argv++; + int to_linear = 0, to_gray = 0, to_color = 0; + int channels = 0; + double c[4]; + + /* FE_TONEAREST is the IEEE754 round to nearest, preferring even, mode; i.e. + * everything rounds to the nearest value except that '.5' rounds to the + * nearest even value. + */ + fesetround(FE_TONEAREST); + + c[3] = c[2] = c[1] = c[0] = 0; + + while (--argc > 0 && **argv == '-') + { + const char *arg = 1+*argv++; + + if (strcmp(arg, "sRGB") == 0) + to_linear = 0; + + else if (strcmp(arg, "linear") == 0) + to_linear = 1; + + else if (strcmp(arg, "gray") == 0) + to_gray = 1, to_color = 0; + + else if (strcmp(arg, "color") == 0) + to_gray = 0, to_color = 1; + + else + usage(prog); + } + + switch (argc) + { + default: + usage(prog); + break; + + case 4: + c[3] = component(prog, argv[3], to_linear); + ++channels; + case 3: + c[2] = component(prog, argv[2], to_linear); + ++channels; + case 2: + c[1] = component(prog, argv[1], to_linear); + ++channels; + case 1: + c[0] = component(prog, argv[0], to_linear); + ++channels; + break; + } + + if (to_linear) + { + int i; + int components = channels; + + if ((components & 1) == 0) + --components; + + for (i=0; i 0) + for (i=0; i 2) + { + fprintf(stderr, "%s: too many channels (%d) for -color\n", + prog, channels); + usage(prog); + } + + c[3] = c[1]; /* alpha, if present */ + c[2] = c[1] = c[0]; + } + + if (to_linear) + { + int i; + if ((channels & 1) == 0) + { + double alpha = c[channels-1]; + for (i=0; i= 0) + c[i] = sRGB_from_linear(c[i]); + + for (i=0; i