summaryrefslogtreecommitdiff
path: root/src/fe-text/textbuffer-view.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/fe-text/textbuffer-view.c')
-rw-r--r--src/fe-text/textbuffer-view.c147
1 files changed, 89 insertions, 58 deletions
diff --git a/src/fe-text/textbuffer-view.c b/src/fe-text/textbuffer-view.c
index 78509151..81deaf54 100644
--- a/src/fe-text/textbuffer-view.c
+++ b/src/fe-text/textbuffer-view.c
@@ -104,65 +104,78 @@ static void textbuffer_cache_unref(TEXT_BUFFER_CACHE_REC *cache)
textbuffer_cache_destroy(cache);
}
-#define FGATTR (ATTR_NOCOLORS | ATTR_RESETFG | 0xff)
-#define BGATTR (ATTR_NOCOLORS | ATTR_RESETBG | 0xff00)
+#define FGATTR (ATTR_NOCOLORS | ATTR_RESETFG | FG_MASK | ATTR_FGCOLOR24)
+#define BGATTR (ATTR_NOCOLORS | ATTR_RESETBG | BG_MASK | ATTR_BGCOLOR24)
static void update_cmd_color(unsigned char cmd, int *color)
{
- static int next_color_bg = 0;
- g_message( "update_cmd_color() color: 0x%08x, cmd: 0x%08x\n", *color, cmd);
-
- if (cmd & 0x80) { /* cmd message */
- switch (cmd) {
-
+ if ((cmd & 0x80) == 0) {
+ if (cmd & LINE_COLOR_BG) {
+ /* set background color */
+ *color &= FGATTR;
+ *color &= ~ATTR_FGCOLOR24;
+ if ((cmd & LINE_COLOR_DEFAULT) == 0)
+ *color |= (cmd & 0x0f) << BG_SHIFT;
+ else {
+ *color = (*color & FGATTR) | ATTR_RESETBG;
+ }
+ } else {
+ /* set foreground color */
+ *color &= BGATTR;
+ *color &= ~ATTR_BGCOLOR24;
+ if ((cmd & LINE_COLOR_DEFAULT) == 0)
+ *color |= cmd & 0x0f;
+ else {
+ *color = (*color & BGATTR) | ATTR_RESETFG;
+ }
+ }
+ } else switch (cmd) {
case LINE_CMD_UNDERLINE:
*color ^= ATTR_UNDERLINE;
- g_message( "update_cmd_color() toggle underline 0x%08d\n", *color);
-
break;
case LINE_CMD_REVERSE:
-
*color ^= ATTR_REVERSE;
- g_message( "update_cmd_color() toggle reverse 0x%08d\n", *color);
-
break;
case LINE_CMD_BLINK:
-
*color ^= ATTR_BLINK;
- g_message( "update_cmd_color() toggle blink 0x%08d\n", *color);
-
break;
case LINE_CMD_BOLD:
-
*color ^= ATTR_BOLD;
- g_message( "update_cmd_color() toggle bold 0x%08d\n", *color);
-
break;
case LINE_CMD_COLOR0:
*color &= BGATTR;
- g_message( "update_cmd_color() set BGATTR RESET 0x%08d\n", *color);
-
- break;
- case LINE_CMD_SELECT_FG:
- next_color_bg = 0;
- g_message( "update_cmd_color() Next color will be FG\n");
-
- break;
-
- case LINE_CMD_SELECT_BG:
- next_color_bg = 1;
- g_message( "update_cmd_color() Next color will be BG\n");
+ *color &= ~ATTR_FGCOLOR24;
break;
}
- } else {
- if (next_color_bg == 1) {
- *color = cmd << 8;
- } else {
- *color = cmd;
- }
- }
}
+#ifdef TERM_TRUECOLOR
+static void unformat_24bit_line_color(const unsigned char **ptr, int off, int *flags, int *fg, int *bg)
+{
+ unsigned int color;
+ unsigned char rgbx[4];
+ unsigned int i;
+ for (i = 0; i < 4; ++i) {
+ rgbx[i] = (*ptr)[i + off];
+ }
+ rgbx[3] -= 0x20;
+ *ptr += 4;
+ for (i = 0; i < 3; ++i) {
+ if (rgbx[3] & (0x10 << i))
+ rgbx[i] -= 0x20;
+ }
+ color = rgbx[0] << 16 | rgbx[1] << 8 | rgbx[2];
+ if (rgbx[3] & 0x1) {
+ *flags = (*flags & FGATTR) | ATTR_BGCOLOR24;
+ *bg = color;
+ }
+ else {
+ *flags = (*flags & BGATTR) | ATTR_FGCOLOR24;
+ *fg = color;
+ }
+}
+#endif
+
static inline unichar read_unichar(const unsigned char *data, const unsigned char **next, int *width)
{
unichar chr = g_utf8_get_char_validated(data, -1);
@@ -188,6 +201,7 @@ view_update_line_cache(TEXT_BUFFER_VIEW_REC *view, LINE_REC *line)
unsigned char cmd;
const unsigned char *ptr, *next_ptr, *last_space_ptr;
int xpos, pos, indent_pos, last_space, last_color, color, linecount;
+ int last_bg24, last_fg24, bg24, fg24;
int char_width;
g_return_val_if_fail(line->text != NULL, NULL);
@@ -221,7 +235,18 @@ view_update_line_cache(TEXT_BUFFER_VIEW_REC *view, LINE_REC *line)
/* set indentation position here - don't do
it if we're too close to right border */
if (xpos < view->width-5) indent_pos = xpos;
- } else
+ } else if (cmd == LINE_COLOR_EXT) {
+ color &= ~ATTR_FGCOLOR24;
+ color = (color & BGATTR) | *ptr++;
+ } else if (cmd == LINE_COLOR_EXT_BG) {
+ color &= ~ATTR_BGCOLOR24;
+ color = (color & FGATTR) | (*ptr++ << BG_SHIFT);
+ }
+#ifdef TERM_TRUECOLOR
+ else if (cmd == LINE_COLOR_24)
+ unformat_24bit_line_color(&ptr, 0, &color, &fg24, &bg24);
+#endif
+ else
update_cmd_color(cmd, &color);
continue;
}
@@ -253,7 +278,7 @@ view_update_line_cache(TEXT_BUFFER_VIEW_REC *view, LINE_REC *line)
sub = g_new0(LINE_CACHE_SUB_REC, 1);
if (last_space > indent_pos && last_space > 10) {
/* go back to last space */
- color = last_color;
+ color = last_color; fg24 = last_fg24; bg24 = last_bg24;
ptr = last_space_ptr;
while (*ptr == ' ') ptr++;
} else if (view->longword_noindent) {
@@ -266,6 +291,9 @@ view_update_line_cache(TEXT_BUFFER_VIEW_REC *view, LINE_REC *line)
sub->indent = xpos;
sub->indent_func = indent_func;
sub->color = color;
+#ifdef TERM_TRUECOLOR
+ sub->fg24 = fg24; sub->bg24 = bg24;
+#endif
lines = g_slist_append(lines, sub);
linecount++;
@@ -277,11 +305,11 @@ view_update_line_cache(TEXT_BUFFER_VIEW_REC *view, LINE_REC *line)
if (!view->utf8 && char_width > 1) {
last_space = xpos;
last_space_ptr = next_ptr;
- last_color = color;
+ last_color = color; last_fg24 = fg24; last_bg24 = bg24;
} else if (*ptr == ' ') {
last_space = xpos;
last_space_ptr = ptr;
- last_color = color;
+ last_color = color; last_fg24 = fg24; last_bg24 = bg24;
}
xpos += char_width;
@@ -359,7 +387,7 @@ static int view_line_draw(TEXT_BUFFER_VIEW_REC *view, LINE_REC *line,
const unsigned char *text, *end, *text_newline;
unsigned char *tmp;
unichar chr;
- int xpos, color, drawcount, first, need_move, need_clrtoeol, char_width;
+ int xpos, color, fg24, bg24, drawcount, first, need_move, need_clrtoeol, char_width;
if (view->dirty) /* don't bother drawing anything - redraw is coming */
return 0;
@@ -373,7 +401,6 @@ static int view_line_draw(TEXT_BUFFER_VIEW_REC *view, LINE_REC *line,
xpos = drawcount = 0; first = TRUE;
text_newline = text =
subline == 0 ? line->text : cache->lines[subline-1].start;
- g_message( "view_line_draw()\n");
for (;;) {
if (text == text_newline) {
if (need_clrtoeol && xpos < term_width) {
@@ -395,6 +422,10 @@ static int view_line_draw(TEXT_BUFFER_VIEW_REC *view, LINE_REC *line,
if (indent_func == NULL)
xpos = cache->lines[subline-1].indent;
color = cache->lines[subline-1].color;
+#ifdef TERM_TRUECOLOR
+ fg24 = cache->lines[subline-1].fg24;
+ bg24 = cache->lines[subline-1].bg24;
+#endif
} else {
indent_func = NULL;
}
@@ -412,12 +443,10 @@ static int view_line_draw(TEXT_BUFFER_VIEW_REC *view, LINE_REC *line,
xpos = indent_func(view, line, ypos);
}
- if (need_move || xpos > 0) {
+ if (need_move || xpos > 0)
term_move(view->window, xpos, ypos);
- }
- g_message( "view_line_draw(): color: 0x%08x\n", color);
- term_set_color(view->window, color);
+ term_set_color2(view->window, color, fg24, bg24);
if (subline == cache->count-1) {
text_newline = NULL;
@@ -443,11 +472,17 @@ static int view_line_draw(TEXT_BUFFER_VIEW_REC *view, LINE_REC *line,
text = tmp;
continue;
} else {
- update_cmd_color(*text, &color);
- g_message( "post update_cmd_color: 0x%08x\n",
- color);
-
- term_set_color(view->window, color);
+ if (*text == LINE_COLOR_EXT)
+ color = (color & BGATTR & ~ATTR_FGCOLOR24) | *++text;
+ else if (*text == LINE_COLOR_EXT_BG)
+ color = (color & FGATTR & ~ATTR_BGCOLOR24) | (*++text << BG_SHIFT);
+#ifdef TERM_TRUECOLOR
+ else if (*text == LINE_COLOR_24)
+ unformat_24bit_line_color(&text, 1, &color, &fg24, &bg24);
+#endif
+ else
+ update_cmd_color(*text, &color);
+ term_set_color2(view->window, color, fg24, bg24);
}
text++;
continue;
@@ -476,13 +511,9 @@ static int view_line_draw(TEXT_BUFFER_VIEW_REC *view, LINE_REC *line,
term_addch(view->window, *text);
} else {
/* low-ascii */
- g_message( "printing inverse char %c\n",
- (chr & 127)+'A'-1);
term_set_color(view->window, ATTR_RESET|ATTR_REVERSE);
term_addch(view->window, (chr & 127)+'A'-1);
- g_message( "setting color back to: 0x%08x\n",
- color);
- term_set_color(view->window, color);
+ term_set_color2(view->window, color, fg24, bg24);
}
}
text = end;