Merge branch 'refs/heads/t/portable_io'
[paraslash.git] / gui_theme.c
1 /*
2 * Copyright (C) 2005 Andre Noll <maan@tuebingen.mpg.de>
3 *
4 * Licensed under the GPL v2. For licencing details see COPYING.
5 */
6
7 /** \file gui_theme.c Theme definitions. */
8
9 #include "para.h"
10 #include "gui.h"
11 #include <curses.h>
12
13 static void init_theme_simple(struct gui_theme *t)
14 {
15 struct stat_item_data *d = t->data;
16 t->author = "Andre Noll";
17 t->lines_min = 5;
18 t->top_lines_min = 2;
19 t->cols_min = 40;
20 t->top_lines_default = 2;
21 t->sb.bg = COLOR_CYAN;
22 t->sb.fg = COLOR_BLACK;
23 t->cmd.bg = COLOR_WHITE;
24 t->cmd.fg = COLOR_BLACK;
25 t->output.bg = COLOR_BLUE;
26 t->output.fg = COLOR_WHITE;
27 t->msg.bg = COLOR_BLUE;
28 t->msg.fg = COLOR_YELLOW;
29 t->err_msg.bg = COLOR_RED;
30 t->err_msg.fg = COLOR_WHITE;
31 t->sep.bg = COLOR_BLUE;
32 t->sep.fg = COLOR_CYAN;
33 t->dflt.fg = COLOR_WHITE;
34 t->dflt.bg = COLOR_BLUE;
35 t->sep_char = '*';
36
37 d[SI_basename].prefix = "";
38 d[SI_basename].postfix = "";
39 d[SI_basename].color.fg = COLOR_WHITE;
40 d[SI_basename].color.bg = COLOR_BLUE;
41 d[SI_basename].align = CENTER;
42 d[SI_basename].x = 0;
43 d[SI_basename].y = 7;
44 d[SI_basename].len = 100;
45
46 d[SI_status].prefix = "para_server: ";
47 d[SI_status].postfix = "";
48 d[SI_status].color.fg = COLOR_WHITE;
49 d[SI_status].color.bg = COLOR_BLUE;
50 d[SI_status].align = CENTER;
51 d[SI_status].x = 0;
52 d[SI_status].y = 60;
53 d[SI_status].len = 50;
54
55 d[SI_audiod_status].prefix = "para_audiod: ";
56 d[SI_audiod_status].postfix = "";
57 d[SI_audiod_status].color.fg = COLOR_WHITE;
58 d[SI_audiod_status].color.bg = COLOR_BLUE;
59 d[SI_audiod_status].align = CENTER;
60 d[SI_audiod_status].x = 50;
61 d[SI_audiod_status].y = 60;
62 d[SI_audiod_status].len = 50;
63
64 }
65
66 static void init_theme_colorful_blackness(struct gui_theme *t)
67 {
68 struct stat_item_data *d = t->data;
69 t->author = "Andre Noll";
70 /* minimal number of lines that is needed to display all
71 * information provided by this theme
72 */
73 t->lines_min = 15;
74 t->cols_min = 80;
75 t->top_lines_min = 9;
76 t->top_lines_default = 11; /* default number of lines */
77
78 t->sb.bg = COLOR_GREEN; /* status bar background */
79 t->sb.fg = COLOR_BLACK; /* status bar foreground */
80 t->cmd.bg = COLOR_BLACK;
81 t->cmd.fg = COLOR_YELLOW;
82 t->output.bg = COLOR_BLACK;
83 t->output.fg = COLOR_CYAN;
84 t->msg.bg = COLOR_BLACK;
85 t->msg.fg = COLOR_WHITE;
86 t->err_msg.bg = COLOR_RED;
87 t->err_msg.fg = COLOR_WHITE;
88 t->sep.bg = COLOR_BLACK; /* color of the separator */
89 t->sep.fg = COLOR_BLUE;
90 t->sep_char = 0; /* default (ACS_HLINE) */
91 t->dflt.bg = COLOR_BLACK;
92 t->dflt.fg = COLOR_MAGENTA;
93
94
95 d[SI_play_time].prefix = "";
96 d[SI_play_time].postfix = "";
97 d[SI_play_time].color.fg = COLOR_CYAN;
98 d[SI_play_time].color.bg = COLOR_BLACK;
99 d[SI_play_time].align = CENTER;
100 d[SI_play_time].x = 0;
101 d[SI_play_time].y = 7;
102 d[SI_play_time].len = 35;
103
104 d[SI_basename].prefix = "";
105 d[SI_basename].postfix = "";
106 d[SI_basename].color.fg = COLOR_CYAN;
107 d[SI_basename].color.bg = COLOR_BLACK;
108 d[SI_basename].align = LEFT;
109 d[SI_basename].x = 35;
110 d[SI_basename].y = 7;
111 d[SI_basename].len = 65;
112
113 d[SI_status].prefix = "";
114 d[SI_status].postfix = " ";
115 d[SI_status].color.fg = COLOR_RED;
116 d[SI_status].color.bg = COLOR_BLACK;
117 d[SI_status].align = RIGHT;
118 d[SI_status].x = 0;
119 d[SI_status].y = 17;
120 d[SI_status].len = 11;
121
122 d[SI_status_flags].prefix = "(";
123 d[SI_status_flags].postfix = ")";
124 d[SI_status_flags].color.fg = COLOR_RED;
125 d[SI_status_flags].color.bg = COLOR_BLACK;
126 d[SI_status_flags].align = LEFT;
127 d[SI_status_flags].x = 11;
128 d[SI_status_flags].y = 17;
129 d[SI_status_flags].len = 10;
130
131 d[SI_image_id].prefix = "img: ";
132 d[SI_image_id].postfix = "";
133 d[SI_image_id].color.fg = COLOR_RED;
134 d[SI_image_id].color.bg = COLOR_BLACK;
135 d[SI_image_id].align = CENTER;
136 d[SI_image_id].x = 21;
137 d[SI_image_id].y = 17;
138 d[SI_image_id].len = 10;
139
140 d[SI_lyrics_id].prefix = "lyr: ";
141 d[SI_lyrics_id].postfix = "";
142 d[SI_lyrics_id].color.fg = COLOR_RED;
143 d[SI_lyrics_id].color.bg = COLOR_BLACK;
144 d[SI_lyrics_id].align = CENTER;
145 d[SI_lyrics_id].x = 31;
146 d[SI_lyrics_id].y = 17;
147 d[SI_lyrics_id].len = 11;
148
149 d[SI_format].prefix = "format: ";
150 d[SI_format].postfix = "";
151 d[SI_format].color.fg = COLOR_RED;
152 d[SI_format].color.bg = COLOR_BLACK;
153 d[SI_format].align = CENTER;
154 d[SI_format].x = 42;
155 d[SI_format].y = 17;
156 d[SI_format].len = 18;
157
158 d[SI_num_played].prefix = "#";
159 d[SI_num_played].postfix = "";
160 d[SI_num_played].color.fg = COLOR_RED;
161 d[SI_num_played].color.bg = COLOR_BLACK;
162 d[SI_num_played].align = LEFT;
163 d[SI_num_played].x = 60;
164 d[SI_num_played].y = 17;
165 d[SI_num_played].len = 5;
166
167 d[SI_bitrate].prefix = "";
168 d[SI_bitrate].postfix = "";
169 d[SI_bitrate].color.fg = COLOR_RED;
170 d[SI_bitrate].color.bg = COLOR_BLACK;
171 d[SI_bitrate].align = CENTER;
172 d[SI_bitrate].x = 65;
173 d[SI_bitrate].y = 17;
174 d[SI_bitrate].len = 13;
175
176 d[SI_frequency].prefix = "";
177 d[SI_frequency].postfix = "";
178 d[SI_frequency].color.fg = COLOR_RED;
179 d[SI_frequency].color.bg = COLOR_BLACK;
180 d[SI_frequency].align = CENTER;
181 d[SI_frequency].x = 78;
182 d[SI_frequency].y = 17;
183 d[SI_frequency].len = 10;
184
185 d[SI_score].prefix = "sc: ";
186 d[SI_score].postfix = "";
187 d[SI_score].color.fg = COLOR_RED;
188 d[SI_score].color.bg = COLOR_BLACK;
189 d[SI_score].align = CENTER;
190 d[SI_score].x = 88;
191 d[SI_score].y = 17;
192 d[SI_score].len = 10;
193
194 d[SI_audiod_status].prefix = "";
195 d[SI_audiod_status].postfix = "";
196 d[SI_audiod_status].color.fg = COLOR_MAGENTA;
197 d[SI_audiod_status].color.bg = COLOR_BLACK;
198 d[SI_audiod_status].align = CENTER;
199 d[SI_audiod_status].x = 0;
200 d[SI_audiod_status].y = 27;
201 d[SI_audiod_status].len = 5;
202
203 d[SI_decoder_flags].prefix = "[";
204 d[SI_decoder_flags].postfix = "]";
205 d[SI_decoder_flags].color.fg = COLOR_MAGENTA;
206 d[SI_decoder_flags].color.bg = COLOR_BLACK;
207 d[SI_decoder_flags].align = CENTER;
208 d[SI_decoder_flags].x = 5;
209 d[SI_decoder_flags].y = 27;
210 d[SI_decoder_flags].len = 10;
211
212 d[SI_mtime].prefix = "mod: ";
213 d[SI_mtime].postfix = "";
214 d[SI_mtime].color.fg = COLOR_MAGENTA;
215 d[SI_mtime].color.bg = COLOR_BLACK;
216 d[SI_mtime].align = CENTER;
217 d[SI_mtime].x = 15;
218 d[SI_mtime].y = 27;
219 d[SI_mtime].len = 22;
220
221 d[SI_file_size].prefix = "";
222 d[SI_file_size].postfix = "kb";
223 d[SI_file_size].color.fg = COLOR_MAGENTA;
224 d[SI_file_size].color.bg = COLOR_BLACK;
225 d[SI_file_size].align = CENTER;
226 d[SI_file_size].x = 37;
227 d[SI_file_size].y = 27;
228 d[SI_file_size].len = 10;
229
230 d[SI_channels].prefix = "";
231 d[SI_channels].postfix = "ch";
232 d[SI_channels].color.fg = COLOR_MAGENTA;
233 d[SI_channels].color.bg = COLOR_BLACK;
234 d[SI_channels].align = CENTER;
235 d[SI_channels].x = 47;
236 d[SI_channels].y = 27;
237 d[SI_channels].len = 5;
238
239 d[SI_last_played].prefix = "lp: ";
240 d[SI_last_played].postfix = "";
241 d[SI_last_played].color.fg = COLOR_MAGENTA;
242 d[SI_last_played].color.bg = COLOR_BLACK;
243 d[SI_last_played].align = CENTER;
244 d[SI_last_played].x = 52;
245 d[SI_last_played].y = 27;
246 d[SI_last_played].len = 21;
247
248 d[SI_num_chunks].prefix = "";
249 d[SI_num_chunks].postfix = "x";
250 d[SI_num_chunks].color.fg = COLOR_MAGENTA;
251 d[SI_num_chunks].color.bg = COLOR_BLACK;
252 d[SI_num_chunks].align = RIGHT;
253 d[SI_num_chunks].x = 73;
254 d[SI_num_chunks].y = 27;
255 d[SI_num_chunks].len = 11;
256
257 d[SI_chunk_time].prefix = "";
258 d[SI_chunk_time].postfix = "ms";
259 d[SI_chunk_time].color.fg = COLOR_MAGENTA;
260 d[SI_chunk_time].color.bg = COLOR_BLACK;
261 d[SI_chunk_time].align = LEFT;
262 d[SI_chunk_time].x = 84;
263 d[SI_chunk_time].y = 27;
264 d[SI_chunk_time].len = 8;
265
266 d[SI_amplification].prefix = "amp:";
267 d[SI_amplification].postfix = "";
268 d[SI_amplification].color.fg = COLOR_MAGENTA;
269 d[SI_amplification].color.bg = COLOR_BLACK;
270 d[SI_amplification].align = RIGHT;
271 d[SI_amplification].x = 92;
272 d[SI_amplification].y = 27;
273 d[SI_amplification].len = 8;
274
275 d[SI_techinfo].prefix = "";
276 d[SI_techinfo].postfix = "";
277 d[SI_techinfo].color.fg = COLOR_GREEN;
278 d[SI_techinfo].color.bg = COLOR_BLACK;
279 d[SI_techinfo].align = CENTER;
280 d[SI_techinfo].x = 0;
281 d[SI_techinfo].y = 43;
282 d[SI_techinfo].len = 100;
283
284 d[SI_title].prefix = "";
285 d[SI_title].postfix = ",";
286 d[SI_title].color.fg = COLOR_GREEN;
287 d[SI_title].color.bg = COLOR_BLACK;
288 d[SI_title].align = RIGHT;
289 d[SI_title].x = 0;
290 d[SI_title].y = 53;
291 d[SI_title].len = 45;
292
293 d[SI_artist].prefix = " by ";
294 d[SI_artist].postfix = "";
295 d[SI_artist].color.fg = COLOR_GREEN;
296 d[SI_artist].color.bg = COLOR_BLACK;
297 d[SI_artist].align = LEFT;
298 d[SI_artist].x = 45;
299 d[SI_artist].y = 53;
300 d[SI_artist].len = 45;
301
302 d[SI_year].prefix = "(";
303 d[SI_year].postfix = ")";
304 d[SI_year].color.fg = COLOR_GREEN;
305 d[SI_year].color.bg = COLOR_BLACK;
306 d[SI_year].align = RIGHT;
307 d[SI_year].x = 90;
308 d[SI_year].y = 53;
309 d[SI_year].len = 10;
310
311 d[SI_album].prefix = "A: ";
312 d[SI_album].postfix = ",";
313 d[SI_album].color.fg = COLOR_GREEN;
314 d[SI_album].color.bg = COLOR_BLACK;
315 d[SI_album].align = RIGHT;
316 d[SI_album].x = 0;
317 d[SI_album].y = 63;
318 d[SI_album].len = 50;
319
320 d[SI_comment].prefix = " C: ";
321 d[SI_comment].postfix = "";
322 d[SI_comment].color.fg = COLOR_GREEN;
323 d[SI_comment].color.bg = COLOR_BLACK;
324 d[SI_comment].align = LEFT;
325 d[SI_comment].x = 50;
326 d[SI_comment].y = 63;
327 d[SI_comment].len = 50;
328
329 d[SI_afs_mode].prefix = "";
330 d[SI_afs_mode].postfix = "";
331 d[SI_afs_mode].color.fg = COLOR_YELLOW;
332 d[SI_afs_mode].color.bg = COLOR_BLACK;
333 d[SI_afs_mode].align = CENTER;
334 d[SI_afs_mode].x = 0;
335 d[SI_afs_mode].y = 77;
336 d[SI_afs_mode].len = 100;
337
338 d[SI_attributes_txt].prefix = "";
339 d[SI_attributes_txt].postfix = "";
340 d[SI_attributes_txt].color.fg = COLOR_YELLOW;
341 d[SI_attributes_txt].color.bg = COLOR_BLACK;
342 d[SI_attributes_txt].align = CENTER;
343 d[SI_attributes_txt].x = 0;
344 d[SI_attributes_txt].y = 87;
345 d[SI_attributes_txt].len = 100;
346
347 d[SI_directory].prefix = "dir: ";
348 d[SI_directory].postfix = "";
349 d[SI_directory].color.fg = COLOR_YELLOW;
350 d[SI_directory].color.bg = COLOR_BLACK;
351 d[SI_directory].align = CENTER;
352 d[SI_directory].x = 0;
353 d[SI_directory].y = 97;
354 d[SI_directory].len = 100;
355 }
356
357 struct theme_description {
358 const char *name;
359 void (*init)(struct gui_theme *t);
360 };
361
362 static struct theme_description themes[] = {
363 {
364 .name = "colorful blackness",
365 .init = init_theme_colorful_blackness,
366 },
367 {
368 .name = "simple",
369 .init = init_theme_simple,
370 },
371 };
372
373 /** Number of elements in the \a themes array. */
374 #define NUM_THEMES (ARRAY_SIZE(themes))
375
376 static int current_theme_num;
377
378 static void set_theme(int num, struct gui_theme *t)
379 {
380 int i;
381 FOR_EACH_STATUS_ITEM(i)
382 t->data[i].len = 0;
383 num %= NUM_THEMES;
384 t->name = themes[num].name;
385 themes[num].init(t);
386 current_theme_num = num;
387 PARA_NOTICE_LOG("theme: %s\n", t->name);
388 }
389
390 /**
391 * Initialize a theme.
392 *
393 * \param name Name of the theme to be initialized.
394 * \param t The function fills out this structure.
395 *
396 * This function exits if there is no theme called \a name.
397 */
398 void theme_init(const char *name, struct gui_theme *t)
399 {
400 int i;
401
402 if (!name)
403 return set_theme(0, t);
404 for (i = 0; i < NUM_THEMES; i++)
405 if (strcmp(name, themes[i].name) == 0)
406 return set_theme(i, t);
407 fprintf(stderr, "Available themes:\n");
408 for (i = 0; i < NUM_THEMES; i++)
409 fprintf(stderr, "\t%s\n", themes[i].name);
410 exit(EXIT_FAILURE);
411 }
412
413 /**
414 * Activate the previous available theme.
415 *
416 * \param t Theme definition is stored here.
417 *
418 * This picks the theme that comes before the currently active one, or the last
419 * available theme, if the current one is the first.
420 *
421 * \sa \ref theme_next().
422 */
423 void theme_prev(struct gui_theme *t)
424 {
425 return set_theme(++current_theme_num, t);
426 }
427
428 /**
429 * Activate the next available theme.
430 *
431 * \param t Theme definition is stored here.
432 *
433 * This works exactly as theme_prev() but cycles forwards through the list of
434 * available themes.
435 */
436 void theme_next(struct gui_theme *t)
437 {
438 return set_theme(--current_theme_num, t);
439 }