Home | History | Annotate | Download | only in mucurses
      1 #include <console.h>
      2 #include <curses.h>
      3 #include "mucurses.h"
      4 
      5 /** @file
      6  *
      7  * MuCurses core functions
      8  *
      9  */
     10 
     11 FILE_LICENCE ( GPL2_OR_LATER );
     12 
     13 static void _wupdcurs ( WINDOW *win ) __nonnull;
     14 void _wputch ( WINDOW *win, chtype ch, int wrap ) __nonnull;
     15 void _wputc ( WINDOW *win, char c, int wrap ) __nonnull;
     16 void _wcursback ( WINDOW *win ) __nonnull;
     17 void _wputchstr ( WINDOW *win, const chtype *chstr, int wrap, int n ) __nonnull;
     18 void _wputstr ( WINDOW *win, const char *str, int wrap, int n ) __nonnull;
     19 int wmove ( WINDOW *win, int y, int x ) __nonnull;
     20 
     21 WINDOW _stdscr = {
     22 	.attrs = A_DEFAULT,
     23 	.ori_y = 0,
     24 	.ori_x = 0,
     25 	.curs_y = 0,
     26 	.curs_x = 0,
     27 	.scr = &_ansi_screen,
     28 };
     29 
     30 /*
     31  *  Primitives
     32  */
     33 
     34 /**
     35  * Update cursor position
     36  *
     37  * @v *win	window in which to update position
     38  */
     39 static void _wupdcurs ( WINDOW *win ) {
     40 	win->scr->movetoyx ( win->scr, win->ori_y + win->curs_y,
     41 			     win->ori_x + win->curs_x );
     42 }
     43 
     44 /**
     45  * Write a single character rendition to a window
     46  *
     47  * @v *win	window in which to write
     48  * @v ch	character rendition to write
     49  * @v wrap	wrap "switch"
     50  */
     51 void _wputch ( WINDOW *win, chtype ch, int wrap ) {
     52 	/* make sure we set the screen cursor to the right position
     53 	   first! */
     54 	_wupdcurs(win);
     55 	win->scr->putc(win->scr, ch);
     56 	if ( ++(win->curs_x) - win->width == 0 ) {
     57 		if ( wrap == WRAP ) {
     58 			win->curs_x = 0;
     59 			/* specification says we should really scroll,
     60 			   but we have no buffer to scroll with, so we
     61 			   can only overwrite back at the beginning of
     62 			   the window */
     63 			if ( ++(win->curs_y) - win->height == 0 )
     64 				win->curs_y = 0;
     65 		} else {
     66 			(win->curs_x)--;
     67 		}
     68 	}
     69 }
     70 
     71 /**
     72  * Write a single character to a window
     73  *
     74  * @v *win	window in which to write
     75  * @v c		character rendition to write
     76  * @v wrap	wrap "switch"
     77  */
     78 void _wputc ( WINDOW *win, char c, int wrap ) {
     79 	_wputch ( win, ( c | win->attrs ), wrap );
     80 }
     81 
     82 /**
     83  * Retreat the cursor back one position (useful for a whole host of
     84  * ops)
     85  *
     86  * @v *win	window in which to retreat
     87  */
     88 void _wcursback ( WINDOW *win ) {
     89 	if ( win->curs_x == 0 ) {
     90 		if ( win->curs_y == 0 )
     91 			win->curs_y = win->height - 1;
     92 		win->curs_x = win->width = 1;
     93 	} else {
     94 		win->curs_x--;
     95 	}
     96 
     97 	_wupdcurs(win);
     98 }
     99 
    100 /**
    101  * Write a chtype string to a window
    102  *
    103  * @v *win	window in which to write
    104  * @v *chstr	chtype string
    105  * @v wrap	wrap "switch"
    106  * @v n		write at most n chtypes
    107  */
    108 void _wputchstr ( WINDOW *win, const chtype *chstr, int wrap, int n ) {
    109 	for ( ; *chstr && n-- ; chstr++ ) {
    110 		_wputch(win,*chstr,wrap);
    111 	}
    112 }
    113 
    114 /**
    115  * Write a standard c-style string to a window
    116  *
    117  * @v *win	window in which to write
    118  * @v *str	string
    119  * @v wrap	wrap "switch"
    120  * @v n		write at most n chars from *str
    121  */
    122 void _wputstr ( WINDOW *win, const char *str, int wrap, int n ) {
    123 	for ( ; *str && n-- ; str++ ) {
    124 		_wputc ( win, *str, wrap );
    125 	}
    126 }
    127 
    128 /**
    129  * Move a window's cursor to the specified position
    130  *
    131  * @v *win	window to be operated on
    132  * @v y		Y position
    133  * @v x		X position
    134  * @ret rc	return status code
    135  */
    136 int wmove ( WINDOW *win, int y, int x ) {
    137 	/* chech for out-of-bounds errors */
    138 	if ( ( (unsigned)y >= win->height ) ||
    139 	     ( (unsigned)x >= win->width ) ) {
    140 		return ERR;
    141 	}
    142 
    143 	win->curs_y = y;
    144 	win->curs_x = x;
    145 	_wupdcurs(win);
    146 	return OK;
    147 }
    148