[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
hurd/console-client ChangeLog console.c display...
From: |
Marcus Brinkmann |
Subject: |
hurd/console-client ChangeLog console.c display... |
Date: |
Fri, 15 Aug 2003 17:07:31 -0400 |
CVSROOT: /cvsroot/hurd
Module name: hurd
Branch:
Changes by: Marcus Brinkmann <address@hidden> 03/08/15 17:07:31
Modified files:
console-client : ChangeLog console.c display.h ncursesw.c vga.c
Log message:
2003-08-11 Marco Gerards <address@hidden>
* console.c (cons_vcons_set_dimension): New function.
* display.h (display_ops): New interface set_dimension.
* ncursesw.c (ncursesw_set_dimension): New function.
(ncursesw_displ): Add ncursesw_set_dimension.
(ncurses_lock): Make variable static.
(current_width): New variable.
(current_height): Likewise.
(cursor_state): Likewise.
(cursor_hidden): Likewise.
(driver_ncursesw_ops): Added ncursesw_set_dimension.
* vga.c (current_width): New variable.
(current_height): Likewise.
(vga_display_set_cursor_status): If the cursor is outside the
screen, don't change the visibility.
(vga_display_set_cursor_pos): Don't set the cursor outside the
physical screen. Update cursor_hidden and hide/unhide
to match cursor_hidden. Function moved to above
vga_display_set_cursor_status.
(vga_display_scroll): Report an error when scrolling is not
possible.
(vga_display_clear): Recalculate cols, rows and length.
(vga_display_write): Make it wrap around the edge.
(vga_set_dimension): New function.
(vga_disp_ops): Added vga_set_dimension.
* ncursesw.c (conspad): New variable.
(padx): Likewise.
(pady): Likewise.
(autoscroll): Likewise.
(refresh_screen): new function.
(input_loop): Use conspad instead of (the default) stdscr.
Call console_exit instead of exiting here. Add keybindings
'j, 'k', 'l' and 'i' to scroll the console, add keybinding 'a'
to switch autoscroll.
(mvwputsn): Use conspad instead of (the default) stdscr.
(ncursesw_scroll): Likewise.
(ncursesw_write): Likewise.
(ncursesw_driver_start): Likewise. Initialize conspad.
(ncursesw_update): Call refresh_screen to refresh the console.
(ncursesw_set_cursor_pos): Use conspad instead of (the default)
stdscr. Make the console autoscroll.
* ncursesw.c (ncursesw_driver_start): Remove endwin call at
the end of the function.
* ncursesw.c (ncursesw_set_cursor_status): If the status can
not be set, use another status that can sanely be used instead
of the unavailable status.
CVSWeb URLs:
http://savannah.gnu.org/cgi-bin/viewcvs/hurd/hurd/console-client/ChangeLog.diff?tr1=1.11&tr2=1.12&r1=text&r2=text
http://savannah.gnu.org/cgi-bin/viewcvs/hurd/hurd/console-client/console.c.diff?tr1=1.2&tr2=1.3&r1=text&r2=text
http://savannah.gnu.org/cgi-bin/viewcvs/hurd/hurd/console-client/display.h.diff?tr1=1.1&tr2=1.2&r1=text&r2=text
http://savannah.gnu.org/cgi-bin/viewcvs/hurd/hurd/console-client/ncursesw.c.diff?tr1=1.2&tr2=1.3&r1=text&r2=text
http://savannah.gnu.org/cgi-bin/viewcvs/hurd/hurd/console-client/vga.c.diff?tr1=1.2&tr2=1.3&r1=text&r2=text
Patches:
Index: hurd/console-client/ChangeLog
diff -u hurd/console-client/ChangeLog:1.11 hurd/console-client/ChangeLog:1.12
--- hurd/console-client/ChangeLog:1.11 Mon Jul 28 18:40:54 2003
+++ hurd/console-client/ChangeLog Fri Aug 15 17:07:31 2003
@@ -1,3 +1,54 @@
+2003-08-11 Marco Gerards <address@hidden>
+
+ * console.c (cons_vcons_set_dimension): New function.
+ * display.h (display_ops): New interface set_dimension.
+ * ncursesw.c (ncursesw_set_dimension): New function.
+ (ncursesw_displ): Add ncursesw_set_dimension.
+ (ncurses_lock): Make variable static.
+ (current_width): New variable.
+ (current_height): Likewise.
+ (cursor_state): Likewise.
+ (cursor_hidden): Likewise.
+ (driver_ncursesw_ops): Added ncursesw_set_dimension.
+ * vga.c (current_width): New variable.
+ (current_height): Likewise.
+ (vga_display_set_cursor_status): If the cursor is outside the
+ screen, don't change the visibility.
+ (vga_display_set_cursor_pos): Don't set the cursor outside the
+ physical screen. Update cursor_hidden and hide/unhide
+ to match cursor_hidden. Function moved to above
+ vga_display_set_cursor_status.
+ (vga_display_scroll): Report an error when scrolling is not
+ possible.
+ (vga_display_clear): Recalculate cols, rows and length.
+ (vga_display_write): Make it wrap around the edge.
+ (vga_set_dimension): New function.
+ (vga_disp_ops): Added vga_set_dimension.
+
+ * ncursesw.c (conspad): New variable.
+ (padx): Likewise.
+ (pady): Likewise.
+ (autoscroll): Likewise.
+ (refresh_screen): new function.
+ (input_loop): Use conspad instead of (the default) stdscr.
+ Call console_exit instead of exiting here. Add keybindings
+ 'j, 'k', 'l' and 'i' to scroll the console, add keybinding 'a'
+ to switch autoscroll.
+ (mvwputsn): Use conspad instead of (the default) stdscr.
+ (ncursesw_scroll): Likewise.
+ (ncursesw_write): Likewise.
+ (ncursesw_driver_start): Likewise. Initialize conspad.
+ (ncursesw_update): Call refresh_screen to refresh the console.
+ (ncursesw_set_cursor_pos): Use conspad instead of (the default)
+ stdscr. Make the console autoscroll.
+
+ * ncursesw.c (ncursesw_driver_start): Remove endwin call at
+ the end of the function.
+
+ * ncursesw.c (ncursesw_set_cursor_status): If the status can
+ not be set, use another status that can sanely be used instead
+ of the unavailable status.
+
2003-07-14 Marco Gerards <address@hidden>
* vga.c: New global variable vga_display_max_glyphs.
Index: hurd/console-client/console.c
diff -u hurd/console-client/console.c:1.2 hurd/console-client/console.c:1.3
--- hurd/console-client/console.c:1.2 Mon Nov 18 02:35:47 2002
+++ hurd/console-client/console.c Fri Aug 15 17:07:31 2003
@@ -1,5 +1,5 @@
/* console.c -- A pluggable console client.
- Copyright (C) 2002 Free Software Foundation, Inc.
+ Copyright (C) 2002, 2003 Free Software Foundation, Inc.
Written by Marcus Brinkmann.
This program is free software; you can redistribute it and/or
@@ -352,6 +352,23 @@
if (input->ops->set_scroll_lock_status)
input->ops->set_scroll_lock_status (input->handle, onoff);
mutex_unlock (&global_lock);
+}
+
+
+/* The user must define this function. Clear the existing screen
+ matrix and set the size of the screen matrix to the dimension COL x
+ ROW. This call will be immediately followed by a call to
+ cons_vcons_write that covers the whole new screen matrix. */
+error_t
+cons_vcons_set_dimension (vcons_t vcons, uint32_t col, uint32_t row)
+{
+ mutex_lock (&global_lock);
+ if (vcons == active_vcons)
+ display_iterate
+ if (display->ops->set_dimension)
+ display->ops->set_dimension (display->handle, col, row);
+ mutex_unlock (&global_lock);
+ return 0;
}
Index: hurd/console-client/display.h
diff -u hurd/console-client/display.h:1.1 hurd/console-client/display.h:1.2
--- hurd/console-client/display.h:1.1 Tue Sep 17 08:26:10 2002
+++ hurd/console-client/display.h Fri Aug 15 17:07:31 2003
@@ -1,5 +1,5 @@
/* display.h - The interface to and for a display driver.
- Copyright (C) 2002 Free Software Foundation, Inc.
+ Copyright (C) 2002, 2003 Free Software Foundation, Inc.
Written by Marcus Brinkmann.
This file is part of the GNU Hurd.
@@ -133,6 +133,13 @@
/* Do not use, do not remove. */
void (*deprecated) (void *handle, int key);
+
+ /* Change the dimension of the physical screen to one that can
+ display the vcons with the size of WIDTH * HEIGHT and clear the
+ old screen. If the physical screen already has the right
+ resolution do nothing. This function is always followed by a
+ write that covers the whole new screen. */
+ error_t (*set_dimension) (void *handle, int width, int height);
};
#endif /* _DISPLAY_H_ */
Index: hurd/console-client/ncursesw.c
diff -u hurd/console-client/ncursesw.c:1.2 hurd/console-client/ncursesw.c:1.3
--- hurd/console-client/ncursesw.c:1.2 Tue Sep 17 22:47:01 2002
+++ hurd/console-client/ncursesw.c Fri Aug 15 17:07:31 2003
@@ -1,5 +1,5 @@
/* ncursesw.c - The ncursesw console driver.
- Copyright (C) 2002 Free Software Foundation, Inc.
+ Copyright (C) 2002, 2003 Free Software Foundation, Inc.
Written by Marcus Brinkmann.
This program is free software; you can redistribute it and/or
@@ -34,7 +34,22 @@
/* ncurses is not thread-safe. This lock protects all calls into the
ncurses library. */
-struct mutex ncurses_lock;
+static struct mutex ncurses_lock;
+
+/* The current width and height the ncursesw driver is using. */
+static int current_width;
+static int current_height;
+
+/* The window on which the console is shown. */
+static WINDOW *conspad;
+
+/* The upper left corner shown in the pad. */
+static int padx;
+static int pady;
+
+/* Autoscroll is on or off. Autoscroll makes scrolling dependant on
+ the cursor position. */
+static int autoscroll;
/* Forward declaration. */
static struct display_ops ncursesw_display_ops;
@@ -258,6 +273,17 @@
return 1;
}
+static error_t
+refresh_screen (void)
+{
+ /* It is possible */
+ if (!current_width && !current_height)
+ return 0;
+ return prefresh (conspad, pady, padx, 0, 0,
+ (current_height <= LINES ? current_height : LINES) - 1,
+ (current_width <= COLS ? current_width : COLS) - 1);
+}
+
static any_t
input_loop (any_t unused)
{
@@ -282,7 +308,7 @@
size_t size = 0;
mutex_lock (&ncurses_lock);
- while ((ret = getch ()) != ERR)
+ while ((ret = wgetch (conspad)) != ERR)
{
int i;
int found;
@@ -292,8 +318,8 @@
switch (ret)
{
case 'x':
- endwin ();
- exit (0);
+ mutex_unlock (&ncurses_lock);
+ console_exit ();
break;
case 23: /* ^W */
assert (size < 100);
@@ -313,6 +339,42 @@
console_switch (1 + (ret - '1'), 0);
mutex_lock (&ncurses_lock);
break;
+ case 'j':
+ /* Scroll pad to left. */
+ if (padx > 0)
+ {
+ padx--;
+ refresh_screen ();
+ }
+ break;
+ case 'k':
+ /* Scroll pad down. */
+ if (pady < current_height - LINES)
+ {
+ pady++;
+ refresh_screen ();
+ }
+ break;
+ case 'l':
+ /* Scroll pad to right. */
+ if (padx < current_width - COLS)
+ {
+ padx++;
+ ncurses_refresh ();
+ }
+ break;
+ case 'i':
+ /* Scroll pad up. */
+ if (pady > 0)
+ {
+ pady--;
+ refresh_screen ();
+ }
+ break;
+ case 'a':
+ /* Switch autoscroll on/off. */
+ autoscroll = !autoscroll;
+ break;
default:
break;
}
@@ -326,13 +388,15 @@
break;
default:
found = 0;
- for (i =0; i < sizeof(keycodes) / sizeof(keycodes[0]); i++)
+ for (i = 0; i < sizeof (keycodes) / sizeof (keycodes[0]);
+ i++)
{
if (keycodes[i].curses == ret)
{
if (keycodes[i].cons)
{
- assert (size < 101 - strlen(keycodes[i].cons));
+ assert (size
+ < 101 - strlen (keycodes[i].cons));
strcpy (&buf[size], keycodes[i].cons);
size += strlen (keycodes[i].cons);
}
@@ -382,7 +446,7 @@
attr_t attr = conchar_attr_to_attr (str->attr);
short color_pair = conchar_attr_to_color_pair (str->attr);
- move (y, x);
+ wmove (conspad, y, x);
while (len)
{
int ret;
@@ -396,7 +460,7 @@
}
if (ucs4_to_altchar (str->chr, &ac))
- addch (ac | attr | color_pair);
+ waddch (conspad, ac | attr | color_pair);
else
{
wch[0] = str->chr;
@@ -409,7 +473,7 @@
assert (!"Do something if setcchar fails.");
}
#endif
- ret = add_wch (&chr);
+ ret = wadd_wch (conspad, &chr);
#if 0
if (ret == ERR)
{
@@ -429,7 +493,7 @@
ncursesw_update (void *handle)
{
mutex_lock (&ncurses_lock);
- refresh ();
+ refresh_screen ();
mutex_unlock (&ncurses_lock);
return 0;
}
@@ -439,7 +503,45 @@
ncursesw_set_cursor_pos (void *handle, uint32_t col, uint32_t row)
{
mutex_lock (&ncurses_lock);
- move (row, col);
+ assert (current_width && current_height);
+ if (autoscroll)
+ {
+ /* Autoscroll to the right. */
+ if (col > COLS + padx)
+ {
+ padx += COLS / 2;
+ if (padx > COLS + current_width)
+ padx = current_width - COLS;
+ ncurses_refresh ();
+ }
+ /* Autoscroll to the left. */
+ else if (col < padx)
+ {
+ padx -= COLS / 2;
+ if (padx < 0)
+ padx = 0;
+ ncurses_refresh ();
+ }
+ /* Autoscroll down. */
+ if (row > LINES + pady)
+ {
+ pady += LINES / 2;
+ if (pady > LINES + current_height)
+ pady = current_height - LINES;
+ ncurses_refresh ();
+ }
+ /* Autoscroll up. */
+ else if (row < pady)
+ {
+ pady -= LINES / 2;
+ if (pady < 0)
+ pady = 0;
+ ncurses_refresh ();
+ }
+ }
+
+ wmove (conspad, row, col);
+
mutex_unlock (&ncurses_lock);
return 0;
}
@@ -449,7 +551,13 @@
ncursesw_set_cursor_status (void *handle, uint32_t status)
{
mutex_lock (&ncurses_lock);
- curs_set (status ? (status == 1 ? 1 : 2) : 0);
+
+ /* If the cursor is invisible and switching to one visible state is
+ impossible, switch to the other visible state or else the cursor
+ will not be shown at all. */
+ if (curs_set (status) == -1 && status)
+ curs_set (status == 1 ? 2 : 1);
+
mutex_unlock (&ncurses_lock);
return 0;
}
@@ -462,11 +570,11 @@
assert (delta >= 0);
mutex_lock (&ncurses_lock);
- idlok (stdscr, TRUE);
- scrollok (stdscr, TRUE);
- scrl (delta);
- idlok (stdscr, FALSE);
- scrollok (stdscr, FALSE);
+ idlok (conspad, TRUE);
+ scrollok (conspad, TRUE);
+ wscrl (conspad, delta);
+ idlok (conspad, FALSE);
+ scrollok (conspad, FALSE);
mutex_unlock (&ncurses_lock);
return 0;
}
@@ -480,9 +588,9 @@
int y;
mutex_lock (&ncurses_lock);
- getyx (stdscr, y, x);
+ getyx (conspad, y, x);
mvwputsn (str, length, col, row);
- wmove (stdscr, y, x);
+ wmove (conspad, y, x);
mutex_unlock (&ncurses_lock);
return 0;
}
@@ -531,10 +639,17 @@
raw ();
noecho ();
nonl ();
- intrflush (stdscr, FALSE);
- nodelay (stdscr, TRUE);
- timeout (1);
- keypad (stdscr, TRUE);
+
+ /* Create a new pad with the size minimal size. This pad will be
+ resized by ncursesw_set_dimension. */
+ conspad = newpad (1, 1);
+ if (!conspad)
+ return errno;
+
+ intrflush (conspad, FALSE);
+ nodelay (conspad, TRUE);
+ wtimeout (conspad, 1);
+ keypad (conspad, TRUE);
err = driver_add_display (&ncursesw_display_ops, NULL);
if (err)
@@ -559,9 +674,8 @@
}
cthread_detach (cthread_fork (input_loop, NULL));
- endwin ();
- return err;
+ return 0;
}
/* Destroy the display HANDLE. */
@@ -579,6 +693,22 @@
return 0;
}
+static error_t
+ncursesw_set_dimension (void *handle, int width, int height)
+{
+ mutex_lock (&ncurses_lock);
+ if (width != current_width || height != current_height)
+ {
+ wresize (conspad, height, width);
+ padx = 0;
+ pady = 0;
+ }
+ current_width = width;
+ current_height = height;
+ mutex_unlock(&ncurses_lock);
+ return 0;
+}
+
struct driver_ops driver_ncursesw_ops =
{
@@ -596,7 +726,8 @@
ncursesw_write,
ncursesw_update,
ncursesw_flash,
- NULL
+ NULL,
+ ncursesw_set_dimension
};
static struct input_ops ncursesw_input_ops =
Index: hurd/console-client/vga.c
diff -u hurd/console-client/vga.c:1.2 hurd/console-client/vga.c:1.3
--- hurd/console-client/vga.c:1.2 Mon Jul 28 18:40:54 2003
+++ hurd/console-client/vga.c Fri Aug 15 17:07:31 2003
@@ -74,6 +74,16 @@
/* Forward declaration. */
static struct display_ops vga_display_ops;
+/* The current width and height the ncursesw driver is using. */
+static int current_width;
+static int current_height;
+
+/* The cursor state to restore the state to. */
+static int cursor_state;
+
+/* Is set to 1 if the cursor moved out of the physical screen and the
+ cursor state should be hidden. */
+static int cursor_hidden;
struct refchr
{
@@ -318,29 +328,54 @@
}
-/* Set the cursor's position on display HANDLE to column COL and row
- ROW. */
+/* Set the cursor's state to STATE on display HANDLE. */
static error_t
-vga_display_set_cursor_pos (void *handle, uint32_t col, uint32_t row)
+vga_display_set_cursor_status (void *handle, uint32_t state)
{
struct vga_display *disp = handle;
- unsigned int pos = row * disp->width + col;
- vga_set_cursor_pos (pos);
+ /* Don't display the cursor if its location is not within the
+ physical screen. */
+ if (!cursor_hidden)
+ {
+ if (state != CONS_CURSOR_INVISIBLE)
+ dynafont_set_cursor (disp->df, state == CONS_CURSOR_VERY_VISIBLE ? 1 :
0);
+
+ vga_display_cursor (state == CONS_CURSOR_INVISIBLE ? 0 : 1);
+ }
+
+ cursor_state = state;
return 0;
}
-/* Set the cursor's state to STATE on display HANDLE. */
+/* Set the cursor's position on display HANDLE to column COL and row
+ ROW. */
static error_t
-vga_display_set_cursor_status (void *handle, uint32_t state)
+vga_display_set_cursor_pos (void *handle, uint32_t col, uint32_t row)
{
struct vga_display *disp = handle;
+ unsigned int pos = row * disp->width + col;
- if (state != CONS_CURSOR_INVISIBLE)
- dynafont_set_cursor (disp->df, state == CONS_CURSOR_VERY_VISIBLE ? 1 : 0);
- vga_display_cursor (state == CONS_CURSOR_INVISIBLE ? 0 : 1);
+ /* Make sure the cursor can only be moved to a position on te
+ physical screen. */
+ if (col < disp->width && row < disp->height)
+ {
+ vga_set_cursor_pos (pos);
+ if (cursor_hidden)
+ {
+ /* Restore the cursor. */
+ cursor_hidden = 0;
+ vga_display_set_cursor_status (handle, cursor_state);
+ }
+ }
+ else if (!cursor_hidden)
+ {
+ /* Hide the cursor. */
+ cursor_hidden = 1;
+ vga_display_cursor (CONS_CURSOR_INVISIBLE);
+ }
return 0;
}
@@ -355,7 +390,12 @@
int count = abs(delta) * disp->width;
int i;
struct refchr *refpos;
-
+
+ /* XXX: If the virtual console is bigger than the physical console it is
+ impossible to scroll because the data to scroll is not in memory. */
+ if (current_height > disp->height)
+ return ENOTSUP;
+
if (delta > 0)
{
memmove (vga_videomem, vga_videomem + 2 * count,
@@ -485,8 +525,31 @@
vga_display_clear (void *handle, size_t length, uint32_t col, uint32_t row)
{
struct vga_display *disp = handle;
- struct refchr *refpos = &disp->refmatrix[row][col];
+ struct refchr *refpos = &disp->refmatrix[row][0];
+ int cols;
+ /* The column can be outside the physical screen, in that case
+ adjust the position. */
+ if (col >= disp->width)
+ {
+ col = disp->width - col;
+ row++;
+ }
+ refpos += col;
+
+ /* The first row is not in the physical screen, nothing has to be
+ done. */
+ if (row >= disp->height)
+ return 0;
+
+ /* The length cannot be used. Recalculate it to wrap the lines. */
+ cols = length / current_width;
+ length = (length % current_width) + cols * disp->width ;
+
+ /* Make sure the end of length is still in the physical screen. */
+ if (length > (disp->width * disp->height - (row * disp->width + col)) - col)
+ length = disp->width * disp->height - (row * disp->width + col) - col;
+
while (length > 0)
{
if (refpos->used)
@@ -511,9 +574,21 @@
uint32_t col, uint32_t row)
{
struct vga_display *disp = handle;
- char *pos = vga_videomem + 2 * (row * disp->width + col);
+ char *pos;
struct refchr *refpos = &disp->refmatrix[row][col];
+ /* The starting column is outside the physical screen. */
+ if (disp->width < current_width && col >= disp->width)
+ {
+ size_t skip = current_width - disp->width;
+ str += skip;
+ length -= skip;
+ col = 0;
+ row++;
+ }
+
+ pos = vga_videomem + 2 * (row * disp->width + col);
+
/* Although all references to the current fgcol or bgcol could have
been released here, for example due to a scroll operation, we
know that the color slots have not been reused yet, as no routine
@@ -524,6 +599,31 @@
while (length--)
{
int charval = dynafont_lookup (disp->df, str);
+ col++;
+
+ /* The virtual console is smaller than the physical screen. */
+ if (col > current_width)
+ {
+ size_t skip = disp->width - current_width;
+ pos += skip * 2;
+ refpos += skip;
+ col = 1;
+ row++;
+ }
+ /* The virtual console is bigger than the physical console. */
+ else if (disp->width < current_width && col == disp->width)
+ {
+ size_t skip = current_width - disp->width;
+ str += skip;
+ length -= skip;
+ col = 1;
+ row++;
+ }
+
+ /* The screen is filled until the bottom of the screen. */
+ if (row >= disp->height)
+ return 0;
+
if (!disp->cur_conchar_attr_init
|| *(uint32_t *) &disp->cur_conchar_attr != *(uint32_t *) &str->attr)
{
@@ -566,6 +666,21 @@
return 0;
}
+static error_t
+vga_set_dimension (void *handle, int width, int height)
+{
+ if (current_width && current_height)
+ vga_display_clear (handle, current_width * current_height, 0, 0);
+
+ current_width = width;
+ current_height = height;
+
+ /* FIXME: Should support greater dimensions by changing the video
+ mode. */
+
+ return 0;
+}
+
struct driver_ops driver_vga_ops =
{
@@ -583,5 +698,6 @@
vga_display_write,
NULL,
vga_display_flash,
- NULL
+ NULL,
+ vga_set_dimension
};
[Prev in Thread] |
Current Thread |
[Next in Thread] |
- hurd/console-client ChangeLog console.c display...,
Marcus Brinkmann <=