COLOR_UNSPECIFIED = 0,
COLOR_NORMAL,
COLOR_ANSI, /* basic 0-7 ANSI colors */
- COLOR_256
+ COLOR_256,
+ COLOR_RGB
} type;
/* The numeric value for ANSI and 256-color modes */
unsigned char value;
+ /* 24-bit RGB color values */
+ unsigned char red, green, blue;
};
/*
return !strncasecmp(word, match, len) && !match[len];
}
+static int get_hex_color(const char *in, unsigned char *out)
+{
+ unsigned int val;
+ val = (hexval(in[0]) << 4) | hexval(in[1]);
+ if (val & ~0xff)
+ return -1;
+ *out = val;
+ return 0;
+}
+
static int parse_color(struct color *out, const char *name, int len)
{
/* Positions in array must match ANSI color codes */
return 0;
}
+ /* Try a 24-bit RGB value */
+ if (len == 7 && name[0] == '#') {
+ if (!get_hex_color(name + 1, &out->red) &&
+ !get_hex_color(name + 3, &out->green) &&
+ !get_hex_color(name + 5, &out->blue)) {
+ out->type = COLOR_RGB;
+ return 0;
+ }
+ }
+
/* Then pick from our human-readable color names... */
for (i = 0; i < ARRAY_SIZE(color_names); i++) {
if (match_word(name, len, color_names[i])) {
} else if (val < 8) {
out->type = COLOR_ANSI;
out->value = val;
+ return 0;
} else if (val < 256) {
out->type = COLOR_256;
out->value = val;
static int parse_attr(const char *name, int len)
{
- static const int attr_values[] = { 1, 2, 4, 5, 7 };
+ static const int attr_values[] = { 1, 2, 4, 5, 7,
+ 22, 22, 24, 25, 27 };
static const char * const attr_names[] = {
- "bold", "dim", "ul", "blink", "reverse"
+ "bold", "dim", "ul", "blink", "reverse",
+ "nobold", "nodim", "noul", "noblink", "noreverse"
};
int i;
for (i = 0; i < ARRAY_SIZE(attr_names); i++) {
return color_parse_mem(value, strlen(value), dst);
}
-#define COLOR_FOREGROUND '3'
-#define COLOR_BACKGROUND '4'
-
/*
* Write the ANSI color codes for "c" to "out"; the string should
* already have the ANSI escape code in it. "out" should have enough
case COLOR_256:
out += sprintf(out, "%c8;5;%d", type, c->value);
break;
+ case COLOR_RGB:
+ out += sprintf(out, "%c8;2;%d;%d;%d", type,
+ c->red, c->green, c->blue);
+ break;
}
return out;
}
attr &= ~bit;
if (sep++)
*dst++ = ';';
- *dst++ = '0' + i;
+ dst += sprintf(dst, "%d", i);
}
if (!color_empty(&fg)) {
if (sep++)
*dst++ = ';';
- dst = color_output(dst, &fg, COLOR_FOREGROUND);
+ /* foreground colors are all in the 3x range */
+ dst = color_output(dst, &fg, '3');
}
if (!color_empty(&bg)) {
if (sep++)
*dst++ = ';';
- dst = color_output(dst, &bg, COLOR_BACKGROUND);
+ /* background colors are all in the 4x range */
+ dst = color_output(dst, &bg, '4');
}
*dst++ = 'm';
}