Description: Add a background_color command Move gfxmenu color handling to video, so that gfxterm can use it too; add a background_color command. Author: Colin Watson Origin: upstream, http://bzr.sv.gnu.org/r/grub/branches/parse-color/ Forwarded: http://lists.gnu.org/archive/html/grub-devel/2010-12/msg00045.html Applied-Upstream: http://bazaar.launchpad.net/~vcs-imports/grub/grub2-bzr/revision/3308 Last-Update: 2011-05-19 Index: b/ChangeLog.parse-color =================================================================== --- /dev/null +++ b/ChangeLog.parse-color @@ -0,0 +1,44 @@ +2010-12-23 Colin Watson + + Move gfxmenu color handling to video, so that gfxterm can use it + too. + + * grub-core/gfxmenu/named_colors.c: Move to ... + * grub-core/video/colors.c: ... here. Rename + grub_gui_get_named_color to grub_video_get_named_color. + * grub-core/gfxmenu/gui_string_util.c (my_isxdigit): Move to ... + * grub-core/video/colors.c (my_isxdigit): ... here. + * grub-core/gfxmenu/gui_string_util.c (parse_hex_color_component): + Move to ... + * grub-core/video/colors.c (parse_hex_color_component): ... here. + * grub-core/gfxmenu/gui_string_util.c (grub_gui_parse_color): Move + to ... + * grub-core/video/colors.c (grub_video_parse_color): ... here. + + * include/grub/gui.h (grub_gui_color_t): Move to ... + * include/grub/video.h (grub_video_rgba_color_t): ... here. + * include/grub/gui.h (grub_gui_color_rgb): Move to ... + * include/grub/video.h (grub_video_rgba_color_rgb): ... here. + * include/grub/gui.h (grub_gui_map_color): Move to ... + * include/grub/video.h (grub_video_map_rgba_color): ... here. + * include/grub/gui_string_util.h (grub_gui_get_named_color): Move + to ... + * include/grub/video.h (grub_video_get_named_color): ... here. + * include/grub/gui_string_util.h (grub_gui_parse_color): Move to ... + * include/grub/video.h (grub_video_parse_color): ... here. + + * grub-core/Makefile.core.def (kernel) [videoinkernel]: Add + video/colors.c. + (gfxmenu): Remove gfxmenu/named_colors.c. + (video) [videomodules]: Add video/colors.c. + + Add a background_color command. + + * grub-core/term/gfxterm.c (grub_gfxterm_background_color_cmd): New + function. + (GRUB_MOD_INIT): Register background_color command. + (GRUB_MOD_FINI): Unregister background_color command. + (redraw_screen_rect): Allow blend/replace of text layer to be + controlled independently from whether there is a background bitmap. + (grub_gfxterm_background_image_cmd): Change blend_text_bg when + changing bitmap. Index: b/grub-core/Makefile.core.def =================================================================== --- a/grub-core/Makefile.core.def +++ b/grub-core/Makefile.core.def @@ -178,6 +178,7 @@ videoinkernel = io/bufio.c; videoinkernel = video/bitmap.c; videoinkernel = video/bitmap_scale.c; + videoinkernel = video/colors.c; videoinkernel = video/fb/fbblit.c; videoinkernel = video/fb/fbfill.c; videoinkernel = video/fb/fbutil.c; @@ -1056,7 +1057,6 @@ common = gfxmenu/gui_progress_bar.c; common = gfxmenu/gui_util.c; common = gfxmenu/gui_string_util.c; - common = gfxmenu/named_colors.c; }; module = { @@ -1463,6 +1463,7 @@ module = { name = video; common = video/video.c; + common = video/colors.c; enable = videomodules; }; Index: b/grub-core/gfxmenu/gui_label.c =================================================================== --- a/grub-core/gfxmenu/gui_label.c +++ b/grub-core/gfxmenu/gui_label.c @@ -48,7 +48,7 @@ char *text; char *template; grub_font_t font; - grub_gui_color_t color; + grub_video_rgba_color_t color; int value; enum align_mode align; }; @@ -107,7 +107,7 @@ grub_gui_set_viewport (&self->bounds, &vpsave); grub_font_draw_string (self->text, self->font, - grub_gui_map_color (self->color), + grub_video_map_rgba_color (self->color), left_x, grub_font_get_ascent (self->font)); grub_gui_restore_viewport (&vpsave); @@ -186,7 +186,7 @@ } else if (grub_strcmp (name, "color") == 0) { - grub_gui_parse_color (value, &self->color); + grub_video_parse_color (value, &self->color); } else if (grub_strcmp (name, "align") == 0) { Index: b/grub-core/gfxmenu/gui_list.c =================================================================== --- a/grub-core/gfxmenu/gui_list.c +++ b/grub-core/gfxmenu/gui_list.c @@ -41,9 +41,9 @@ int item_spacing; grub_font_t item_font; grub_font_t selected_item_font; - grub_gui_color_t item_color; + grub_video_rgba_color_t item_color; int selected_item_color_set; - grub_gui_color_t selected_item_color; + grub_video_rgba_color_t selected_item_color; int draw_scrollbar; int need_to_recreate_scrollbar; @@ -269,13 +269,13 @@ (is_selected && self->selected_item_font ? self->selected_item_font : self->item_font); - grub_gui_color_t text_color = + grub_video_rgba_color_t text_color = ((is_selected && self->selected_item_color_set) ? self->selected_item_color : self->item_color); grub_font_draw_string (item_title, font, - grub_gui_map_color (text_color), + grub_video_map_rgba_color (text_color), sel_leftpad + self->icon_width + icon_text_space, (item_top + (item_height - (ascent + descent)) / 2 + ascent)); @@ -431,7 +431,7 @@ } else if (grub_strcmp (name, "item_color") == 0) { - grub_gui_parse_color (value, &self->item_color); + grub_video_parse_color (value, &self->item_color); } else if (grub_strcmp (name, "selected_item_color") == 0) { @@ -441,7 +441,7 @@ } else { - if (grub_gui_parse_color (value, &self->selected_item_color) + if (grub_video_parse_color (value, &self->selected_item_color) == GRUB_ERR_NONE) self->selected_item_color_set = 1; } @@ -564,7 +564,7 @@ { list_impl_t self; grub_font_t default_font; - grub_gui_color_t default_fg_color; + grub_video_rgba_color_t default_fg_color; self = grub_zalloc (sizeof (*self)); if (! self) @@ -576,7 +576,7 @@ self->visible = 1; default_font = grub_font_get ("Unknown Regular 16"); - default_fg_color = grub_gui_color_rgb (0, 0, 0); + default_fg_color = grub_video_rgba_color_rgb (0, 0, 0); self->icon_width = 32; self->icon_height = 32; Index: b/grub-core/gfxmenu/gui_progress_bar.c =================================================================== --- a/grub-core/gfxmenu/gui_progress_bar.c +++ b/grub-core/gfxmenu/gui_progress_bar.c @@ -40,10 +40,10 @@ int show_text; char *template; grub_font_t font; - grub_gui_color_t text_color; - grub_gui_color_t border_color; - grub_gui_color_t bg_color; - grub_gui_color_t fg_color; + grub_video_rgba_color_t text_color; + grub_video_rgba_color_t border_color; + grub_video_rgba_color_t bg_color; + grub_video_rgba_color_t fg_color; char *theme_dir; int need_to_recreate_pixmaps; @@ -109,7 +109,7 @@ f.height = self->bounds.height - 2; /* Border. */ - grub_video_fill_rect (grub_gui_map_color (self->border_color), + grub_video_fill_rect (grub_video_map_rgba_color (self->border_color), f.x - 1, f.y - 1, f.width + 2, f.height + 2); @@ -117,12 +117,12 @@ int barwidth = (f.width * (self->value - self->start) / (self->end - self->start)); - grub_video_fill_rect (grub_gui_map_color (self->bg_color), + grub_video_fill_rect (grub_video_map_rgba_color (self->bg_color), f.x + barwidth, f.y, f.width - barwidth, f.height); /* Bar foreground. */ - grub_video_fill_rect (grub_gui_map_color (self->fg_color), + grub_video_fill_rect (grub_video_map_rgba_color (self->fg_color), f.x, f.y, barwidth, f.height); } @@ -161,7 +161,8 @@ if (self->template) { grub_font_t font = self->font; - grub_video_color_t text_color = grub_gui_map_color (self->text_color); + grub_video_color_t text_color = + grub_video_map_rgba_color (self->text_color); int width = self->bounds.width; int height = self->bounds.height; char *text; @@ -298,19 +299,19 @@ } else if (grub_strcmp (name, "text_color") == 0) { - grub_gui_parse_color (value, &self->text_color); + grub_video_parse_color (value, &self->text_color); } else if (grub_strcmp (name, "border_color") == 0) { - grub_gui_parse_color (value, &self->border_color); + grub_video_parse_color (value, &self->border_color); } else if (grub_strcmp (name, "bg_color") == 0) { - grub_gui_parse_color (value, &self->bg_color); + grub_video_parse_color (value, &self->bg_color); } else if (grub_strcmp (name, "fg_color") == 0) { - grub_gui_parse_color (value, &self->fg_color); + grub_video_parse_color (value, &self->fg_color); } else if (grub_strcmp (name, "bar_style") == 0) { @@ -379,9 +380,9 @@ self->progress.component.ops = &progress_bar_ops; self->visible = 1; self->font = grub_font_get ("Unknown Regular 16"); - grub_gui_color_t black = { .red = 0, .green = 0, .blue = 0, .alpha = 255 }; - grub_gui_color_t gray = { .red = 128, .green = 128, .blue = 128, .alpha = 255 }; - grub_gui_color_t lightgray = { .red = 200, .green = 200, .blue = 200, .alpha = 255 }; + grub_video_rgba_color_t black = { .red = 0, .green = 0, .blue = 0, .alpha = 255 }; + grub_video_rgba_color_t gray = { .red = 128, .green = 128, .blue = 128, .alpha = 255 }; + grub_video_rgba_color_t lightgray = { .red = 200, .green = 200, .blue = 200, .alpha = 255 }; self->text_color = black; self->border_color = black; self->bg_color = gray; Index: b/grub-core/gfxmenu/gui_string_util.c =================================================================== --- a/grub-core/gfxmenu/gui_string_util.c +++ b/grub-core/gfxmenu/gui_string_util.c @@ -204,124 +204,3 @@ return grub_new_substring (file_path, 0, last_slash + 1); } - -static __inline int -my_isxdigit (char c) -{ - return ((c >= '0' && c <= '9') - || (c >= 'a' && c <= 'f') - || (c >= 'A' && c <= 'F')); -} - -static int -parse_hex_color_component (const char *s, unsigned start, unsigned end) -{ - unsigned len; - char buf[3]; - - len = end - start; - /* Check the limits so we don't overrun the buffer. */ - if (len < 1 || len > 2) - return 0; - - if (len == 1) - { - buf[0] = s[start]; /* Get the first and only hex digit. */ - buf[1] = buf[0]; /* Duplicate the hex digit. */ - } - else if (len == 2) - { - buf[0] = s[start]; - buf[1] = s[start + 1]; - } - - buf[2] = '\0'; - - return grub_strtoul (buf, 0, 16); -} - -/* Parse a color string of the form "r, g, b", "#RGB", "#RGBA", - "#RRGGBB", or "#RRGGBBAA". */ -grub_err_t -grub_gui_parse_color (const char *s, grub_gui_color_t *color) -{ - grub_gui_color_t c; - - /* Skip whitespace. */ - while (*s && grub_isspace (*s)) - s++; - - if (*s == '#') - { - /* HTML-style. Number if hex digits: - [6] #RRGGBB [3] #RGB - [8] #RRGGBBAA [4] #RGBA */ - - s++; /* Skip the '#'. */ - /* Count the hexits to determine the format. */ - int hexits = 0; - const char *end = s; - while (my_isxdigit (*end)) - { - end++; - hexits++; - } - - /* Parse the color components based on the format. */ - if (hexits == 3 || hexits == 4) - { - c.red = parse_hex_color_component (s, 0, 1); - c.green = parse_hex_color_component (s, 1, 2); - c.blue = parse_hex_color_component (s, 2, 3); - if (hexits == 4) - c.alpha = parse_hex_color_component (s, 3, 4); - else - c.alpha = 255; - } - else if (hexits == 6 || hexits == 8) - { - c.red = parse_hex_color_component (s, 0, 2); - c.green = parse_hex_color_component (s, 2, 4); - c.blue = parse_hex_color_component (s, 4, 6); - if (hexits == 8) - c.alpha = parse_hex_color_component (s, 6, 8); - else - c.alpha = 255; - } - else - return grub_error (GRUB_ERR_BAD_ARGUMENT, - "invalid HTML-type color string `%s'", s); - } - else if (grub_isdigit (*s)) - { - /* Comma separated decimal values. */ - c.red = grub_strtoul (s, 0, 0); - if ((s = grub_strchr (s, ',')) == 0) - return grub_error (GRUB_ERR_BAD_ARGUMENT, - "missing 1st comma separator in color `%s'", s); - s++; - c.green = grub_strtoul (s, 0, 0); - if ((s = grub_strchr (s, ',')) == 0) - return grub_error (GRUB_ERR_BAD_ARGUMENT, - "missing 2nd comma separator in color `%s'", s); - s++; - c.blue = grub_strtoul (s, 0, 0); - if ((s = grub_strchr (s, ',')) == 0) - c.alpha = 255; - else - { - s++; - c.alpha = grub_strtoul (s, 0, 0); - } - } - else - { - if (! grub_gui_get_named_color (s, &c)) - return grub_error (GRUB_ERR_BAD_ARGUMENT, - "invalid named color `%s'", s); - } - - if (grub_errno == GRUB_ERR_NONE) - *color = c; - return grub_errno; -} Index: b/grub-core/gfxmenu/named_colors.c =================================================================== --- a/grub-core/gfxmenu/named_colors.c +++ /dev/null @@ -1,209 +0,0 @@ -/* named_colors.c - Named color values. */ -/* - * GRUB -- GRand Unified Bootloader - * Copyright (C) 2008 Free Software Foundation, Inc. - * - * GRUB is free software: you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation, either version 3 of the License, or - * (at your option) any later version. - * - * GRUB is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with GRUB. If not, see . - */ - -#include -#include -#include -#include - -struct named_color -{ - const char *name; - grub_gui_color_t color; -}; - -/* - Named color list generated from the list of SVG color keywords from - , - processed through the following Perl command: - perl -ne 'chomp;split;print "{ \"$_[0]\", RGB_COLOR($_[2]) },\n"' - */ - -#define RGB_COLOR(r,g,b) {.red = r, .green = g, .blue = b, .alpha = 255} - -static struct named_color named_colors[] = -{ - { "aliceblue", RGB_COLOR(240,248,255) }, - { "antiquewhite", RGB_COLOR(250,235,215) }, - { "aqua", RGB_COLOR(0,255,255) }, - { "aquamarine", RGB_COLOR(127,255,212) }, - { "azure", RGB_COLOR(240,255,255) }, - { "beige", RGB_COLOR(245,245,220) }, - { "bisque", RGB_COLOR(255,228,196) }, - { "black", RGB_COLOR(0,0,0) }, - { "blanchedalmond", RGB_COLOR(255,235,205) }, - { "blue", RGB_COLOR(0,0,255) }, - { "blueviolet", RGB_COLOR(138,43,226) }, - { "brown", RGB_COLOR(165,42,42) }, - { "burlywood", RGB_COLOR(222,184,135) }, - { "cadetblue", RGB_COLOR(95,158,160) }, - { "chartreuse", RGB_COLOR(127,255,0) }, - { "chocolate", RGB_COLOR(210,105,30) }, - { "coral", RGB_COLOR(255,127,80) }, - { "cornflowerblue", RGB_COLOR(100,149,237) }, - { "cornsilk", RGB_COLOR(255,248,220) }, - { "crimson", RGB_COLOR(220,20,60) }, - { "cyan", RGB_COLOR(0,255,255) }, - { "darkblue", RGB_COLOR(0,0,139) }, - { "darkcyan", RGB_COLOR(0,139,139) }, - { "darkgoldenrod", RGB_COLOR(184,134,11) }, - { "darkgray", RGB_COLOR(169,169,169) }, - { "darkgreen", RGB_COLOR(0,100,0) }, - { "darkgrey", RGB_COLOR(169,169,169) }, - { "darkkhaki", RGB_COLOR(189,183,107) }, - { "darkmagenta", RGB_COLOR(139,0,139) }, - { "darkolivegreen", RGB_COLOR(85,107,47) }, - { "darkorange", RGB_COLOR(255,140,0) }, - { "darkorchid", RGB_COLOR(153,50,204) }, - { "darkred", RGB_COLOR(139,0,0) }, - { "darksalmon", RGB_COLOR(233,150,122) }, - { "darkseagreen", RGB_COLOR(143,188,143) }, - { "darkslateblue", RGB_COLOR(72,61,139) }, - { "darkslategray", RGB_COLOR(47,79,79) }, - { "darkslategrey", RGB_COLOR(47,79,79) }, - { "darkturquoise", RGB_COLOR(0,206,209) }, - { "darkviolet", RGB_COLOR(148,0,211) }, - { "deeppink", RGB_COLOR(255,20,147) }, - { "deepskyblue", RGB_COLOR(0,191,255) }, - { "dimgray", RGB_COLOR(105,105,105) }, - { "dimgrey", RGB_COLOR(105,105,105) }, - { "dodgerblue", RGB_COLOR(30,144,255) }, - { "firebrick", RGB_COLOR(178,34,34) }, - { "floralwhite", RGB_COLOR(255,250,240) }, - { "forestgreen", RGB_COLOR(34,139,34) }, - { "fuchsia", RGB_COLOR(255,0,255) }, - { "gainsboro", RGB_COLOR(220,220,220) }, - { "ghostwhite", RGB_COLOR(248,248,255) }, - { "gold", RGB_COLOR(255,215,0) }, - { "goldenrod", RGB_COLOR(218,165,32) }, - { "gray", RGB_COLOR(128,128,128) }, - { "green", RGB_COLOR(0,128,0) }, - { "greenyellow", RGB_COLOR(173,255,47) }, - { "grey", RGB_COLOR(128,128,128) }, - { "honeydew", RGB_COLOR(240,255,240) }, - { "hotpink", RGB_COLOR(255,105,180) }, - { "indianred", RGB_COLOR(205,92,92) }, - { "indigo", RGB_COLOR(75,0,130) }, - { "ivory", RGB_COLOR(255,255,240) }, - { "khaki", RGB_COLOR(240,230,140) }, - { "lavender", RGB_COLOR(230,230,250) }, - { "lavenderblush", RGB_COLOR(255,240,245) }, - { "lawngreen", RGB_COLOR(124,252,0) }, - { "lemonchiffon", RGB_COLOR(255,250,205) }, - { "lightblue", RGB_COLOR(173,216,230) }, - { "lightcoral", RGB_COLOR(240,128,128) }, - { "lightcyan", RGB_COLOR(224,255,255) }, - { "lightgoldenrodyellow", RGB_COLOR(250,250,210) }, - { "lightgray", RGB_COLOR(211,211,211) }, - { "lightgreen", RGB_COLOR(144,238,144) }, - { "lightgrey", RGB_COLOR(211,211,211) }, - { "lightpink", RGB_COLOR(255,182,193) }, - { "lightsalmon", RGB_COLOR(255,160,122) }, - { "lightseagreen", RGB_COLOR(32,178,170) }, - { "lightskyblue", RGB_COLOR(135,206,250) }, - { "lightslategray", RGB_COLOR(119,136,153) }, - { "lightslategrey", RGB_COLOR(119,136,153) }, - { "lightsteelblue", RGB_COLOR(176,196,222) }, - { "lightyellow", RGB_COLOR(255,255,224) }, - { "lime", RGB_COLOR(0,255,0) }, - { "limegreen", RGB_COLOR(50,205,50) }, - { "linen", RGB_COLOR(250,240,230) }, - { "magenta", RGB_COLOR(255,0,255) }, - { "maroon", RGB_COLOR(128,0,0) }, - { "mediumaquamarine", RGB_COLOR(102,205,170) }, - { "mediumblue", RGB_COLOR(0,0,205) }, - { "mediumorchid", RGB_COLOR(186,85,211) }, - { "mediumpurple", RGB_COLOR(147,112,219) }, - { "mediumseagreen", RGB_COLOR(60,179,113) }, - { "mediumslateblue", RGB_COLOR(123,104,238) }, - { "mediumspringgreen", RGB_COLOR(0,250,154) }, - { "mediumturquoise", RGB_COLOR(72,209,204) }, - { "mediumvioletred", RGB_COLOR(199,21,133) }, - { "midnightblue", RGB_COLOR(25,25,112) }, - { "mintcream", RGB_COLOR(245,255,250) }, - { "mistyrose", RGB_COLOR(255,228,225) }, - { "moccasin", RGB_COLOR(255,228,181) }, - { "navajowhite", RGB_COLOR(255,222,173) }, - { "navy", RGB_COLOR(0,0,128) }, - { "oldlace", RGB_COLOR(253,245,230) }, - { "olive", RGB_COLOR(128,128,0) }, - { "olivedrab", RGB_COLOR(107,142,35) }, - { "orange", RGB_COLOR(255,165,0) }, - { "orangered", RGB_COLOR(255,69,0) }, - { "orchid", RGB_COLOR(218,112,214) }, - { "palegoldenrod", RGB_COLOR(238,232,170) }, - { "palegreen", RGB_COLOR(152,251,152) }, - { "paleturquoise", RGB_COLOR(175,238,238) }, - { "palevioletred", RGB_COLOR(219,112,147) }, - { "papayawhip", RGB_COLOR(255,239,213) }, - { "peachpuff", RGB_COLOR(255,218,185) }, - { "peru", RGB_COLOR(205,133,63) }, - { "pink", RGB_COLOR(255,192,203) }, - { "plum", RGB_COLOR(221,160,221) }, - { "powderblue", RGB_COLOR(176,224,230) }, - { "purple", RGB_COLOR(128,0,128) }, - { "red", RGB_COLOR(255,0,0) }, - { "rosybrown", RGB_COLOR(188,143,143) }, - { "royalblue", RGB_COLOR(65,105,225) }, - { "saddlebrown", RGB_COLOR(139,69,19) }, - { "salmon", RGB_COLOR(250,128,114) }, - { "sandybrown", RGB_COLOR(244,164,96) }, - { "seagreen", RGB_COLOR(46,139,87) }, - { "seashell", RGB_COLOR(255,245,238) }, - { "sienna", RGB_COLOR(160,82,45) }, - { "silver", RGB_COLOR(192,192,192) }, - { "skyblue", RGB_COLOR(135,206,235) }, - { "slateblue", RGB_COLOR(106,90,205) }, - { "slategray", RGB_COLOR(112,128,144) }, - { "slategrey", RGB_COLOR(112,128,144) }, - { "snow", RGB_COLOR(255,250,250) }, - { "springgreen", RGB_COLOR(0,255,127) }, - { "steelblue", RGB_COLOR(70,130,180) }, - { "tan", RGB_COLOR(210,180,140) }, - { "teal", RGB_COLOR(0,128,128) }, - { "thistle", RGB_COLOR(216,191,216) }, - { "tomato", RGB_COLOR(255,99,71) }, - { "turquoise", RGB_COLOR(64,224,208) }, - { "violet", RGB_COLOR(238,130,238) }, - { "wheat", RGB_COLOR(245,222,179) }, - { "white", RGB_COLOR(255,255,255) }, - { "whitesmoke", RGB_COLOR(245,245,245) }, - { "yellow", RGB_COLOR(255,255,0) }, - { "yellowgreen", RGB_COLOR(154,205,50) }, - { 0, { 0, 0, 0, 0 } } /* Terminator. */ -}; - -/* Get the color named NAME. If the color was found, returns 1 and - stores the color into *COLOR. If the color was not found, returns 0 and - does not modify *COLOR. */ -int -grub_gui_get_named_color (const char *name, - grub_gui_color_t *color) -{ - int i; - for (i = 0; named_colors[i].name; i++) - { - if (grub_strcmp (named_colors[i].name, name) == 0) - { - *color = named_colors[i].color; - return 1; - } - } - return 0; -} Index: b/grub-core/gfxmenu/theme_loader.c =================================================================== --- a/grub-core/gfxmenu/theme_loader.c +++ b/grub-core/gfxmenu/theme_loader.c @@ -135,11 +135,11 @@ return grub_errno; } else if (! grub_strcmp ("title-color", name)) - grub_gui_parse_color (value, &view->title_color); + grub_video_parse_color (value, &view->title_color); else if (! grub_strcmp ("message-color", name)) - grub_gui_parse_color (value, &view->message_color); + grub_video_parse_color (value, &view->message_color); else if (! grub_strcmp ("message-bg-color", name)) - grub_gui_parse_color (value, &view->message_bg_color); + grub_video_parse_color (value, &view->message_bg_color); else if (! grub_strcmp ("desktop-image", name)) { struct grub_video_bitmap *raw_bitmap; @@ -170,7 +170,7 @@ view->desktop_image = scaled_bitmap; } else if (! grub_strcmp ("desktop-color", name)) - grub_gui_parse_color (value, &view->desktop_color); + grub_video_parse_color (value, &view->desktop_color); else if (! grub_strcmp ("terminal-box", name)) { grub_err_t err; Index: b/grub-core/gfxmenu/view.c =================================================================== --- a/grub-core/gfxmenu/view.c +++ b/grub-core/gfxmenu/view.c @@ -50,8 +50,8 @@ { grub_gfxmenu_view_t view; grub_font_t default_font; - grub_gui_color_t default_fg_color; - grub_gui_color_t default_bg_color; + grub_video_rgba_color_t default_fg_color; + grub_video_rgba_color_t default_bg_color; view = grub_malloc (sizeof (*view)); if (! view) @@ -63,8 +63,8 @@ view->screen.height = height; default_font = grub_font_get ("Unknown Regular 16"); - default_fg_color = grub_gui_color_rgb (0, 0, 0); - default_bg_color = grub_gui_color_rgb (255, 255, 255); + default_fg_color = grub_video_rgba_color_rgb (0, 0, 0); + default_bg_color = grub_video_rgba_color_rgb (255, 255, 255); view->canvas = 0; @@ -131,7 +131,7 @@ } else { - grub_video_fill_rect (grub_gui_map_color (view->desktop_color), + grub_video_fill_rect (grub_video_map_rgba_color (view->desktop_color), bounds->x, bounds->y, bounds->width, bounds->height); } @@ -150,7 +150,7 @@ int y = 40 + grub_font_get_ascent (view->title_font); grub_font_draw_string (view->title_text, view->title_font, - grub_gui_map_color (view->title_color), + grub_video_map_rgba_color (view->title_color), x, y); } @@ -244,13 +244,13 @@ return; grub_font_t font = view->message_font; - grub_video_color_t color = grub_gui_map_color (view->message_color); + grub_video_color_t color = grub_video_map_rgba_color (view->message_color); /* Border. */ grub_video_fill_rect (color, f.x-1, f.y-1, f.width+2, f.height+2); /* Fill. */ - grub_video_fill_rect (grub_gui_map_color (view->message_bg_color), + grub_video_fill_rect (grub_video_map_rgba_color (view->message_bg_color), f.x, f.y, f.width, f.height); /* Center the text. */ Index: b/grub-core/term/gfxterm.c =================================================================== --- a/grub-core/term/gfxterm.c +++ b/grub-core/term/gfxterm.c @@ -130,6 +130,7 @@ static unsigned int bitmap_width; static unsigned int bitmap_height; static struct grub_video_bitmap *bitmap; +static int blend_text_bg; static struct grub_dirty_region dirty_region; @@ -476,26 +477,27 @@ /* Render background layer. */ grub_video_fill_rect (color, x, ty, width, h); } - - /* Render text layer as blended. */ - grub_video_blit_render_target (text_layer, GRUB_VIDEO_BLIT_BLEND, x, y, - x - virtual_screen.offset_x, - y - virtual_screen.offset_y, - width, height); } else { /* Render background layer. */ color = virtual_screen.bg_color_display; grub_video_fill_rect (color, x, y, width, height); - - /* Render text layer as replaced (to get texts background color). */ - grub_video_blit_render_target (text_layer, GRUB_VIDEO_BLIT_REPLACE, x, y, - x - virtual_screen.offset_x, - y - virtual_screen.offset_y, - width, height); } + if (blend_text_bg) + /* Render text layer as blended. */ + grub_video_blit_render_target (text_layer, GRUB_VIDEO_BLIT_BLEND, x, y, + x - virtual_screen.offset_x, + y - virtual_screen.offset_y, + width, height); + else + /* Render text layer as replaced (to get texts background color). */ + grub_video_blit_render_target (text_layer, GRUB_VIDEO_BLIT_REPLACE, x, y, + x - virtual_screen.offset_x, + y - virtual_screen.offset_y, + width, height); + /* Restore saved viewport. */ grub_video_set_viewport (saved_view.x, saved_view.y, saved_view.width, saved_view.height); @@ -1127,6 +1129,7 @@ { grub_video_bitmap_destroy (bitmap); bitmap = 0; + blend_text_bg = 0; /* Mark whole screen as dirty. */ dirty_region_add (0, 0, window.width, window.height); @@ -1166,6 +1169,8 @@ /* If bitmap was loaded correctly, display it. */ if (bitmap) { + blend_text_bg = 1; + /* Determine bitmap dimensions. */ bitmap_width = grub_video_bitmap_get_width (bitmap); bitmap_height = grub_video_bitmap_get_height (bitmap); @@ -1180,6 +1185,48 @@ return grub_errno; } +static grub_err_t +grub_gfxterm_background_color_cmd (grub_command_t cmd __attribute__ ((unused)), + int argc, char **args) +{ + grub_video_rgba_color_t color; + struct grub_video_render_target *old_target; + + if (argc != 1) + return grub_error (GRUB_ERR_BAD_ARGUMENT, "missing operand"); + + /* Check that we have video adapter active. */ + if (grub_video_get_info (NULL) != GRUB_ERR_NONE) + return grub_errno; + + if (grub_video_parse_color (args[0], &color) != GRUB_ERR_NONE) + return grub_errno; + + /* Destroy existing background bitmap if loaded. */ + if (bitmap) + { + grub_video_bitmap_destroy (bitmap); + bitmap = 0; + + /* Mark whole screen as dirty. */ + dirty_region_add (0, 0, window.width, window.height); + } + + /* Set the background and border colors. The background color needs to be + compatible with the text layer. */ + grub_video_get_active_render_target (&old_target); + grub_video_set_active_render_target (text_layer); + virtual_screen.bg_color = grub_video_map_rgba_color (color); + grub_video_set_active_render_target (old_target); + virtual_screen.bg_color_display = grub_video_map_rgba_color (color); + blend_text_bg = 1; + + /* Mark whole screen as dirty. */ + dirty_region_add (0, 0, window.width, window.height); + + return GRUB_ERR_NONE; +} + static struct grub_term_output grub_video_term = { .name = "gfxterm", @@ -1201,6 +1248,7 @@ }; static grub_extcmd_t background_image_cmd_handle; +static grub_command_t background_color_cmd_handle; GRUB_MOD_INIT(gfxterm) { @@ -1211,10 +1259,16 @@ N_("[-m (stretch|normal)] FILE"), N_("Load background image for active terminal."), background_image_cmd_options); + background_color_cmd_handle = + grub_register_command ("background_color", + grub_gfxterm_background_color_cmd, + N_("COLOR"), + N_("Set background color for active terminal.")); } GRUB_MOD_FINI(gfxterm) { + grub_unregister_command (background_color_cmd_handle); grub_unregister_extcmd (background_image_cmd_handle); grub_term_unregister_output (&grub_video_term); } Index: b/include/grub/gfxmenu_view.h =================================================================== --- a/include/grub/gfxmenu_view.h +++ b/include/grub/gfxmenu_view.h @@ -87,11 +87,11 @@ grub_font_t title_font; grub_font_t message_font; char *terminal_font_name; - grub_gui_color_t title_color; - grub_gui_color_t message_color; - grub_gui_color_t message_bg_color; + grub_video_rgba_color_t title_color; + grub_video_rgba_color_t message_color; + grub_video_rgba_color_t message_bg_color; struct grub_video_bitmap *desktop_image; - grub_gui_color_t desktop_color; + grub_video_rgba_color_t desktop_color; grub_gfxmenu_box_t terminal_box; char *title_text; char *progress_message_text; Index: b/include/grub/gui.h =================================================================== --- a/include/grub/gui.h +++ b/include/grub/gui.h @@ -31,16 +31,6 @@ status changes. */ #define GRUB_GFXMENU_TIMEOUT_COMPONENT_ID "__timeout__" -/* A representation of a color. Unlike grub_video_color_t, this - representation is independent of any video mode specifics. */ -typedef struct grub_gui_color -{ - grub_uint8_t red; - grub_uint8_t green; - grub_uint8_t blue; - grub_uint8_t alpha; -} grub_gui_color_t; - typedef struct grub_gui_component *grub_gui_component_t; typedef struct grub_gui_container *grub_gui_container_t; typedef struct grub_gui_list *grub_gui_list_t; @@ -242,23 +232,6 @@ r->height); } -static __inline grub_gui_color_t -grub_gui_color_rgb (int r, int g, int b) -{ - grub_gui_color_t c; - c.red = r; - c.green = g; - c.blue = b; - c.alpha = 255; - return c; -} - -static __inline grub_video_color_t -grub_gui_map_color (grub_gui_color_t c) -{ - return grub_video_map_rgba (c.red, c.green, c.blue, c.alpha); -} - static inline int grub_video_have_common_points (const grub_video_rect_t *a, const grub_video_rect_t *b) Index: b/include/grub/gui_string_util.h =================================================================== --- a/include/grub/gui_string_util.h +++ b/include/grub/gui_string_util.h @@ -30,8 +30,4 @@ char *grub_get_dirname (const char *file_path); -int grub_gui_get_named_color (const char *name, grub_gui_color_t *color); - -grub_err_t grub_gui_parse_color (const char *s, grub_gui_color_t *color); - #endif /* GRUB_GUI_STRING_UTIL_HEADER */ Index: b/include/grub/video.h =================================================================== --- a/include/grub/video.h +++ b/include/grub/video.h @@ -27,6 +27,15 @@ specific coding format. */ typedef grub_uint32_t grub_video_color_t; +/* Video color in hardware independent format. */ +typedef struct grub_video_rgba_color +{ + grub_uint8_t red; + grub_uint8_t green; + grub_uint8_t blue; + grub_uint8_t alpha; +} grub_video_rgba_color_t; + /* This structure is driver specific and should not be accessed directly by outside code. */ struct grub_video_render_target; @@ -428,4 +437,27 @@ grub_video_driver_id_t EXPORT_FUNC (grub_video_get_driver_id) (void); +static __inline grub_video_rgba_color_t +grub_video_rgba_color_rgb (int r, int g, int b) +{ + grub_video_rgba_color_t c; + c.red = r; + c.green = g; + c.blue = b; + c.alpha = 255; + return c; +} + +static __inline grub_video_color_t +grub_video_map_rgba_color (grub_video_rgba_color_t c) +{ + return grub_video_map_rgba (c.red, c.green, c.blue, c.alpha); +} + +int EXPORT_FUNC (grub_video_get_named_color) (const char *name, + grub_video_rgba_color_t *color); + +grub_err_t EXPORT_FUNC (grub_video_parse_color) (const char *s, + grub_video_rgba_color_t *color); + #endif /* ! GRUB_VIDEO_HEADER */ Index: b/grub-core/video/colors.c =================================================================== --- /dev/null +++ b/grub-core/video/colors.c @@ -0,0 +1,330 @@ +/* named_colors.c - Named color values. */ +/* + * GRUB -- GRand Unified Bootloader + * Copyright (C) 2008 Free Software Foundation, Inc. + * + * GRUB is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * GRUB is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with GRUB. If not, see . + */ + +#include +#include +#include +#include + +struct named_color +{ + const char *name; + grub_video_rgba_color_t color; +}; + +/* + Named color list generated from the list of SVG color keywords from + , + processed through the following Perl command: + perl -ne 'chomp;split;print "{ \"$_[0]\", RGB_COLOR($_[2]) },\n"' + */ + +#define RGB_COLOR(r,g,b) {.red = r, .green = g, .blue = b, .alpha = 255} + +static struct named_color named_colors[] = +{ + { "aliceblue", RGB_COLOR(240,248,255) }, + { "antiquewhite", RGB_COLOR(250,235,215) }, + { "aqua", RGB_COLOR(0,255,255) }, + { "aquamarine", RGB_COLOR(127,255,212) }, + { "azure", RGB_COLOR(240,255,255) }, + { "beige", RGB_COLOR(245,245,220) }, + { "bisque", RGB_COLOR(255,228,196) }, + { "black", RGB_COLOR(0,0,0) }, + { "blanchedalmond", RGB_COLOR(255,235,205) }, + { "blue", RGB_COLOR(0,0,255) }, + { "blueviolet", RGB_COLOR(138,43,226) }, + { "brown", RGB_COLOR(165,42,42) }, + { "burlywood", RGB_COLOR(222,184,135) }, + { "cadetblue", RGB_COLOR(95,158,160) }, + { "chartreuse", RGB_COLOR(127,255,0) }, + { "chocolate", RGB_COLOR(210,105,30) }, + { "coral", RGB_COLOR(255,127,80) }, + { "cornflowerblue", RGB_COLOR(100,149,237) }, + { "cornsilk", RGB_COLOR(255,248,220) }, + { "crimson", RGB_COLOR(220,20,60) }, + { "cyan", RGB_COLOR(0,255,255) }, + { "darkblue", RGB_COLOR(0,0,139) }, + { "darkcyan", RGB_COLOR(0,139,139) }, + { "darkgoldenrod", RGB_COLOR(184,134,11) }, + { "darkgray", RGB_COLOR(169,169,169) }, + { "darkgreen", RGB_COLOR(0,100,0) }, + { "darkgrey", RGB_COLOR(169,169,169) }, + { "darkkhaki", RGB_COLOR(189,183,107) }, + { "darkmagenta", RGB_COLOR(139,0,139) }, + { "darkolivegreen", RGB_COLOR(85,107,47) }, + { "darkorange", RGB_COLOR(255,140,0) }, + { "darkorchid", RGB_COLOR(153,50,204) }, + { "darkred", RGB_COLOR(139,0,0) }, + { "darksalmon", RGB_COLOR(233,150,122) }, + { "darkseagreen", RGB_COLOR(143,188,143) }, + { "darkslateblue", RGB_COLOR(72,61,139) }, + { "darkslategray", RGB_COLOR(47,79,79) }, + { "darkslategrey", RGB_COLOR(47,79,79) }, + { "darkturquoise", RGB_COLOR(0,206,209) }, + { "darkviolet", RGB_COLOR(148,0,211) }, + { "deeppink", RGB_COLOR(255,20,147) }, + { "deepskyblue", RGB_COLOR(0,191,255) }, + { "dimgray", RGB_COLOR(105,105,105) }, + { "dimgrey", RGB_COLOR(105,105,105) }, + { "dodgerblue", RGB_COLOR(30,144,255) }, + { "firebrick", RGB_COLOR(178,34,34) }, + { "floralwhite", RGB_COLOR(255,250,240) }, + { "forestgreen", RGB_COLOR(34,139,34) }, + { "fuchsia", RGB_COLOR(255,0,255) }, + { "gainsboro", RGB_COLOR(220,220,220) }, + { "ghostwhite", RGB_COLOR(248,248,255) }, + { "gold", RGB_COLOR(255,215,0) }, + { "goldenrod", RGB_COLOR(218,165,32) }, + { "gray", RGB_COLOR(128,128,128) }, + { "green", RGB_COLOR(0,128,0) }, + { "greenyellow", RGB_COLOR(173,255,47) }, + { "grey", RGB_COLOR(128,128,128) }, + { "honeydew", RGB_COLOR(240,255,240) }, + { "hotpink", RGB_COLOR(255,105,180) }, + { "indianred", RGB_COLOR(205,92,92) }, + { "indigo", RGB_COLOR(75,0,130) }, + { "ivory", RGB_COLOR(255,255,240) }, + { "khaki", RGB_COLOR(240,230,140) }, + { "lavender", RGB_COLOR(230,230,250) }, + { "lavenderblush", RGB_COLOR(255,240,245) }, + { "lawngreen", RGB_COLOR(124,252,0) }, + { "lemonchiffon", RGB_COLOR(255,250,205) }, + { "lightblue", RGB_COLOR(173,216,230) }, + { "lightcoral", RGB_COLOR(240,128,128) }, + { "lightcyan", RGB_COLOR(224,255,255) }, + { "lightgoldenrodyellow", RGB_COLOR(250,250,210) }, + { "lightgray", RGB_COLOR(211,211,211) }, + { "lightgreen", RGB_COLOR(144,238,144) }, + { "lightgrey", RGB_COLOR(211,211,211) }, + { "lightpink", RGB_COLOR(255,182,193) }, + { "lightsalmon", RGB_COLOR(255,160,122) }, + { "lightseagreen", RGB_COLOR(32,178,170) }, + { "lightskyblue", RGB_COLOR(135,206,250) }, + { "lightslategray", RGB_COLOR(119,136,153) }, + { "lightslategrey", RGB_COLOR(119,136,153) }, + { "lightsteelblue", RGB_COLOR(176,196,222) }, + { "lightyellow", RGB_COLOR(255,255,224) }, + { "lime", RGB_COLOR(0,255,0) }, + { "limegreen", RGB_COLOR(50,205,50) }, + { "linen", RGB_COLOR(250,240,230) }, + { "magenta", RGB_COLOR(255,0,255) }, + { "maroon", RGB_COLOR(128,0,0) }, + { "mediumaquamarine", RGB_COLOR(102,205,170) }, + { "mediumblue", RGB_COLOR(0,0,205) }, + { "mediumorchid", RGB_COLOR(186,85,211) }, + { "mediumpurple", RGB_COLOR(147,112,219) }, + { "mediumseagreen", RGB_COLOR(60,179,113) }, + { "mediumslateblue", RGB_COLOR(123,104,238) }, + { "mediumspringgreen", RGB_COLOR(0,250,154) }, + { "mediumturquoise", RGB_COLOR(72,209,204) }, + { "mediumvioletred", RGB_COLOR(199,21,133) }, + { "midnightblue", RGB_COLOR(25,25,112) }, + { "mintcream", RGB_COLOR(245,255,250) }, + { "mistyrose", RGB_COLOR(255,228,225) }, + { "moccasin", RGB_COLOR(255,228,181) }, + { "navajowhite", RGB_COLOR(255,222,173) }, + { "navy", RGB_COLOR(0,0,128) }, + { "oldlace", RGB_COLOR(253,245,230) }, + { "olive", RGB_COLOR(128,128,0) }, + { "olivedrab", RGB_COLOR(107,142,35) }, + { "orange", RGB_COLOR(255,165,0) }, + { "orangered", RGB_COLOR(255,69,0) }, + { "orchid", RGB_COLOR(218,112,214) }, + { "palegoldenrod", RGB_COLOR(238,232,170) }, + { "palegreen", RGB_COLOR(152,251,152) }, + { "paleturquoise", RGB_COLOR(175,238,238) }, + { "palevioletred", RGB_COLOR(219,112,147) }, + { "papayawhip", RGB_COLOR(255,239,213) }, + { "peachpuff", RGB_COLOR(255,218,185) }, + { "peru", RGB_COLOR(205,133,63) }, + { "pink", RGB_COLOR(255,192,203) }, + { "plum", RGB_COLOR(221,160,221) }, + { "powderblue", RGB_COLOR(176,224,230) }, + { "purple", RGB_COLOR(128,0,128) }, + { "red", RGB_COLOR(255,0,0) }, + { "rosybrown", RGB_COLOR(188,143,143) }, + { "royalblue", RGB_COLOR(65,105,225) }, + { "saddlebrown", RGB_COLOR(139,69,19) }, + { "salmon", RGB_COLOR(250,128,114) }, + { "sandybrown", RGB_COLOR(244,164,96) }, + { "seagreen", RGB_COLOR(46,139,87) }, + { "seashell", RGB_COLOR(255,245,238) }, + { "sienna", RGB_COLOR(160,82,45) }, + { "silver", RGB_COLOR(192,192,192) }, + { "skyblue", RGB_COLOR(135,206,235) }, + { "slateblue", RGB_COLOR(106,90,205) }, + { "slategray", RGB_COLOR(112,128,144) }, + { "slategrey", RGB_COLOR(112,128,144) }, + { "snow", RGB_COLOR(255,250,250) }, + { "springgreen", RGB_COLOR(0,255,127) }, + { "steelblue", RGB_COLOR(70,130,180) }, + { "tan", RGB_COLOR(210,180,140) }, + { "teal", RGB_COLOR(0,128,128) }, + { "thistle", RGB_COLOR(216,191,216) }, + { "tomato", RGB_COLOR(255,99,71) }, + { "turquoise", RGB_COLOR(64,224,208) }, + { "violet", RGB_COLOR(238,130,238) }, + { "wheat", RGB_COLOR(245,222,179) }, + { "white", RGB_COLOR(255,255,255) }, + { "whitesmoke", RGB_COLOR(245,245,245) }, + { "yellow", RGB_COLOR(255,255,0) }, + { "yellowgreen", RGB_COLOR(154,205,50) }, + { 0, { 0, 0, 0, 0 } } /* Terminator. */ +}; + +/* Get the color named NAME. If the color was found, returns 1 and + stores the color into *COLOR. If the color was not found, returns 0 and + does not modify *COLOR. */ +int +grub_video_get_named_color (const char *name, + grub_video_rgba_color_t *color) +{ + int i; + for (i = 0; named_colors[i].name; i++) + { + if (grub_strcmp (named_colors[i].name, name) == 0) + { + *color = named_colors[i].color; + return 1; + } + } + return 0; +} + +static __inline int +my_isxdigit (char c) +{ + return ((c >= '0' && c <= '9') + || (c >= 'a' && c <= 'f') + || (c >= 'A' && c <= 'F')); +} + +static int +parse_hex_color_component (const char *s, unsigned start, unsigned end) +{ + unsigned len; + char buf[3]; + + len = end - start; + /* Check the limits so we don't overrun the buffer. */ + if (len < 1 || len > 2) + return 0; + + if (len == 1) + { + buf[0] = s[start]; /* Get the first and only hex digit. */ + buf[1] = buf[0]; /* Duplicate the hex digit. */ + } + else if (len == 2) + { + buf[0] = s[start]; + buf[1] = s[start + 1]; + } + + buf[2] = '\0'; + + return grub_strtoul (buf, 0, 16); +} + +/* Parse a color string of the form "r, g, b", "#RGB", "#RGBA", + "#RRGGBB", or "#RRGGBBAA". */ +grub_err_t +grub_video_parse_color (const char *s, grub_video_rgba_color_t *color) +{ + grub_video_rgba_color_t c; + + /* Skip whitespace. */ + while (*s && grub_isspace (*s)) + s++; + + if (*s == '#') + { + /* HTML-style. Number if hex digits: + [6] #RRGGBB [3] #RGB + [8] #RRGGBBAA [4] #RGBA */ + + s++; /* Skip the '#'. */ + /* Count the hexits to determine the format. */ + int hexits = 0; + const char *end = s; + while (my_isxdigit (*end)) + { + end++; + hexits++; + } + + /* Parse the color components based on the format. */ + if (hexits == 3 || hexits == 4) + { + c.red = parse_hex_color_component (s, 0, 1); + c.green = parse_hex_color_component (s, 1, 2); + c.blue = parse_hex_color_component (s, 2, 3); + if (hexits == 4) + c.alpha = parse_hex_color_component (s, 3, 4); + else + c.alpha = 255; + } + else if (hexits == 6 || hexits == 8) + { + c.red = parse_hex_color_component (s, 0, 2); + c.green = parse_hex_color_component (s, 2, 4); + c.blue = parse_hex_color_component (s, 4, 6); + if (hexits == 8) + c.alpha = parse_hex_color_component (s, 6, 8); + else + c.alpha = 255; + } + else + return grub_error (GRUB_ERR_BAD_ARGUMENT, + "invalid HTML-type color string `%s'", s); + } + else if (grub_isdigit (*s)) + { + /* Comma separated decimal values. */ + c.red = grub_strtoul (s, 0, 0); + if ((s = grub_strchr (s, ',')) == 0) + return grub_error (GRUB_ERR_BAD_ARGUMENT, + "missing 1st comma separator in color `%s'", s); + s++; + c.green = grub_strtoul (s, 0, 0); + if ((s = grub_strchr (s, ',')) == 0) + return grub_error (GRUB_ERR_BAD_ARGUMENT, + "missing 2nd comma separator in color `%s'", s); + s++; + c.blue = grub_strtoul (s, 0, 0); + if ((s = grub_strchr (s, ',')) == 0) + c.alpha = 255; + else + { + s++; + c.alpha = grub_strtoul (s, 0, 0); + } + } + else + { + if (! grub_video_get_named_color (s, &c)) + return grub_error (GRUB_ERR_BAD_ARGUMENT, + "invalid named color `%s'", s); + } + + if (grub_errno == GRUB_ERR_NONE) + *color = c; + return grub_errno; +}