Hi!
After a while, I remembered, that usual pure pc console can handle only
64 color combinations, but curses also reserves colorpair 0 so,
programmer have only 63 color pairs and operates 'default' colors. Thus,
I decided to switch to on-demand colorpair allocation. Attached patch
does this. It also takes into account COLOR_PAIRS, thus, if terminal
have more than 64 color pairs, they will be used (though, you should
have really rainbow color scheme to achieve this :). Also those two new
colors now are named 'gray' (bright black) and 'darkwhite' (not bright
white).
Looks like it is working.
--
Михайло Даниленко
-------------------------------
jabber: <[email protected]>
icq: 200352743
--- a/src/gui/curses/gui-curses-chat.c 2009-03-14 23:42:49.000000000 +0200
+++ b/src/gui/curses/gui-curses-chat.c 2009-05-22 20:45:28.000000000 +0300
@@ -131,17 +131,7 @@
void
gui_chat_set_color (t_gui_window *window, int fg, int bg)
{
- if (((fg == -1) || (fg == 99))
- && ((bg == -1) || (bg == 99)))
- wattron (GUI_CURSES(window)->win_chat, COLOR_PAIR(63));
- else
- {
- if ((fg == -1) || (fg == 99))
- fg = WEECHAT_COLOR_WHITE;
- if ((bg == -1) || (bg == 99))
- bg = 0;
- wattron (GUI_CURSES(window)->win_chat, COLOR_PAIR((bg * 8) + fg));
- }
+ wattron (GUI_CURSES(window)->win_chat, COLOR_PAIR(gui_color_get_pair_fgbg (fg, bg)));
}
/*
--- a/src/gui/curses/gui-curses-color.c 2009-03-14 23:42:49.000000000 +0200
+++ b/src/gui/curses/gui-curses-color.c 2009-05-22 21:53:52.000000000 +0300
@@ -38,6 +38,7 @@
t_gui_color gui_weechat_colors[] =
{ { -1, 0, 0, "default" },
{ WEECHAT_COLOR_BLACK, 0, 0, "black" },
+ { WEECHAT_COLOR_BLACK, 0, A_BOLD, "gray" },
{ WEECHAT_COLOR_RED, 0, 0, "red" },
{ WEECHAT_COLOR_RED, 0, A_BOLD, "lightred" },
{ WEECHAT_COLOR_GREEN, 0, 0, "green" },
@@ -50,6 +51,7 @@
{ WEECHAT_COLOR_MAGENTA, 0, A_BOLD, "lightmagenta" },
{ WEECHAT_COLOR_CYAN, 0, 0, "cyan" },
{ WEECHAT_COLOR_CYAN, 0, A_BOLD, "lightcyan" },
+ { WEECHAT_COLOR_WHITE, 0, 0, "darkwhite" },
{ WEECHAT_COLOR_WHITE, 0, A_BOLD, "white" },
{ 0, 0, 0, NULL }
};
@@ -75,6 +77,19 @@
t_gui_color *gui_color[GUI_NUM_COLORS];
+static int gui_color_pairs_allocated = 0;
+/* black ... white, default */
+static int gui_color_pairs[9][9] = {
+ { 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+ { 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+ { 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+ { 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+ { 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+ { 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+ { 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+ { 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+ { 0, 0, 0, 0, 0, 0, 0, 0, 0 }
+};
/*
* gui_color_assign: assign a WeeChat color (read from config)
@@ -450,6 +465,51 @@
}
/*
+ * gui_color_get_pair_fgbg: get color pair with foreground and background ncurses color values
+ */
+
+static const char gui_curses_color_mapping[8] = { 0, 4, 2, 6, 1, 5, 3, 7 };
+
+int
+gui_color_get_pair_fgbg (int fg, int bg)
+{
+ if (!has_colors ())
+ /* XXX: no idea, what to return here, this is not initialized either */
+ return gui_color_pairs[8][8];
+
+ if (fg == 99)
+ fg = -1;
+ if (bg == 99)
+ bg = -1;
+
+ if (gui_color_pairs[bg == -1 ? 8 : bg][fg == -1 ? 8 : fg])
+ return gui_color_pairs[bg == -1 ? 8 : bg][fg == -1 ? 8 : fg];
+
+ if (gui_color_pairs_allocated+1 >= COLOR_PAIRS)
+ /*
+ * FIXME: on first encounter, issue an error message like:
+ * ERROR: Color pairs resource exausted.
+ * This means, that we can no more allocate new background-foreground color pairs.
+ * Thus, any elements, colored with new color pair will be shown in default colors.
+ * If you have modified color settings, you can try to restart program to
+ * get rid of no more used color pairs. Or, either you have too much rainbow-like
+ * scheme, or your terminal have much less than 64 color pairs.
+ */
+ return gui_color_pairs[8][8];
+
+ if (init_pair (++gui_color_pairs_allocated, (fg != -1) ? gui_curses_color_mapping[fg%8] : fg,
+ (bg != -1) ? gui_curses_color_mapping[bg%8] : bg) == ERR) {
+ /* XXX: error message? */
+ gui_color_pairs_allocated--;
+ return gui_color_pairs[8][8];
+ }
+
+ gui_color_pairs[bg == -1 ? 8 : bg][fg == -1 ? 8 : fg] = gui_color_pairs_allocated;
+
+ return gui_color_pairs_allocated;
+}
+
+/*
* gui_color_get_pair: get color pair with a WeeChat color number
*/
@@ -459,20 +519,13 @@
int fg, bg;
if ((num_color < 0) || (num_color > GUI_NUM_COLORS - 1))
- return WEECHAT_COLOR_WHITE;
-
- fg = gui_color[num_color]->foreground;
- bg = gui_color[num_color]->background;
-
- if (((fg == -1) || (fg == 99))
- && ((bg == -1) || (bg == 99)))
- return 63;
- if ((fg == -1) || (fg == 99))
- fg = WEECHAT_COLOR_WHITE;
- if ((bg == -1) || (bg == 99))
- bg = 0;
-
- return (bg * 8) + fg;
+ fg = bg = -1;
+ else {
+ fg = gui_color[num_color]->foreground;
+ bg = gui_color[num_color]->background;
+ }
+
+ return gui_color_get_pair_fgbg (fg, bg);
}
/*
@@ -482,21 +535,7 @@
void
gui_color_init_pairs ()
{
- int i;
- char shift_colors[8] = { 0, 4, 2, 6, 1, 5, 3, 7 };
-
- if (has_colors ())
- {
- for (i = 1; i < 64; i++)
- init_pair (i, shift_colors[i % 8], (i < 8) ? -1 : shift_colors[i / 8]);
-
- /* disable white on white, replaced by black on white */
- init_pair (63, -1, -1);
-
- /* white on default bg is default (-1) */
- if (!cfg_col_real_white)
- init_pair (WEECHAT_COLOR_WHITE, -1, -1);
- }
+ /* In curses this function now also does nothing, just as in gtk+ :) */
}
/*
--- a/src/gui/curses/gui-curses.h 2009-03-14 23:42:49.000000000 +0200
+++ b/src/gui/curses/gui-curses.h 2009-05-22 20:39:11.000000000 +0300
@@ -78,6 +78,7 @@
extern int gui_refresh_screen_needed;
/* color functions */
+extern int gui_color_get_pair_fgbg (int, int);
extern int gui_color_get_pair (int);
extern void gui_color_init ();
--- a/src/gui/curses/gui-curses-input.c 2009-03-14 23:42:49.000000000 +0200
+++ b/src/gui/curses/gui-curses-input.c 2009-05-22 20:45:11.000000000 +0300
@@ -53,18 +53,8 @@
irc_color %= GUI_NUM_IRC_COLORS;
if (gui_irc_colors[irc_color][1] & A_BOLD)
wattron (GUI_CURSES(window)->win_input, A_BOLD);
-
- if (((fg == -1) || (fg == 99))
- && ((bg == -1) || (bg == 99)))
- wattron (GUI_CURSES(window)->win_input, COLOR_PAIR(63));
- else
- {
- if ((fg == -1) || (fg == 99))
- fg = WEECHAT_COLOR_WHITE;
- if ((bg == -1) || (bg == 99))
- bg = 0;
- wattron (GUI_CURSES(window)->win_input, COLOR_PAIR((bg * 8) + fg));
- }
+
+ wattron (GUI_CURSES(window)->win_input, COLOR_PAIR(gui_color_get_pair_fgbg (fg, bg)));
}
/*