1#include <curses.h>
2#include <stddef.h>
3#include <stdlib.h>
4#include "mucurses.h"
5
6/** @file
7 *
8 * MuCurses windows instance functions
9 *
10 */
11
12/**
13 * Delete a window
14 *
15 * @v *win	pointer to window being deleted
16 * @ret rc	return status code
17 */
18int delwin ( WINDOW *win ) {
19	if ( win == NULL )
20		return ERR;
21
22	/* I think we should blank the region covered by the window -
23	   ncurses doesn't do this, but they have a buffer, so they
24	   may just be deleting from an offscreen context whereas we
25	   are guaranteed to be deleting something onscreen */
26	wmove( win, 0, 0 );
27	chtype killch = (chtype)' ';
28	do {
29		_wputch( win, killch, WRAP );
30	} while ( win->curs_x + win->curs_y );
31
32	free( win );
33
34	wmove ( stdscr, 0, 0 );
35
36	return OK;
37}
38
39/**
40 * Create a new derived window
41 *
42 * @v parent	parent window
43 * @v nlines	window height
44 * @v ncols	window width
45 * @v begin_y	window y origin (relative to parent)
46 * @v begin_x	window x origin (relative to parent)
47 * @ret ptr	return pointer to child window
48 */
49WINDOW *derwin ( WINDOW *parent, int nlines, int ncols,
50	     		  	 int begin_y, int begin_x ) {
51	WINDOW *child;
52	if ( parent == NULL )
53		return NULL;
54	if ( ( child = malloc( sizeof( WINDOW ) ) ) == NULL )
55		return NULL;
56	if ( ( (unsigned)ncols > parent->width ) ||
57	     ( (unsigned)nlines > parent->height ) )
58		return NULL;
59	child->ori_y = parent->ori_y + begin_y;
60	child->ori_x = parent->ori_x + begin_x;
61	child->height = nlines;
62	child->width = ncols;
63	child->parent = parent;
64	child->scr = parent->scr;
65	return child;
66}
67
68/**
69 * Create a duplicate of the specified window
70 *
71 * @v orig	original window
72 * @ret ptr	pointer to duplicate window
73 */
74WINDOW *dupwin ( WINDOW *orig ) {
75	WINDOW *copy;
76	if ( orig == NULL )
77		return NULL;
78	if ( ( copy = malloc( sizeof( WINDOW ) ) ) == NULL )
79		return NULL;
80	copy->scr = orig->scr;
81	copy->attrs = orig->attrs;
82	copy->ori_y = orig->ori_y;
83	copy->ori_x = orig->ori_x;
84	copy->curs_y = orig->curs_y;
85	copy->curs_x = orig->curs_x;
86	copy->height = orig->height;
87	copy->width = orig->width;
88	return copy;
89}
90
91/**
92 * Move window origin to specified coordinates
93 *
94 * @v *win	window to move
95 * @v y		Y position
96 * @v x		X position
97 * @ret rc	return status code
98 */
99int mvwin ( WINDOW *win, int y, int x ) {
100	if ( win == NULL )
101		return ERR;
102	if ( ( ( (unsigned)y + win->height ) > LINES ) ||
103	     ( ( (unsigned)x + win->width ) > COLS ) )
104		return ERR;
105
106	win->ori_y = y;
107	win->ori_x = x;
108
109	return OK;
110}
111
112/**
113 * Create new WINDOW
114 *
115 * @v nlines	number of lines
116 * @v ncols	number of columns
117 * @v begin_y	column origin
118 * @v begin_x	line origin
119 * @ret *win	return pointer to new window
120 */
121WINDOW *newwin ( int nlines, int ncols, int begin_y, int begin_x ) {
122	WINDOW *win;
123	if ( ( win = malloc( sizeof(WINDOW) ) ) == NULL )
124		return NULL;
125	if ( ( (unsigned)( begin_y + nlines ) > stdscr->height ) &&
126	     ( (unsigned)( begin_x + ncols ) > stdscr->width ) )
127		return NULL;
128	win->ori_y = begin_y;
129	win->ori_x = begin_x;
130	win->height = nlines;
131	win->width = ncols;
132	win->scr = stdscr->scr;
133	win->parent = stdscr;
134	return win;
135}
136
137/**
138 * Create a new sub-window
139 *
140 * @v orig	parent window
141 * @v nlines	window height
142 * @v ncols	window width
143 * @v begin_y	window y origin (absolute)
144 * @v begin_x	window x origin (absolute)
145 * @ret ptr	return pointer to child window
146 */
147WINDOW *subwin ( WINDOW *parent, int nlines, int ncols,
148			         int begin_y, int begin_x ) {
149	WINDOW *child;
150	if ( parent == NULL )
151		return NULL;
152	if ( ( child = malloc( sizeof( WINDOW ) ) ) == NULL )
153		return NULL;
154	child = newwin( nlines, ncols, begin_y, begin_x );
155	child->parent = parent;
156	child->scr = parent->scr;
157	return child;
158}
159