/* dump.c */ /* try out for the ``play routines'' */ /* $Author: Espie $ * $Date: 91/05/16 15:04:51 $ * $Revision: 1.48 $ * $Log: dump.c,v $ * Revision 1.48 91/05/16 15:04:51 Espie * *** empty log message *** * * Revision 1.47 91/05/12 19:57:22 Espie * Corrected the loader's logic. * Change of behavior: release the audio.device briefly when * changing songs. That looks better after all (mixing albums, for * instance). * * Revision 1.46 91/05/12 15:56:25 Espie * Tried to correct some snapshot problem, plus some more cleanup. * * Revision 1.45 91/05/11 14:57:44 Espie * *** empty log message *** * * Revision 1.44 91/05/10 00:02:56 Espie * Added albums, moved all iterator stuff to files.c * * Revision 1.43 91/05/09 17:34:37 Espie * Support for wb icons added, more coherent song loading. * Default and specialized options added. * * Revision 1.42 91/05/08 18:34:52 Espie * * Details changed. * * Revision 1.41 91/05/08 15:50:12 Espie * Moved wb stuff to files.c (new iterator project...). * * Revision 1.40 91/05/07 02:53:02 Espie * Reads the cli defaults in player.config now. * * Revision 1.39 91/05/06 23:33:08 Espie * Added more workbench support, * now supports tooltypes. * The new requester call gives back a WBArg-like * answer, everything gets simpler and simpler... * * Revision 1.38 91/05/05 19:05:57 Espie * *** empty log message *** * * Revision 1.37 91/05/05 15:37:45 Espie * Separated the play structure into a private/public parts... * More to come ! * * Revision 1.36 91/05/05 04:00:21 Espie * Added some support for workbench arguments. * * Revision 1.35 91/05/03 02:48:39 Espie * *** empty log message *** * * Revision 1.34 91/05/02 23:32:02 Espie * Simpler, more functional. * * Revision 1.33 91/05/02 11:17:56 Espie * Simplified again ! * Added test for loaded song, so that we don't request the audio hw for nothing. * Added lockout to prevent loading two songs at once. * Should ideally put a queue there, and handle wbargs for multiselects... * * Revision 1.32 91/05/02 01:28:40 Espie * Dump is simpler than ever ! * Does not try to handle the number of replays correctly... * * Revision 1.31 91/05/01 00:50:06 Espie * Small bug fix: display->new_title. * * Revision 1.30 91/04/30 16:51:35 Espie * New interface for changing titles (new titles erases the old one). * Suppressed every IO. * * Revision 1.29 91/04/30 01:48:35 Espie * Cleaned up a bit what is still alive :-). * * Revision 1.28 91/04/30 00:36:22 Espie * Stable version III. * * Revision 1.27 91/04/30 00:23:11 Espie * Added more control for the file requester (now works from workbench). * * Revision 1.26 91/04/29 23:53:28 Espie * New loader ``on the fly''. * Now, load.c needs some modifications. * * Revision 1.25 91/04/29 15:05:58 Espie * ...still vanishing ! * * Revision 1.24 91/04/29 13:03:43 Espie * Interfaced to new audio_soft. * * Revision 1.23 91/04/29 03:53:13 Espie * Vanishing program. * * Revision 1.22 91/04/29 02:21:53 Espie * First attempt at an interface. * * Revision 1.21 91/04/28 22:53:05 Espie * transpose added. * * Revision 1.20 91/04/28 20:35:26 Espie * Small bug corrected (reset tempo at start of piece). * Looks more and more like a kludge, real player coming soon. * * Revision 1.19 91/04/27 20:48:53 Espie * *** empty log message *** * * Revision 1.18 91/04/27 16:45:38 Espie * Added crude priority control for tests. * * Revision 1.17 91/04/27 04:02:16 Espie * Added auto-timing code, suppressed fastest speed * --> need to get more control on the speed * (one timing for the new_notes, another for the effects). * * Revision 1.16 91/04/27 00:25:47 Espie * *** empty log message *** * * Revision 1.15 91/04/26 16:29:54 Espie * See interrupt.c for changes indication. * * Revision 1.14 91/04/24 16:10:19 Espie * Small changes, (missed a goto loop...) * * Revision 1.13 91/04/24 15:24:58 Espie * Now dump works with lots of signal: from audio_soft, the player and the user. * Will write a real interface soon. * * Revision 1.12 91/04/24 13:58:01 Espie * Added automatic version check. * * Revision 1.11 91/04/23 21:27:58 Espie * Almost completely new logic. Demonstrates most commands of play.c, * uses new interrupts. * * Revision 1.10 91/04/21 20:05:09 Espie * *** empty log message *** * * Revision 1.9 91/04/21 12:11:35 Espie * Stable version, known as bunch II. * Also features ``right'' log description. * * Revision 1.8 91/04/21 11:15:30 Espie * Added more comprehensive command line options 1/2:-) * * Revision 1.7 91/04/20 18:14:19 Espie * * Revision 1.6 91/04/19 13:21:56 Espie * Prototype for a real player, which waits for events, * and processes them. * * Revision 1.5 91/04/19 02:19:44 Espie * Simplified dump. Plays, and wait for ^C/^D. * * Revision 1.4 91/04/18 20:22:44 Espie * no big change in this file. * * Revision 1.3 91/04/18 02:25:51 Espie * bunch I. * * Revision 1.2 91/04/18 02:17:54 Espie * this version plays a module. * No commands implemented, just notes. * No interrupts, just sequence. * * Revision 1.1 91/04/17 18:51:13 Espie * Initial revision * */ #include #include #include #include #include #include #include #include #include #include #include "song.h" #include "public_play.h" #include "proto.h" LONG _Stack = 4000; char *_procname = "Experiment IV player"; LONG _priority = 0; LONG _BackGroundIO = 0; struct pub_play *play; #define tstclr(mask, val) ( (mask) & (val) ? ( (mask) &= ~(val), TRUE) : FALSE) /* quick and dirty... */ struct song *the_song; int counter; struct iterator *it; /* to wade through several identifiers at once */ char *get_song_args(BOOL req) { char *result; while ((result = next_song(&it, req)) && is_info(result)); return result; } int def_volume, def_transpose, def_speed, def_mode, def_repeat; char *mode_names[] = { "STD", "OLD", "NEW", NULL}; char *speed_names[] = {"PAL", "NTSC", "FAST", "SCAN", "SLOW", "NULL"}; char *file_names[] = {"UNKNOWN", "ALBUM"}; LOCAL void setup_the_song(struct song *new) { song_available(FALSE); unload_song(the_song); the_song = new; if (new) { new_title(0, the_song->info->length, the_song->title); setup_song(new); song_available(TRUE); } else no_title(); } LOCAL void change_song(char *arg, struct song *new) { char **tools; int speed, mode, transpose /*, volume, repeat */; tools = grab_tooltypes(it, arg); /* volume = get_arg(tools, "VOLUME", def_volume); */ speed = map_arg(tools, "SPEED", speed_names, def_speed); mode = map_arg(tools, "MODE", mode_names, def_mode); transpose = get_arg(tools, "TRANSPOSE", def_transpose); /* repeat = get_arg(tools, "REPEAT", def_repeat); */ /* modified repeat to def_repeat there */ play->oneshot = def_repeat == 1; counter = def_repeat; play->signaled &= ~ON_END; /* pref_volume(volume); */ pref_speed(speed); pref_mode(mode); play->transpose = transpose; (void)safe_unload_song(); setup_the_song(new); launch_play(0); } BOOL safe_unload_song(void) { if (the_song) { setup_the_song(NULL); return TRUE; } else return FALSE; } BOOL safe_load_song(char *arg) { struct song *new; new = load_song(arg); if (new) change_song(arg, new); else { if (load_error() < 0 && the_song) { safe_unload_song(); new = load_song(arg); if (new) change_song(arg, new); else return FALSE; } else return FALSE; } return TRUE; } main(int argc, char *argv[]) { int pri, xoffset, yoffset; char *arg; SetUpCleanUp(NIL); open_libraries(); onbreak(nobreak); it = setup_arguments(argc, argv); pri = do_get_arg("PRIORITY", 0); def_repeat = do_get_arg("REPEAT", 0); xoffset = do_get_arg("X", 0); yoffset = do_get_arg("Y", 1); def_volume = do_get_arg("VOLUME", 100); def_transpose = do_get_arg("TRANSPOSE", 0); def_speed = do_map_arg("SPEED", speed_names, 0); def_mode = do_map_arg("MODE", mode_names, 0); play = init_events(pri, xoffset, yoffset); pref_volume(def_volume); pref_speed(def_speed); pref_mode(def_mode); play->transpose = def_transpose; while (arg = get_song_args(FALSE)) if (safe_load_song(arg)) break; play->on_signal = ON_END|ON_COMMAND|ON_PATTERN|ON_PROBLEM|ON_BLIP; forever wait_abort(); } /* due to the file requester and check_abort, * we might just invoke try_change_song() recursively. * lock_out insures that one invocation only can succeed. */ void try_change_song(void) { static BOOL lock_out = FALSE; char *arg; if (lock_out) return; lock_out = TRUE; do { if (!(arg = get_song_args(TRUE))) break; } while (!safe_load_song(arg)); lock_out = FALSE; } void add_some_songs(struct AppMessage *msg) { insert_args(&it, msg); try_change_song(); } void handle_player() { if (counter == 1) play->oneshot = TRUE; if tstclr(play->signaled, ON_PATTERN) update_title(play->pattern, the_song->info->length, the_song->title); if (tstclr(play->signaled, ON_END)) { counter--; if (counter == 0) try_change_song(); } }