aboutsummaryrefslogtreecommitdiff
path: root/console.c
diff options
context:
space:
mode:
authorbalrog <balrog@c046a42c-6fe2-441c-8c8c-71466251a162>2008-02-10 16:33:14 +0000
committerbalrog <balrog@c046a42c-6fe2-441c-8c8c-71466251a162>2008-02-10 16:33:14 +0000
commit4d3b6f6e126553107a78999bd1070b086ae3c023 (patch)
tree53efc029b509407306b900d509256fdaabd6f49f /console.c
parentc0be16d39fd7187764dcd3d65a63167c92e48142 (diff)
Add an ncurses UI.
git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@3976 c046a42c-6fe2-441c-8c8c-71466251a162
Diffstat (limited to 'console.c')
-rw-r--r--console.c113
1 files changed, 97 insertions, 16 deletions
diff --git a/console.c b/console.c
index e7c00eccb3..880ac831a5 100644
--- a/console.c
+++ b/console.c
@@ -121,6 +121,7 @@ struct TextConsole {
vga_hw_update_ptr hw_update;
vga_hw_invalidate_ptr hw_invalidate;
vga_hw_screen_dump_ptr hw_screen_dump;
+ vga_hw_text_update_ptr hw_text_update;
void *hw;
int g_width, g_height;
@@ -135,6 +136,7 @@ struct TextConsole {
TextAttributes t_attrib_default; /* default text attributes */
TextAttributes t_attrib; /* currently active text attributes */
TextCell *cells;
+ int text_x[2], text_y[2], cursor_invalidate;
enum TTYState state;
int esc_params[MAX_ESC_PARAMS];
@@ -171,6 +173,12 @@ void vga_hw_screen_dump(const char *filename)
consoles[0]->hw_screen_dump(consoles[0]->hw, filename);
}
+void vga_hw_text_update(console_ch_t *chardata)
+{
+ if (active_console && active_console->hw_text_update)
+ active_console->hw_text_update(active_console->hw, chardata);
+}
+
/* convert a RGBA color to a color index usable in graphic primitives */
static unsigned int vga_get_color(DisplayState *ds, unsigned int rgba)
{
@@ -515,12 +523,25 @@ static void text_console_resize(TextConsole *s)
s->cells = cells;
}
+static inline void text_update_xy(TextConsole *s, int x, int y)
+{
+ s->text_x[0] = MIN(s->text_x[0], x);
+ s->text_x[1] = MAX(s->text_x[1], x);
+ s->text_y[0] = MIN(s->text_y[0], y);
+ s->text_y[1] = MAX(s->text_y[1], y);
+}
+
static void update_xy(TextConsole *s, int x, int y)
{
TextCell *c;
int y1, y2;
if (s == active_console) {
+ if (!s->ds->depth) {
+ text_update_xy(s, x, y);
+ return;
+ }
+
y1 = (s->y_base + y) % s->total_height;
y2 = y1 - s->y_displayed;
if (y2 < 0)
@@ -542,6 +563,12 @@ static void console_show_cursor(TextConsole *s, int show)
if (s == active_console) {
int x = s->x;
+
+ if (!s->ds->depth) {
+ s->cursor_invalidate = 1;
+ return;
+ }
+
if (x >= s->width) {
x = s->width - 1;
}
@@ -571,6 +598,14 @@ static void console_refresh(TextConsole *s)
if (s != active_console)
return;
+ if (!s->ds->depth) {
+ s->text_x[0] = 0;
+ s->text_y[0] = 0;
+ s->text_x[1] = s->width - 1;
+ s->text_y[1] = s->height - 1;
+ s->cursor_invalidate = 1;
+ return;
+ }
vga_fill_rect(s->ds, 0, 0, s->ds->width, s->ds->height,
color_table[0][COLOR_BLACK]);
@@ -648,6 +683,14 @@ static void console_put_lf(TextConsole *s)
c++;
}
if (s == active_console && s->y_displayed == s->y_base) {
+ if (!s->ds->depth) {
+ s->text_x[0] = 0;
+ s->text_y[0] = 0;
+ s->text_x[1] = s->width - 1;
+ s->text_y[1] = s->height - 1;
+ return;
+ }
+
vga_bitblt(s->ds, 0, FONT_HEIGHT, 0, 0,
s->width * FONT_WIDTH,
(s->height - 1) * FONT_HEIGHT);
@@ -998,21 +1041,7 @@ void console_select(unsigned int index)
s = consoles[index];
if (s) {
active_console = s;
- if (s->console_type != GRAPHIC_CONSOLE) {
- if (s->g_width != s->ds->width ||
- s->g_height != s->ds->height) {
- if (s->console_type == TEXT_CONSOLE_FIXED_SIZE) {
- dpy_resize(s->ds, s->g_width, s->g_height);
- } else {
- s->g_width = s->ds->width;
- s->g_height = s->ds->height;
- text_console_resize(s);
- }
- }
- console_refresh(s);
- } else {
- vga_hw_invalidate();
- }
+ vga_hw_invalidate();
}
}
@@ -1116,6 +1145,52 @@ void kbd_put_keysym(int keysym)
}
}
+static void text_console_invalidate(void *opaque)
+{
+ TextConsole *s = (TextConsole *) opaque;
+
+ if (s->console_type != GRAPHIC_CONSOLE) {
+ if (s->g_width != s->ds->width ||
+ s->g_height != s->ds->height) {
+ if (s->console_type == TEXT_CONSOLE_FIXED_SIZE)
+ dpy_resize(s->ds, s->g_width, s->g_height);
+ else {
+ s->g_width = s->ds->width;
+ s->g_height = s->ds->height;
+ text_console_resize(s);
+ }
+ }
+ }
+ console_refresh(s);
+}
+
+static void text_console_update(void *opaque, console_ch_t *chardata)
+{
+ TextConsole *s = (TextConsole *) opaque;
+ int i, j, src;
+
+ if (s->text_x[0] <= s->text_x[1]) {
+ src = (s->y_base + s->text_y[0]) * s->width;
+ chardata += s->text_y[0] * s->width;
+ for (i = s->text_y[0]; i <= s->text_y[1]; i ++)
+ for (j = 0; j < s->width; j ++, src ++)
+ console_write_ch(chardata ++, s->cells[src].ch |
+ (s->cells[src].t_attrib.fgcol << 12) |
+ (s->cells[src].t_attrib.bgcol << 8) |
+ (s->cells[src].t_attrib.bold << 21));
+ dpy_update(s->ds, s->text_x[0], s->text_y[0],
+ s->text_x[1] - s->text_x[0], i - s->text_y[0]);
+ s->text_x[0] = s->width;
+ s->text_y[0] = s->height;
+ s->text_x[1] = 0;
+ s->text_y[1] = 0;
+ }
+ if (s->cursor_invalidate) {
+ dpy_cursor(s->ds, s->x, s->y);
+ s->cursor_invalidate = 0;
+ }
+}
+
static TextConsole *new_console(DisplayState *ds, console_type_t console_type)
{
TextConsole *s;
@@ -1150,6 +1225,7 @@ static TextConsole *new_console(DisplayState *ds, console_type_t console_type)
TextConsole *graphic_console_init(DisplayState *ds, vga_hw_update_ptr update,
vga_hw_invalidate_ptr invalidate,
vga_hw_screen_dump_ptr screen_dump,
+ vga_hw_text_update_ptr text_update,
void *opaque)
{
TextConsole *s;
@@ -1160,13 +1236,14 @@ TextConsole *graphic_console_init(DisplayState *ds, vga_hw_update_ptr update,
s->hw_update = update;
s->hw_invalidate = invalidate;
s->hw_screen_dump = screen_dump;
+ s->hw_text_update = text_update;
s->hw = opaque;
return s;
}
int is_graphic_console(void)
{
- return active_console->console_type == GRAPHIC_CONSOLE;
+ return active_console && active_console->console_type == GRAPHIC_CONSOLE;
}
void console_color_init(DisplayState *ds)
@@ -1234,6 +1311,10 @@ CharDriverState *text_console_init(DisplayState *ds, const char *p)
s->g_width = width;
s->g_height = height;
+ s->hw_invalidate = text_console_invalidate;
+ s->hw_text_update = text_console_update;
+ s->hw = s;
+
/* Set text attribute defaults */
s->t_attrib_default.bold = 0;
s->t_attrib_default.uline = 0;