1 /***
2 ***
3 *** MP - a free music module player based on ncurses (GUI)
4 *** and mikmod (sound engine).
5 ***
6 ***
7 *** Copyright (C) 2003-2004 Gael Gence <gael.gence@skynet.be>
8 *** and Gregoire Welraeds
9 ***
10 ***
11 ***
12 *** For licence, please refer to the COPYING file distributed
13 *** with the archive.
14 ***
15 ***
16 ***
17 *** Home site: http://mp.waw.cx/
18 ***
19 ***/
20
21 #include <stdlib.h>
22 #include <string.h>
23 #include <unistd.h>
24 #include <signal.h>
25 #include <dirent.h>
26 #include <fcntl.h>
27 #include <sys/ioctl.h>
28 #include <sys/types.h>
29 #include <sys/stat.h>
30 #include <sys/soundcard.h>
31
32 #include <curses.h>
33 #include <panel.h>
34 #include <mikmod.h>
35
36
37 /******************************************************************************
38 ***
39 *** Defines.
40 ***
41 ******************************************************************************/
42
43 #define VERSION "0.6" /* here it is */
44 #define NAME_MAX 255
45
46
47 /*** Various. ***/
48 #define MIN_FREQ 4000 /* minimum frequency */
49 #define MAX_FREQ 60000 /* maximum frequency */
50 #define MAX_CHANNELS 64 /* max # channels */
51
52 #define CHN_START 7 /* display channel y start */
53 #define FILE_Y 1 /* module file y pos */
54 #define TITLE_Y 2 /* module title y pos */
55 #define DRIVER_Y 3 /* driver info y pos */
56 #define MODINFO_Y 4 /* module info y pos */
57
58 #define EFFECTS 10 /* # of effects */
59
60 /*** Options. ***/
61 #define OPTIONS 12 /* # of options */
62 #define _16BITS_OPT 0 /* option # */
63 #define STEREO_OPT 1 /* option # */
64 #define REVSTEREO_OPT 2 /* option # */
65 #define SURROUND_OPT 3 /* option # */
66 #define INTERPOLATE_OPT 4 /* option # */
67 #define HQMIXER_OPT 6 /* option # */
68 #define MIXFREQ_OPT 7 /* option # */
69 #define LOOP_OPT 9 /* option # */
70 #define FADE_OPT 10 /* option # */
71 #define RANDOM_OPT 11 /* option # */
72 #define DELAY_OPT 13 /* option # */
73 #define SAVE_OPT 15 /* option # */
74
75 /*** Limits. ***/
76 #define SPEED_LIMIT 256
77 #define REVERB_LIMIT 15
78 #define STEREO_LIMIT 128
79 #define TEMPO_LIMIT 256
80 #define BPM_LIMIT 256
81 #define GENVOL_LIMIT 128
82 #define MODVOL_LIMIT 256
83 #define REALVOL_LIMIT 65535
84 #define MIXVOL_LIMIT 25700
85 #define BASS_LIMIT 256
86 #define TREBLE_LIMIT 256
87
88 #define MAX_FILES 16384
89
90 /*** Message IDs ***/
91 #define ERROR_MSG 1
92 #define INFO_MSG 2
93
94 /*** Keys. ***/
95 #undef KEY_TAB
96 #define KEY_TAB 9
97
98 #undef KEY_ENTER
99 #define KEY_ENTER 10
100
101 #undef KEY_DELETE
102 #define KEY_DELETE 330
103
104 #undef KEY_BACKSPACE
105 #define KEY_BACKSPACE 263
106
107 #undef KEY_ESCAPE
108 #define KEY_ESCAPE 27
109
110 #undef KEY_SPACE
111 #define KEY_SPACE 0
112
113 /*** Windows coords. ***/
114 #define AC_W 68
115 #define AC_H 16
116 int AC_X;
117 int AC_Y; /* all channels window */
118
119 #define VFREQ_W 68
120 #define VFREQ_H 16
121 int VFREQ_X;
122 int VFREQ_Y; /* all channels window */
123
124 #define VPOS_W 68
125 #define VPOS_H 16
126 int VPOS_X;
127 int VPOS_Y; /* voices position window */
128
129 #define FS_W 60
130 #define FS_H (LINES-3)
131 int FS_X;
132 int FS_Y; /* file selector window */
133
134 #define PL_W 72
135 #define PL_H (LINES-2)
136 int PL_X;
137 int PL_Y; /* playlist window */
138
139 #define EFT_W 40
140 #define EFT_H EFFECTS+4
141 int EFT_X;
142 int EFT_Y; /* effect window */
143
144 #define OPT_W 40
145 #define OPT_H OPTIONS+8
146 int OPT_X;
147 int OPT_Y; /* options window */
148
149 #define SMP_W 54
150 #define SMP_H 15
151 int SMP_X;
152 int SMP_Y; /* samples window */
153
154 #define INS_W 54
155 #define INS_H 13
156 int INS_X;
157 int INS_Y; /* instruments window */
158
159 #define DSP_X 0
160 #define DSP_Y 0
161 int DSP_W;
162 int DSP_H; /* display window */
163
164 #define HELP_H 20
165 #define HELP_W 70
166 int HELP_X;
167 int HELP_Y; /* help window */
168
169 /*** Colors. ***/
170 #define WHITE 0
171 #define RED 1
172 #define GREEN 2
173 #define BLUE 3
174 #define YELLOW 4
175 #define CYAN 5
176 #define MAGENTA 6
177 #define BLUE_BLUE 7
178 #define CYAN_BLUE 8
179 #define GREEN_BLUE 9
180 #define YELLOW_BLUE 10
181 #define MAGENTA_MAGENTA 11
182 #define CYAN_CYAN 12
183 #define RED_RED 13
184 #define WHITE_RED 14
185
186
187 /******************************************************************************
188 ***
189 *** Global variables.
190 ***
191 ******************************************************************************/
192
193 /*** Various. ***/
194 int pos = 0; /* current position */
195 int page = 0; /* vertical page */
196 int gauge_style = 1; /* block */
197
198 int curch = 0; /* current channel number */
199 int oldcurch = 0; /* last channel number */
200 chtype oldc1, oldc2; /* previous characters (pointer) */
201
202 MODULE *mod = NULL; /* current module */
203
204 int DELAY = 40; /* screen refresh delay */
205
206 /*** Mixer. ***/
207 char *mixerdev = "/dev/mixer"; /* mixer device */
208 int mixerfd = 0; /* mixer file descriptor */
209 int mixerok = 0; /* set to 1 of open succeeds */
210 int treble = 0;
211 int bass = 0;
212 int mixvol = 0;
213
214 /*** Options. ***/
215 char _16bits = 1;
216 char stereo = 1;
217 char surround = 1;
218 char hq_mixer = 1;
219 char loop_module = 0; /* yes by default in MikMod */
220 char fade_module = 0;
221 char random_mode = 0;
222 char reverse_stereo = 0;
223 char interpolate = 0;
224
225 /*** Flags. ***/
226 char stopped = 0; /* set to 1 when module stooped */
227 char in_playlist = 0; /* set to 1 when playlist */
228 char output = 1; /* used for muting all channels */
229 char playing = 0; /* 1 playing module, 0 not playing */
230 char real_volume = 1; /* real volume display switch */
231 char ptn_view = 0; /* pattern view */
232
233 /*** Paths and names. ***/
234 char option_file[NAME_MAX+1]; /* option file path */
235
236 char moddir[NAME_MAX+1]; /* module directory */
237 char full_modname[NAME_MAX+1]; /* full module path */
238 char *short_modname; /* module name only */
239
240 char pl_file[NAME_MAX+1]; /* playlist file */
241
242 /*** Channels info arrays. ***/
243 int lastvol[MAX_CHANNELS]; /* last volume of each channel */
244 int maxvol[MAX_CHANNELS]; /* max channels volume */
245 int maxrvol[MAX_CHANNELS]; /* max channels real volume */
246 int maxfreq[MAX_CHANNELS]; /* max channels frequency */
247 int maxpos[MAX_CHANNELS]; /* max channels frequency */
248 char muted[MAX_CHANNELS]; /* keep channels mute status */
249 int maxrvoli;
250
251 /*** Current file size in bytes and KB. ***/
252 int file_sizeb;
253 float file_size;
254
255 /*** Windows. ***/
256 WINDOW *dspwin;
257 PANEL *dsppan;
258
259 WINDOW *eftwin;
260 PANEL *eftpan;
261
262 WINDOW *optwin;
263 PANEL *optpan;
264
265 WINDOW *acwin;
266 PANEL *acpan;
267
268 WINDOW *vposwin;
269 PANEL *vpospan;
270
271 WINDOW *vfreqwin;
272 PANEL *vfreqpan;
273
274 WINDOW *poswin;
275 PANEL *pospan;
276
277 WINDOW *helpwin;
278 PANEL *helppan;
279
280 WINDOW *smpwin;
281 PANEL *smppan;
282
283 WINDOW *inswin;
284 PANEL *inspan;
285
286 WINDOW *fswin;
287 PANEL *fspan;
288
289 WINDOW *plwin;
290 PANEL *plpan;
291
292
293 /******************************************************************************
294 ***
295 *** Prototypes.
296 ***
297 ******************************************************************************/
298
299 /* Used once. */
300 static void init_nc(void); /* init ncurses */
301 static void init_windows(void); /* init windows */
302 static void init_sound(void); /* init mikmod */
303 static void leave(int ignored); /* leave cleanly */
304
305 /* Get voice information. */
306 static inline int get_voice_volume(int channel);
307 static inline int get_voice_realvol(int channel);
308 static inline int get_voice_panning(int channel);
309 static inline int get_voice_freq(int channel);
310 static inline int get_voice_pos(int channel);
311 static inline int get_channel_period(int channel);
312
313 /* Module related. */
314 static int play_module(char *modname);
315 void module_control(int c);
316 static void do_pause(void);
317 static void do_stop(void);
318
319 /* Windows. */
320 static void options(void);
321 static void effects(void);
322
323 /* Info. */
324 static void refresh_driver_info(void);
325 static void refresh_info(void);
326 static void refresh_module_info(void);
327 static void refresh_legend(void);
328 static void refresh_pl_info(void);
329
330 /* Utils. */
331 static void draw_pointer(void);
332 static void draw_gauge(WINDOW *win, int x, int y, int pc, int vh, int style);
333 static void get_string(WINDOW *win, int ys, int xs, char *prompt, char *str);
334 static char *file_select(void);
335 static void mp_move_panel(PANEL *pan);
336 static void message(char *msg, int level);
337
338
339 /******************************************************************************
340 ***
341 *** Functions.
342 ***
343 ******************************************************************************/
344
345 /*** . ***/
dot(void)346 static void dot(void)
347 {
348 printf(".");
349 }
350
351 /*** Initialize ncurses and colors. ***/
init_nc(void)352 static void init_nc(void)
353 {
354 /* Init ncurses. */
355 if ((initscr()) == NULL) {
356 fprintf(stderr, "MP: Can't init ncurses.\n");
357 exit(-1);
358 }
359
360 /* Set display (main) window dimensions. */
361 DSP_W = COLS;
362 DSP_H = LINES;
363
364 /* Set window options. */
365 cbreak();
366 noecho();
367 timeout(DELAY);
368 curs_set(0);
369 keypad(stdscr, TRUE);
370
371 /* Init colors. */
372 if ((has_colors()) == FALSE) {
373 endwin();
374 fprintf(stderr, "mp: Terminal doesn't support colors.\n");
375 exit(-1);
376 }
377 start_color();
378
379 init_pair(RED, COLOR_RED, COLOR_BLACK);
380 init_pair(GREEN, COLOR_GREEN, COLOR_BLACK);
381 init_pair(BLUE, COLOR_BLUE, COLOR_BLACK);
382 init_pair(YELLOW, COLOR_YELLOW, COLOR_BLACK);
383 init_pair(CYAN, COLOR_CYAN, COLOR_BLACK);
384 init_pair(MAGENTA, COLOR_MAGENTA, COLOR_BLACK);
385
386 init_pair(BLUE_BLUE, COLOR_BLUE, COLOR_BLUE);
387 init_pair(CYAN_BLUE, COLOR_CYAN, COLOR_BLUE);
388 init_pair(GREEN_BLUE, COLOR_GREEN, COLOR_BLUE);
389 init_pair(YELLOW_BLUE, COLOR_YELLOW, COLOR_BLUE);
390 init_pair(MAGENTA_MAGENTA, COLOR_MAGENTA, COLOR_MAGENTA);
391 init_pair(CYAN_CYAN, COLOR_CYAN, COLOR_CYAN);
392 init_pair(RED_RED, COLOR_RED, COLOR_RED);
393 init_pair(WHITE_RED, COLOR_WHITE, COLOR_RED);
394
395 /* Calculate default windows coords. */
396 AC_X = ((COLS/2)-(AC_W/2));
397 AC_Y = ((LINES/2)-(AC_H/2)); /* all channels window */
398
399 VFREQ_X = ((COLS/2)-(VFREQ_W/2));
400 VFREQ_Y = ((LINES/2)-(VFREQ_H/2)); /* voices frequency */
401
402 VPOS_X = ((COLS/2)-(VPOS_W/2));
403 VPOS_Y = ((LINES/2)-(VPOS_H/2)); /* voices position */
404
405 FS_X = ((COLS/2)-(FS_W/2));
406 FS_Y = ((LINES/2)-(FS_H/2)); /* file selector window */
407
408 PL_X = ((COLS/2)-(PL_W/2));
409 PL_Y = ((LINES/2)-(PL_H/2)); /* playlist window */
410
411 EFT_X = ((COLS/2)-(EFT_W/2));
412 EFT_Y = ((LINES/2)-(EFT_H/2)); /* effect window */
413
414 OPT_X = ((COLS/2)-(OPT_W/2));
415 OPT_Y = ((LINES/2)-(OPT_H)/2); /* options window */
416
417 SMP_X = ((COLS/2)-(SMP_W)/2);
418 SMP_Y = ((LINES/2)-(SMP_H/2)); /* samples window */
419
420 INS_X = ((COLS/2)-(INS_W)/2);
421 INS_Y = ((LINES/2)-(INS_H/2)); /* instruments window */
422
423 HELP_X = ((COLS/2)-(HELP_W)/2);
424 HELP_Y = ((LINES/2)-(HELP_H/2)); /* help window */
425 }
426
427 /*** Initialize windows. ***/
init_windows(void)428 static void init_windows(void)
429 {
430 dspwin = newwin(DSP_H, DSP_W, DSP_Y, DSP_X);
431 wtimeout(dspwin, DELAY);
432 keypad(dspwin, TRUE);
433 leaveok(dspwin, TRUE);
434 box(dspwin, 0, 0);
435 refresh_legend();
436
437 dsppan = new_panel(dspwin);
438
439 wattrset(dspwin, COLOR_PAIR(GREEN_BLUE)|A_BOLD);
440 mvwprintw(dspwin, 0, 0, "%80s", "Press 'h' for help ");
441 wattrset(dspwin, COLOR_PAIR(CYAN_BLUE)|A_BOLD);
442 mvwprintw(dspwin, 0, 0, " :: MP v%s ::", VERSION);
443
444 update_panels();
445 doupdate();
446 }
447
448 /*** Initialize MikMod. ***/
init_sound(void)449 static void init_sound(void)
450 {
451 /* Register loaders and drivers. */
452 MikMod_RegisterAllDrivers();
453 MikMod_RegisterAllLoaders();
454
455 /* Set options. */
456 if (_16bits == 1)
457 md_mode |= DMODE_16BITS;
458 else
459 md_mode &= ~DMODE_16BITS;
460
461 if (stereo == 1)
462 md_mode |= DMODE_STEREO;
463 else
464 md_mode &= ~DMODE_STEREO;
465
466 if (reverse_stereo == 1)
467 md_mode |= DMODE_REVERSE;
468 else
469 md_mode &= ~DMODE_REVERSE;
470
471 if (interpolate == 1)
472 md_mode |= DMODE_INTERP;
473 else
474 md_mode &= ~DMODE_INTERP;
475
476 if (surround == 1)
477 md_mode |= DMODE_SURROUND;
478 else
479 md_mode &= ~DMODE_SURROUND;
480
481 if (hq_mixer == 1)
482 md_mode |= DMODE_HQMIXER;
483 else
484 md_mode &= ~DMODE_HQMIXER;
485
486 /* Initialize MikMod. */
487 if (MikMod_Init("")) {
488 fprintf(stderr, "\nMP: Couln't initialize sound, reason: %s.\n",
489 MikMod_strerror(MikMod_errno));
490 fprintf(stderr, " Verify settings in $HOME/.mp/options\n");
491 exit(-1);
492 }
493
494 /* Open mixer (for volume, treble and bass). */
495 if ((mixerfd = open(mixerdev, O_RDWR)) == -1)
496 mixerok = 0;
497 else
498 mixerok = 1;
499
500 ioctl(mixerfd, MIXER_READ(SOUND_MIXER_VOLUME), &mixvol);
501 ioctl(mixerfd, MIXER_READ(SOUND_MIXER_BASS), &bass);
502 ioctl(mixerfd, MIXER_READ(SOUND_MIXER_TREBLE), &treble);
503 }
504
505 /*** Close everything. ***/
leave(int ignored)506 static void leave(int ignored)
507 {
508 /* Close mixer. */
509 if (mixerok)
510 close(mixerfd);
511
512 /* Close MikMod. */
513 if (mod)
514 Player_Free(mod);
515 MikMod_Exit();
516
517 /* Close ncurses. */
518 endwin();
519
520 /* Exit... */
521 printf(":: MP v%s ::\n", VERSION); /* ;) */
522
523 exit(0);
524 }
525
526 /*** About window. ***/
about(void)527 static void about(void)
528 {
529 WINDOW *tmpwin;
530 PANEL *tmppan;
531
532 tmpwin = newwin(14, 40, (LINES/2)-6, (COLS/2)-20);
533 wtimeout(tmpwin, DELAY);
534 keypad(tmpwin, TRUE);
535 tmppan = new_panel(tmpwin);
536 box(tmpwin, 0, 0);
537
538 wattrset(tmpwin, COLOR_PAIR(CYAN)|A_BOLD);
539 mvwprintw(tmpwin, 2, 12, ":: ");
540 wattrset(tmpwin, COLOR_PAIR(GREEN)|A_BOLD);
541 wprintw(tmpwin, "About ");
542 wattrset(tmpwin, COLOR_PAIR(BLUE)|A_BOLD);
543 wprintw(tmpwin, "MP ");
544 wattrset(tmpwin, COLOR_PAIR(CYAN)|A_BOLD);
545 wprintw(tmpwin, "::");
546 wattrset(tmpwin, COLOR_PAIR(CYAN)|A_BOLD);
547 mvwprintw(tmpwin, 4, 8, "Copyright (c) 2003-2004");
548 wattrset(tmpwin, COLOR_PAIR(CYAN)|A_NORMAL);
549 mvwprintw(tmpwin, 5, 4, "Gael Gence and Gregoire Welraeds");
550 wattrset(tmpwin, COLOR_PAIR(WHITE)|A_NORMAL);
551 mvwprintw(tmpwin, 8, 5, "mp.c v%s (280104): 5984 lines", VERSION);
552 wattrset(tmpwin, COLOR_PAIR(BLUE)|A_BOLD);
553 mvwprintw(tmpwin, 11, 11, "http:");
554 wattrset(tmpwin, COLOR_PAIR(CYAN)|A_BOLD);
555 mvwprintw(tmpwin, 11, 16, "// /");
556 wattrset(tmpwin, COLOR_PAIR(YELLOW)|A_BOLD);
557 mvwprintw(tmpwin, 11, 18, "mp.waw.cx");
558
559 while ((wgetch(tmpwin)) != 'q') {
560 if (mod && playing) {
561 refresh_info();
562 refresh_module_info();
563 update_panels();
564 doupdate();
565 MikMod_Update();
566 }
567 }
568
569 del_panel(tmppan);
570 delwin(tmpwin);
571 }
572
573 /******************************************************************************/
574
575 /*** Get voice volume. ***/
get_voice_volume(int channel)576 static inline int get_voice_volume(int channel)
577 {
578 int i;
579
580 i = Voice_GetVolume(channel);
581
582 if (maxvol[channel] < i)
583 maxvol[channel] = i;
584
585 return i;
586 }
587
588 /*** Get playing volume. ***/
get_voice_realvol(int channel)589 static inline int get_voice_realvol(int channel)
590 {
591 int i;
592
593 i = Voice_RealVolume(channel);
594
595 if (maxrvol[channel] < i)
596 maxrvol[channel] = i;
597
598 if (maxrvoli < i)
599 maxrvoli = i;
600
601 return i;
602 }
603
604 /*** Get voice panning. ***/
get_voice_panning(int channel)605 static inline int get_voice_panning(int channel)
606 {
607 return(Voice_GetPanning(channel));
608 }
609
610 /*** Get voice frequency. ***/
get_voice_freq(int channel)611 static inline int get_voice_freq(int channel)
612 {
613 int i;
614
615 i = Voice_GetFrequency(channel);
616 if (maxfreq[channel] < i)
617 maxfreq[channel] = i;
618
619 return i;
620 }
621
622 /*** Get voice position. ***/
get_voice_pos(int channel)623 static inline int get_voice_pos(int channel)
624 {
625 int i;
626
627 i = Voice_GetPosition(channel);
628 if (maxpos[channel] < i)
629 maxpos[channel] = i;
630
631 return i;
632 }
633
634 /*** Get channel period. ***/
get_channel_period(int channel)635 static inline int get_channel_period(int channel)
636 {
637 return(Player_GetChannelPeriod(channel));
638 }
639
640 /*** Get channel voice. ***/
get_channel_voice(int channel)641 static inline int get_channel_voice(int channel)
642 {
643 return(Player_GetChannelVoice(channel));
644 }
645
646 /*****************************************************************************/
647
648 /*** Show module info. ***/
649 #define CMT_H 21
650 #define CMT_W 73
651 int CMT_X;
652 int CMT_Y;
653
module_info(MODULE * mod)654 static void module_info(MODULE *mod)
655 {
656 int i;
657 int c;
658 int x, y, cnt, len, xoff = 0;
659 WINDOW *tmpwin, *minfowin;
660 PANEL *minfopan;
661
662 if (mod == NULL)
663 return;
664
665 if (mod->comment == NULL) {
666 message("No comment in this module.", INFO_MSG);
667 return;
668 }
669
670 CMT_X = ((COLS/2)-(CMT_W/2));
671 CMT_Y = ((LINES/2)-(CMT_H/2));
672
673 tmpwin = newwin(CMT_H, CMT_W, CMT_Y, CMT_X);
674 if (tmpwin == NULL)
675 return;
676 wtimeout(tmpwin, DELAY);
677 keypad(tmpwin, TRUE);
678 box(tmpwin, 0, 0);
679 mvwprintw(tmpwin, 0, 2, "[ ]");
680 wattrset(tmpwin, COLOR_PAIR(YELLOW)|A_BOLD);
681 mvwprintw(tmpwin, 0, 4, "Comment");
682 wattrset(tmpwin, A_NORMAL);
683
684 minfopan = new_panel(tmpwin);
685 minfowin = subwin(tmpwin, CMT_H-2, CMT_W-2, CMT_Y+1, CMT_X+1);
686
687 wattrset(minfowin, COLOR_PAIR(CYAN)|A_NORMAL);
688 cnt = 0;
689 len = strlen(mod->comment);
690 for (y = 0; y < CMT_H; y++) {
691 if (y == CMT_H-1 && xoff == 0) {
692 for (i = 0; i < CMT_H-2; i++) {
693 wattrset(minfowin, COLOR_PAIR(WHITE)|A_NORMAL);
694 mvwaddch(minfowin, i, 34, '|');
695 wattrset(minfowin, COLOR_PAIR(CYAN)|A_NORMAL);
696 }
697 y = 0;
698 xoff = 36;
699 }
700 for (x = 0; x < (CMT_W/2)-3; x++, cnt++) {
701 if (cnt >= len) break;
702 mvwaddch(minfowin, y, x + xoff, mod->comment[cnt]);
703 }
704 }
705
706 /*** Loop ***/
707 while ((c = wgetch(tmpwin)) != 'q') {
708 module_control(c);
709
710 if (mod && playing) {
711 refresh_info();
712 refresh_module_info();
713 update_panels();
714 doupdate();
715 MikMod_Update();
716 }
717 }
718
719 del_panel(minfopan);
720 delwin(minfowin);
721 }
722
723 /*** Load and start module. ***/
play_module(char * modname)724 static int play_module(char *modname)
725 {
726 int i;
727 struct stat sbuf;
728 char buf[NAME_MAX+1];
729 MODULE *new;
730
731 /* Check file. */
732 if (access(modname, R_OK) != 0) {
733 /* Avoid core dump if file can't be read. */
734 playing = 0;
735 beep();
736 message("File can't be read.", ERROR_MSG);
737 return -1;
738 }
739
740 stat(modname, &sbuf);
741 if (S_ISREG(sbuf.st_mode) == 0) {
742 playing = 0;
743 beep();
744 message("Not a file.", ERROR_MSG);
745 return -1;
746 }
747
748 file_size = (((float) (sbuf.st_size)) / 1024.0);
749 file_sizeb = sbuf.st_size;
750 if ((short_modname = rindex(modname, '/')) != NULL)
751 short_modname++;
752 else
753 short_modname = modname;
754
755 /* Load module. */
756 new = Player_Load(modname, MAX_CHANNELS, 0);
757 if (new != NULL) {
758 if (mod != NULL)
759 Player_Free(mod);
760 mod = new;
761
762 wattrset(dspwin, COLOR_PAIR(WHITE)|A_NORMAL);
763 for (i = 1; i < COLS-2; i++)
764 mvwaddch(dspwin, TITLE_Y, i, ' ');
765
766 wattrset(dspwin, COLOR_PAIR(WHITE)|A_BOLD);
767 mvwprintw(dspwin, 2, 1, "Title : ");
768 wattrset(dspwin, COLOR_PAIR(CYAN)|A_NORMAL);
769 wprintw(dspwin, strlen(mod->songname) > 0 ?
770 mod->songname : "");
771
772 wattrset(dspwin, COLOR_PAIR(WHITE)|A_NORMAL);
773 wprintw(dspwin, " - " );
774 wattrset(dspwin, COLOR_PAIR(WHITE)|A_BOLD);
775 wprintw(dspwin, "Type: ");
776 wattrset(dspwin, COLOR_PAIR(CYAN|A_NORMAL));
777 wprintw(dspwin, strlen(mod->modtype) > 0 ?
778 mod->modtype : "");
779
780 } else {
781 beep();
782 sprintf(buf, "%s.", MikMod_strerror(MikMod_errno));
783 message(buf, ERROR_MSG);
784 return -1;
785 }
786 curch = 0;
787 memset(muted, 0, sizeof(muted));
788
789 refresh_module_info();
790 refresh_info();
791 draw_pointer();
792
793 /* Start the module. */
794 if (mod != NULL) {
795 pos = 0;
796 mod->loop = loop_module;
797 mod->fadeout = fade_module;
798 for (i = 0; i < MAX_CHANNELS; maxvol[i] = MODVOL_LIMIT, i++);
799
800 wattrset(dspwin, COLOR_PAIR(WHITE)|A_NORMAL);
801 for (i = 1; i < COLS-2; i++)
802 mvwaddch(dspwin, FILE_Y, i, ' ');
803
804 wattrset(dspwin, COLOR_PAIR(WHITE)|A_BOLD);
805 mvwprintw(dspwin, FILE_Y, 1, "File : ");
806 wattrset(dspwin, COLOR_PAIR(WHITE)|A_NORMAL);
807 wprintw(dspwin, "%s [ %d smp, %d ins, %d bytes, %.1f KB ]",
808 short_modname,
809 mod->numsmp,
810 mod->numins,
811 file_sizeb,
812 file_size);
813
814 wnoutrefresh(dspwin);
815 doupdate();
816
817 Player_Start(mod);
818 playing = 1;
819 }
820
821 return 0;
822 }
823
824 /*** Pause the module. ***/
do_pause(void)825 static void do_pause(void)
826 {
827 int c;
828 WINDOW *tmpwin;
829
830 if (mod && playing) {
831 tmpwin = newwin(5, 13, (LINES/2)-4, 34);
832 box(tmpwin, 0, 0);
833 wattrset(tmpwin, (COLOR_PAIR(YELLOW)|A_BOLD));
834 mvwprintw(tmpwin, 2, 2, "Paused...");
835
836 Player_TogglePause();
837
838 wnoutrefresh(tmpwin);
839 doupdate();
840
841 while ((c = wgetch(tmpwin)) != 'p');
842
843 Player_Start(mod);
844 playing = 1;
845
846 delwin(tmpwin);
847 touchwin(dspwin);
848 doupdate();
849
850 } else {
851 Player_Start(mod);
852 playing = 1;
853 }
854 }
855
856 /*** Pause the module. ***/
do_stop(void)857 static void do_stop(void)
858 {
859 WINDOW *tmpwin;
860
861 tmpwin = newwin(5, 15, (LINES/2)-4, 34);
862 box(tmpwin, 0, 0);
863 wattrset(tmpwin, (COLOR_PAIR(RED)|A_BOLD));
864 mvwprintw(tmpwin, 2, 2, "Stopping...");
865 wnoutrefresh(tmpwin);
866 doupdate();
867
868 Player_SetPosition(0);
869 Player_Stop();
870 stopped = 1;
871 playing = 0;
872 mod->patpos = 0;
873
874 usleep(500000);
875
876 delwin(tmpwin);
877 touchwin(dspwin);
878 doupdate();
879 }
880
881 /*****************************************************************************/
882
883 /***
884 *** Options window.
885 ***/
886 char *options_strings[OPTIONS+4] = {
887 "16bit",
888 "Stereo",
889 "Reverse stereo",
890 "Surround",
891 "Interpolate",
892 "",
893 "High quality mixer",
894 "Mixing frequency",
895 "",
896 "Loop module",
897 "Fadeout module",
898 "Random mode (playlist)",
899 "",
900 "Refresh delay",
901 "",
902 "Save options"
903 };
904
905 /*** Print option and status. ***/
print_opt(WINDOW * win,int opt)906 static void print_opt(WINDOW *win, int opt)
907 {
908 int c;
909
910 if (opt == MIXFREQ_OPT) {
911 mvwprintw(win, opt+2, 3, " %s [ %5d ] ",
912 options_strings[opt], md_mixfreq);
913
914 } else if (opt == DELAY_OPT) {
915 mvwprintw(win, opt+2, 3, " %s [ %5d ] ",
916 options_strings[opt], DELAY);
917
918 } else if (opt == SAVE_OPT) {
919 mvwprintw(win, opt+2, 3, " %s ", options_strings[opt]);
920
921 } else {
922 if (opt == HQMIXER_OPT && hq_mixer)
923 c = 'X';
924 else if (opt == _16BITS_OPT && _16bits)
925 c = 'X';
926 else if (opt == STEREO_OPT && stereo)
927 c = 'X';
928 else if (opt == REVSTEREO_OPT && reverse_stereo)
929 c = 'X';
930 else if (opt == SURROUND_OPT && surround)
931 c = 'X';
932 else if (opt == INTERPOLATE_OPT && interpolate)
933 c = 'X';
934
935 else if (opt == LOOP_OPT && loop_module)
936 c = 'X';
937 else if (opt == FADE_OPT && fade_module)
938 c = 'X';
939 else if (opt == RANDOM_OPT && random_mode)
940 c = 'X';
941 else
942 c = ' ';
943
944 mvwprintw(win, opt+2, 3, " [%c] %s ",
945 c, options_strings[opt]);
946 }
947 }
948
949 /*** Get mix frequency from user. ***/
get_mix_freq(WINDOW * win)950 static void get_mix_freq(WINDOW *win)
951 {
952 int c;
953 int freq = md_mixfreq;
954
955 while ((c = wgetch(win)) != KEY_ENTER) {
956 switch (c) {
957 case ERR: break;
958
959 case KEY_RIGHT:
960 if (freq*2 < MAX_FREQ)
961 freq *= 2;
962 else
963 freq = MAX_FREQ;
964 break;
965
966 case KEY_LEFT:
967 if (freq/2 > MIN_FREQ)
968 freq /= 2;
969 else
970 freq = MIN_FREQ;
971 break;
972
973 case KEY_UP:
974 if (freq < MAX_FREQ)
975 freq++;
976 break;
977 case KEY_PPAGE:
978 if (freq+100 <= MAX_FREQ)
979 freq += 100;
980 break;
981
982 case KEY_DOWN:
983 if (freq > MIN_FREQ)
984 freq--;
985 break;
986 case KEY_NPAGE:
987 if (freq-100 >= MIN_FREQ)
988 freq -= 100;
989 break;
990 }
991
992 wattrset(win, A_NORMAL);
993 mvwprintw(win, MIXFREQ_OPT+2, 3, " %s [ ] ",
994 options_strings[MIXFREQ_OPT]);
995 wattrset(win, A_REVERSE);
996 mvwprintw(win, MIXFREQ_OPT+2, 24, " %5d ", freq);
997
998 if (mod && playing) {
999 refresh_info();
1000 refresh_module_info();
1001 update_panels();
1002 doupdate();
1003 MikMod_Update();
1004 }
1005 }
1006
1007 md_mixfreq = freq;
1008 refresh_driver_info();
1009 }
1010
1011 /*** Get DELAY from user. ***/
get_delay(WINDOW * win)1012 static void get_delay(WINDOW *win)
1013 {
1014 int c;
1015 int delay = DELAY;
1016
1017 while ((c = wgetch(win)) != KEY_ENTER) {
1018 switch (c) {
1019 case ERR: break;
1020
1021 case KEY_RIGHT:
1022 if (delay*2 < 10000)
1023 delay *= 2;
1024 else
1025 delay = 10000;
1026 break;
1027
1028 case KEY_LEFT:
1029 if (delay/2 > 0)
1030 delay /= 2;
1031 else
1032 delay = 0;
1033 break;
1034
1035 case KEY_UP:
1036 if (delay < 10000)
1037 delay++;
1038 break;
1039 case KEY_PPAGE:
1040 if (delay+5 <= 10000)
1041 delay += 5;
1042 break;
1043
1044 case KEY_DOWN:
1045 if (delay > 0)
1046 delay--;
1047 break;
1048 case KEY_NPAGE:
1049 if (delay-5 >= 0)
1050 delay -= 5;
1051 break;
1052 }
1053
1054 wattrset(win, A_NORMAL);
1055 mvwprintw(win, DELAY_OPT+2, 3, " %s [ ] ",
1056 options_strings[DELAY_OPT]);
1057 wattrset(win, A_REVERSE);
1058 mvwprintw(win, DELAY_OPT+2, 21, " %5d ", delay);
1059
1060 if (mod && playing) {
1061 refresh_info();
1062 refresh_module_info();
1063 update_panels();
1064 doupdate();
1065 MikMod_Update();
1066 }
1067 }
1068
1069 DELAY = delay;
1070 }
1071
1072 /*** Read options file. ***/
read_options_file(void)1073 static void read_options_file(void)
1074 {
1075 int cnt;
1076 FILE *f;
1077 char c;
1078 char fixed_path[NAME_MAX+1];
1079 char buf[NAME_MAX+1];
1080 char *ptr1;
1081
1082 sprintf(fixed_path, "%s/%s", (getenv("HOME")), ".mp/options");
1083 if ((f = fopen(fixed_path, "r")) == NULL)
1084 return;
1085
1086 cnt = 0;
1087 memset(buf, 0, NAME_MAX);
1088 while ((fread(&c, 1, 1, f)) > 0) {
1089 if (c != '\n') {
1090 buf[cnt++] = c;
1091 continue;
1092 }
1093
1094 /* 16bits. */
1095 if (!(strncmp(buf, "16bits", 5))) {
1096 ptr1 = rindex(buf, '=');
1097 ptr1++;
1098 if (atoi(ptr1)) {
1099 _16bits=1;
1100 } else {
1101 _16bits=0;
1102 }
1103
1104 /* Stereo. */
1105 } else if (!(strncmp(buf, "stereo", 6))) {
1106 ptr1 = rindex(buf, '=');
1107 ptr1++;
1108 if (atoi(ptr1)) {
1109 stereo=1;
1110 } else {
1111 stereo=0;
1112 }
1113
1114 /* Reverse stereo. */
1115 } else if (!(strncmp(buf, "reverse_stereo", 14))) {
1116 ptr1 = rindex(buf, '=');
1117 ptr1++;
1118 if (atoi(ptr1)) {
1119 reverse_stereo=1;
1120 } else {
1121 reverse_stereo=0;
1122 }
1123
1124 /* Surround. */
1125 } else if (!(strncmp(buf, "surround", 8))) {
1126 ptr1 = rindex(buf, '=');
1127 ptr1++;
1128 if (atoi(ptr1)) {
1129 surround=1;
1130 } else {
1131 surround=0;
1132 }
1133
1134 /* Interpolate. */
1135 } else if (!(strncmp(buf, "interpolate", 11))) {
1136 ptr1 = rindex(buf, '=');
1137 ptr1++;
1138 if ((atoi(ptr1)) == 1) {
1139 interpolate=1;
1140 } else {
1141 interpolate=0;
1142 }
1143
1144 /* HQ mixer. */
1145 } else if (!(strncmp(buf, "hq_mixer", 8))) {
1146 ptr1 = rindex(buf, '=');
1147 ptr1++;
1148 if ((atoi(ptr1)) == 1) {
1149 hq_mixer=1;
1150 } else {
1151 hq_mixer=0;
1152 }
1153
1154 /* Loop module. */
1155 } else if (!(strncmp(buf, "loop_module", 11))) {
1156 ptr1 = rindex(buf, '=');
1157 ptr1++;
1158 if ((atoi(ptr1)) == 1) {
1159 loop_module=1;
1160 } else {
1161 loop_module=0;
1162 }
1163
1164 /* Fadeout module. */
1165 } else if (!(strncmp(buf, "fade_module", 11))) {
1166 ptr1 = rindex(buf, '=');
1167 ptr1++;
1168 if ((atoi(ptr1)) == 1) {
1169 fade_module=1;
1170 } else {
1171 fade_module=0;
1172 }
1173
1174 /* Random mode (playlist). */
1175 } else if (!(strncmp(buf, "random_mode", 11))) {
1176 ptr1 = rindex(buf, '=');
1177 ptr1++;
1178 if (atoi(ptr1)) {
1179 random_mode=1;
1180 } else {
1181 random_mode=0;
1182 }
1183
1184 /* Screen refresh delay. */
1185 } else if (!(strncmp(buf, "delay", 5))) {
1186 ptr1 = rindex(buf, '=');
1187 ptr1++;
1188 DELAY = atoi(ptr1);
1189
1190 /*** Windows coords. ***/
1191 } else if (!(strncmp(buf, "AC_X", 4))) {
1192 ptr1 = rindex(buf, '=');
1193 ptr1++;
1194 AC_X=atoi(ptr1);
1195 } else if (!(strncmp(buf, "AC_Y", 4))) {
1196 ptr1 = rindex(buf, '=');
1197 ptr1++;
1198 AC_Y=atoi(ptr1);
1199
1200 } else if (!(strncmp(buf, "VFREQ_X", 7))) {
1201 ptr1 = rindex(buf, '=');
1202 ptr1++;
1203 VFREQ_X=atoi(ptr1);
1204 } else if (!(strncmp(buf, "VFREQ_Y", 7))) {
1205 ptr1 = rindex(buf, '=');
1206 ptr1++;
1207 VFREQ_Y=atoi(ptr1);
1208
1209 } else if (!(strncmp(buf, "VPOS_X", 6))) {
1210 ptr1 = rindex(buf, '=');
1211 ptr1++;
1212 VPOS_X=atoi(ptr1);
1213 } else if (!(strncmp(buf, "VPOS_Y", 6))) {
1214 ptr1 = rindex(buf, '=');
1215 ptr1++;
1216 VPOS_Y=atoi(ptr1);
1217
1218 } else if (!(strncmp(buf, "OPT_X", 5))) {
1219 ptr1 = rindex(buf, '=');
1220 ptr1++;
1221 OPT_X=atoi(ptr1);
1222 } else if (!(strncmp(buf, "OPT_Y", 5))) {
1223 ptr1 = rindex(buf, '=');
1224 ptr1++;
1225 OPT_Y=atoi(ptr1);
1226
1227 } else if (!(strncmp(buf, "EFT_X", 5))) {
1228 ptr1 = rindex(buf, '=');
1229 ptr1++;
1230 EFT_X=atoi(ptr1);
1231 } else if (!(strncmp(buf, "EFT_Y", 5))) {
1232 ptr1 = rindex(buf, '=');
1233 ptr1++;
1234 EFT_Y=atoi(ptr1);
1235 }
1236
1237 cnt = 0;
1238 memset(buf, 0, NAME_MAX);
1239 }
1240
1241 /* Check coords. */
1242 if (EFT_Y+EFT_H >= LINES)
1243 EFT_Y = 2;
1244
1245 if (OPT_Y+OPT_H >= LINES)
1246 OPT_Y = 2;
1247
1248 if (VFREQ_Y+VFREQ_H >= LINES)
1249 VFREQ_Y = 2;
1250
1251 if (VPOS_Y+VPOS_H >= LINES)
1252 VPOS_Y = 2;
1253
1254 if (AC_Y+AC_H >= LINES)
1255 AC_Y = 2;
1256
1257 fclose(f);
1258 }
1259
1260 /*** Save options file. ***/
save_options_file(void)1261 static void save_options_file(void)
1262 {
1263 FILE *f;
1264 char fixed_path[NAME_MAX+1];
1265 char buf[NAME_MAX+1];
1266
1267 sprintf(fixed_path, "%s/%s", (getenv("HOME")), ".mp/options");
1268
1269 f = fopen(fixed_path, "w");
1270 if (f == NULL) {
1271 sprintf(buf, "Can't open '%s'.", fixed_path);
1272 message(buf, ERROR_MSG);
1273 return;
1274 }
1275
1276 /* 16bits. */
1277 if (_16bits) {
1278 sprintf(buf, "16bits=1\n");
1279 fwrite(buf, strlen(buf), 1, f);
1280 } else {
1281 sprintf(buf, "16bits=0\n");
1282 fwrite(buf, strlen(buf), 1, f);
1283 }
1284
1285 /* Stereo. */
1286 if (stereo) {
1287 sprintf(buf, "stereo=1\n");
1288 fwrite(buf, strlen(buf), 1, f);
1289 } else {
1290 sprintf(buf, "stereo=0\n");
1291 fwrite(buf, strlen(buf), 1, f);
1292 }
1293
1294 /* Stereo. */
1295 if (reverse_stereo) {
1296 sprintf(buf, "reverse_stereo=1\n");
1297 fwrite(buf, strlen(buf), 1, f);
1298 } else {
1299 sprintf(buf, "reverse_stereo=0\n");
1300 fwrite(buf, strlen(buf), 1, f);
1301 }
1302
1303 /* Surround. */
1304 if (surround) {
1305 sprintf(buf, "surround=1\n");
1306 fwrite(buf, strlen(buf), 1, f);
1307 } else {
1308 sprintf(buf, "surround=0\n");
1309 fwrite(buf, strlen(buf), 1, f);
1310 }
1311
1312 /* Interpolate. */
1313 if (interpolate) {
1314 sprintf(buf, "interpolate=1\n");
1315 fwrite(buf, strlen(buf), 1, f);
1316 } else {
1317 sprintf(buf, "interpolate=0\n");
1318 fwrite(buf, strlen(buf), 1, f);
1319 }
1320
1321 /* HQ/LQ mixer. */
1322 if (hq_mixer) {
1323 sprintf(buf, "hq_mixer=1\n");
1324 fwrite(buf, strlen(buf), 1, f);
1325 } else {
1326 sprintf(buf, "hq_mixer=0\n");
1327 fwrite(buf, strlen(buf), 1, f);
1328 }
1329
1330 /* Loop module. */
1331 if (loop_module) {
1332 sprintf(buf, "loop_module=1\n");
1333 fwrite(buf, strlen(buf), 1, f);
1334 } else {
1335 sprintf(buf, "loop_module=0\n");
1336 fwrite(buf, strlen(buf), 1, f);
1337 }
1338
1339 /* Fadeout module. */
1340 if (fade_module) {
1341 sprintf(buf, "fade_module=1\n");
1342 fwrite(buf, strlen(buf), 1, f);
1343 } else {
1344 sprintf(buf, "fade_module=0\n");
1345 fwrite(buf, strlen(buf), 1, f);
1346 }
1347
1348 /* Random mode. */
1349 if (random_mode) {
1350 sprintf(buf, "random_mode=1\n");
1351 fwrite(buf, strlen(buf), 1, f);
1352 } else {
1353 sprintf(buf, "random_mode=0\n");
1354 fwrite(buf, strlen(buf), 1, f);
1355 }
1356
1357 /* Screen refresh delay. */
1358 sprintf(buf, "delay=%d\n", DELAY);
1359 fwrite(buf, strlen(buf), 1, f);
1360
1361 /* Windows coords. */
1362 sprintf(buf, "AC_X=%d\n", AC_X);
1363 fwrite(buf, strlen(buf), 1, f);
1364 sprintf(buf, "AC_Y=%d\n", AC_Y);
1365 fwrite(buf, strlen(buf), 1, f);
1366
1367 sprintf(buf, "VPOS_X=%d\n", VPOS_X);
1368 fwrite(buf, strlen(buf), 1, f);
1369 sprintf(buf, "VPOS_Y=%d\n", VPOS_Y);
1370 fwrite(buf, strlen(buf), 1, f);
1371
1372 sprintf(buf, "VFREQ_X=%d\n", VFREQ_X);
1373 fwrite(buf, strlen(buf), 1, f);
1374 sprintf(buf, "VFREQ_Y=%d\n", VFREQ_Y);
1375 fwrite(buf, strlen(buf), 1, f);
1376
1377 sprintf(buf, "OPT_X=%d\n", OPT_X);
1378 fwrite(buf, strlen(buf), 1, f);
1379 sprintf(buf, "OPT_Y=%d\n", OPT_Y);
1380 fwrite(buf, strlen(buf), 1, f);
1381
1382 sprintf(buf, "EFT_X=%d\n", EFT_X);
1383 fwrite(buf, strlen(buf), 1, f);
1384 sprintf(buf, "EFT_Y=%d\n", EFT_Y);
1385 fwrite(buf, strlen(buf), 1, f);
1386
1387 fclose(f);
1388
1389 sprintf(buf, "'%s' saved.", fixed_path);
1390 message(buf, INFO_MSG);
1391 }
1392
1393 /*** Enter options window. ***/
options(void)1394 static void options(void)
1395 {
1396 int c, opt = 0;
1397 WINDOW *tmpwin;
1398
1399 optwin = tmpwin = newwin(OPT_H, OPT_W, OPT_Y, OPT_X);
1400 wtimeout(tmpwin, DELAY);
1401 keypad(tmpwin, TRUE);
1402 box(tmpwin, 0, 0);
1403 optpan = new_panel(tmpwin);
1404
1405 wattrset(tmpwin, COLOR_PAIR(WHITE)|A_NORMAL);
1406 mvwprintw(tmpwin, 0, 2, "[ ]");
1407 wattrset(tmpwin, COLOR_PAIR(YELLOW)|A_BOLD);
1408 mvwprintw(tmpwin, 0, 4, "Options");
1409
1410 /* Prepare display. */
1411 for (c = 0; c < OPTIONS+4; c++) {
1412 if (strlen(options_strings[c]) == 0) {
1413 mvwprintw(tmpwin, c+2, 1, "");
1414 continue;
1415 }
1416
1417 if (c == 0)
1418 wattrset(tmpwin, (COLOR_PAIR(WHITE)|A_REVERSE));
1419 else
1420 wattrset(tmpwin, (COLOR_PAIR(WHITE)|A_NORMAL));
1421
1422 print_opt(tmpwin, c);
1423 }
1424
1425 wnoutrefresh(tmpwin);
1426 doupdate();
1427
1428 /*** Loop. ***/
1429 while ((c = wgetch(tmpwin)) != 'q') {
1430 if (c == KEY_ESCAPE)
1431 break;
1432
1433 if (c == 'm')
1434 mp_move_panel(optpan);
1435
1436 switch (c) {
1437 case ERR: case KEY_ESCAPE: break;
1438
1439 case KEY_ENTER:
1440 /* HQ/LQ mixer. */
1441 if (opt == HQMIXER_OPT) {
1442 hq_mixer = 1-hq_mixer;
1443 if (!hq_mixer) {
1444 md_mode &= ~DMODE_HQMIXER;
1445 } else
1446 md_mode |= DMODE_HQMIXER;
1447
1448 refresh_driver_info();
1449
1450 /* 16 bit */
1451 } else if (opt == _16BITS_OPT) {
1452 _16bits = 1-_16bits;
1453 if (!_16bits)
1454 md_mode &= ~DMODE_16BITS;
1455 else
1456 md_mode |= DMODE_16BITS;
1457
1458 refresh_driver_info();
1459
1460 /* Stereo */
1461 } else if (opt == STEREO_OPT) {
1462 stereo = 1-stereo;
1463 if (!stereo) {
1464 md_mode &= ~DMODE_STEREO;
1465 if (reverse_stereo) {
1466 md_mode &=
1467 ~DMODE_REVERSE;
1468 reverse_stereo =
1469 1-reverse_stereo;
1470 }
1471 } else
1472 md_mode |= DMODE_STEREO;
1473
1474 refresh_driver_info();
1475
1476 /* Surround */
1477 } else if (opt == SURROUND_OPT) {
1478 surround = 1-surround;
1479 if (!surround) {
1480 md_mode &= ~DMODE_SURROUND;
1481 } else
1482 md_mode |= DMODE_SURROUND;
1483
1484 refresh_driver_info();
1485
1486 /* Mix freqency */
1487 } else if (opt == MIXFREQ_OPT) {
1488 get_mix_freq(tmpwin);
1489
1490 /* Loop module */
1491 } else if (opt == LOOP_OPT) {
1492 loop_module = 1-loop_module;
1493 mod->loop = loop_module;
1494
1495 /* Fadeout */
1496 } else if (opt == FADE_OPT) {
1497 fade_module = 1-fade_module;
1498 mod->fadeout = fade_module;
1499
1500 /* Reverse stereo */
1501 } else if (opt == REVSTEREO_OPT) {
1502 if (md_mode & DMODE_STEREO)
1503 reverse_stereo =
1504 1-reverse_stereo;
1505 else
1506 break;
1507
1508 if (!reverse_stereo) {
1509 md_mode &= ~DMODE_REVERSE;
1510 } else
1511 md_mode |= DMODE_REVERSE;
1512
1513 refresh_driver_info();
1514
1515 /* Interpolate */
1516 } else if (opt == INTERPOLATE_OPT) {
1517 interpolate = 1-interpolate;
1518 if (!interpolate) {
1519 md_mode &= ~DMODE_INTERP;
1520 } else
1521 md_mode |= DMODE_INTERP;
1522
1523 /* Random */
1524 } else if (opt == RANDOM_OPT) {
1525 random_mode = 1-random_mode;
1526
1527 /* Delay */
1528 } else if (opt == DELAY_OPT) {
1529 get_delay(tmpwin);
1530
1531 /* Save file */
1532 } else if (opt == SAVE_OPT) {
1533 save_options_file();
1534 }
1535
1536 wattrset(tmpwin, (COLOR_PAIR(WHITE)|A_REVERSE));
1537 print_opt(tmpwin, opt);
1538 break;
1539
1540 /* Select option. */
1541 case KEY_UP:
1542 wattrset(tmpwin, (COLOR_PAIR(WHITE)|A_NORMAL));
1543 print_opt(tmpwin, opt);
1544 if (opt == 6 || opt == 9 ||
1545 opt == 13 || opt == 15)
1546 opt -= 2;
1547 else
1548 if (opt > 0) opt--;
1549 wattrset(tmpwin, (COLOR_PAIR(WHITE)|A_REVERSE));
1550 print_opt(tmpwin, opt);
1551 break;
1552 case KEY_PPAGE:
1553 wattrset(tmpwin, (COLOR_PAIR(WHITE)|A_NORMAL));
1554 print_opt(tmpwin, opt);
1555 opt = 0;
1556 wattrset(tmpwin, (COLOR_PAIR(WHITE)|A_REVERSE));
1557 print_opt(tmpwin, opt);
1558 break;
1559
1560 case KEY_DOWN:
1561 wattrset(tmpwin, (COLOR_PAIR(WHITE)|A_NORMAL));
1562 print_opt(tmpwin, opt);
1563 if (opt == 4 || opt == 7 ||
1564 opt == 11 || opt == 13)
1565 opt += 2;
1566 else
1567 if (opt < (OPTIONS+3)-1) opt++;
1568 wattrset(tmpwin, (COLOR_PAIR(WHITE)|A_REVERSE));
1569 print_opt(tmpwin, opt);
1570 break;
1571 case KEY_NPAGE:
1572 wattrset(tmpwin, (COLOR_PAIR(WHITE)|A_NORMAL));
1573 print_opt(tmpwin, opt);
1574 opt = 15;
1575 wattrset(tmpwin, (COLOR_PAIR(WHITE)|A_REVERSE));
1576 print_opt(tmpwin, opt);
1577 break;
1578 }
1579
1580 if (mod && playing) {
1581 refresh_info();
1582 refresh_module_info();
1583 MikMod_Update();
1584 }
1585
1586 update_panels();
1587 doupdate();
1588 }
1589
1590 del_panel(optpan);
1591 update_panels();
1592 doupdate();
1593 }
1594
1595
1596 /***
1597 *** Effects panel.
1598 ***/
effects(void)1599 static void effects(void)
1600 {
1601 int i;
1602 int c;
1603 int pc;
1604 int effect = 0;
1605 float f1, f2;
1606 char *effect_strings[EFFECTS] = {
1607 " Speed ",
1608 " Tempo ",
1609 " BPM ",
1610 " Reverb ",
1611 " Stereo ",
1612 " Gen Vol ",
1613 " Mod Vol ",
1614 " Mix Vol ",
1615 " Bass ",
1616 " Treble "
1617 };
1618
1619 eftwin = newwin(EFT_H, EFT_W, EFT_Y, EFT_X);
1620 wtimeout(eftwin, DELAY);
1621 keypad(eftwin, TRUE);
1622 box(eftwin, 0, 0);
1623 eftpan = new_panel(eftwin);
1624 top_panel(eftpan);
1625
1626 wattrset(eftwin, (COLOR_PAIR(WHITE)|A_NORMAL));
1627 mvwprintw(eftwin, 0, 2, "[ ]");
1628 wattrset(eftwin, COLOR_PAIR(YELLOW)|A_BOLD);
1629 mvwprintw(eftwin, 0, 4, "Effects");
1630
1631 /* Prepare display. */
1632 for (c = 0; c < EFFECTS; c++) {
1633 wattrset(eftwin, (COLOR_PAIR(WHITE)|A_NORMAL));
1634 if (c == 0)
1635 wattrset(eftwin, (COLOR_PAIR(WHITE)|A_REVERSE));
1636 mvwprintw(eftwin, c+2, 1, effect_strings[c]);
1637 switch (c) {
1638 case 0: /* speed */
1639 f1 = mod->sngspd;
1640 f2 = SPEED_LIMIT;
1641 pc = 100*(f1/f2);
1642 pc = 100-pc;
1643 draw_gauge(eftwin, 12, c+2, pc, 1, gauge_style);
1644 break;
1645 case 1: /* tempo */
1646 f1 = mod->inittempo;
1647 f2 = TEMPO_LIMIT;
1648 pc = 100*(f1/f2);
1649 draw_gauge(eftwin, 12, c+2, pc, 1, gauge_style);
1650 break;
1651 case 2: /* BPM */
1652 f1 = mod->bpm;
1653 f2 = BPM_LIMIT;
1654 pc = 100*(f1/f2);
1655 draw_gauge(eftwin, 12, c+2, pc, 1, gauge_style);
1656 break;
1657 case 3: /* reverb */
1658 f1 = md_reverb;
1659 f2 = REVERB_LIMIT;
1660 pc = 100*(f1/f2);
1661 draw_gauge(eftwin, 12, c+2, pc, 1, gauge_style);
1662 break;
1663 case 4: /* stereo */
1664 f1 = md_pansep;
1665 f2 = STEREO_LIMIT;
1666 pc = 100*(f1/f2);
1667 draw_gauge(eftwin, 12, c+2, pc, 1, gauge_style);
1668 break;
1669 case 5: /* general volume */
1670 f1 = md_volume;
1671 f2 = GENVOL_LIMIT;
1672 pc = 100*(f1/f2);
1673 draw_gauge(eftwin, 12, c+2, pc, 1, gauge_style);
1674 break;
1675 case 6: /* module volume */
1676 f1 = mod->volume;
1677 f2 = MODVOL_LIMIT;
1678 pc = 100*(f1/f2);
1679 draw_gauge(eftwin, 12, c+2, pc, 1, gauge_style);
1680 break;
1681 case 7: /* mixer volume */
1682 f1 = mixvol;
1683 f2 = MIXVOL_LIMIT;
1684 pc = 100*(f1/f2);
1685 draw_gauge(eftwin, 12, c+2, pc, 1, gauge_style);
1686 break;
1687 case 8: /* bass level */
1688 f1 = bass;
1689 f2 = BASS_LIMIT;
1690 pc = 100*(f1/f2);
1691 draw_gauge(eftwin, 12, c+2, pc, 1, gauge_style);
1692 break;
1693 case 9: /* treble level */
1694 f1 = treble;
1695 f2 = TREBLE_LIMIT;
1696 pc = 100*(f1/f2);
1697 draw_gauge(eftwin, 12, c+2, pc, 1, gauge_style);
1698 break;
1699 }
1700 }
1701
1702 /*** Loop ***/
1703 while ((c = wgetch(eftwin)) != 'q') {
1704 if (c == KEY_ESCAPE)
1705 break;
1706
1707 if (c == 'm')
1708 mp_move_panel(eftpan);
1709
1710 switch (c) {
1711 case ERR: break;
1712
1713 /* UP */
1714 case KEY_UP:
1715 wattrset(eftwin, (COLOR_PAIR(WHITE)|A_NORMAL));
1716 mvwprintw(eftwin, effect+2, 1,
1717 effect_strings[effect]);
1718 if (effect > 0) effect--;
1719 wattrset(eftwin, (COLOR_PAIR(WHITE)|A_REVERSE));
1720 mvwprintw(eftwin, effect+2, 1,
1721 effect_strings[effect]);
1722 break;
1723 case KEY_PPAGE:
1724 wattrset(eftwin, (COLOR_PAIR(WHITE)|A_NORMAL));
1725 mvwprintw(eftwin, effect+2, 1,
1726 effect_strings[effect]);
1727 effect = 0;
1728 wattrset(eftwin, (COLOR_PAIR(WHITE)|A_REVERSE));
1729 mvwprintw(eftwin, effect+2, 1,
1730 effect_strings[effect]);
1731 break;
1732
1733 /* DOWN */
1734 case KEY_DOWN:
1735 wattrset(eftwin, (COLOR_PAIR(WHITE)|A_NORMAL));
1736 mvwprintw(eftwin, effect+2, 1,
1737 effect_strings[effect]);
1738 if (effect < EFFECTS-1) effect++;
1739 wattrset(eftwin, (COLOR_PAIR(WHITE)|A_REVERSE));
1740 mvwprintw(eftwin, effect+2, 1,
1741 effect_strings[effect]);
1742 break;
1743 case KEY_NPAGE:
1744 wattrset(eftwin, (COLOR_PAIR(WHITE)|A_NORMAL));
1745 mvwprintw(eftwin, effect+2, 1,
1746 effect_strings[effect]);
1747 effect = EFFECTS-1;
1748 wattrset(eftwin, (COLOR_PAIR(WHITE)|A_REVERSE));
1749 mvwprintw(eftwin, effect+2, 1,
1750 effect_strings[effect]);
1751 break;
1752
1753 case KEY_LEFT:
1754 switch (effect) {
1755 case 0: /* speed */
1756 if (mod->sngspd < SPEED_LIMIT)
1757 mod->sngspd++;
1758 f1 = mod->sngspd;
1759 f2 = SPEED_LIMIT;
1760 pc = 100*(f1/f2);
1761 pc = 100-pc;
1762 draw_gauge(eftwin, 12, effect+2,
1763 pc, 1, gauge_style);
1764 break;
1765 case 1: /* tempo */
1766 if (mod->inittempo > 0)
1767 mod->inittempo--;
1768 f1 = mod->inittempo;
1769 f2 = TEMPO_LIMIT;
1770 pc = 100*(f1/f2);
1771 draw_gauge(eftwin, 12, effect+2,
1772 pc, 1, gauge_style);
1773 break;
1774 case 2: /* BPM */
1775 if (mod->bpm > 1)
1776 mod->bpm--;
1777 f1 = mod->bpm;
1778 f2 = BPM_LIMIT;
1779 pc = 100*(f1/f2);
1780 draw_gauge(eftwin, 12, effect+2,
1781 pc, 1, gauge_style);
1782 break;
1783 case 3: /* reverb */
1784 if (md_reverb > 0)
1785 md_reverb--;
1786 f1 = md_reverb;
1787 f2 = REVERB_LIMIT;
1788 pc = 100*(f1/f2);
1789 draw_gauge(eftwin, 12, effect+2,
1790 pc, 1, gauge_style);
1791 break;
1792 case 4: /* stereo */
1793 if (md_pansep > 0)
1794 md_pansep--;
1795 f1 = md_pansep;
1796 f2 = STEREO_LIMIT;
1797 pc = 100*(f1/f2);
1798 draw_gauge(eftwin, 12, effect+2,
1799 pc, 1, gauge_style);
1800 break;
1801 case 5: /* general volume */
1802 if (md_volume > 0)
1803 md_volume--;
1804 f1 = md_volume;
1805 f2 = GENVOL_LIMIT;
1806 pc = 100*(f1/f2);
1807 draw_gauge(eftwin, 12, effect+2,
1808 pc, 1, gauge_style);
1809 break;
1810 case 6: /* module volume */
1811 if (mod->volume > 0)
1812 mod->volume--;
1813 f1 = mod->volume;
1814 f2 = MODVOL_LIMIT;
1815 pc = 100*(f1/f2);
1816 draw_gauge(eftwin, 12, effect+2,
1817 pc, 1, gauge_style);
1818 break;
1819 case 7: /* mixer volume */
1820 if (mixvol > 771)
1821 mixvol -= 771;
1822 else
1823 mixvol = 0;
1824 f1 = mixvol;
1825 f2 = MIXVOL_LIMIT;
1826 pc = 100*(f1/f2);
1827 draw_gauge(eftwin, 12, effect+2,
1828 pc, 1, gauge_style);
1829 ioctl(
1830 mixerfd,
1831 MIXER_WRITE(SOUND_MIXER_VOLUME),
1832 &mixvol
1833 );
1834 break;
1835 case 8: /* mixer bass */
1836 if (bass > 0)
1837 bass--;
1838 f1 = bass;
1839 f2 = BASS_LIMIT;
1840 pc = 100*(f1/f2);
1841 draw_gauge(eftwin, 12, effect+2,
1842 pc, 1, gauge_style);
1843 ioctl(
1844 mixerfd,
1845 MIXER_WRITE(SOUND_MIXER_BASS),
1846 &bass
1847 );
1848 break;
1849 case 9: /* mixer treble */
1850 if (treble > 0)
1851 treble--;
1852 f1 = treble;
1853 f2 = TREBLE_LIMIT;
1854 pc = 100*(f1/f2);
1855 draw_gauge(eftwin, 12, effect+2,
1856 pc, 1, gauge_style);
1857 ioctl(
1858 mixerfd,
1859 MIXER_WRITE(SOUND_MIXER_TREBLE),
1860 &treble
1861 );
1862 break;
1863
1864 }
1865 break;
1866
1867 case KEY_RIGHT:
1868 switch (effect) {
1869 case 0: /* speed */
1870 if (mod->sngspd > 0)
1871 mod->sngspd--;
1872 f1 = mod->sngspd;
1873 f2 = SPEED_LIMIT;
1874 pc = 100*(f1/f2);
1875 pc = 100-pc;
1876 draw_gauge(eftwin, 12, effect+2,
1877 pc, 1, gauge_style);
1878 break;
1879 case 1: /* tempo */
1880 if (mod->inittempo<TEMPO_LIMIT)
1881 mod->inittempo++;
1882 f1 = mod->inittempo;
1883 f2 = TEMPO_LIMIT;
1884 pc = 100*(f1/f2);
1885 draw_gauge(eftwin, 12, effect+2,
1886 pc, 1, gauge_style);
1887 break;
1888 case 2: /* BPM */
1889 if (mod->bpm < BPM_LIMIT)
1890 mod->bpm++;
1891 f1 = mod->bpm;
1892 f2 = BPM_LIMIT;
1893 pc = 100*(f1/f2);
1894 draw_gauge(eftwin, 12, effect+2,
1895 pc, 1, gauge_style);
1896 break;
1897 case 3: /* reverb */
1898 if (md_reverb < REVERB_LIMIT)
1899 md_reverb++;
1900 f1 = md_reverb;
1901 f2 = REVERB_LIMIT;
1902 pc = 100*(f1/f2);
1903 draw_gauge(eftwin, 12, effect+2,
1904 pc, 1, gauge_style);
1905 break;
1906 case 4: /* stereo */
1907 if (md_pansep < STEREO_LIMIT)
1908 md_pansep++;
1909 f1 = md_pansep;
1910 f2 = STEREO_LIMIT;
1911 pc = 100*(f1/f2);
1912 draw_gauge(eftwin, 12, effect+2,
1913 pc, 1, gauge_style);
1914 break;
1915 case 5: /* general volume */
1916 if (md_volume < GENVOL_LIMIT)
1917 md_volume++;
1918 f1 = md_volume;
1919 f2 = GENVOL_LIMIT;
1920 pc = 100*(f1/f2);
1921 draw_gauge(eftwin, 12, effect+2,
1922 pc, 1, gauge_style);
1923 break;
1924 case 6: /* module volume */
1925 if (mod->volume < MODVOL_LIMIT)
1926 mod->volume++;
1927 f1 = mod->volume;
1928 f2 = MODVOL_LIMIT;
1929 pc = 100*(f1/f2);
1930 draw_gauge(eftwin, 12, effect+2,
1931 pc, 1, gauge_style);
1932 break;
1933 case 7: /* mixer volume */
1934 if (mixvol < MIXVOL_LIMIT)
1935 mixvol += 771;
1936 f1 = mixvol;
1937 f2 = MIXVOL_LIMIT;
1938 pc = 100*(f1/f2);
1939 draw_gauge(eftwin, 12, effect+2,
1940 pc, 1, gauge_style);
1941 ioctl(
1942 mixerfd,
1943 MIXER_WRITE(SOUND_MIXER_VOLUME),
1944 &mixvol
1945 );
1946 break;
1947 case 8: /* mixer bass */
1948 if (bass < BASS_LIMIT)
1949 bass++;
1950 f1 = bass;
1951 f2 = BASS_LIMIT;
1952 pc = 100*(f1/f2);
1953 draw_gauge(eftwin, 12, effect+2,
1954 pc, 1, gauge_style);
1955 i = (bass * 16);
1956 ioctl(
1957 mixerfd,
1958 MIXER_WRITE(SOUND_MIXER_BASS),
1959 &i
1960 );
1961 break;
1962 case 9: /* mixer treble */
1963 if (treble < TREBLE_LIMIT)
1964 treble++;
1965 f1 = treble;
1966 f2 = TREBLE_LIMIT;
1967 pc = 100*(f1/f2);
1968 draw_gauge(eftwin, 12, effect+2,
1969 pc, 1, gauge_style);
1970 ioctl(
1971 mixerfd,
1972 MIXER_WRITE(SOUND_MIXER_TREBLE),
1973 &treble
1974 );
1975 break;
1976 }
1977 break;
1978 }
1979
1980 if (mod && playing) {
1981 refresh_info();
1982 refresh_module_info();
1983 MikMod_Update();
1984 }
1985
1986 update_panels();
1987 doupdate();
1988 }
1989
1990 del_panel(eftpan);
1991 touchwin(dspwin);
1992 doupdate();
1993 }
1994
1995 /*****************************************************************************/
1996
1997 /***
1998 *** Instruments panel.
1999 ***/
2000 int insnum; /* instrument number */
2001 INSTRUMENT *curins; /* pointer to current instrument */
2002
2003 int ins_val; /* used for buttons */
2004
2005 /*** Show instrument. ***/
show_instrument(WINDOW * win,INSTRUMENT * ins,int num)2006 static void show_instrument(WINDOW *win, INSTRUMENT *ins, int num)
2007 {
2008 if (mod->instruments == NULL) {
2009 message("No instruments in this module.", ERROR_MSG);
2010 return;
2011 }
2012
2013 wattrset(win, A_BOLD);
2014 mvwprintw(win, 2, 1, " #: ");
2015 wattrset(win, A_NORMAL);
2016 wprintw(win, "%-4d/%4d", num, mod->numins);
2017
2018 wattrset(win, A_BOLD);
2019 mvwprintw(win, 3, 1, " Name: ");
2020 wattrset(win, A_NORMAL);
2021 wprintw(win, "%-40s", ins->insname);
2022
2023 wattrset(win, A_BOLD);
2024 mvwprintw(win, 4, 1, " Flags: ");
2025 wattrset(win, A_NORMAL);
2026 wprintw(win, "0x%04x", ins->flags);
2027
2028 wattrset(win, A_BOLD);
2029 mvwprintw(win, 5, 1, " Pan: ");
2030 wattrset(win, A_NORMAL);
2031 wprintw(win, "%-3d", ins->panning);
2032
2033 wattrset(win, A_BOLD);
2034 mvwprintw(win, 6, 1, " Vol: ");
2035 wattrset(win, A_NORMAL);
2036 wprintw(win, "%-4d", ins->globvol);
2037 }
2038
2039 /*** Instruments window buttons. ***/
ins_buttons(WINDOW * win)2040 static int ins_buttons(WINDOW *win)
2041 {
2042 int i, c;
2043 int in_loop = 1;
2044 char *ins_btns[3] = {
2045 "[ Next ]",
2046 "[ Prev ]",
2047 // "[ Play ]",
2048 // "[ Stop ]",
2049 "[ Quit ]"
2050 };
2051
2052 ins_val = 0;
2053
2054 wattrset(win, COLOR_PAIR(WHITE)|A_NORMAL);
2055 for (i = 0; i < 3; i++) {
2056 if (ins_val == i)
2057 wattrset(win, A_REVERSE);
2058 else
2059 wattrset(win, A_NORMAL);
2060
2061 mvwprintw(win, INS_H-3, 5+(i*18), "%s", ins_btns[i]);
2062 }
2063
2064 while (in_loop) {
2065 switch ((c = wgetch(win))) {
2066 case KEY_ESCAPE:
2067 case 'q':
2068 ins_val = 2;
2069 in_loop = 0;
2070 break;
2071
2072 case KEY_RIGHT:
2073 wattrset(win, A_NORMAL);
2074 mvwprintw(win, INS_H-3, 5+(ins_val*18),
2075 "%s", ins_btns[ins_val]);
2076 if (ins_val < 2) ins_val++;
2077 wattrset(win, A_REVERSE);
2078 mvwprintw(win, INS_H-3, 5+(ins_val*18),
2079 "%s", ins_btns[ins_val]);
2080 break;
2081 case KEY_LEFT:
2082 wattrset(win, A_NORMAL);
2083 mvwprintw(win, INS_H-3, 5+(ins_val*18),
2084 "%s", ins_btns[ins_val]);
2085 if (ins_val > 0) ins_val--;
2086 wattrset(win, A_REVERSE);
2087 mvwprintw(win, INS_H-3, 5+(ins_val*18),
2088 "%s", ins_btns[ins_val]);
2089 break;
2090 case KEY_ENTER:
2091 /* Next. */
2092 if (ins_val == 0) {
2093 if (insnum < mod->numins-1) {
2094 insnum++;
2095 curins++;
2096 show_instrument(win,
2097 curins, insnum+1);
2098 }
2099
2100 /* Previous. */
2101 } else if (ins_val == 1) {
2102 if (insnum > 0) {
2103 insnum--;
2104 curins--;
2105 show_instrument(win,
2106 curins, insnum+1);
2107 }
2108
2109 /* Play. */
2110 /*} else if (ins_val == 2) {
2111 int i = Sample_Play(cursmp, 1, 0);
2112 fprintf(stderr, "%d\n", i);*/
2113
2114 /* Stop. */
2115 /*} else if (ins_val == 3) {*/
2116
2117 /* Quit. */
2118 } else if (ins_val == 2) {
2119 in_loop = 0;
2120 continue;
2121 }
2122 break;
2123 }
2124
2125
2126 if (mod && playing) {
2127 refresh_module_info();
2128 refresh_info();
2129 update_panels();
2130 doupdate();
2131 MikMod_Update();
2132 }
2133 }
2134
2135 return ins_val;
2136 }
2137
2138 /*** Open instruments window. ***/
show_instruments(void)2139 void show_instruments(void)
2140 {
2141 int i;
2142 WINDOW *tmpwin;
2143
2144 inswin = tmpwin = newwin(INS_H, INS_W, INS_Y, INS_X);
2145 wtimeout(tmpwin, DELAY);
2146 keypad(tmpwin, TRUE);
2147 box(tmpwin, 0, 0);
2148 inspan = new_panel(inswin);
2149
2150 wattrset(tmpwin, COLOR_PAIR(WHITE)|A_NORMAL);
2151 mvwprintw(tmpwin, 0, 2, "[ ]");
2152 wattrset(tmpwin, COLOR_PAIR(YELLOW)|A_BOLD);
2153 mvwprintw(tmpwin, 0, 4, "Instruments");
2154
2155 wattrset(tmpwin, COLOR_PAIR(WHITE)|A_NORMAL);
2156 for (i = 1; i < INS_W-1; i++)
2157 mvwaddch(tmpwin, INS_H-5, i, ACS_HLINE);
2158 mvwaddch(tmpwin, INS_H-5, 0, ACS_LTEE);
2159 mvwaddch(tmpwin, INS_H-5, INS_W-1, ACS_RTEE);
2160
2161 insnum = 0;
2162 curins = mod->instruments;
2163 show_instrument(tmpwin, mod->instruments, insnum+1);
2164 ins_buttons(tmpwin);
2165
2166 del_panel(inspan);
2167 touchwin(dspwin);
2168 update_panels();
2169 doupdate();
2170
2171 }
2172
2173 /*****************************************************************************/
2174
2175 /***
2176 *** Sample window.
2177 ***/
2178 int smpnum; /* sample number */
2179 SAMPLE *cursmp; /* pointer to current sample */
2180
2181 int smp_val; /* used for buttons */
2182
2183 /*** Show sample. ***/
show_sample(WINDOW * win,SAMPLE * smp,int num)2184 static void show_sample(WINDOW *win, SAMPLE *smp, int num)
2185 {
2186 wattrset(win, A_BOLD);
2187 mvwprintw(win, 2, 1, " #: ");
2188 wattrset(win, A_NORMAL);
2189 wprintw(win, "%-4d/%4d", num, mod->numsmp);
2190
2191 wattrset(win, A_BOLD);
2192 mvwprintw(win, 3, 1, " Name: ");
2193 wattrset(win, A_NORMAL);
2194 wprintw(win, "%-40s", smp->samplename);
2195
2196 wattrset(win, A_BOLD);
2197 mvwprintw(win, 4, 1,
2198 " ");
2199 mvwprintw(win, 4, 1, " Flags: ");
2200 wattrset(win, A_NORMAL);
2201 if (smp->flags & SF_16BITS)
2202 wprintw(win, "16bit ");
2203 if (smp->flags & SF_STEREO)
2204 wprintw(win, "stereo ");
2205 if (smp->flags & SF_SIGNED)
2206 wprintw(win, "signed ");
2207 if (smp->flags & SF_ITPACKED)
2208 wprintw(win, "IT_packed ");
2209 if (smp->flags & SF_BIDI)
2210 wprintw(win, "bidir ");
2211 if (smp->flags & SF_LOOP)
2212 wprintw(win, "loop ");
2213 if (smp->flags & SF_REVERSE)
2214 wprintw(win, "reverse ");
2215 if (smp->flags & SF_OWNPAN)
2216 wprintw(win, "own_pan ");
2217 wprintw(win, "(0x%04x)", smp->flags);
2218
2219 wattrset(win, A_BOLD);
2220 mvwprintw(win, 5, 1, "Length: ");
2221 wattrset(win, A_NORMAL);
2222 wprintw(win, "%-8d", smp->length);
2223
2224 wattrset(win, A_BOLD);
2225 mvwprintw(win, 6, 1, " Pan: ");
2226 wattrset(win, A_NORMAL);
2227 wprintw(win, "%-3d", smp->panning);
2228
2229 wattrset(win, A_BOLD);
2230 mvwprintw(win, 7, 1, " Speed: ");
2231 wattrset(win, A_NORMAL);
2232 wprintw(win, "%-6d", smp->speed);
2233
2234 wattrset(win, A_BOLD);
2235 mvwprintw(win, 8, 1, " Vol: ");
2236 wattrset(win, A_NORMAL);
2237 wprintw(win, "%-4d (glob. %-4d)",
2238 smp->volume,
2239 smp->globvol);
2240
2241 }
2242
2243 /*** Samples window buttons. ***/
smp_buttons(WINDOW * win)2244 static int smp_buttons(WINDOW *win)
2245 {
2246 int i, c;
2247 int in_loop = 1;
2248 char *smp_btns[3] = {
2249 "[ Next ]",
2250 "[ Prev ]",
2251 // "[ Play ]",
2252 // "[ Stop ]",
2253 "[ Quit ]"
2254 };
2255
2256 smp_val = 0;
2257
2258 wattrset(win, COLOR_PAIR(WHITE)|A_NORMAL);
2259 for (i = 0; i < 3; i++) {
2260 if (smp_val == i)
2261 wattrset(win, A_REVERSE);
2262 else
2263 wattrset(win, A_NORMAL);
2264
2265 mvwprintw(win, SMP_H-3, 5+(i*18), "%s", smp_btns[i]);
2266 }
2267
2268 while (in_loop) {
2269 switch ((c = wgetch(win))) {
2270 case KEY_ESCAPE:
2271 case 'q':
2272 smp_val = 2;
2273 in_loop = 0;
2274 break;
2275
2276 case 'm':
2277 mp_move_panel(smppan);
2278 break;
2279
2280 case KEY_RIGHT:
2281 wattrset(win, A_NORMAL);
2282 mvwprintw(win, SMP_H-3, 5+(smp_val*18),
2283 "%s", smp_btns[smp_val]);
2284 if (smp_val < 2) smp_val++;
2285 wattrset(win, A_REVERSE);
2286 mvwprintw(win, SMP_H-3, 5+(smp_val*18),
2287 "%s", smp_btns[smp_val]);
2288 break;
2289 case KEY_LEFT:
2290 wattrset(win, A_NORMAL);
2291 mvwprintw(win, SMP_H-3, 5+(smp_val*18),
2292 "%s", smp_btns[smp_val]);
2293 if (smp_val > 0) smp_val--;
2294 wattrset(win, A_REVERSE);
2295 mvwprintw(win, SMP_H-3, 5+(smp_val*18),
2296 "%s", smp_btns[smp_val]);
2297 break;
2298 case KEY_ENTER:
2299 /* Next. */
2300 if (smp_val == 0) {
2301 if (smpnum < mod->numsmp-1) {
2302 smpnum++;
2303 cursmp++;
2304 show_sample(win,
2305 cursmp, smpnum+1);
2306 }
2307
2308 /* Previous. */
2309 } else if (smp_val == 1) {
2310 if (smpnum > 0) {
2311 smpnum--;
2312 cursmp--;
2313 show_sample(win,
2314 cursmp, smpnum+1);
2315 }
2316
2317 /* Play. */
2318 /*} else if (smp_val == 2) {
2319 int i = Sample_Play(cursmp, 1, 0);
2320 fprintf(stderr, "%d\n", i);*/
2321
2322 /* Stop. */
2323 /*} else if (smp_val == 3) {*/
2324
2325 /* Quit. */
2326 } else if (smp_val == 2) {
2327 in_loop = 0;
2328 continue;
2329 }
2330 break;
2331 }
2332
2333
2334 if (mod && playing) {
2335 refresh_module_info();
2336 refresh_info();
2337 update_panels();
2338 doupdate();
2339 MikMod_Update();
2340 }
2341 }
2342
2343 return smp_val;
2344 }
2345
2346 /*** Open samples window. ***/
show_samples(void)2347 void show_samples(void)
2348 {
2349 int i;
2350 WINDOW *tmpwin;
2351
2352 smpwin = tmpwin = newwin(SMP_H, SMP_W, SMP_Y, SMP_X);
2353 wtimeout(tmpwin, DELAY);
2354 keypad(tmpwin, TRUE);
2355 box(tmpwin, 0, 0);
2356 smppan = new_panel(tmpwin);
2357 wattrset(tmpwin, COLOR_PAIR(WHITE)|A_NORMAL);
2358 mvwprintw(tmpwin, 0, 2, "[ ]");
2359 wattrset(tmpwin, COLOR_PAIR(YELLOW)|A_BOLD);
2360 mvwprintw(tmpwin, 0, 4, "Samples");
2361
2362 wattrset(tmpwin, COLOR_PAIR(WHITE)|A_NORMAL);
2363 for (i = 1; i < SMP_W-1; i++)
2364 mvwaddch(tmpwin, SMP_H-5, i, ACS_HLINE);
2365 mvwaddch(tmpwin, SMP_H-5, 0, ACS_LTEE);
2366 mvwaddch(tmpwin, SMP_H-5, SMP_W-1, ACS_RTEE);
2367
2368 smpnum = 0;
2369 cursmp = mod->samples;
2370 show_sample(tmpwin, mod->samples, smpnum+1);
2371 smp_buttons(tmpwin);
2372
2373 del_panel(smppan);
2374 delwin(smpwin);
2375 touchwin(dspwin);
2376 update_panels();
2377 doupdate();
2378
2379 }
2380
2381
2382
2383 /*****************************************************************************/
2384
2385 /***
2386 *** Various functions.
2387 ***/
2388
2389 /*** Get a string from anywhere in a window. ***/
2390 char getstrtab = 0;
2391
get_string(WINDOW * win,int ys,int xs,char * prompt,char * str)2392 static void get_string(WINDOW *win, int ys, int xs, char *prompt, char *str)
2393 {
2394 int slen = strlen(prompt) + strlen(str);
2395 int c, i, j, k;
2396 int piece;
2397 int in_loop = 1;
2398 int x = xs + slen;
2399 int maxlen = 57 - strlen(prompt);
2400 char strbuf[NAME_MAX+1], *bufp = strbuf;
2401
2402 k = i = strlen(str);
2403 mvwprintw(win, ys, xs, "%s%s", prompt, str); curs_set(TRUE);
2404
2405 wnoutrefresh(win);
2406 doupdate();
2407
2408 /*** Loop ***/
2409 getstrtab = 0;
2410 while (in_loop) {
2411 switch ((c = wgetch(win))) {
2412 case ERR: break;
2413
2414 case KEY_ENTER:
2415 in_loop = 0;
2416 continue;
2417 break;
2418
2419 case KEY_DELETE:
2420 case KEY_BACKSPACE:
2421 if (x == xs+strlen(prompt)) {
2422 beep();
2423 break;
2424 }
2425
2426 if (i == 1 || (k % maxlen-1)) {
2427 str[--i] = 0;
2428 mvwaddch(win, ys, x--, '\b');
2429 waddch(win, ' ');
2430 waddch(win, '\b');
2431 k--;
2432
2433 } else {
2434 piece = (i / maxlen);
2435 bufp = strbuf;
2436 sprintf(bufp, str);
2437 bufp += (piece * maxlen);
2438 bufp[maxlen] = '\0';
2439
2440 if (piece > 0)
2441 bufp[0] = '~';
2442 k = strlen(bufp);
2443
2444 j = strlen(prompt);
2445 for (; j < FS_W-2; j++)
2446 mvwaddch(win, ys, j, ' ');
2447 x = xs + (strlen(prompt)
2448 + strlen(bufp));
2449 mvwprintw(win, ys, xs,
2450 "%s%s", prompt, bufp);
2451 }
2452 break;
2453
2454 /*
2455 case KEY_LEFT:
2456 if (x == xs+strlen(prompt)+1) {
2457 beep();
2458 break;
2459 }
2460 wmove(win, ys, --x);
2461 i--;
2462 break;
2463
2464 case KEY_RIGHT:
2465 if (x == 48) {
2466 beep();
2467 break;
2468 }
2469 wmove(win, ys, --x);
2470 i++;
2471 break;
2472 */
2473
2474 case KEY_ESCAPE:
2475 in_loop = 0;
2476 continue;
2477 break;
2478
2479 case KEY_TAB:
2480 getstrtab = 1;
2481 in_loop = 0;
2482 continue;
2483 break;
2484
2485 /* Ignored characters. */
2486 case KEY_UP:
2487 case KEY_DOWN:
2488 case KEY_LEFT:
2489 case KEY_RIGHT:
2490 break;
2491
2492 /* Add character. */
2493 default:
2494 if (i >= NAME_MAX) {
2495 beep();
2496 break;
2497 }
2498
2499 if (i == 0 || (k % maxlen)) {
2500 str[i++] = (char ) c;
2501 mvwaddch(win, ys, x++, c);
2502 k++;
2503
2504 } else {
2505 bufp = strbuf;
2506 sprintf(bufp, str);
2507 bufp += i-4;
2508 bufp[0] = '~';
2509 bufp[5] = '\0';
2510 k = 5;
2511
2512 j = strlen(prompt);
2513 for (; j < FS_W-2; j++)
2514 mvwaddch(win, ys, j, ' ');
2515 x = xs + (strlen(prompt)
2516 + strlen(bufp));
2517 mvwprintw(win, ys, xs,
2518 "%s%s", prompt, bufp);
2519
2520 str[i++] = (char ) c;
2521 mvwaddch(win, ys, x++, c);
2522 }
2523 break;
2524 }
2525
2526 if (mod && playing) {
2527 refresh_info();
2528 refresh_module_info();
2529 update_panels();
2530 doupdate();
2531 MikMod_Update();
2532 }
2533
2534 }
2535 str[i] = '\0';
2536
2537 curs_set(FALSE);
2538 touchwin(dspwin);
2539 doupdate();
2540 }
2541
2542 /*** Move panel. ***/
mp_move_panel(PANEL * pan)2543 static void mp_move_panel(PANEL *pan)
2544 {
2545 int c;
2546 int x = pan->win->_begx, y = pan->win->_begy;
2547
2548 while ((c = wgetch(pan->win)) != KEY_ENTER ||
2549 c == KEY_ESCAPE) {
2550 switch (c) {
2551 case KEY_UP:
2552 if (y)
2553 move_panel(pan, --y, x);
2554 break;
2555 case KEY_DOWN:
2556 if (y < (LINES-(pan->win->_maxy+1)))
2557 move_panel(pan, ++y, x);
2558 break;
2559 case KEY_LEFT:
2560 if (x)
2561 move_panel(pan, y, --x);
2562 break;
2563 case KEY_RIGHT:
2564 if (x < (COLS-(pan->win->_maxx+1)))
2565 move_panel(pan, y, ++x);
2566 break;
2567 }
2568
2569 if (mod && playing) {
2570 refresh_info();
2571 refresh_module_info();
2572 MikMod_Update();
2573 }
2574
2575 update_panels();
2576 doupdate();
2577 }
2578
2579 if (pan->win == acwin) {
2580 AC_X = acwin->_begx;
2581 AC_Y = acwin->_begy;
2582
2583 } else if (pan->win == helpwin) {
2584 HELP_X = helpwin->_begx;
2585 HELP_Y = helpwin->_begy;
2586
2587 } else if (pan->win == vfreqwin) {
2588 VFREQ_X = vfreqwin->_begx;
2589 VFREQ_Y = vfreqwin->_begy;
2590
2591 } else if (pan->win == vposwin) {
2592 VPOS_X = vposwin->_begx;
2593 VPOS_Y = vposwin->_begy;
2594
2595 } else if (pan->win == eftwin) {
2596 EFT_X = eftwin->_begx;
2597 EFT_Y = eftwin->_begy;
2598
2599 } else if (pan->win == optwin) {
2600 OPT_X = optwin->_begx;
2601 OPT_Y = optwin->_begy;
2602
2603 } else if (pan->win == smpwin) {
2604 SMP_X = smpwin->_begx;
2605 SMP_Y = smpwin->_begy;
2606 }
2607 }
2608
2609 /*****************************************************************************/
2610
2611 /***
2612 *** File selector.
2613 ***/
2614
2615 /*** Variables. ***/
2616 int fs_val;
2617 int current, nument;
2618 int fspage = 0, lastpage = 0;
2619
2620 struct dirent *drent[MAX_FILES];
2621 char dname[MAX_FILES][NAME_MAX+1];
2622 char dnamed[MAX_FILES][NAME_MAX+1];
2623 char dnamef[MAX_FILES][NAME_MAX+1];
2624 DIR *dentry = NULL;
2625
2626 char modpath[NAME_MAX+1];
2627 char dirname[NAME_MAX+1];
2628 char filename[NAME_MAX+1];
2629 char lastdir[NAME_MAX+1];
2630
2631 /*** List directory content in window win (without reading). ***/
list_dir(WINDOW * win)2632 static void list_dir(WINDOW *win)
2633 {
2634 int y;
2635 int cnt = fspage*(FS_H-10);
2636 struct stat sbuf;
2637 char strbuf[NAME_MAX+1];
2638
2639 for (y = 5; y < FS_H-5; y++, cnt++) {
2640 if ((drent[cnt]) == NULL) break;
2641
2642 strncpy(strbuf, dname[cnt], 48);
2643 strbuf[48] = '\0';
2644
2645 stat(dname[cnt], &sbuf);
2646 file_size =
2647 (((float)(sbuf.st_size)) / 1024.0);
2648 file_sizeb = sbuf.st_size;
2649
2650 if (S_ISDIR(sbuf.st_mode)) {
2651 wattrset(win, COLOR_PAIR(WHITE)|A_BOLD);
2652 mvwprintw(win, y, 1, "%-48s", strbuf);
2653 wattrset(win, COLOR_PAIR(WHITE)|A_NORMAL);
2654 wprintw(win, " ");
2655
2656 } else {
2657 wattrset(win, COLOR_PAIR(WHITE)|A_NORMAL);
2658 mvwprintw(win, y, 1, "%-48s %9d", strbuf, file_sizeb);
2659 }
2660 }
2661
2662 for (; y < FS_H-5; y++)
2663 mvwprintw(win, y, 1, "%-58s", "");
2664 }
2665
2666 /*** Print the directory content in window win. ***/
print_dir(WINDOW * win)2667 static void print_dir(WINDOW *win)
2668 {
2669 int i;
2670 int y;
2671 int cnt;
2672 int d = 0, f = 0;
2673 char strbuf[NAME_MAX+1];
2674 struct stat _sbuf, *sbuf = &_sbuf;
2675
2676 wattrset(win, A_NORMAL);
2677 mvwprintw(win, 2, 1, "Dir: %-52s", dirname);
2678 wattrset(win, A_BOLD);
2679 mvwaddch(win, 2, 1, 'D');
2680 wattrset(win, A_NORMAL);
2681
2682 /* Read dir. */
2683 cnt = 0, nument = 0;
2684 while ((drent[cnt] = readdir(dentry)) != NULL) {
2685 if ((strcmp(drent[cnt]->d_name, ".")) == 0) continue;
2686
2687 stat(drent[cnt]->d_name, sbuf);
2688 if (S_ISDIR(sbuf->st_mode))
2689 strcpy(dnamed[d++], drent[cnt]->d_name);
2690 else
2691 strcpy(dnamef[f++], drent[cnt]->d_name);
2692
2693 cnt++, nument++;
2694 }
2695 drent[cnt] = NULL;
2696
2697 /* Copy dir and file name to entries name buffer
2698 * (this is needed by list_dir). */
2699 for (i = 0, cnt = 0; i < d; i++, cnt++)
2700 strcpy(dname[cnt], dnamed[i]);
2701 for (i = 0; i < f; i++, cnt++)
2702 strcpy(dname[cnt], dnamef[i]);
2703
2704 /* Print entries. */
2705 for (y = 0, i = 0; i < FS_H-10; i++, y++) {
2706 if (i == nument) break;
2707
2708 strncpy(strbuf, dname[i+current], 48);
2709 strbuf[48] = '\0';
2710
2711 stat(dname[i+current], sbuf);
2712 file_size =
2713 (((float)(sbuf->st_size)) / 1024.0);
2714 file_sizeb = sbuf->st_size;
2715 if (S_ISDIR(sbuf->st_mode)) {
2716 if (i == current)
2717 wattrset(win, COLOR_PAIR(CYAN_BLUE)|A_BOLD);
2718 else
2719 wattrset(win, COLOR_PAIR(WHITE)|A_BOLD);
2720 mvwprintw(win, y+5, 1, "%-48s", strbuf);
2721 wattrset(win, COLOR_PAIR(WHITE)|A_NORMAL);
2722 wprintw(win, " ");
2723
2724 } else {
2725 if (i == current)
2726 wattrset(win, COLOR_PAIR(CYAN_BLUE)|A_BOLD);
2727 else
2728 wattrset(win, COLOR_PAIR(WHITE)|A_NORMAL);
2729
2730 mvwprintw(win, y+5, 1, "%-48s %9d", strbuf,
2731 file_sizeb);
2732 }
2733
2734 }
2735
2736 wattrset(win, A_NORMAL);
2737 for (; y < FS_H-10; y++)
2738 mvwprintw(win, y+5, 1, "%-58s", "");
2739
2740 wnoutrefresh(win);
2741 }
2742
2743 /*** Check symlink. ***/
check_symlink(char * dir)2744 static int check_symlink(char *dir)
2745 {
2746 int i;
2747 char strbuf[NAME_MAX+1], *ptr;
2748
2749 i = readlink(dir, strbuf, NAME_MAX);
2750 switch (i) {
2751 case 0:
2752 case -1:
2753 return -1;
2754 break;
2755
2756 default:
2757 /* not added by readlink */
2758 if (strbuf[i-1] == '/')
2759 strbuf[i-1] = '\0';
2760 else {
2761 strbuf[i] = '\0';
2762 }
2763
2764 if (strbuf[0] == '/') { /* absolute path */
2765 sprintf(dirname, strbuf);
2766 } else {
2767 i = strlen((ptr = rindex(dir, '/')));
2768 fprintf(stderr, "%s\n", strbuf);
2769 sprintf(ptr+1, strbuf);
2770 }
2771 break;
2772 }
2773
2774 return 0;
2775 }
2776
2777 /*** Check directory entry. ***/
check_dentry(char * name,WINDOW * win)2778 static void check_dentry(char *name, WINDOW *win)
2779 {
2780 char *tmpstr;
2781 char strbuf[NAME_MAX+1];
2782 int len1, len2, len3;
2783 struct stat _sbuf, *sbuf = &_sbuf;
2784
2785 check_symlink(dirname);
2786 stat(name, sbuf);
2787 if (S_ISDIR(sbuf->st_mode)) {
2788 if (strcmp(name, "..") == 0) {
2789 len1 = strlen(dirname);
2790 len2 = strlen(tmpstr = rindex(dirname, '/'));
2791 len3 = len1 - len2;
2792 if (len3 == 0)
2793 sprintf(dirname, "/");
2794 else
2795 dirname[len3] = '\0';
2796 } else {
2797 if (strlen(dirname) == 1)
2798 sprintf(dirname, "%s%s", dirname, name);
2799 else
2800 sprintf(dirname, "%s/%s", dirname, name);
2801 }
2802
2803 check_symlink(name);
2804 chdir(name);
2805 dentry=opendir(".");
2806 current = 0;
2807 print_dir(win);
2808 closedir(dentry);
2809
2810 mvwprintw(win, FS_H-4, 1, "%-48s", "File:");
2811 wattrset(win, A_BOLD);
2812 mvwaddch(win, FS_H-4, 1, 'F');
2813 wattrset(win, A_NORMAL);
2814
2815 } else if (S_ISREG(sbuf->st_mode)) {
2816 wattrset(win, (COLOR_PAIR(WHITE)|A_NORMAL));
2817 strncpy(strbuf, dname[current], 42);
2818 strbuf[42] = '\0';
2819
2820 mvwprintw(win, FS_H-4, 1, "File: %-42s", strbuf);
2821 strcpy(modpath, name);
2822 wattrset(win, A_BOLD);
2823 mvwaddch(win, FS_H-4, 1, 'F');
2824 wattrset(win, A_NORMAL);
2825 }
2826 }
2827
2828 /*** File selector buttons. ***/
fs_buttons(WINDOW * win)2829 static int fs_buttons(WINDOW *win)
2830 {
2831 int c;
2832 int in_loop = 1;
2833 fs_val = 0;
2834
2835 wattrset(win, A_REVERSE);
2836 mvwprintw(win, FS_H-2, 16, "[ OK ]");
2837 wattrset(win, A_NORMAL);
2838 mvwprintw(win, FS_H-2, 34, "[ Cancel ]");
2839
2840 wnoutrefresh(win);
2841 doupdate();
2842
2843 while (in_loop) {
2844 switch ((c = wgetch(win))) {
2845 case KEY_RIGHT:
2846 wattrset(win, A_NORMAL);
2847 mvwprintw(win, FS_H-2, 16, "[ OK ]");
2848 wattrset(win, A_REVERSE);
2849 mvwprintw(win, FS_H-2, 34, "[ Cancel ]");
2850 fs_val = 1;
2851 break;
2852 case KEY_LEFT:
2853 wattrset(win, A_REVERSE);
2854 mvwprintw(win, FS_H-2, 16, "[ OK ]");
2855 wattrset(win, A_NORMAL);
2856 mvwprintw(win, FS_H-2, 34, "[ Cancel ]");
2857 fs_val = 0;
2858 break;
2859 case KEY_TAB:
2860 wattrset(win, A_NORMAL);
2861 mvwprintw(win, FS_H-2, 16, "[ OK ]");
2862 mvwprintw(win, FS_H-2, 34, "[ Cancel ]");
2863 fs_val = 2;
2864 in_loop = 0;
2865 continue;
2866 break;
2867 case KEY_ENTER:
2868 in_loop = 0;
2869 continue;
2870 break;
2871 }
2872
2873
2874 if (mod && playing) {
2875 refresh_info();
2876 refresh_module_info();
2877 doupdate();
2878 update_panels();
2879 MikMod_Update();
2880 }
2881 }
2882
2883 return fs_val;
2884 }
2885
2886 /*** Enter file selector. ***/
file_select(void)2887 static char *file_select(void)
2888 {
2889 int i;
2890 int in_loop = 1;
2891 int tabsw = 0;
2892 char strbuf[NAME_MAX+1];
2893 WINDOW *tmpwin;
2894 struct stat sbuf;
2895
2896 fswin = tmpwin = newwin(FS_H, FS_W, FS_Y, FS_X);
2897 keypad(tmpwin, TRUE);
2898 wtimeout(tmpwin, DELAY);
2899 box(tmpwin, 0, 0);
2900 fspan = new_panel(fswin);
2901
2902 wattrset(tmpwin, (COLOR_PAIR(WHITE)|A_NORMAL));
2903 mvwprintw(tmpwin, 0, 2, "[ ]");
2904 wattrset(tmpwin, (COLOR_PAIR(YELLOW)|A_BOLD));
2905 mvwprintw(tmpwin, 0, 4, "Select file");
2906
2907 wattrset(tmpwin, A_NORMAL);
2908 mvwprintw(tmpwin, FS_H-4, 1, "File: ");
2909 wattrset(tmpwin, A_BOLD);
2910 mvwaddch(tmpwin, FS_H-4, 1, 'F');
2911 wattrset(tmpwin, A_NORMAL);
2912
2913 mvwaddch(tmpwin, 4, 0, ACS_LTEE);
2914 mvwaddch(tmpwin, FS_H-3, 0, ACS_LTEE);
2915 mvwaddch(tmpwin, FS_H-5, 0, ACS_LTEE);
2916 for (i = 1; i < FS_W-1; i++) {
2917 mvwaddch(tmpwin, 4, i, ACS_HLINE);
2918 mvwaddch(tmpwin, FS_H-3, i, ACS_HLINE);
2919 mvwaddch(tmpwin, FS_H-5, i, ACS_HLINE);
2920 }
2921 mvwaddch(tmpwin, 4, FS_W-1, ACS_RTEE);
2922 mvwaddch(tmpwin, FS_H-3, FS_W-1, ACS_RTEE);
2923 mvwaddch(tmpwin, FS_H-5, FS_W-1, ACS_RTEE);
2924
2925 wattrset(tmpwin, A_NORMAL);
2926 mvwprintw(tmpwin, FS_H-2, 16, "[ OK ]");
2927 mvwprintw(tmpwin, FS_H-2, 34, "[ Cancel ]");
2928
2929 memset(modpath, 0, 256);
2930
2931 /* Check and open dir. */
2932 if (strlen(lastdir) == 0)
2933 sprintf(dirname, (getenv("PWD")));
2934 else
2935 sprintf(dirname, lastdir);
2936
2937 check_symlink(dirname);
2938 dentry = opendir(dirname);
2939 chdir(dirname);
2940 print_dir(tmpwin);
2941 closedir(dentry);
2942
2943 update_panels();
2944 doupdate();
2945
2946 /*** Loop ***/
2947 fspage = lastpage = 0;
2948 while (in_loop) {
2949 switch ((wgetch(tmpwin))) {
2950 case ERR: break;
2951
2952 case 'm':
2953 mp_move_panel(fspan);
2954 break;
2955
2956 /* Edit directory name. */
2957 case 'd': case 'D':
2958 stat(dname[current], &sbuf);
2959 if (S_ISREG(sbuf.st_mode) == 0)
2960 wattrset(tmpwin, A_BOLD);
2961 else
2962 wattrset(tmpwin, A_NORMAL);
2963 mvwprintw(tmpwin,
2964 (current%(FS_H-10))+5, 1,
2965 "%-48s", strbuf);
2966
2967 sprintf(lastdir, dirname);
2968 wattrset(tmpwin, A_REVERSE);
2969 get_string(tmpwin, 2, 1, "Dir: ", dirname);
2970 wattrset(tmpwin, A_NORMAL);
2971
2972 if (chdir(dirname)) {
2973 sprintf(dirname, lastdir);
2974 mvwprintw(tmpwin, 2, 1,
2975 "Dir: %-52s", dirname);
2976 wattrset(tmpwin, A_BOLD);
2977 mvwaddch(tmpwin, 2, 1, 'D');
2978
2979 wattrset(tmpwin, A_REVERSE);
2980 strncpy(strbuf, dname[current], 48);
2981 mvwprintw(tmpwin,
2982 (current%(FS_H-10))+5, 1,
2983 "%-48s", strbuf);
2984
2985 beep();
2986 break;
2987 }
2988
2989 current = 0;
2990 check_symlink(dirname);
2991 dentry = opendir(dirname);
2992 print_dir(tmpwin);
2993 closedir(dentry);
2994
2995 wattrset(tmpwin,
2996 COLOR_PAIR(CYAN_BLUE)|A_BOLD);
2997 strncpy(strbuf, dname[current], 48);
2998 mvwprintw(tmpwin,
2999 (current%(FS_H-10))+5, 1,
3000 "%-48s", strbuf);
3001 break;
3002
3003 /* Edit file name. */
3004 case 'f': case 'F':
3005 stat(dname[current], &sbuf);
3006 if (S_ISREG(sbuf.st_mode) == 0)
3007 wattrset(tmpwin, A_BOLD);
3008 else
3009 wattrset(tmpwin, A_NORMAL);
3010 mvwprintw(tmpwin,
3011 (current%(FS_H-10))+5, 1,
3012 "%-48s", strbuf);
3013
3014 wattrset(tmpwin, A_REVERSE);
3015 get_string(tmpwin,FS_H-4, 1,
3016 "File: ", modpath);
3017 wattrset(tmpwin, A_NORMAL);
3018
3019 if (strlen(modpath) != 0 &&
3020 getstrtab != 1) {
3021 fs_val = 0; /* OK */
3022 in_loop = 0;
3023 continue;
3024 }
3025
3026 mvwprintw(tmpwin, FS_H-4, 1,
3027 "File: %-52s", modpath);
3028
3029 wattrset(tmpwin,
3030 COLOR_PAIR(CYAN_BLUE)|A_BOLD);
3031 strncpy(strbuf, dname[current], 48);
3032 mvwprintw(tmpwin,
3033 (current%(FS_H-10))+5, 1,
3034 "%-48s", strbuf);
3035
3036 break;
3037
3038 /* Enter buttons (OK, Cancel). */
3039 case KEY_TAB:
3040 tabsw = 1-tabsw;
3041 if (tabsw == 1) {
3042 stat(dname[current], &sbuf);
3043 if (S_ISREG(sbuf.st_mode) == 0)
3044 wattrset(tmpwin, A_BOLD);
3045 else
3046 wattrset(tmpwin, A_NORMAL);
3047
3048 strncpy(strbuf, dname[current], 48);
3049 strbuf[48] = '\0';
3050 mvwprintw(tmpwin,
3051 (current%(FS_H-10))+5, 1,
3052 "%-48s", strbuf);
3053
3054 fs_buttons(tmpwin);
3055
3056 if (fs_val != 2) {
3057 in_loop = 0;
3058 continue;
3059 }
3060 tabsw = 0;
3061 }
3062
3063 if (tabsw == 0) {
3064 strncpy(strbuf, dname[current], 48);
3065 strbuf[48] = '\0';
3066 wattrset(tmpwin,
3067 COLOR_PAIR(CYAN_BLUE)|A_BOLD);
3068 mvwprintw(tmpwin,
3069 (current%(FS_H-10))+5, 1,
3070 "%-48s", strbuf);
3071 }
3072 break;
3073
3074 case KEY_ENTER:
3075 check_dentry(dname[current], tmpwin);
3076 break;
3077
3078 /* Up. */
3079 case KEY_UP:
3080 stat(dname[current], &sbuf);
3081
3082 if (S_ISREG(sbuf.st_mode) == 0)
3083 wattrset(tmpwin, A_BOLD);
3084 else
3085 wattrset(tmpwin, A_NORMAL);
3086
3087 strncpy(strbuf, dname[current], 48);
3088 strbuf[48] = '\0';
3089 mvwprintw(tmpwin, (current%(FS_H-10))+5, 1,
3090 "%-48s", strbuf);
3091
3092 if (current > 0) current--;
3093 fspage = (current/(FS_H-10));
3094 if (lastpage > fspage) {
3095 lastpage = fspage;
3096 list_dir(tmpwin);
3097 }
3098
3099 wattrset(tmpwin, COLOR_PAIR(CYAN_BLUE)|A_BOLD);
3100 strncpy(strbuf, dname[current], 48);
3101 strbuf[48] = '\0';
3102 mvwprintw(tmpwin, (current%(FS_H-10))+5, 1,
3103 "%-48s", strbuf);
3104 break;
3105 case KEY_PPAGE:
3106 wattrset(tmpwin, A_NORMAL);
3107 mvwprintw(tmpwin, (current%(FS_H-10))+5, 1,
3108 "%-48s", dname[current]);
3109 if (((fspage-1)*(FS_H-10)) >= 0)
3110 current = (--fspage*(FS_H-10));
3111 else
3112 current = 0;
3113
3114 fspage = (current/(FS_H-10));
3115 if (lastpage > fspage) {
3116 lastpage = fspage;
3117 list_dir(tmpwin);
3118 }
3119
3120 wattrset(tmpwin, COLOR_PAIR(CYAN_BLUE)|A_BOLD);
3121 mvwprintw(tmpwin, (current%(FS_H-10))+5, 1,
3122 "%-48s", dname[current]);
3123 break;
3124
3125 /* Down. */
3126 case KEY_DOWN:
3127 stat(dname[current], &sbuf);
3128
3129 if (S_ISREG(sbuf.st_mode) == 0)
3130 wattrset(tmpwin, A_BOLD);
3131 else
3132 wattrset(tmpwin, A_NORMAL);
3133
3134 strncpy(strbuf, dname[current], 48);
3135 strbuf[48] = '\0';
3136 mvwprintw(tmpwin, (current%(FS_H-10))+5, 1,
3137 "%-48s", strbuf);
3138
3139 if (current < nument-1) current++;
3140 fspage = (current/(FS_H-10));
3141 if (lastpage < fspage) {
3142 lastpage = fspage;
3143 list_dir(tmpwin);
3144 }
3145
3146 wattrset(tmpwin, COLOR_PAIR(CYAN_BLUE)|A_BOLD);
3147 strncpy(strbuf, dname[current], 48);
3148 strbuf[48] = '\0';
3149 mvwprintw(tmpwin, (current%(FS_H-10))+5, 1,
3150 "%-48s", strbuf);
3151 break;
3152 case KEY_NPAGE:
3153 wattrset(tmpwin, A_NORMAL);
3154 mvwprintw(tmpwin, (current%(FS_H-10))+5, 1,
3155 "%-48s", dname[current]);
3156
3157 if (((fspage+1)*(FS_H-10)) < nument)
3158 current = ((fspage+1)*(FS_H-10));
3159 else
3160 current = nument-1;
3161
3162 fspage = (current/(FS_H-10));
3163 lastpage = fspage;
3164
3165 list_dir(tmpwin);
3166 wattrset(tmpwin, COLOR_PAIR(CYAN_BLUE)|A_BOLD);
3167 mvwprintw(tmpwin, (current%(FS_H-10))+5, 1,
3168 "%-48s", dname[current]);
3169 break;
3170 }
3171
3172 if (mod && playing) {
3173 refresh_info();
3174 refresh_module_info();
3175 update_panels();
3176 doupdate();
3177
3178 MikMod_Update();
3179 }
3180
3181 update_panels();
3182 doupdate();
3183 }
3184 current = 0;
3185 sprintf(lastdir, dirname);
3186 sprintf(full_modname, "%s/%s", dirname, modpath);
3187
3188 del_panel(fspan);
3189 delwin(fswin);
3190 update_panels();
3191 doupdate();
3192
3193 if (fs_val == 0)
3194 return modpath;
3195 else
3196 return NULL;
3197 }
3198
3199 /*****************************************************************************/
3200
3201 /*** Display the load message. ***/
loading(int on)3202 static void loading(int on)
3203 {
3204 WINDOW *tmpwin = NULL;
3205
3206 if (on == 0) {
3207 delwin(tmpwin);
3208 touchwin(dspwin);
3209 doupdate();
3210
3211 return;
3212 }
3213
3214 tmpwin = newwin(5, 14, (LINES/2)-3, 33);
3215 box(tmpwin, 0, 0);
3216 wattrset(tmpwin, (COLOR_PAIR(GREEN)|A_BOLD));
3217 mvwprintw(tmpwin, 2, 2, "Loading...");
3218 wnoutrefresh(tmpwin);
3219 doupdate();
3220 }
3221
3222 /*** Display a message in a separate window and wait
3223 *** for user confirmation (OK). ***/
message(char * msg,int level)3224 static void message(char *msg, int level)
3225 {
3226 int c;
3227 int len = strlen(msg);
3228 WINDOW *tmpwin;
3229 PANEL *tmppan;
3230
3231 tmpwin = newwin(6, len+4, (LINES/2)-4, (COLS/2)-((len+4)/2));
3232 wtimeout(tmpwin, DELAY);
3233 keypad(tmpwin, TRUE);
3234 box(tmpwin, 0, 0);
3235 tmppan = new_panel(tmpwin);
3236
3237 if (level == ERROR_MSG)
3238 wattrset(tmpwin, (COLOR_PAIR(RED)|A_BOLD));
3239 else
3240 wattrset(tmpwin, (COLOR_PAIR(GREEN)|A_BOLD));
3241 mvwprintw(tmpwin, 1, 2, msg);
3242 wattrset(tmpwin, (COLOR_PAIR(WHITE)|A_REVERSE));
3243 mvwprintw(tmpwin, 4, (((len+4)/2)-3), "[ OK ]");
3244
3245 while ((c = wgetch(tmpwin)) != KEY_ENTER) {
3246 if (mod && playing) {
3247 refresh_info();
3248 refresh_module_info();
3249 update_panels();
3250 doupdate();
3251 MikMod_Update();
3252 }
3253 }
3254
3255 del_panel(tmppan);
3256 delwin(tmpwin);
3257 update_panels();
3258 doupdate();
3259 }
3260
3261 /*****************************************************************************/
3262
3263 /***
3264 *** Playlist.
3265 ***/
3266 int pl_val = 0;
3267 int pl_files = 0;
3268 int pl_cnt = 0;
3269 int pl_page = 0;
3270 int pl_entry = 0;
3271 int pl_playtime = 0;
3272 char need_to_clear = 0;
3273
3274 typedef struct {
3275 int played;
3276 char dir[NAME_MAX+1];
3277 char name[NAME_MAX+1];
3278 char fname[NAME_MAX+1]; /* full path */
3279 } list_entry;
3280
3281 list_entry list_files[4096];
3282
3283 #define MP_PL_HEADER "MP PLAYING LIST"
3284 #define MP_PL_HEADER_SIZE 15
3285
3286 /*** Load playlist file. ***/
load_pl_file(char * name)3287 static int load_pl_file(char *name)
3288 {
3289 char c;
3290 int cnt;
3291 int len;
3292
3293 FILE *file;
3294 char *fname;
3295 char buf[NAME_MAX+1];
3296
3297 /* Open file. */
3298 file = fopen(name, "r");
3299 if (file == NULL) {
3300 beep();
3301 sprintf(buf, "Can't open '%s'.", name);
3302 message(buf, ERROR_MSG);
3303 return -1;
3304 }
3305
3306 /* Check if it is an MP playlist file. */
3307 fread(buf, MP_PL_HEADER_SIZE, 1, file);
3308 buf[MP_PL_HEADER_SIZE] = '\0';
3309 if ((strncmp(buf, MP_PL_HEADER, MP_PL_HEADER_SIZE)) != 0) {
3310 beep();
3311 sprintf(buf, "Not a playlist file.");
3312 message(buf, ERROR_MSG);
3313 return -1;
3314 }
3315 fread(buf, 1, 1, file); /* skip '\n' */
3316
3317 /* Read data... */
3318 pl_files = 0;
3319 cnt = 0;
3320 memset(buf, 0, NAME_MAX);
3321 while ((fread(&c, 1, 1, file)) > 0) {
3322 if (c != '\n') {
3323 buf[cnt++] = c;
3324 continue;
3325 }
3326 cnt = 0;
3327
3328 sprintf(list_files[pl_files].fname, buf);
3329
3330 fname = rindex(buf, '/');
3331 fname[(strlen(fname)+1)] = '\0';
3332 sprintf(list_files[pl_files].name, fname+1);
3333
3334 len = ((strlen(buf)) - (strlen(fname)));
3335 buf[len] = '\0';
3336
3337 sprintf(list_files[pl_files].dir, buf);
3338
3339 pl_files++;
3340
3341 memset(buf, 0, NAME_MAX);
3342 }
3343
3344 /* Close file. */
3345 fclose(file);
3346
3347 return 0;
3348 }
3349
3350 /*** Save playlist file. ***/
save_pl_file(char * name)3351 static int save_pl_file(char *name)
3352 {
3353 int i;
3354
3355 FILE *file;
3356 char buf[NAME_MAX+1];
3357
3358 /* Open file. */
3359 file = fopen(name, "w");
3360 if (file == NULL) {
3361 beep();
3362 sprintf(buf, "Can't open '%s'.", name);
3363 message(buf, ERROR_MSG);
3364 return -1;
3365 }
3366
3367 /* Add header. */
3368 fwrite(MP_PL_HEADER, MP_PL_HEADER_SIZE, 1, file);
3369 fwrite("\n", 1, 1, file);
3370
3371 /* Write data... */
3372 for (i = 0; i < pl_files; i++) {
3373 sprintf(buf, "%s/%s\n",
3374 list_files[i].dir,
3375 list_files[i].name);
3376
3377 fwrite(buf, strlen(buf), 1, file);
3378 }
3379
3380 /* Close file. */
3381 fclose(file);
3382
3383 sprintf(buf, "'%s' saved.", name);
3384 message(buf, INFO_MSG);
3385
3386 return 0;
3387 }
3388
3389 /*** Refresh playlist. ***/
refresh_list_entries(WINDOW * win)3390 static void refresh_list_entries(WINDOW *win)
3391 {
3392 int i;
3393 int offset = (pl_page * (PL_H-2));
3394
3395 wattrset(win, (COLOR_PAIR(CYAN)|A_NORMAL));
3396 for (i = 0; i < PL_H-2; i++) {
3397 if (offset+i >= pl_files) {
3398 mvwprintw(win, i+1, 1,
3399 "%3d: %-48s",
3400 (pl_page * (PL_H-2))+i+1, "EMPTY");
3401 continue;
3402 }
3403 mvwprintw(win, i+1, 1, "%-48s", "");
3404 mvwprintw(win, i+1, 1, "%3d: %s/%s",
3405 offset+i+1,
3406 list_files[offset + i].dir,
3407 list_files[offset + i].name
3408 );
3409 }
3410
3411 wattrset(win, (COLOR_PAIR(WHITE)|A_NORMAL));
3412 mvwprintw(win, PL_H-1, PL_W-34, "[ %5d entries ]", pl_files);
3413 }
3414
3415 /*** Playlist module info. ***/
3416 #define MINF_H 12
3417 #define MINF_W 60
3418 #define MINF_X ((COLS/2)-(MINF_W/2))
3419 #define MINF_Y ((LINES/2)-(MINF_H/2))
pl_mod_info(char * path)3420 static void pl_mod_info(char *path)
3421 {
3422 int c;
3423 int in_loop = 1;
3424 struct stat sbuf;
3425 WINDOW *tmpwin;
3426 PANEL *tmppan;
3427 MODULE *infomod;
3428
3429 if (path == NULL)
3430 return;
3431
3432 tmpwin = newwin(MINF_H, MINF_W, MINF_Y, MINF_X);
3433 wtimeout(tmpwin, DELAY);
3434 keypad(tmpwin, TRUE);
3435 box(tmpwin, 0, 0);
3436 tmppan = new_panel(tmpwin);
3437
3438 wattrset(tmpwin, A_NORMAL);
3439 mvwprintw(tmpwin, 0, 2, "[ ]");
3440 wattrset(tmpwin, COLOR_PAIR(CYAN)|A_BOLD);
3441 mvwprintw(tmpwin, 0, 4, "Module info");
3442
3443 wattrset(tmpwin, COLOR_PAIR(YELLOW)|A_BOLD);
3444 mvwprintw(tmpwin, (MINF_H/2)-1, 16, "Please wait...");
3445 wnoutrefresh(tmpwin);
3446 doupdate();
3447 if ((infomod = Player_Load(path, 64, 0)) == NULL) {
3448 del_panel(tmppan);
3449 delwin(tmpwin);
3450 update_panels();
3451 doupdate();
3452 message(MikMod_strerror(MikMod_errno), ERROR_MSG);
3453
3454 return;
3455 }
3456 wattrset(tmpwin, COLOR_PAIR(WHITE)|A_NORMAL);
3457 stat(path, &sbuf);
3458 mvwprintw(tmpwin, (MINF_H/2)-1, 16, " ");
3459 mvwprintw(tmpwin, 1, 1, " File: %s - Size: %d",
3460 list_files[pl_entry].name,
3461 sbuf.st_size);
3462 mvwprintw(tmpwin, 2, 1, " Name: %s", infomod->songname);
3463 mvwprintw(tmpwin, 3, 1, " Type: %s", infomod->modtype);
3464 mvwprintw(tmpwin, 4, 1, " Chn: %d", infomod->numchn);
3465 mvwprintw(tmpwin, 5, 1, "Samples: %d", infomod->numsmp);
3466 mvwprintw(tmpwin, 6, 1, " Instr.: %d", infomod->numins);
3467 mvwprintw(tmpwin, 7, 1, " BMP: %d", infomod->bpm);
3468 mvwprintw(tmpwin, 8, 1, " Speed: %d", infomod->sngspd);
3469 mvwprintw(tmpwin, 9, 1, " Tempo: %d", infomod->inittempo);
3470 mvwprintw(tmpwin, 10, 1, " Vol: %d", infomod->initvolume);
3471 Player_Free(infomod);
3472
3473 while (in_loop) {
3474 switch ((c = wgetch(tmpwin))) {
3475 case 'q': case KEY_ESCAPE:
3476 in_loop = 0;
3477 continue;
3478 break;
3479 }
3480
3481 if (mod && playing) {
3482 refresh_info();
3483 refresh_module_info();
3484 update_panels();
3485 doupdate();
3486 MikMod_Update();
3487 }
3488 }
3489
3490 del_panel(tmppan);
3491 delwin(tmpwin);
3492 update_panels();
3493 doupdate();
3494 }
3495
3496 /*** Delete playlist entry. ***/
3497 #define PL_DEL 1
3498 #define PL_UP 2
3499 #define PL_DOWN 3
3500 #define PL_INFO 4
3501
handle_pl_entry(WINDOW * win,int action)3502 static void handle_pl_entry(WINDOW *win, int action)
3503 {
3504 int i;
3505 int c;
3506 int in_loop = 1;
3507 int lastpage = pl_page;
3508
3509 refresh_list_entries(win);
3510 wattrset(win, COLOR_PAIR(CYAN)|A_REVERSE);
3511 mvwprintw(win, (pl_entry % (PL_H-2))+1, 6,
3512 "%s", list_files[pl_entry].fname);
3513 wnoutrefresh(win);
3514 doupdate();
3515
3516 /*** Main loop. ***/
3517 while (in_loop) {
3518 switch ((c = wgetch(win))) {
3519 /* Cancel. */
3520 case KEY_ESCAPE:
3521 case KEY_TAB:
3522 in_loop = 0;
3523 continue;
3524 break;
3525
3526 /* Action. */
3527 case KEY_ENTER:
3528 if (action == PL_DEL) {
3529 memset(&list_files[pl_entry], 0,
3530 sizeof(list_entry));
3531
3532 if (pl_entry == pl_files-1) {
3533 if (pl_entry)
3534 pl_entry = 0;
3535 if (pl_files)
3536 pl_files--;
3537
3538 in_loop = 0;
3539 continue;
3540 }
3541
3542 for (i=pl_entry; i < pl_files-1; i++) {
3543 memcpy(&list_files[i],
3544 &list_files[i+1],
3545 (sizeof(list_entry)));
3546 }
3547 pl_files--;
3548
3549 in_loop = 0;
3550 continue;
3551
3552 } else if (action == PL_UP) {
3553 if (pl_entry > 0) {
3554 list_entry t;
3555 memcpy(&t,
3556 &list_files[pl_entry-1],
3557 (sizeof(list_entry)));
3558 memcpy(&list_files[pl_entry-1],
3559 &list_files[pl_entry],
3560 (sizeof(list_entry)));
3561 memcpy(&list_files[pl_entry],
3562 &t,
3563 (sizeof(list_entry)));
3564 }
3565
3566 in_loop = 0;
3567 continue;
3568
3569 } else if (action == PL_DOWN) {
3570 if (pl_entry < pl_files-1) {
3571 list_entry t;
3572 memcpy(&t,
3573 &list_files[pl_entry+1],
3574 (sizeof(list_entry)));
3575 memcpy(&list_files[pl_entry+1],
3576 &list_files[pl_entry],
3577 (sizeof(list_entry)));
3578 memcpy(&list_files[pl_entry],
3579 &t,
3580 (sizeof(list_entry)));
3581 }
3582
3583 in_loop = 0;
3584 continue;
3585
3586 } else if (action == PL_INFO) {
3587 if (playing) {
3588 message("Player is running.",
3589 ERROR_MSG);
3590 break;
3591 }
3592 pl_mod_info(list_files[pl_entry].fname);
3593 }
3594 break;
3595
3596 /* Select entry (up/down). */
3597 case KEY_UP:
3598 if (pl_entry > 0) {
3599 wattrset(win,
3600 COLOR_PAIR(CYAN)|A_NORMAL);
3601 mvwprintw(win,
3602 (pl_entry % (PL_H-2))+1,
3603 6, "%s",
3604 list_files[pl_entry].fname);
3605 pl_entry--;
3606 } else
3607 break;
3608
3609 pl_page = (pl_entry / (PL_H-2));
3610 if (lastpage != pl_page) {
3611 lastpage = pl_page;
3612 refresh_list_entries(win);
3613 }
3614
3615 wattrset(win,
3616 COLOR_PAIR(CYAN)|A_REVERSE);
3617 mvwprintw(win,
3618 (pl_entry % (PL_H-2))+1, 6, "%s",
3619 list_files[pl_entry].fname);
3620
3621 break;
3622 case KEY_PPAGE:
3623 if (pl_entry > 0) {
3624 wattrset(win,
3625 COLOR_PAIR(CYAN)|A_NORMAL);
3626 mvwprintw(win,
3627 (pl_entry % (PL_H-2))+1,
3628 6, "%s",
3629 list_files[pl_entry].fname);
3630 pl_entry--;
3631 } else
3632 break;
3633
3634 if (((pl_page-1)*(PL_H-2)) > 0) {
3635 pl_page--;
3636 pl_entry = pl_page * (PL_H-2);
3637 } else
3638 pl_entry = 0;
3639 pl_page = (pl_entry / (PL_H-2));
3640 if (lastpage != pl_page) {
3641 lastpage = pl_page;
3642 refresh_list_entries(win);
3643 }
3644
3645 refresh_list_entries(win);
3646
3647 wattrset(win,
3648 COLOR_PAIR(CYAN)|A_REVERSE);
3649 mvwprintw(win,
3650 (pl_entry % (PL_H-2))+1, 6, "%s",
3651 list_files[pl_entry].fname);
3652
3653 break;
3654
3655 case KEY_DOWN:
3656 if (pl_entry < pl_files-1) {
3657 wattrset(win,
3658 COLOR_PAIR(CYAN)|A_NORMAL);
3659 mvwprintw(win,
3660 (pl_entry % (PL_H-2))+1,
3661 6, "%s",
3662 list_files[pl_entry].fname);
3663 pl_entry++;
3664 } else
3665 break;
3666
3667 pl_page = (pl_entry / (PL_H-2));
3668 if (lastpage != pl_page) {
3669 lastpage = pl_page;
3670 refresh_list_entries(win);
3671 }
3672
3673 wattrset(win,
3674 COLOR_PAIR(CYAN)|A_REVERSE);
3675 mvwprintw(win,
3676 (pl_entry % (PL_H-2))+1, 6, "%s",
3677 list_files[pl_entry].fname);
3678
3679 break;
3680 case KEY_NPAGE:
3681 if (pl_entry < pl_files-1) {
3682 wattrset(win,
3683 COLOR_PAIR(CYAN)|A_NORMAL);
3684 mvwprintw(win,
3685 (pl_entry % (PL_H-2))+1,
3686 6, "%s",
3687 list_files[pl_entry].fname);
3688 pl_entry--;
3689 } else
3690 break;
3691
3692 if (((pl_page+1)*(PL_H-2)) < pl_files-1) {
3693 pl_page++;
3694 pl_entry = pl_page * (PL_H-2);
3695 } else
3696 pl_entry = pl_files-1;
3697 pl_page = (pl_entry / (PL_H-2));
3698 if (lastpage != pl_page) {
3699 lastpage = pl_page;
3700 refresh_list_entries(win);
3701 }
3702
3703 refresh_list_entries(win);
3704
3705 wattrset(win,
3706 COLOR_PAIR(CYAN)|A_REVERSE);
3707 mvwprintw(win,
3708 (pl_entry % (PL_H-2))+1, 6, "%s",
3709 list_files[pl_entry].fname);
3710
3711 break;
3712 }
3713
3714 if (mod && playing) {
3715 refresh_info();
3716 refresh_module_info();
3717 update_panels();
3718 doupdate();
3719 MikMod_Update();
3720 }
3721 }
3722
3723 wattrset(win, COLOR_PAIR(CYAN)|A_NORMAL);
3724 mvwprintw(win, (pl_entry % (PL_H-2))+1, 6,
3725 "%s", list_files[pl_entry].fname);
3726
3727 refresh_list_entries(win);
3728 wnoutrefresh(win);
3729 doupdate();
3730 }
3731
3732 /*** Playlist buttons. ***/
pl_buttons(WINDOW * win)3733 static int pl_buttons(WINDOW *win)
3734 {
3735 int i, c;
3736 int ys;
3737 int in_loop = 1;
3738 char *name;
3739 char *pl_btns[10] = {
3740 "[ Add file ]",
3741 "[ Add dir ]",
3742 "[ Remove ]",
3743 "[ Clear ]",
3744 "[ Move up ]",
3745 "[ Move down ]",
3746 "[ Info ]",
3747 "[ Load ]",
3748 "[ Save ]",
3749 "[ Done ]"
3750 };
3751 struct stat sbuf;
3752
3753 pl_val = 0;
3754
3755 wattrset(win, COLOR_PAIR(WHITE)|A_NORMAL);
3756 for (i = 0, ys = 0; i < 10; i++, ys++) {
3757 if (pl_val == i)
3758 wattrset(win, A_REVERSE);
3759 else
3760 wattrset(win, A_NORMAL);
3761
3762 mvwprintw(win, 2+(ys*2), (PL_W-15), "%s", pl_btns[i]);
3763 }
3764
3765 while (in_loop) {
3766 switch ((c = wgetch(win))) {
3767 /* Quit playlist. */
3768 case 'q':
3769 pl_val = 255;
3770 in_loop = 0;
3771 continue;
3772 break;
3773
3774 /* Move. */
3775 case 'm':
3776 mp_move_panel(plpan);
3777 break;
3778
3779 /* Down. */
3780 case KEY_NPAGE:
3781 wattrset(win, A_NORMAL);
3782 mvwprintw(win, 2+(pl_val*2), PL_W-15,
3783 "%s", pl_btns[pl_val]);
3784 pl_val = 9;
3785 wattrset(win, A_REVERSE);
3786 mvwprintw(win, 2+(pl_val*2), PL_W-15,
3787 "%s", pl_btns[pl_val]);
3788 break;
3789 case KEY_DOWN:
3790 wattrset(win, A_NORMAL);
3791 mvwprintw(win, 2+(pl_val*2), PL_W-15,
3792 "%s", pl_btns[pl_val]);
3793 if (pl_val < 9) pl_val++;
3794 wattrset(win, A_REVERSE);
3795 mvwprintw(win, 2+(pl_val*2), PL_W-15,
3796 "%s", pl_btns[pl_val]);
3797 break;
3798
3799 /* Up. */
3800 case KEY_PPAGE:
3801 wattrset(win, A_NORMAL);
3802 mvwprintw(win, 2+(pl_val*2), PL_W-15,
3803 "%s", pl_btns[pl_val]);
3804 pl_val = 0;
3805 wattrset(win, A_REVERSE);
3806 mvwprintw(win, 2+(pl_val*2), PL_W-15,
3807 "%s", pl_btns[pl_val]);
3808 break;
3809 case KEY_UP:
3810 wattrset(win, A_NORMAL);
3811 mvwprintw(win, 2+(pl_val*2), PL_W-15,
3812 "%s", pl_btns[pl_val]);
3813 if (pl_val > 0) pl_val--;
3814 wattrset(win, A_REVERSE);
3815 mvwprintw(win, 2+(pl_val*2), PL_W-15,
3816 "%s", pl_btns[pl_val]);
3817 break;
3818
3819 /* Visit playlist. */
3820 case KEY_TAB:
3821 if (pl_files > 0) {
3822 wattrset(win, A_NORMAL);
3823 mvwprintw(win, 2+(pl_val*2), PL_W-15,
3824 "%s", pl_btns[pl_val]);
3825 wnoutrefresh(win);
3826 doupdate();
3827
3828 handle_pl_entry(win, 0);
3829
3830 wattrset(win, A_REVERSE);
3831 mvwprintw(win, 2+(pl_val*2), PL_W-15,
3832 "%s", pl_btns[pl_val]);
3833 wnoutrefresh(win);
3834 doupdate();
3835 }
3836 break;
3837
3838 /* Action. */
3839 case KEY_ENTER:
3840 /* Add file. */
3841 if (pl_val == 0) {
3842 name = file_select();
3843 if (name!=NULL && (strlen(name)) > 0) {
3844 sprintf(list_files[pl_files].fname,
3845 "%s/%s", lastdir, name);
3846 sprintf(list_files[pl_files].name,
3847 name);
3848 sprintf(list_files[pl_files].dir,
3849 lastdir);
3850
3851 pl_files++;
3852 }
3853
3854 touchwin(win);
3855 refresh_list_entries(win);
3856
3857 /* Add dir. */
3858 } else if (pl_val == 1) {
3859 file_select();
3860 if (fs_val != 0) break;
3861
3862 for (i = 0; i < nument; i++) {
3863 stat(dname[i], &sbuf);
3864 if (S_ISREG(sbuf.st_mode)) {
3865 sprintf(
3866 list_files[pl_files].fname,
3867 "%s/%s", lastdir, dname[i]);
3868 sprintf(
3869 list_files[pl_files].name,
3870 dname[i]);
3871 sprintf(
3872 list_files[pl_files].dir,
3873 lastdir);
3874 pl_files++;
3875 }
3876 }
3877
3878 touchwin(win);
3879 refresh_list_entries(win);
3880
3881 /* Remove. */
3882 } else if (pl_val == 2) {
3883 if (pl_files > 0) {
3884 wattrset(win, A_NORMAL);
3885 mvwprintw(win, 2+(pl_val*2),
3886 PL_W-15,
3887 "%s", pl_btns[pl_val]);
3888 wnoutrefresh(win);
3889 doupdate();
3890
3891 handle_pl_entry(win, PL_DEL);
3892
3893 wattrset(win, A_REVERSE);
3894 mvwprintw(win, 2+(pl_val*2),
3895 PL_W-15,
3896 "%s", pl_btns[pl_val]);
3897 wnoutrefresh(win);
3898 doupdate();
3899 }
3900
3901 /* Clear. */
3902 } else if (pl_val == 3) {
3903 for (i = 0; i < pl_files; i++) {
3904 memset(&list_files[i],
3905 0, sizeof(list_entry));
3906 }
3907 pl_files = 0;
3908 refresh_list_entries(win);
3909
3910 /* Move up. */
3911 } else if (pl_val == 4) {
3912 if (pl_files > 0) {
3913 wattrset(win, A_NORMAL);
3914 mvwprintw(win, 2+(pl_val*2),
3915 PL_W-15,
3916 "%s", pl_btns[pl_val]);
3917 wnoutrefresh(win);
3918 doupdate();
3919
3920 handle_pl_entry(win, PL_UP);
3921
3922 wattrset(win, A_REVERSE);
3923 mvwprintw(win, 2+(pl_val*2),
3924 PL_W-15,
3925 "%s", pl_btns[pl_val]);
3926
3927 wnoutrefresh(win);
3928 doupdate();
3929 }
3930 refresh_list_entries(win);
3931
3932 /* Move down. */
3933 } else if (pl_val == 5) {
3934 if (pl_files > 0) {
3935 wattrset(win, A_NORMAL);
3936 mvwprintw(win, 2+(pl_val*2),
3937 PL_W-15,
3938 "%s", pl_btns[pl_val]);
3939 wnoutrefresh(win);
3940 doupdate();
3941
3942 handle_pl_entry(win, PL_DOWN);
3943
3944 wattrset(win, A_REVERSE);
3945 mvwprintw(win, 2+(pl_val*2),
3946 PL_W-15,
3947 "%s", pl_btns[pl_val]);
3948
3949 wnoutrefresh(win);
3950 doupdate();
3951 }
3952 refresh_list_entries(win);
3953
3954 /* Info. */
3955 } else if (pl_val == 6) {
3956 if (pl_files > 0) {
3957 wattrset(win, A_NORMAL);
3958 mvwprintw(win, 2+(pl_val*2),
3959 PL_W-15,
3960 "%s", pl_btns[pl_val]);
3961 wnoutrefresh(win);
3962 doupdate();
3963
3964 handle_pl_entry(win, PL_INFO);
3965
3966 wattrset(win, A_REVERSE);
3967 mvwprintw(win, 2+(pl_val*2),
3968 PL_W-15,
3969 "%s", pl_btns[pl_val]);
3970 wnoutrefresh(win);
3971 doupdate();
3972 }
3973 refresh_list_entries(win);
3974
3975 /* Load. */
3976 } else if (pl_val == 7) {
3977 char *f = file_select();
3978 if (f == NULL) {
3979 touchwin(win);
3980 break;
3981 }
3982 sprintf(pl_file, "%s/%s",
3983 lastdir, f);
3984 load_pl_file(pl_file);
3985
3986 refresh_list_entries(win);
3987 touchwin(win);
3988
3989 /* Save. */
3990 } else if (pl_val == 8) {
3991 char *f = file_select();
3992 if (f == NULL) {
3993 touchwin(win);
3994 break;
3995 }
3996 sprintf(pl_file, "%s/%s",
3997 lastdir, f);
3998 save_pl_file(pl_file);
3999
4000 refresh_list_entries(win);
4001 touchwin(win);
4002
4003 /* Done. */
4004 } else if (pl_val == 9) {
4005 if (pl_files)
4006 in_playlist = 1;
4007 in_loop = 0;
4008
4009 continue;
4010 }
4011 break;
4012 }
4013
4014 if (mod && playing) {
4015 refresh_info();
4016 refresh_module_info();
4017 update_panels();
4018 doupdate();
4019 MikMod_Update();
4020 }
4021 }
4022
4023 return pl_val;
4024 }
4025
4026 /*** Playlist handler (called with alarm(1)) ***/
update_playlist(int unused)4027 void update_playlist(int unused)
4028 {
4029 int i;
4030
4031 if (in_playlist) {
4032 if (mod->sngpos >= mod->numpos) { /* end of module */
4033 wattrset(dspwin, COLOR_PAIR(WHITE)|A_NORMAL);
4034 for (i = 1; i < 40; i++)
4035 mvwaddch(dspwin, DSP_H-1, i, ACS_HLINE);
4036
4037 pl_playtime += mod->sngtime;
4038 if (!random_mode) {
4039 if (pl_cnt < pl_files-1) {
4040 pl_cnt++;
4041 refresh_pl_info();
4042
4043 loading(1);
4044 play_module(list_files[pl_cnt].fname);
4045 loading(0);
4046
4047 touchwin(dspwin);
4048
4049 } else {
4050 mvwprintw(dspwin, DSP_H-1, 2,
4051 "[ Playlist finished %3d/%3d (%02d:%02d) ]",
4052 pl_cnt+1,
4053 pl_files,
4054 (pl_playtime/1000)/60,
4055 (pl_playtime/1000)%60);
4056
4057 in_playlist = 0;
4058 need_to_clear = 1;
4059 }
4060
4061 } else { /* random_mode */
4062 if (pl_cnt < pl_files-1) {
4063 int i = 1 +
4064 (((float) pl_files-1) * \
4065 rand()) / (RAND_MAX+1.0);
4066 pl_cnt++;
4067 pl_playtime += mod->sngtime;
4068 refresh_pl_info();
4069
4070 loading(1);
4071 play_module(list_files[i].fname);
4072 loading(0);
4073
4074 touchwin(dspwin);
4075 }
4076 }
4077 }
4078
4079 } else {
4080 for (i = 1; i < 40; i++); /* reset last line */
4081 // mvwaddch(dspwin, DSP_H-1, i, ACS_HLINE);
4082 }
4083
4084 alarm(1);
4085 }
4086
4087 /*** Install playlist handler ***/
install_pl_handler(void)4088 void install_pl_handler(void)
4089 {
4090 pl_cnt = 0;
4091
4092 signal(SIGALRM, update_playlist);
4093
4094 alarm(1);
4095 }
4096
4097 /*** Refresh playlist information (bottom of screen) ***/
refresh_pl_info(void)4098 static void refresh_pl_info(void)
4099 {
4100 int i;
4101
4102 wattrset(dspwin, COLOR_PAIR(WHITE)|A_NORMAL);
4103 for (i = 1; i < 48; i++)
4104 mvwaddch(dspwin, DSP_H-1, i, ACS_HLINE);
4105 mvwprintw(dspwin, DSP_H-1, 2, "[ ]");
4106 wattrset(dspwin, COLOR_PAIR(YELLOW_BLUE)|A_BOLD);
4107 mvwprintw(dspwin, DSP_H-1, 4, "Playlist:");
4108 wattrset(dspwin, COLOR_PAIR(WHITE)|A_NORMAL);
4109 mvwprintw(dspwin, DSP_H-1, 16, "%3d/%3d (%02d:%02d)",
4110 pl_cnt+1,
4111 pl_files,
4112 ((mod->sngtime+pl_playtime)/1000)/60,
4113 ((mod->sngtime+pl_playtime)/1000)%60);
4114 }
4115
4116 /*** Enter playlist. ***/
playlist(void)4117 static void playlist(void)
4118 {
4119 int i;
4120 WINDOW *tmpwin;
4121
4122 plwin = tmpwin = newwin(PL_H, PL_W, PL_Y, PL_X);
4123 keypad(tmpwin, TRUE);
4124 wtimeout(tmpwin, DELAY);
4125 box(tmpwin, 0, 0);
4126 plpan = new_panel(plwin);
4127
4128 wattrset(tmpwin, (COLOR_PAIR(WHITE)|A_NORMAL));
4129 mvwprintw(tmpwin, 0, 2,
4130 "[ ]");
4131 wattrset(tmpwin, (COLOR_PAIR(YELLOW)|A_BOLD));
4132 mvwprintw(tmpwin, 0, 4,
4133 " Playlist (press 'q' to quit without starting)");
4134
4135 wattrset(tmpwin, (COLOR_PAIR(WHITE)|A_NORMAL));
4136 for (i = 1; i < PL_H-1; i++)
4137 mvwaddch(tmpwin, i, PL_W-17, ACS_VLINE);
4138 mvwaddch(tmpwin, PL_H-1, PL_W-17, ACS_BTEE);
4139
4140 refresh_list_entries(tmpwin);
4141 pl_buttons(tmpwin);
4142
4143 del_panel(plpan);
4144 delwin(plwin);
4145 refresh_info();
4146 refresh_module_info();
4147 touchwin(dspwin);
4148 update_panels();
4149 doupdate();
4150 }
4151
4152 /*****************************************************************************/
4153
4154 /*** Draw a gauge. ***/
draw_gauge(WINDOW * win,int x,int y,int pc,int vh,int style)4155 static void draw_gauge(WINDOW *win, int x, int y, int pc, int vh, int style)
4156 {
4157 int i;
4158 int c = 0;
4159 int ipc = pc;
4160
4161 if (pc > 100)
4162 pc = 100;
4163
4164 if (style == 1 && vh == 1) {
4165 c = ' ';
4166 if (pc < 30)
4167 wattrset(win, COLOR_PAIR(GREEN)|A_REVERSE);
4168 else
4169 wattrset(win, COLOR_PAIR(CYAN)|A_REVERSE);
4170 } else if (style == 1 && vh == 0) {
4171 wattrset(win, COLOR_PAIR(BLUE)|A_REVERSE);
4172 c = ' ';
4173 } else if (style == 2)
4174 c = ACS_BULLET;
4175 else if (style == 3) {
4176 if (vh == 1)
4177 c = ACS_RARROW;
4178 else
4179 c = ACS_UARROW;
4180 } else if (style == 4)
4181 c = '*';
4182 else if (style == 5)
4183 c = '#';
4184
4185 if (vh) { /* horizontal */
4186 pc /= 5;
4187
4188 for (i = 0; i < pc; i++)
4189 mvwaddch(win, y, x+i, c);
4190
4191 if (style == 1)
4192 wattrset(win, COLOR_PAIR(GREEN)|A_NORMAL);
4193
4194 for (; i < 20; i++)
4195 mvwaddch(win, y, x+i, ' ');
4196
4197 if (pc == 20) {
4198 if (style == 1) {
4199 c = ' ';
4200 wattrset(win, COLOR_PAIR(RED_RED)|A_NORMAL);
4201 } else
4202 wattrset(win, COLOR_PAIR(RED)|A_BOLD);
4203
4204 mvwaddch(win, y, x+i-1, c);
4205
4206 wattrset(win, COLOR_PAIR(RED)|A_BOLD);
4207 wprintw(win, " %3d%%", ipc);
4208
4209 } else {
4210 wattrset(win, COLOR_PAIR(WHITE)|A_NORMAL);
4211 wprintw(win, " %3d%%", ipc);
4212 }
4213
4214 } else { /* vertical */
4215 pc /= 10;
4216
4217 if (style == 1)
4218 wattrset(win, COLOR_PAIR(BLUE)|A_REVERSE);
4219 else
4220 wattrset(win, COLOR_PAIR(BLUE)|A_NORMAL);
4221
4222 for (i = 0; i < pc; i++)
4223 mvwaddch(win, y-i, x, c);
4224
4225 if (style == 1)
4226 wattrset(win, COLOR_PAIR(BLUE)|A_NORMAL);
4227 wattrset(win, COLOR_PAIR(BLUE)|A_BOLD);
4228 for (; i < 10; i++)
4229 mvwaddch(win, y-i, x, ACS_HLINE);
4230
4231 if (pc == 10) {
4232 if (style == 1) {
4233 c = ' ';
4234 wattrset(win, COLOR_PAIR(RED_RED)|A_BOLD);
4235 } else
4236 wattrset(win, COLOR_PAIR(RED)|A_NORMAL);
4237
4238 mvwaddch(win, y-i+1, x, c);
4239 }
4240 }
4241 }
4242
4243 /*** Draw channel pointer. ***/
draw_pointer(void)4244 static void draw_pointer(void)
4245 {
4246 wattrset(dspwin, (COLOR_PAIR(WHITE|A_NORMAL)));
4247 mvwaddch(dspwin, (oldcurch%(DSP_H-CHN_START))+CHN_START-1, 0, oldc1);
4248 mvwaddch(dspwin, (oldcurch%(DSP_H-CHN_START))+CHN_START-1, 3, oldc2);
4249 oldc1 = mvwinch(dspwin, (curch%(DSP_H-CHN_START))+CHN_START-1, 0);
4250 oldc2 = mvwinch(dspwin, (curch%(DSP_H-CHN_START))+CHN_START-1, 3);
4251 oldcurch = curch;
4252 mvwaddch(dspwin, (curch%(DSP_H-CHN_START))+CHN_START-1, 0, '>');
4253 mvwaddch(dspwin, (curch%(DSP_H-CHN_START))+CHN_START-1, 3, '<');
4254 }
4255
4256 /*** Display help. ***/
display_help(void)4257 static void display_help(void)
4258 {
4259 int c, in_loop = 1;
4260
4261 helpwin = newwin(HELP_H, HELP_W, HELP_Y, HELP_X);
4262 wtimeout(helpwin, DELAY);
4263 keypad(helpwin, TRUE);
4264 box(helpwin, 0, 0);
4265
4266 helppan = new_panel(helpwin);
4267 top_panel(helppan);
4268
4269 wattrset(helpwin, COLOR_PAIR(WHITE)|A_NORMAL);
4270 mvwprintw(helpwin, 0, 2, "[ ]");
4271 wattrset(helpwin, COLOR_PAIR(YELLOW)|A_BOLD);
4272 mvwprintw(helpwin, 0, 4, "Help");
4273
4274 /* COL 1 */
4275 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4276 mvwprintw(helpwin, 1, 2, "Play or pause.............");
4277 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4278 wprintw(helpwin, "p");
4279
4280 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4281 mvwprintw(helpwin, 2, 2, "Stop module...............");
4282 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4283 wprintw(helpwin, "t");
4284
4285 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4286 mvwprintw(helpwin, 3, 2, "Module comment............");
4287 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4288 wprintw(helpwin, "i");
4289
4290 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4291 mvwprintw(helpwin, 4, 2, "Restart pattern...........");
4292 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4293 wprintw(helpwin, "a");
4294
4295 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4296 mvwprintw(helpwin, 5, 2, "Restart module............");
4297 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4298 wprintw(helpwin, "A");
4299
4300 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4301 mvwprintw(helpwin, 7, 2, "Next position.............");
4302 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4303 wprintw(helpwin, "n");
4304
4305 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4306 mvwprintw(helpwin, 8, 2, "Next module...............");
4307 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4308 wprintw(helpwin, "N");
4309
4310 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4311 mvwprintw(helpwin, 9, 2, "Prev position.............");
4312 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4313 wprintw(helpwin, "v");
4314
4315 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4316 mvwprintw(helpwin, 10, 2, "Prev module...............");
4317 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4318 wprintw(helpwin, "V");
4319
4320 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4321 mvwprintw(helpwin, 12, 2, "File selector.............");
4322 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4323 wprintw(helpwin, "f");
4324
4325 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4326 mvwprintw(helpwin, 13, 2, "Quit MP or close panel....");
4327 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4328 wprintw(helpwin, "q");
4329
4330 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4331 mvwprintw(helpwin, 15, 2, "Show all channels.........");
4332 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4333 wprintw(helpwin, "c");
4334
4335 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4336 mvwprintw(helpwin, 16, 2, "Show all voices...........");
4337 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4338 wprintw(helpwin, "T");
4339
4340 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4341 mvwprintw(helpwin, 17, 2, "Voices position...........");
4342 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4343 wprintw(helpwin, "Y");
4344
4345 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4346 mvwprintw(helpwin, 18, 2, "Voices frequency..........");
4347 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4348 wprintw(helpwin, "y");
4349
4350 /* COL 2 */
4351 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4352 mvwprintw(helpwin, 1, 34, "Bpm up/down...............");
4353 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4354 wprintw(helpwin, "b/B");
4355
4356 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4357 mvwprintw(helpwin, 2, 34, "Reverb up/down............");
4358 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4359 wprintw(helpwin, "r/R");
4360
4361 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4362 mvwprintw(helpwin, 3, 34, "Tempo up/down.............");
4363 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4364 wprintw(helpwin, "k/K");
4365
4366 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4367 mvwprintw(helpwin, 4, 34, "Speed up/down.............");
4368 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4369 wprintw(helpwin, "s/S");
4370
4371 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4372 mvwprintw(helpwin, 5, 34, "Volume up/down............");
4373 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4374 wprintw(helpwin, "+/-");
4375
4376 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4377 mvwprintw(helpwin, 6, 34, "Reverse stereo............");
4378 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4379 wprintw(helpwin, "!");
4380
4381 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4382 mvwprintw(helpwin, 7, 34, "Switch volume display.....");
4383 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4384 wprintw(helpwin, "u");
4385
4386 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4387 mvwprintw(helpwin, 9, 34, "Playlist panel............");
4388 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4389 wprintw(helpwin, "l");
4390
4391 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4392 mvwprintw(helpwin, 10, 34, "Effects panel.............");
4393 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4394 wprintw(helpwin, "e");
4395
4396 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4397 mvwprintw(helpwin, 11, 34, "Options panel.............");
4398 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4399 wprintw(helpwin, "o");
4400
4401 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4402 mvwprintw(helpwin, 12, 34, "Samples panel.............");
4403 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4404 wprintw(helpwin, "w");
4405
4406 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4407 mvwprintw(helpwin, 13, 34, "Instruments panel.........");
4408 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4409 wprintw(helpwin, "W");
4410
4411 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4412 mvwprintw(helpwin, 15, 34, "Select channel............");
4413 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4414 wprintw(helpwin, "UP/DOWN");
4415
4416 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4417 mvwprintw(helpwin, 16, 34, "Mute/unmute channel.......");
4418 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4419 wprintw(helpwin, "ENTER");
4420
4421 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4422 mvwprintw(helpwin, 17, 34, "Mute/unmute all channels..");
4423 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4424 wprintw(helpwin, "M");
4425
4426 wattrset(helpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4427 mvwprintw(helpwin, 18, 34, "About.....................");
4428 wattrset(helpwin, COLOR_PAIR(CYAN)|A_BOLD);
4429 wprintw(helpwin, "?");
4430
4431 wnoutrefresh(helpwin);
4432 doupdate();
4433
4434 /*** Loop ***/
4435 while (in_loop) {
4436 switch ((c = wgetch(helpwin))) {
4437 case 'q': case 'Q': case KEY_ESCAPE:
4438 in_loop = 0;
4439 continue;
4440 break;
4441
4442 case 'm':
4443 mp_move_panel(helppan);
4444 break;
4445 }
4446
4447 if (mod && playing) {
4448 refresh_info();
4449 refresh_module_info();
4450 MikMod_Update();
4451 update_panels();
4452 doupdate();
4453 }
4454 }
4455
4456 del_panel(helppan);
4457 update_panels();
4458 doupdate();
4459 }
4460
4461
4462 /******************************************************************************/
4463
4464 /*** Show voices position. ***/
show_voices_pos(void)4465 static void show_voices_pos(void)
4466 {
4467 int i; /* counter */
4468 int c; /* character */
4469 int x; /* x position */
4470 int step; /* x step */
4471 int add; /* add to x */
4472 int pc; /* percent */
4473
4474 unsigned char pan; /* panning */
4475 float pos1, pos2; /* positions */
4476
4477 WINDOW *tmpwin; /* channel window (temporary) */
4478
4479 /* Create window. */
4480 tmpwin = newwin(VPOS_H, VPOS_W, VPOS_Y, VPOS_X);
4481 vposwin = tmpwin;
4482 wtimeout(tmpwin, DELAY);
4483 keypad(tmpwin, TRUE);
4484 box(tmpwin, 0, 0);
4485 vpospan = new_panel(tmpwin);
4486 wattrset(tmpwin, (COLOR_PAIR(CYAN_BLUE)|A_BOLD));
4487 mvwprintw(tmpwin, 0, 0, "%-68s", " Voices position");
4488 wattrset(tmpwin, A_NORMAL);
4489
4490 wattrset(tmpwin, (COLOR_PAIR(CYAN)|A_NORMAL));
4491
4492 /* Calculate x step and add. */
4493 if (mod->numchn <= 32)
4494 step = 2;
4495 else step = 1;
4496 add = step == 1 ? 1 : 0;
4497
4498 /* Display channel counter. */
4499 for (c = 0; c < mod->numchn; c++) {
4500 if (c == 0) {
4501 mvwaddch(tmpwin, VPOS_H-3, 2, '|');
4502 mvwprintw(tmpwin, VPOS_H-2, 2, "1");
4503 continue;
4504 }
4505
4506 if ((c % 4) == 0) {
4507 mvwaddch(tmpwin, VPOS_H-3, (c*step) + add, '|');
4508 mvwprintw(tmpwin, VPOS_H-2,
4509 (c*step) + add, "%d", c);
4510 }
4511 }
4512 mvwaddch(tmpwin, VPOS_H-3, (c*step) + add, '|');
4513 mvwprintw(tmpwin, VPOS_H-2, (c*step) + add, "%d", c);
4514
4515 /*** Loop ***/
4516 while ((c = wgetch(tmpwin)) != 'q') {
4517 if (c == KEY_ESCAPE)
4518 break;
4519 else if (c == 'e')
4520 effects();
4521 else if (c == 'o')
4522 options();
4523 else if (c == 'p')
4524 do_pause();
4525 else if (c == 'm')
4526 mp_move_panel(vpospan);
4527
4528 /* Draw voices. */
4529 for (x = 0, i = 0; i < mod->numchn; x += step, i++) {
4530 pos1 = get_voice_pos(i);
4531 pos2 = maxfreq[i];
4532 if (pos2 <= 0) pos2=1;
4533 pc = (int) (100.0 * (pos1 / pos2));
4534 draw_gauge(tmpwin, x+2, VPOS_H-4, pc, 0, gauge_style);
4535 if (step == 2)
4536 draw_gauge(tmpwin, x+3, VPOS_H-4,
4537 pc, 0, gauge_style);
4538
4539 /* Panning. */
4540 pan = (unsigned char) get_voice_panning(i);
4541 if (pan == 128)
4542 wattrset(tmpwin, COLOR_PAIR(BLUE)|A_BOLD);
4543 else if (pan == 0 || (pan > 0 && pan < 128))
4544 wattrset(tmpwin, COLOR_PAIR(MAGENTA)|A_BOLD);
4545 else
4546 wattrset(tmpwin, COLOR_PAIR(CYAN)|A_BOLD);
4547
4548 mvwaddch(tmpwin, 2, x+2,
4549 (pan == 128 ? 'M' :
4550 (pan == 0 || (pan > 0 && pan < 128)) ?
4551 'L' :'R')
4552 );
4553 }
4554
4555 if (mod && playing) {
4556 refresh_info();
4557 refresh_module_info();
4558 MikMod_Update();
4559 }
4560
4561 update_panels();
4562 doupdate();
4563 }
4564
4565 del_panel(vpospan);
4566 touchwin(dspwin);
4567 wnoutrefresh(dspwin);
4568 doupdate();
4569 update_panels();
4570 }
4571
4572 /*** Show voices frequency. ***/
show_voices_freq(void)4573 static void show_voices_freq(void)
4574 {
4575 int i; /* counter */
4576 int c; /* character */
4577 int x; /* x position */
4578 int step; /* x step */
4579 int add; /* add to x */
4580 int pc; /* percent */
4581
4582 unsigned char pan; /* panning */
4583 float freq1, freq2; /* frequencies */
4584
4585 WINDOW *tmpwin; /* channel window (temporary) */
4586
4587
4588 /* Create window. */
4589 vfreqwin = tmpwin = newwin(VFREQ_H, VFREQ_W, VFREQ_Y, VFREQ_X);
4590 wtimeout(tmpwin, DELAY);
4591 keypad(tmpwin, TRUE);
4592 box(tmpwin, 0, 0);
4593 vfreqpan = new_panel(tmpwin);
4594 wattrset(tmpwin, (COLOR_PAIR(CYAN_BLUE)|A_BOLD));
4595 mvwprintw(tmpwin, 0, 0, "%-68s", " Voices frequency");
4596
4597 /* Calculate x step and add. */
4598 if (mod->numchn <= 32)
4599 step = 2;
4600 else step = 1;
4601 add = step == 1 ? 1 : 0;
4602
4603 /* Display channel counter. */
4604 wattrset(tmpwin, (COLOR_PAIR(CYAN)|A_NORMAL));
4605 for (c = 0; c < mod->numchn; c++) {
4606 if (c == 0) {
4607 mvwaddch(tmpwin, VFREQ_H-3, 2, '|');
4608 mvwprintw(tmpwin, VFREQ_H-2, 2, "1");
4609 continue;
4610 }
4611
4612 if ((c % 4) == 0) {
4613 mvwaddch(tmpwin, VFREQ_H-3, (c*step) + add, '|');
4614 mvwprintw(tmpwin, VFREQ_H-2,
4615 (c*step) + add, "%d", c);
4616 }
4617 }
4618 mvwaddch(tmpwin, VFREQ_H-3, (c*step) + add, '|');
4619 mvwprintw(tmpwin, VFREQ_H-2, (c*step) + add, "%d", c);
4620
4621 /*** Loop ***/
4622 while ((c = wgetch(tmpwin)) != 'q') {
4623 if (c == KEY_ESCAPE)
4624 break;
4625 else if (c == 'e')
4626 effects();
4627 else if (c == 'o')
4628 options();
4629 else if (c == 'p')
4630 do_pause();
4631 else if (c == 'm')
4632 mp_move_panel(vfreqpan);
4633
4634 /* Draw channels. */
4635 for (x = 0, i = 0; i < mod->numchn; x += step, i++) {
4636 pan = (unsigned char) get_voice_panning(i);
4637 freq1 = get_voice_freq(i);
4638 freq2 = maxfreq[i];
4639 if (freq2 <= 0) freq2 = 1;
4640
4641 pc = (int) (100.0 * (freq1 / freq2));
4642 draw_gauge(tmpwin, x+2, VFREQ_H-4, pc, 0, gauge_style);
4643
4644 if (step == 2)
4645 draw_gauge(tmpwin, x+3, VFREQ_H-4,
4646 pc, 0, gauge_style);
4647
4648 if (pan == 128)
4649 wattrset(tmpwin, COLOR_PAIR(BLUE)|A_BOLD);
4650 else if (pan == 0 || (pan > 0 && pan < 128))
4651 wattrset(tmpwin, COLOR_PAIR(MAGENTA)|A_BOLD);
4652 else
4653 wattrset(tmpwin, COLOR_PAIR(CYAN)|A_BOLD);
4654
4655 mvwaddch(tmpwin, 2, x+2,
4656 (pan == 128 ? 'M' :
4657 (pan == 0 || (pan > 0 && pan < 128)) ?
4658 'L' :'R')
4659 );
4660 }
4661
4662 if (mod && playing) {
4663 refresh_info();
4664 refresh_module_info();
4665 MikMod_Update();
4666 }
4667
4668 update_panels();
4669 doupdate();
4670 }
4671
4672 del_panel(vfreqpan);
4673 touchwin(dspwin);
4674 wnoutrefresh(dspwin);
4675 update_panels();
4676 doupdate();
4677 }
4678
4679 /*** Show all channels. ***/
show_all_channels(void)4680 static void show_all_channels(void)
4681 {
4682 int i; /* counter */
4683 int c; /* character */
4684 int x; /* x position */
4685 int step; /* x step */
4686 int add; /* add to x */
4687 int pc; /* percent */
4688 int lastmod = 0; /* for playlist checking */
4689
4690 unsigned char pan; /* panning */
4691 float vol1, vol2; /* volume */
4692
4693 WINDOW *tmpwin; /* channel window (temporary) */
4694
4695 /* Create window. */
4696 acwin = tmpwin = newwin(AC_H, AC_W, AC_Y, AC_X);
4697 wtimeout(tmpwin, DELAY);
4698 keypad(tmpwin, TRUE);
4699 box(tmpwin, 0, 0);
4700 acpan = new_panel(tmpwin);
4701 wattrset(tmpwin, (COLOR_PAIR(CYAN_BLUE)|A_BOLD));
4702 mvwprintw(tmpwin, 0, 0, "%-68s", " All channels");
4703
4704 /* Calculate x step and add. */
4705 CHN_CNT:
4706 step = mod->numchn <= 32 ? 2 : 1;
4707 add = step == 1 ? 1 : 0;
4708
4709 /* Print channel counter. */
4710 wattrset(tmpwin, COLOR_PAIR(WHITE)|A_NORMAL);
4711 for (i = 1; i < AC_H-1; i++)
4712 mvwprintw(tmpwin, i, 1, "%66s", "");
4713 wattrset(tmpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4714 for (c = 0; c < mod->numchn; c++) {
4715 if (c == 0) {
4716 mvwaddch(tmpwin, AC_H-3, 2, '|');
4717 mvwprintw(tmpwin, AC_H-2, 2, "1");
4718 continue;
4719 }
4720
4721 if (!(c % 4)) {
4722 mvwaddch(tmpwin, AC_H-3, (c * step) + add, '|');
4723 mvwprintw(tmpwin, AC_H-2,
4724 (c*step) + add, "%d", c);
4725 }
4726 }
4727 mvwaddch(tmpwin, AC_H-3, (c * step) + add, '|');
4728 mvwprintw(tmpwin, AC_H-2, (c * step) + add, "%d", c);
4729
4730 /*** Loop ***/
4731 if (in_playlist)
4732 lastmod = pl_cnt;
4733 while ((c = wgetch(tmpwin)) != 'q') {
4734 if (c == KEY_ESCAPE)
4735 break;
4736 else if (c == 'e')
4737 effects();
4738 else if (c == 'o')
4739 options();
4740 else if (c == 'u') {
4741 real_volume = 1-real_volume;
4742 refresh_legend();
4743 } else if (c == 'm')
4744 mp_move_panel(acpan);
4745 else
4746 module_control(c);
4747
4748 if (c == '*') {
4749 if (gauge_style < 5)
4750 gauge_style++;
4751 else
4752 gauge_style = 1;
4753 }
4754
4755 /* Draw channels. */
4756 for (x = 0, i = 0; i < mod->numchn; x += step, i++) {
4757 if (real_volume) {
4758 vol1 = get_voice_realvol(i);
4759 vol2 = maxrvol[i];
4760 if (vol2 <= 0) vol2=1;
4761 pc = (int) (100.0 * (vol1 / vol2));
4762 draw_gauge(tmpwin, x+2, AC_H-4,
4763 pc, 0, gauge_style);
4764
4765 } else {
4766 vol1 = get_voice_volume(i);
4767 vol2 = maxvol[i];
4768 if (vol2 <= 0) vol2 = 1;
4769 pc = (int) (100.0 * (vol1 / vol2));
4770 draw_gauge(tmpwin, x+2, AC_H-4,
4771 pc, 0, gauge_style);
4772 }
4773 if (step == 2)
4774 draw_gauge(tmpwin, x+3, AC_H-4,
4775 pc, 0, gauge_style);
4776
4777 /* Volume.
4778 vol1 = get_voice_volume(i);
4779 if (vol1 > 0)
4780 wattrset(tmpwin, COLOR_PAIR(GREEN)|A_BOLD);
4781 else
4782 wattrset(tmpwin, COLOR_PAIR(WHITE)|A_NORMAL);
4783 if (vol1 >= 128 && vol1 < MODVOL_LIMIT)
4784 wattrset(tmpwin, COLOR_PAIR(YELLOW)|A_BOLD);
4785 else if (vol1 >= MODVOL_LIMIT)
4786 wattrset(tmpwin, COLOR_PAIR(RED)|A_BOLD);
4787 mvwaddch(tmpwin, 1, x+2, ACS_BLOCK);*/
4788
4789 /* Panning. */
4790 pan = (unsigned char) get_voice_panning(i);
4791 if (pan == 128)
4792 wattrset(tmpwin, COLOR_PAIR(BLUE)|A_BOLD);
4793 else if (pan == 0 || (pan > 0 && pan < 128))
4794 wattrset(tmpwin, COLOR_PAIR(MAGENTA)|A_BOLD);
4795 else
4796 wattrset(tmpwin, COLOR_PAIR(CYAN)|A_BOLD);
4797 mvwaddch(tmpwin, 2, x+2,
4798 (pan == 128 ? 'M' :
4799 (pan == 0 || (pan > 0 && pan < 128)) ?
4800 'L' :'R')
4801 );
4802 }
4803
4804 wattrset(tmpwin, A_NORMAL);
4805 mvwprintw(tmpwin, AC_H-1, AC_W-18, "%s",
4806 (real_volume ? "[ Real volume ]":"[ Voice volume ]")
4807 );
4808
4809 if (mod && playing) {
4810 refresh_info();
4811 refresh_module_info();
4812 MikMod_Update();
4813
4814 if (in_playlist) {
4815 if (pl_cnt != lastmod) {
4816 lastmod = pl_cnt;
4817 goto CHN_CNT;
4818 }
4819 }
4820 }
4821
4822 update_panels();
4823 doupdate();
4824 }
4825
4826 del_panel(acpan);
4827 update_panels();
4828 doupdate();
4829 }
4830
4831 /*** Show all voices. ***/
show_all_voices(void)4832 static void show_all_voices(void)
4833 {
4834 int i; /* counter */
4835 int c; /* character */
4836 int x; /* x position */
4837 int step; /* x step */
4838 int add; /* add to x */
4839 int pc; /* percent */
4840 int lastmod = 0; /* for playlist checking */
4841
4842 unsigned char pan; /* panning */
4843 float vol1, vol2; /* volume */
4844
4845 WINDOW *tmpwin; /* channel window (temporary) */
4846
4847 /* Create window. */
4848 acwin = tmpwin = newwin(AC_H+2, AC_W, AC_Y, AC_X);
4849 wtimeout(tmpwin, DELAY);
4850 keypad(tmpwin, TRUE);
4851 box(tmpwin, 0, 0);
4852 acpan = new_panel(tmpwin);
4853 wattrset(tmpwin, (COLOR_PAIR(CYAN_BLUE)|A_BOLD));
4854 mvwprintw(tmpwin, 0, 0, "%-68s", " All voices");
4855
4856 /* Calculate x step and add. */
4857 CHN_CNT:
4858 step = 1;
4859 add = 1;
4860
4861 /* Print voices counter. */
4862 wattrset(tmpwin, COLOR_PAIR(WHITE)|A_NORMAL);
4863 for (i = 1; i < AC_H-1; i++)
4864 mvwprintw(tmpwin, i, 1, "%66s", "");
4865 wattrset(tmpwin, COLOR_PAIR(CYAN)|A_NORMAL);
4866 for (c = 0; c < 64; c++) {
4867 if (c == 0) {
4868 mvwaddch(tmpwin, AC_H-2, 2, '|');
4869 mvwprintw(tmpwin, AC_H-1, 2, "1");
4870 continue;
4871 }
4872
4873 if (!(c % 4)) {
4874 mvwaddch(tmpwin, AC_H-2, (c * step) + add, '|');
4875 mvwprintw(tmpwin, AC_H-1,
4876 (c*step) + add, "%d", c);
4877 }
4878 }
4879 mvwaddch(tmpwin, AC_H-2, (c * step) + add, '|');
4880 mvwprintw(tmpwin, AC_H-1, (c * step) + add, "%d", c);
4881
4882 /*** Loop ***/
4883 if (in_playlist)
4884 lastmod = pl_cnt;
4885 while ((c = wgetch(tmpwin)) != 'q') {
4886 if (c == KEY_ESCAPE)
4887 break;
4888 else if (c == 'e')
4889 effects();
4890 else if (c == 'o')
4891 options();
4892 else if (c == 'u') {
4893 real_volume = 1-real_volume;
4894 refresh_legend();
4895 } else if (c == 'm')
4896 mp_move_panel(acpan);
4897 else
4898 module_control(c);
4899
4900 if (c == '*') {
4901 if (gauge_style < 5)
4902 gauge_style++;
4903 else
4904 gauge_style = 1;
4905 }
4906
4907 /* Draw voices. */
4908 for (x = 0, i = 0; i < 64; x += step, i++) {
4909 if (real_volume) {
4910 vol1 = get_voice_realvol(i);
4911 vol2 = maxrvol[i];
4912 if (vol2 <= 0) vol2=1;
4913 pc = (int) (100.0 * (vol1 / vol2));
4914 draw_gauge(tmpwin, x+2, AC_H-4,
4915 pc, 0, gauge_style);
4916
4917 } else {
4918 vol1 = get_voice_volume(i);
4919 vol2 = maxvol[i];
4920 if (vol2 <= 0) vol2 = 1;
4921 pc = (int) (100.0 * (vol1 / vol2));
4922 draw_gauge(tmpwin, x+2, AC_H-4,
4923 pc, 0, gauge_style);
4924 }
4925
4926 /* Volume. */
4927 vol1 = get_voice_volume(i);
4928 if (vol1 > 0)
4929 wattrset(tmpwin, COLOR_PAIR(GREEN)|A_BOLD);
4930 else
4931 wattrset(tmpwin, COLOR_PAIR(WHITE)|A_NORMAL);
4932 if (vol1 >= 128 && vol1 < MODVOL_LIMIT)
4933 wattrset(tmpwin, COLOR_PAIR(YELLOW)|A_BOLD);
4934 else if (vol1 >= MODVOL_LIMIT)
4935 wattrset(tmpwin, COLOR_PAIR(RED)|A_BOLD);
4936 mvwaddch(tmpwin, AC_H-3, x+2, ACS_BLOCK);
4937
4938 /* Panning. */
4939 pan = (unsigned char) get_voice_panning(i);
4940 if (pan == 128)
4941 wattrset(tmpwin, COLOR_PAIR(BLUE)|A_BOLD);
4942 else if (pan == 0 || (pan > 0 && pan < 128))
4943 wattrset(tmpwin, COLOR_PAIR(MAGENTA)|A_BOLD);
4944 else
4945 wattrset(tmpwin, COLOR_PAIR(CYAN)|A_BOLD);
4946 mvwaddch(tmpwin, 2, x+2,
4947 (pan == 128 ? 'M' :
4948 (pan == 0 || (pan > 0 && pan < 128)) ?
4949 'L' :'R')
4950 );
4951 }
4952
4953 wattrset(tmpwin, COLOR_PAIR(YELLOW_BLUE)|A_BOLD);
4954 mvwprintw(tmpwin, 0, AC_W-14, "%s",
4955 (real_volume ? " Real volume ":" Voice volume ")
4956 );
4957
4958 if (mod && playing) {
4959 refresh_info();
4960 refresh_module_info();
4961 MikMod_Update();
4962
4963 if (in_playlist) {
4964 if (pl_cnt != lastmod) {
4965 lastmod = pl_cnt;
4966 goto CHN_CNT;
4967 }
4968 }
4969 }
4970
4971 update_panels();
4972 doupdate();
4973 }
4974
4975 del_panel(acpan);
4976 update_panels();
4977 doupdate();
4978 }
4979 /*** Enter tracks view. ***/
track_view(void)4980 void track_view(void)
4981 {
4982 int c;
4983 int i, j;
4984 int opcode;
4985 UBYTE *curtrk;
4986 WINDOW *tmpwin;
4987 PANEL *tmppan;
4988
4989 /* Create window. */
4990 tmpwin = newwin(22, 70, 1, 4);
4991 wtimeout(tmpwin, DELAY);
4992 keypad(tmpwin, TRUE);
4993 box(tmpwin, 0, 0);
4994 tmppan = new_panel(tmpwin);
4995
4996 wattrset(tmpwin, (COLOR_PAIR(WHITE)|A_NORMAL));
4997 mvwprintw(tmpwin, 0, 2, "[ ]");
4998 wattrset(tmpwin, (COLOR_PAIR(YELLOW)|A_BOLD));
4999 mvwprintw(tmpwin, 0, 4, "Pattern view");
5000 wattrset(tmpwin, A_NORMAL);
5001
5002 /*** Loop ***/
5003 while ((c = wgetch(tmpwin)) != 'q') {
5004 if (c == 'p')
5005 do_pause();
5006
5007 if (c == 'm')
5008 mp_move_panel(tmppan);
5009
5010 for (j = 0; j < 4 /* mod->numtrk */; j++) {
5011 curtrk = mod->tracks[j]; /* ptr to array of UBYTES */
5012 for (i = 1; i < 21; i++) {
5013 wattrset(tmpwin, COLOR_PAIR(CYAN)|A_NORMAL);
5014 mvwprintw(tmpwin, i, 1, "%3d", mod->patpos+i);
5015 if ((mod->patpos+i) > mod->numrow) {
5016 mvwprintw(tmpwin, i, (j*8)+6, "----");
5017 continue;
5018 }
5019 opcode = curtrk[(i+mod->patpos)+
5020 (mod->sngpos*mod->numpos)];
5021 wattrset(tmpwin, COLOR_PAIR(WHITE)|A_NORMAL);
5022 if (opcode)
5023 mvwprintw(tmpwin, i, (j*8)+6,
5024 "%04x", opcode);
5025 else
5026 mvwprintw(tmpwin, i, (j*8)+6, "----");
5027
5028 }
5029 }
5030
5031 if (mod && playing) {
5032 refresh_info();
5033 refresh_module_info();
5034 update_panels();
5035 doupdate();
5036 MikMod_Update();
5037 }
5038 }
5039
5040 del_panel(tmppan);
5041 delwin(tmpwin);
5042 }
5043
5044 /*** Display module info. ***/
5045 int hidden = 1, hcnt = 0, hc[4] = { '-', '\\', '|', '/' }, pp = 0;
refresh_module_info(void)5046 static void refresh_module_info(void)
5047 {
5048 int i;
5049
5050 if (mod->sngpos >= mod->numpos)
5051 return;
5052
5053 wattrset(dspwin, COLOR_PAIR(CYAN)|A_BOLD);
5054 mvwprintw(dspwin, MODINFO_Y, 1, "Ch:");
5055 wattrset(dspwin, COLOR_PAIR(WHITE)|A_NORMAL);
5056 wprintw(dspwin, "%2d/%2d",
5057 mod->realchn,
5058 mod->numchn);
5059
5060 wattrset(dspwin, COLOR_PAIR(CYAN)|A_BOLD);
5061 mvwprintw(dspwin, MODINFO_Y, 11, "Pat:");
5062 wattrset(dspwin, COLOR_PAIR(WHITE)|A_NORMAL);
5063 wprintw(dspwin, "%3d %3d/%3d",
5064 (mod->patterns[mod->sngpos]+1 > mod->numpos ?
5065 mod->numpos : mod->patterns[mod->sngpos]+1),
5066 (mod->sngpos+1 > mod->numpos ?
5067 mod->numpos : mod->sngpos+1), mod->numpos);
5068
5069 wattrset(dspwin, COLOR_PAIR(CYAN)|A_BOLD);
5070 mvwprintw(dspwin, MODINFO_Y, 28, "Pos:");
5071 wattrset(dspwin, COLOR_PAIR(WHITE)|A_NORMAL);
5072 wprintw(dspwin, "%3d", mod->patpos);
5073
5074 wattrset(dspwin, COLOR_PAIR(CYAN)|A_BOLD);
5075 mvwprintw(dspwin, MODINFO_Y, 37, "Bpm:");
5076 wattrset(dspwin, COLOR_PAIR(WHITE)|A_NORMAL);
5077 wprintw(dspwin, "%3d", mod->bpm);
5078
5079 wattrset(dspwin, COLOR_PAIR(CYAN)|A_BOLD);
5080 mvwprintw(dspwin, MODINFO_Y, 46, "Spd:");
5081 wattrset(dspwin, COLOR_PAIR(WHITE)|A_NORMAL);
5082 wprintw(dspwin, "%3d", mod->sngspd);
5083
5084 wattrset(dspwin, COLOR_PAIR(CYAN)|A_BOLD);
5085 mvwprintw(dspwin, MODINFO_Y, 55, "Tmp:");
5086 wattrset(dspwin, COLOR_PAIR(WHITE)|A_NORMAL);
5087 wprintw(dspwin, "%3d", mod->inittempo);
5088
5089 wattrset(dspwin, COLOR_PAIR(CYAN)|A_BOLD);
5090 mvwprintw(dspwin, MODINFO_Y, 64, "Rvb:");
5091 wattrset(dspwin, COLOR_PAIR(WHITE)|A_NORMAL);
5092 wprintw(dspwin, "%2d", md_reverb);
5093
5094 wattrset(dspwin, COLOR_PAIR(CYAN)|A_BOLD);
5095 mvwprintw(dspwin, MODINFO_Y, 72, "Vol:");
5096 wattrset(dspwin, COLOR_PAIR(WHITE)|A_NORMAL);
5097 wprintw(dspwin, "%3d", mod->volume);
5098
5099 wattrset(dspwin, COLOR_PAIR(WHITE)|A_NORMAL);
5100 mvwprintw(dspwin, DSP_H-1, COLS-17, "[ ]");
5101 wattrset(dspwin, COLOR_PAIR(CYAN)|A_BOLD);
5102 mvwprintw(dspwin, DSP_H-1, COLS-15, "Time:");
5103 wattrset(dspwin, COLOR_PAIR(WHITE)|A_NORMAL);
5104 mvwprintw(dspwin, DSP_H-1, COLS-9, "%02d:%02d",
5105 ((mod->sngtime/1000)/60),
5106 ((mod->sngtime/1000)%60));
5107
5108 if (in_playlist)
5109 refresh_pl_info();
5110 else if (need_to_clear) {
5111 for (i = 1; i < 60; i++)
5112 mvwaddch(dspwin, DSP_H-1, i, ACS_HLINE);
5113 need_to_clear = 0;
5114 }
5115
5116 if (!hidden && pp != mod->patpos) {
5117 wattrset(dspwin, COLOR_PAIR(GREEN_BLUE)|A_BOLD);
5118 mvwaddch(dspwin, 0, 1, hc[(hcnt) & 3]);
5119 mvwaddch(dspwin, 0, 2, hc[(hcnt+1) & 3]);
5120 mvwaddch(dspwin, 0, 9+strlen(VERSION), hc[(hcnt+2) & 3]);
5121 mvwaddch(dspwin, 0, 10+strlen(VERSION), hc[(hcnt+3) & 3]);
5122 hcnt++, pp = mod->patpos;
5123 wattrset(dspwin, COLOR_PAIR(WHITE)|A_NORMAL);
5124 }
5125 }
5126
5127 /*** Display channels info. ***/
refresh_info(void)5128 static void refresh_info(void)
5129 {
5130 int i;
5131 int vol = 0, pc;
5132 int panc, panx;
5133 int period;
5134 float vol1, vol2;
5135 float f1, f2;
5136 unsigned char pan, vpan;
5137 chtype attr;
5138
5139 if (mod == NULL) {
5140 for (i = (page*(DSP_H-CHN_START));
5141 i < ((page+1)*(DSP_H-CHN_START)); i++) {
5142 int y = i%(DSP_H-CHN_START);
5143
5144 wattrset(dspwin, COLOR_PAIR(WHITE)|A_NORMAL);
5145 mvwprintw(dspwin, y+4, 1,
5146 " %02d %6d %6d %6d %6d %3d ",
5147 y, 0, 0, 0, 0, 0);
5148
5149 draw_gauge(dspwin, 52, y+CHN_START-1,
5150 0, 1, gauge_style);
5151 }
5152
5153 return;
5154 }
5155
5156 for (i = (page*(DSP_H-CHN_START));
5157 i < ((page+1)*(DSP_H-CHN_START)); i++) {
5158 int y = i%(DSP_H-CHN_START);
5159
5160 if (i > mod->numchn-1) {
5161 if ((mod->sngpos == 0 && mod->patpos < 1)
5162 || lastpage < page)
5163 mvwprintw(dspwin, y+CHN_START-1, 1, "%78s", "");
5164 continue;
5165 }
5166
5167 /* Print line. */
5168 if (muted[i] == 0) {
5169 period = get_channel_period(i);
5170
5171 /* Channel # */
5172 if (period == 0)
5173 vol = 0;
5174 else
5175 vol = get_voice_volume(get_channel_voice(i));
5176 if (vol > 0) {
5177 wattrset(dspwin,
5178 (attr = COLOR_PAIR(CYAN_BLUE)|A_BOLD));
5179 } else {
5180 wattrset(dspwin,
5181 (attr = COLOR_PAIR(WHITE)|A_NORMAL));
5182 }
5183 mvwprintw(dspwin, y+CHN_START-1, 1, "%02d", i+1);
5184
5185 /* Channel period. */
5186 wattrset(dspwin,
5187 (attr = COLOR_PAIR(WHITE)|A_NORMAL));
5188 mvwprintw(dspwin, y+CHN_START-1, 5, "%6d", period);
5189
5190 /* Set line color from voice volume. */
5191 if (period == 0) {
5192 vol = 0;
5193 wattrset(dspwin,
5194 (attr = COLOR_PAIR(WHITE)|A_NORMAL));
5195 goto NO_VOLCLR;
5196 }
5197 vol = get_voice_volume(get_channel_voice(i));
5198 if (vol > 0 && vol < 64)
5199 wattrset(dspwin,
5200 (attr = COLOR_PAIR(GREEN)|A_NORMAL));
5201 else if (vol > 64 && vol < 128)
5202 wattrset(dspwin,
5203 (attr = COLOR_PAIR(GREEN)|A_BOLD));
5204 else if (vol >= 128 && vol < 192)
5205 wattrset(dspwin,
5206 (attr = COLOR_PAIR(YELLOW)|A_BOLD));
5207 else if (vol >= 192 && vol < 256)
5208 wattrset(dspwin,
5209 (attr = COLOR_PAIR(RED)|A_BOLD));
5210
5211 else if (vol == 256)
5212 wattrset(dspwin,
5213 (attr = COLOR_PAIR(WHITE_RED)|A_BOLD));
5214
5215
5216 NO_VOLCLR:
5217 if (period != 0) {
5218 mvwprintw(dspwin, y+CHN_START-1, 13,
5219 "%2d %6d %6d",
5220 (get_channel_voice(i)+1),
5221 (get_voice_freq(get_channel_voice(i))),
5222 (get_voice_pos(get_channel_voice(i))));
5223
5224 } else {
5225 mvwprintw(dspwin, y+CHN_START-1, 13,
5226 "%2d %6d %6d", 0, 0, 0);
5227 }
5228
5229 /* Panning. */
5230 pan = (unsigned char) get_voice_panning(
5231 get_channel_voice(i));
5232 if (period == 0)
5233 pan = 128;
5234 if (pan == 128) {
5235 wattrset(dspwin,
5236 COLOR_PAIR(BLUE)|A_BOLD);
5237 } else if (pan == 0 || (pan > 0 && pan < 128)) {
5238 wattrset(dspwin,
5239 COLOR_PAIR(MAGENTA)|A_BOLD);
5240 } else {
5241 wattrset(dspwin,
5242 COLOR_PAIR(CYAN)|A_BOLD);
5243 }
5244 mvwprintw(dspwin, y+CHN_START-1, 33, ".......");
5245 if (pan == 0) {
5246 wattrset(dspwin,
5247 COLOR_PAIR(MAGENTA_MAGENTA)|A_BOLD);
5248 } else if (pan == 255) {
5249 wattrset(dspwin,
5250 COLOR_PAIR(CYAN_CYAN)|A_BOLD);
5251 }
5252
5253 vpan = 0;
5254 panx = 0;
5255 panc = (pan == 128 ? 'M' :
5256 (pan == 0 ||
5257 (pan > 0 && pan < 128) ? 'L' : 'R'));
5258
5259 if (panc == 'M') {
5260 panx = 3;
5261 vpan = 128;
5262
5263 } else if (panc == 'L') {
5264 if (pan == 0) {
5265 panx = 0;
5266 vpan = 127;
5267 } else if (pan == 127) {
5268 panx = 2;
5269 vpan = 0;
5270 } else {
5271 f1 = pan;
5272 f2 = 100.0 * (f1 / 127.0);
5273 f2 /= 33.0;
5274 panx = f2;
5275 vpan = 127 - pan;
5276 }
5277
5278 } else if (panc == 'R') {
5279 pan -= 128;
5280 f1 = pan;
5281 f2 = 100.0 * (f1 / 127.0);
5282 f2 /= 33.0;
5283
5284 panx = f2;
5285 if (panx > 2)
5286 panx = 2;
5287 panx += 4;
5288
5289 vpan = pan;
5290 }
5291 mvwaddch(dspwin, y+CHN_START-1, 33+panx, panc);
5292
5293 wattrset(dspwin, COLOR_PAIR(CYAN)|A_NORMAL);
5294 mvwprintw(dspwin, y+CHN_START-1, 41, "%3d", vpan);
5295
5296 /* Volume. */
5297 wattrset(dspwin, attr);
5298 mvwprintw(dspwin, y+CHN_START-1, 46,
5299 "%3d %c", vol,
5300 (lastvol[i] == vol ? '=' :
5301 (lastvol[i] < vol ? '+' : '-')));
5302 lastvol[i] = vol;
5303
5304 if (real_volume) {
5305 if (period == 0) {
5306 pc = 0;
5307 goto NO_CALC;
5308 }
5309 vol1 = get_voice_realvol(
5310 get_channel_voice(i));
5311 vol2 = maxrvol[i];
5312 if (vol2 <= 0) vol2 = 1;
5313 pc = (int) (100.0 * (vol1 / vol2));
5314 if (pc > 100) pc = 100;
5315 NO_CALC:
5316 draw_gauge(dspwin, 54, y+CHN_START-1,
5317 pc, 1, gauge_style);
5318
5319 } else {
5320 vol1 = vol;
5321 vol2 = maxvol[i];
5322 if (vol2 <= 0) vol2 = 1;
5323 pc = (int) (100.0 * (vol1 / vol2));
5324 draw_gauge(dspwin, 54, y+CHN_START-1,
5325 pc, 1, gauge_style);
5326 }
5327
5328 } else {
5329 wattrset(dspwin, A_NORMAL);
5330 mvwprintw(dspwin, y+CHN_START-1, 1,
5331 "%02d ------ -- ------ ------- ------- --- MUTED",
5332 i+1);
5333 draw_gauge(dspwin, 54, y+CHN_START-1,
5334 0, 1, gauge_style);
5335 }
5336 }
5337
5338 draw_pointer();
5339 }
5340
5341 /*** Refresh driver info. ***/
refresh_driver_info(void)5342 static void refresh_driver_info(void)
5343 {
5344 int i;
5345
5346 for (i = 1; i < COLS-1; i++)
5347 mvwaddch(dspwin, 3, i, ' ');
5348
5349 wattrset(dspwin, COLOR_PAIR(WHITE)|A_BOLD);
5350 mvwprintw(dspwin, 3, 1, "Driver : ");
5351 wattrset(dspwin, COLOR_PAIR(MAGENTA)|A_BOLD);
5352 wprintw(dspwin, md_driver->Name);
5353 wattrset(dspwin, COLOR_PAIR(WHITE)|A_NORMAL);
5354 wprintw(dspwin, " - ");
5355
5356 wattrset(dspwin, COLOR_PAIR(MAGENTA)|A_BOLD);
5357 wprintw(dspwin, "%s %s %s %s %s",
5358 (md_mode & DMODE_16BITS ? "16bit" : "8bit"),
5359 (md_mode & DMODE_REVERSE ? "!STEREO" : \
5360 (md_mode & DMODE_STEREO ? "STEREO" : "MONO" )),
5361 (md_mode & DMODE_SURROUND ? "SURROUND" : "NORMAL" ),
5362 (md_mode & DMODE_HQMIXER ? "HQMIXER" : "LQMIXER" ),
5363 (md_mode & DMODE_SOFT_MUSIC ? "(soft)" : "(hard)"));
5364
5365 wattrset(dspwin, COLOR_PAIR(YELLOW)|A_BOLD);
5366 wprintw(dspwin, " %d Hz", md_mixfreq);
5367
5368 wattrset(dspwin, COLOR_PAIR(WHITE)|A_NORMAL);
5369 }
5370
5371 /*** Refresh legend bar. ***/
refresh_legend(void)5372 static void refresh_legend(void)
5373 {
5374 if (real_volume) {
5375 wattrset(dspwin, A_REVERSE);
5376 mvwprintw(dspwin, CHN_START-2, 0, "%-80s",
5377 " Ch Period Vc Freq Pos Panning Volume Real volume");
5378 } else {
5379 wattrset(dspwin, A_REVERSE);
5380 mvwprintw(dspwin, CHN_START-2, 0, "%-80s",
5381 " Ch Period Vc Freq Pos Panning Volume Voice volume");
5382 }
5383 }
5384
5385 /******************************************************************************/
5386
5387 /*** Print the usual usage string. ***/
usage(void)5388 static void usage(void)
5389 {
5390 fprintf(stderr, ":: MP v%s ::\n", VERSION);
5391 fprintf(stderr, "Usage: mp [ -h | -v ]... [ module | playlist ]...\n");
5392 fprintf(stderr, " -h help\n");
5393 fprintf(stderr, " -v version\n");
5394 fprintf(stderr, " module .xm, .it, .mod...\n");
5395 fprintf(stderr, " playlist .pli\n");
5396 }
5397
5398 /*** Main control keys. ***/
module_control(int c)5399 void module_control(int c)
5400 {
5401 int i;
5402
5403 switch (c) {
5404 /*
5405 * Next position.
5406 */
5407 case 'n':
5408 if (pos < mod->numpos-1) {
5409 Player_NextPosition();
5410 MikMod_Update();
5411 pos = mod->sngpos;
5412 }
5413 break;
5414
5415 /*
5416 * Next module.
5417 */
5418 case 'N':
5419 if (in_playlist && pl_cnt < pl_files-1) {
5420 if (random_mode) {
5421 pl_cnt = (int)
5422 (((float)pl_files-1)*(rand()/
5423 (RAND_MAX+1.0)));
5424 } else {
5425 pl_cnt++;
5426
5427 }
5428
5429 pl_playtime += mod->sngtime;
5430 Player_Stop();
5431 loading(1);
5432 play_module(
5433 list_files[pl_cnt].fname);
5434 loading(0);
5435
5436 refresh_pl_info();
5437 }
5438 break;
5439
5440 /*
5441 * Prev position.
5442 */
5443 case 'v':
5444 if (mod->sngpos > 0) {
5445 mod->sngpos--;
5446 MikMod_Update();
5447 pos = mod->sngpos;
5448 }
5449 break;
5450
5451 /*
5452 * Prev module.
5453 */
5454 case 'V':
5455 if (in_playlist && pl_cnt > 0) {
5456 pl_cnt--;
5457
5458 Player_Stop();
5459
5460 loading(1);
5461 play_module(
5462 list_files[pl_cnt].fname);
5463 loading(0);
5464
5465 refresh_pl_info();
5466 }
5467 break;
5468
5469 /*
5470 * Restart module.
5471 */
5472 case 'A':
5473 if (playing == 0)
5474 playing = 1;
5475
5476 Player_SetPosition(0);
5477 pos = 0;
5478
5479 if (stopped) {
5480 stopped = 0;
5481 Player_Start(mod);
5482 }
5483 break;
5484
5485 /*
5486 * Restart pattern.
5487 */
5488 case 'a':
5489 mod->patpos = 0;
5490 MikMod_Update();
5491 break;
5492
5493 /*
5494 * Playlist.
5495 */
5496 case 'l':
5497 playlist();
5498
5499 if (in_playlist && pl_files != 0
5500 && pl_val != 255) {
5501 install_pl_handler();
5502 pl_playtime = 0;
5503
5504 Player_Stop();
5505 loading(1);
5506 play_module(list_files[pl_cnt].fname);
5507 loading(0);
5508
5509 refresh_pl_info();
5510 }
5511 break;
5512
5513 /* ;-) */
5514 case KEY_F(12):
5515 hidden = 1-hidden;
5516 if (hidden) {
5517 wattrset(dspwin, COLOR_PAIR(CYAN_BLUE)|A_BOLD);
5518 mvwprintw(dspwin, 0, 0,
5519 " :: MP v%s ::", VERSION);
5520 }
5521 break;
5522
5523 /*
5524 * Play or pause.
5525 */
5526 case 'p':
5527 if (stopped) {
5528 if (mod) {
5529 Player_Start(mod);
5530 stopped = 0;
5531 playing = 1;
5532 }
5533 } else {
5534 do_pause();
5535 }
5536 break;
5537
5538 /*
5539 * Stop.
5540 */
5541 case 't':
5542 do_stop();
5543 break;
5544
5545
5546 /*
5547 * Reverb +/-
5548 */
5549 case 'r':
5550 if (md_reverb > 0)
5551 md_reverb--;
5552 break;
5553 case 'R':
5554 if (md_reverb < REVERB_LIMIT)
5555 md_reverb++;
5556 break;
5557
5558 /*
5559 * Speed +/-
5560 */
5561 case 's':
5562 if (mod->sngspd > 0)
5563 mod->sngspd--;
5564 break;
5565 case 'S':
5566 if (mod->sngspd < SPEED_LIMIT)
5567 mod->sngspd++;
5568 break;
5569
5570 /*
5571 * BPM +/-
5572 */
5573 case 'b':
5574 if (mod->bpm > 1)
5575 mod->bpm--;
5576 break;
5577 case 'B':
5578 if (mod->bpm < BPM_LIMIT)
5579 mod->bpm++;
5580 break;
5581
5582 /*
5583 * Tempo +/-
5584 */
5585 case 'k':
5586 if (mod->inittempo > 0)
5587 mod->inittempo--;
5588 break;
5589 case 'K':
5590 if (mod->inittempo < TEMPO_LIMIT)
5591 mod->inittempo++;
5592 break;
5593
5594 /*
5595 * Volume +/-
5596 */
5597 case '+':
5598 if (mod->volume < MODVOL_LIMIT)
5599 mod->volume++;
5600 break;
5601 case '-':
5602 if (mod->volume > 0)
5603 mod->volume--;
5604 break;
5605
5606 /*
5607 * Reverse stereo
5608 */
5609 case '!':
5610 if ((md_mode & DMODE_STEREO))
5611 reverse_stereo = 1-reverse_stereo;
5612 else
5613 break;
5614
5615 if (!reverse_stereo) {
5616 md_mode &= ~DMODE_REVERSE;
5617 } else
5618 md_mode |= DMODE_REVERSE;
5619
5620 refresh_driver_info();
5621 break;
5622
5623 /*
5624 * Switch volume display.
5625 */
5626 case 'u':
5627 real_volume = 1-real_volume;
5628 refresh_legend();
5629 break;
5630
5631
5632 /*
5633 * Mute all channels.
5634 */
5635 case 'M':
5636 for (i = 0; i < mod->numchn; i++) {
5637 if (output == 1) {
5638 muted[i] = 1;
5639 Player_Mute(i);
5640 } else {
5641 muted[i] = 0;
5642 Player_Unmute(i);
5643 }
5644 }
5645 output = 1-output;
5646 draw_pointer();
5647 break;
5648
5649 /*
5650 * Module info.
5651 */
5652 case 'i':
5653 if (mod)
5654 module_info(mod);
5655 break;
5656
5657 /*
5658 * Help.
5659 */
5660 case 'h': case 'H':
5661 display_help();
5662 break;
5663
5664 /*
5665 * About.
5666 */
5667 case '?':
5668 about();
5669 break;
5670
5671 }
5672 }
5673
5674 /******************************************************************************
5675 ***
5676 *** Start here.
5677 ***
5678 ******************************************************************************/
5679
main(int argc,char * argv[])5680 int main(int argc, char *argv[])
5681 {
5682 /* Variables. */
5683 int key;
5684 struct stat sbuf;
5685 char str[NAME_MAX+1];
5686 char *modname;
5687
5688 /* If called without arguments. */
5689 if (argv[1] == NULL) {
5690 usage();
5691 exit(-1);
5692
5693 /* Help? */
5694 } else if (strncmp(argv[1], "-h", 2) == 0) {
5695 usage();
5696 exit(0);
5697
5698 /* Version? */
5699 } else if (strncmp(argv[1], "-v", 2) == 0) {
5700 fprintf(stderr, ":: MP v%s ::\n", VERSION);
5701 exit(0);
5702
5703 /* Check file. */
5704 } else if (access(argv[1], R_OK) != 0) {
5705 fprintf(stderr, "MP: Can't open '%s'\n", argv[1]);
5706 exit(-1);
5707
5708 stat(argv[1], &sbuf);
5709 if (S_ISREG(sbuf.st_mode) == 0) {
5710 fprintf(stderr, "MP: Can't open '%s'\n", argv[1]);
5711 exit(-1);
5712 }
5713 }
5714
5715 /*
5716 * Check for presence of the '.mp' directory
5717 * in the user homedir.
5718 */
5719 sprintf(str, "%s/.mp", (getenv("HOME")));
5720 if (access(str, R_OK) != 0) {
5721 fprintf(stderr, "MP: Can't access '%s', creating it.\n", str);
5722 mkdir(str, 0644);
5723 } else {
5724 read_options_file();
5725 }
5726
5727 /* Init sound. */
5728 init_sound();
5729
5730 /* Init curses. */
5731 init_nc();
5732 read_options_file();
5733 init_windows();
5734 oldc1 = mvwinch(dspwin, curch+3, 0);
5735 oldc2 = mvwinch(dspwin, curch+3, 3);
5736 /*
5737 * Load module.
5738 */
5739 if (argv[1] != NULL) {
5740 loading(1);
5741 if (play_module(argv[1])) {
5742 leave(0);
5743 usage();
5744 exit(-1);
5745 } else
5746 playing = 1;
5747 loading(0);
5748
5749 } else {
5750 wattrset(dspwin, COLOR_PAIR(WHITE)|A_NORMAL);
5751 mvwprintw(dspwin, 0, 1,
5752 " No module loaded. Press 'f' for file selector. ");
5753 playing = 0;
5754 }
5755
5756 /* Create screen. */
5757 refresh_driver_info();
5758 refresh_info();
5759 refresh_module_info();
5760 doupdate();
5761
5762 /* Ensure we do a clean exit if those signals are received... */
5763 signal(SIGTERM, leave);
5764 signal(SIGINT, leave);
5765 signal(SIGUSR1, leave);
5766 signal(SIGUSR2, leave);
5767
5768 /*** Main loop ***/
5769 while ((key = wgetch(dspwin)) != 'q') {
5770 module_control(key);
5771 switch (key) {
5772 /*
5773 * Show all channels.
5774 */
5775 case 'c': case 'C':
5776 if (mod != NULL)
5777 show_all_channels();
5778 else
5779 beep();
5780 break;
5781
5782 /*
5783 * Show voices frequency.
5784 */
5785 case 'y':
5786 if (mod != NULL)
5787 show_voices_freq();
5788 else
5789 beep();
5790 break;
5791
5792 /*
5793 * Show voices position.
5794 */
5795 case 'Y':
5796 if (mod != NULL)
5797 show_voices_pos();
5798 else
5799 beep();
5800 break;
5801
5802 /*
5803 * Select file.
5804 */
5805 case 'f':
5806 modname = file_select();
5807
5808 touchwin(dspwin);
5809 wnoutrefresh(dspwin);
5810 doupdate();
5811
5812 if (modname != NULL && (strlen(modname)) > 0) {
5813 loading(1);
5814 if (!(play_module(full_modname))) {
5815 in_playlist = 0;
5816 need_to_clear = 1;
5817 }
5818 loading(0);
5819
5820 touchwin(dspwin);
5821
5822 }
5823 break;
5824
5825 /*
5826 * Effects.
5827 */
5828 case 'e':
5829 effects();
5830 break;
5831
5832 /*
5833 * Options.
5834 */
5835 case 'o':
5836 options();
5837 break;
5838
5839 /*
5840 * Show samples.
5841 */
5842 case 'w':
5843 show_samples();
5844 break;
5845
5846 /*
5847 * Show instruments.
5848 */
5849 case 'W':
5850 show_instruments();
5851 break;
5852
5853 /*
5854 * Move up.
5855 */
5856 case KEY_UP:
5857 if (mod == NULL) break;
5858 if (curch > 0) curch--;
5859 page = (curch/(DSP_H-CHN_START));
5860 draw_pointer();
5861 break;
5862 case KEY_PPAGE:
5863 if (mod == NULL) break;
5864 if (curch == 0) break;
5865 if (curch == (page*(DSP_H-CHN_START))) {
5866 curch = (--page*(DSP_H-CHN_START));
5867 break;
5868 }
5869 curch = (page*(DSP_H-CHN_START));
5870 draw_pointer();
5871 break;
5872
5873 /*
5874 * Move down.
5875 */
5876 case KEY_DOWN:
5877 if (mod == NULL) break;
5878 if (curch < mod->numchn-1) curch++;
5879 page = (curch/(DSP_H-CHN_START));
5880 draw_pointer();
5881 break;
5882 case KEY_NPAGE:
5883 if (mod == NULL) break;
5884 if (((page+1)*(DSP_H-CHN_START))
5885 >= mod->numchn) {
5886 curch = mod->numchn-1;
5887 draw_pointer();
5888 break;
5889 }
5890 curch = ((page+1)*(DSP_H-CHN_START));
5891 page = (curch/(DSP_H-CHN_START));
5892 draw_pointer();
5893 break;
5894
5895 /*
5896 * Change gauge style.
5897 */
5898 case '*':
5899 if (gauge_style < 5)
5900 gauge_style++;
5901 else
5902 gauge_style = 1;
5903 break;
5904
5905
5906 /*
5907 * Tracks view.
5908 */
5909 case 'T':
5910 //track_view();
5911 show_all_voices();
5912 break;
5913
5914 /*
5915 * Bass.
5916 */
5917 case '<':
5918 if (bass) {
5919 bass--;
5920 ioctl(mixerfd,
5921 MIXER_WRITE(SOUND_MIXER_BASS),
5922 &bass);
5923 }
5924 break;
5925 case '>':
5926 if (bass < BASS_LIMIT) {
5927 bass++;
5928 ioctl(mixerfd,
5929 MIXER_WRITE(SOUND_MIXER_BASS),
5930 &bass);
5931 }
5932 break;
5933
5934 /*
5935 * Treble.
5936 */
5937 case 'x':
5938 if (treble) {
5939 treble--;
5940 ioctl(mixerfd,
5941 MIXER_WRITE(SOUND_MIXER_BASS),
5942 &treble);
5943 }
5944 break;
5945 case 'X':
5946 if (treble < TREBLE_LIMIT) {
5947 treble++;
5948 ioctl(mixerfd,
5949 MIXER_WRITE(SOUND_MIXER_BASS),
5950 &treble);
5951 }
5952 break;
5953
5954 /*
5955 * Mute channel.
5956 */
5957 case KEY_ENTER:
5958 if (muted[curch]) {
5959 muted[curch] = 0;
5960 Player_Unmute(curch);
5961 refresh_info();
5962 } else {
5963 muted[curch] = 1;
5964 Player_Mute(curch);
5965 refresh_info();
5966 }
5967 draw_pointer();
5968 break;
5969 }
5970
5971 if (mod && playing) {
5972 refresh_info();
5973 refresh_module_info();
5974 update_panels();
5975 doupdate();
5976 MikMod_Update();
5977 }
5978 }
5979
5980 /* Leaving... */
5981 in_playlist = 0;
5982
5983 /* End here. */
5984 clear();
5985 refresh();
5986 leave(0);
5987 }
5988
5989 /* EOF */
5990