1 /* vi:set ts=8 sts=8 sw=8:
2  *
3  * PMS  <<Practical Music Search>>
4  * Copyright (C) 2006-2010  Kim Tore Jensen
5  *
6  * This program is free software: you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation, either version 3 of the License, or
9  * (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program.  If not, see <http://www.gnu.org/licenses/>.
18  *
19  *
20  * display.h - ncurses, display and window management
21  *
22  */
23 
24 #ifndef _PMS_DISPLAY_H_
25 #define _PMS_DISPLAY_H_
26 
27 #include <cmath>
28 #include <cstdlib>
29 #include <string>
30 #include <vector>
31 #include "mycurses.h"
32 #include "types.h"
33 #include "field.h"
34 #include "string.h"
35 #include "command.h"
36 #include "color.h"
37 
38 using namespace std;
39 
40 
41 class Display;
42 
43 enum pms_win_role
44 {
45 	WIN_ROLE_STATIC = 0,
46 	WIN_ROLE_TOPBAR,
47 	WIN_ROLE_PLAYLIST,
48 	WIN_ROLE_STATUSBAR,
49 	WIN_ROLE_POSITIONREADOUT,
50 	WIN_ROLE_WINDOWLIST,
51 	WIN_ROLE_BINDLIST,
52 	WIN_ROLE_DIRECTORYLIST
53 };
54 
55 class pms_column
56 {
57 private:
58 	unsigned long		median;
59 	unsigned int		items;
60 public:
61 				pms_column(string, Item, unsigned int);
~pms_column()62 				~pms_column() {};
63 	string			title;
64 	Item			type;
65 	unsigned int		minlen;
66 	int			abslen;
67 	void			addmedian(unsigned int);
68 	unsigned int		len();
69 };
70 
71 
72 /*
73  * Window class and derived classes
74  */
75 class pms_window
76 {
77 protected:
78 	WINDOW			*handle;
79 
80 	int			border[4];
81 	string			title;
82 
83 	void			drawborders();
84 	void			drawtitle();
85 public:
86 	int			x;
87 	int			y;
88 	int			width;
89 	int			height;
90 	bool			stretch;
91 
92 	bool			wantdraw;
93 	int			cursor; //songlist offset of the song the cursor is on
94 	int			scrolloffset; //songlist offset of top song visible (only used for normal scrolling mode)
95 
96 				pms_window();
97 				~pms_window();
98 
h()99 	WINDOW			*h() { return handle; };
100 
101 	void			setborders(bool, bool, bool, bool); // top, right, bottom, left
102 	bool			resize(int, int, int, int); // x, y, width, height
103 	void			clear(bool, color *);
104 	void			settitle(string);
105 
left()106 	int			left() { return x + border[3]; };
top()107 	int			top() { return y + border[0]; };
right()108 	int			right() { return x + width - 1 - border[1] - border[3]; };
bottom()109 	int			bottom() { return y + height - 1 - border[0] - border[2]; };
bwidth()110 	int			bwidth() { return width - border[1] - border[3]; };
bheight()111 	int			bheight() { return height - border[0] - border[2]; };
centered(string s)112 	int			centered(string s) { return (bwidth() / 2) - (s.size() / 2); };
hasborder(int i)113 	int			hasborder(int i) { if (i >= 0 && i <= 3) return border[i]; else return 0; };
114 
115 
plist()116 	virtual Songlist *	plist() { return NULL; };
setplist(Songlist *)117 	virtual void		setplist(Songlist *) {};
set_column_size()118 	virtual void		set_column_size() {};
draw()119 	virtual void		draw() {};
120 	virtual int		posof_jump(string, int, bool = false) { return -1; };
121 	virtual bool		jumpto(string, int, bool = false) { return false; };
fulltitle()122 	virtual string		fulltitle() { return title; };
size()123 	virtual unsigned int	size() { return 0; };
124 	virtual int		type() = 0;
current()125 	virtual pms_window *	current() { return NULL; };
lastwin()126 	virtual pms_window *	lastwin() { return NULL; };
switchlastwin()127 	virtual void		switchlastwin() {};
gotocurrent()128 	virtual bool		gotocurrent() { return false; };
129 
130 	/*
131 	 * Scroll
132 	 */
133 
134 	unsigned int		cursordrawstart();
scursor()135 	virtual int		scursor() { return cursor; };
136 
137 	virtual void		movecursor(int);
138 	virtual void		setcursor(int);
139 	virtual void		scrollwin(int);
140 };
141 
142 class pms_scroller
143 {
144 protected:
145 };
146 
147 
148 
149 
150 /*
151  * Different types of windows
152  */
153 
154 
155 class pms_win_playlist : public pms_window, public pms_scroller
156 {
157 	vector<pms_column *>	column;
158 public:
159 				pms_win_playlist();
160 
161 	Songlist		*list;
162 
163 	int			posof_jump(string, int, bool = false);
164 	bool			jumpto(string, int, bool = false);
165 	void			set_column_size();
166 
167 	/* Virtual override */
listsize()168 	unsigned int		listsize() { return (list ? list->size() : 0); };
scursor()169 	virtual int		scursor() { return (list ? list->cursor() : 0); };
plist()170 	Songlist *		plist() { return list; };
171 	void			setplist(Songlist *);
size()172 	unsigned int		size() { return (list ? list->size() : 0); };
173 	void			draw();
174 	void			movecursor(int);
175 	void			setcursor(int);
176 	string			fulltitle();
177 	bool			gotocurrent();
type()178 	int			type() { return WIN_ROLE_PLAYLIST; };
179 };
180 
181 class pms_win_topbar : public pms_window
182 {
183 	Control *			comm;
184 public:
185 					pms_win_topbar(Control *);
movecursor(int)186 	void				movecursor(int) {};
setcursor(int)187 	void				setcursor(int) {};
scrollwin(int)188 	void				scrollwin(int) {};
189 	void				draw();
type()190 	int				type() { return WIN_ROLE_TOPBAR; };
191 	int				height();
192 };
193 
194 class pms_win_statusbar : public pms_window
195 {
196 private:
197 	string				text;
198 public:
set(statusbar_mode,string)199 	void				set(statusbar_mode, string) {};
movecursor(int)200 	void				movecursor(int) {};
setcursor(int)201 	void				setcursor(int) {};
scrollwin(int)202 	void				scrollwin(int) {};
draw()203 	void				draw() {};
type()204 	int				type() { return WIN_ROLE_STATUSBAR; };
205 };
206 
207 class pms_win_positionreadout : public pms_window
208 {
209 private:
210 	string				text;
211 public:
set(string)212 	void				set(string) {};
213 	void				draw();
type()214 	int				type() { return WIN_ROLE_POSITIONREADOUT; };
215 };
216 
217 class pms_win_windowlist : public pms_window
218 {
219 private:
220 	Display *			mydisp;
221 	vector<pms_column *>		column;
222 	vector<pms_win_playlist *> *	wlist;
223 	pms_win_playlist *		originwin;
224 	pms_window *			clastwin;
225 	pms_window *			selected;
226 public:
227 					pms_win_windowlist(Display *, vector<pms_win_playlist *> *);
228 
type()229 	int				type() { return WIN_ROLE_WINDOWLIST; };
230 
231 	pms_window *			current();
232 	pms_window *			lastwin();
233 	void				switchlastwin();
234 
size()235 	unsigned int			size() { return (wlist ? wlist->size() : 0); };
236 	void				draw();
237 };
238 
239 class pms_win_bindings : public pms_window
240 {
241 private:
242 	vector<pms_column *>		column;
243 	vector<string>			key, command, desc;
244 public:
245 					pms_win_bindings();
246 
type()247 	int				type() { return WIN_ROLE_BINDLIST; };
248 
size()249 	unsigned int			size() { return key.size(); };
250 	void				draw();
251 };
252 
253 
254 
255 /*
256  * Display class: manages ncurses and windows
257  */
258 class Display
259 {
260 private:
261 	vector<pms_window *>		windows;
262 	vector<pms_win_playlist *>	playlists;
263 	pms_window *			curwin;		// Pointer to active window
264 
265 	Control *			comm;
266 	mmask_t				oldmmask;
267 	mmask_t				mmask;
268 
269 public:
270 	pms_win_topbar *		topbar;
271 	pms_win_statusbar *		statusbar;
272 	pms_win_positionreadout *	positionreadout;
273 	pms_window *			lastwin;
274 
275 					Display(Control *);
276 					~Display();
277 
actwin()278 	pms_window *			actwin() { return curwin; };
279 	pms_window *			playingwin();
280 
281 	mmask_t				setmousemask();
282 	bool				init();
283 	void				uninit();
284 	void				resized();
285 	void				refresh();
286 	void				movecursor(int);
287 	void				setcursor(int);
288 	void				scrollwin(int);
289 	Song *				cursorsong();
290 	void				draw();
291 	void				forcedraw();
292 	void				set_xterm_title();
293 
294 	pms_window *			findwlist(Songlist *);
295 
296 	pms_window *			nextwindow();
297 	pms_window *			prevwindow();
298 	bool				activate(pms_window *);
299 
300 	pms_win_bindings *		create_bindlist();
301 	pms_win_windowlist *		create_windowlist();
302 	pms_win_playlist *		create_playlist();
303 	bool				delete_window(pms_window *);
304 };
305 
306 void	colprint(pms_window * w, int y, int x, color * c, const char *fmt, ...);
307 mmask_t	setmousemask();
308 
309 
310 #endif /* _PMS_DISPLAY_H_ */
311