Mercurial > audlegacy
annotate Plugins/Input/console/Audacious_Driver.cpp @ 147:6fe2bfbe6fc2 trunk
[svn] Move SPC-specific code into SPC-specific routines.
author | nenolod |
---|---|
date | Thu, 10 Nov 2005 18:05:56 -0800 |
parents | 4309d2df6586 |
children | fe9cb5132263 |
rev | line source |
---|---|
90
252843aac42f
[svn] Import the initial sources for console music support.
nenolod
parents:
diff
changeset
|
1 /* |
252843aac42f
[svn] Import the initial sources for console music support.
nenolod
parents:
diff
changeset
|
2 * Audacious: Cross platform multimedia player |
252843aac42f
[svn] Import the initial sources for console music support.
nenolod
parents:
diff
changeset
|
3 * Copyright (c) 2005 Audacious Team |
252843aac42f
[svn] Import the initial sources for console music support.
nenolod
parents:
diff
changeset
|
4 * |
252843aac42f
[svn] Import the initial sources for console music support.
nenolod
parents:
diff
changeset
|
5 * Driver for Game_Music_Emu library. See details at: |
252843aac42f
[svn] Import the initial sources for console music support.
nenolod
parents:
diff
changeset
|
6 * http://www.slack.net/~ant/libs/ |
252843aac42f
[svn] Import the initial sources for console music support.
nenolod
parents:
diff
changeset
|
7 */ |
252843aac42f
[svn] Import the initial sources for console music support.
nenolod
parents:
diff
changeset
|
8 |
94 | 9 #include "Audacious_Driver.h" |
90
252843aac42f
[svn] Import the initial sources for console music support.
nenolod
parents:
diff
changeset
|
10 |
98
e42694a28331
[svn] More progress -- now loads as an audacious module. :)
nenolod
parents:
96
diff
changeset
|
11 extern "C" { |
e42694a28331
[svn] More progress -- now loads as an audacious module. :)
nenolod
parents:
96
diff
changeset
|
12 |
109 | 13 #include <glib.h> |
96 | 14 #include <glib/gi18n.h> |
109 | 15 #include <gtk/gtk.h> |
94 | 16 #include "libaudacious/configfile.h" |
17 #include "libaudacious/util.h" | |
18 #include "libaudacious/titlestring.h" | |
145 | 19 #include "audacious/input.h" |
95 | 20 #include "audacious/output.h" |
145 | 21 #include "audacious/playback.h" |
94 | 22 |
98
e42694a28331
[svn] More progress -- now loads as an audacious module. :)
nenolod
parents:
96
diff
changeset
|
23 }; |
e42694a28331
[svn] More progress -- now loads as an audacious module. :)
nenolod
parents:
96
diff
changeset
|
24 |
145 | 25 struct AudaciousConsoleConfig audcfg = { 180, FALSE, 32000 }; |
26 | |
94 | 27 #include <cstring> |
28 | |
101
59ba6595fdf1
[svn] More accurate sound reproduction, but there is warbling. Still locks up player on completion.
nenolod
parents:
100
diff
changeset
|
29 #ifdef WORDS_BIGENDIAN |
59ba6595fdf1
[svn] More accurate sound reproduction, but there is warbling. Still locks up player on completion.
nenolod
parents:
100
diff
changeset
|
30 # define MY_FMT FMT_S16_BE |
59ba6595fdf1
[svn] More accurate sound reproduction, but there is warbling. Still locks up player on completion.
nenolod
parents:
100
diff
changeset
|
31 #else |
59ba6595fdf1
[svn] More accurate sound reproduction, but there is warbling. Still locks up player on completion.
nenolod
parents:
100
diff
changeset
|
32 # define MY_FMT FMT_S16_LE |
59ba6595fdf1
[svn] More accurate sound reproduction, but there is warbling. Still locks up player on completion.
nenolod
parents:
100
diff
changeset
|
33 #endif |
59ba6595fdf1
[svn] More accurate sound reproduction, but there is warbling. Still locks up player on completion.
nenolod
parents:
100
diff
changeset
|
34 |
94 | 35 static Spc_Emu *spc = NULL; |
95 | 36 static GThread *decode_thread; |
37 | |
147
6fe2bfbe6fc2
[svn] Move SPC-specific code into SPC-specific routines.
nenolod
parents:
146
diff
changeset
|
38 static void *play_loop_spc(gpointer arg); |
100 | 39 static void console_init(void); |
109 | 40 extern "C" void console_aboutbox(void); |
96 | 41 static void console_stop(void); |
42 static void console_pause(gshort p); | |
43 static int get_time(void); | |
103 | 44 static gboolean console_ip_is_going; |
100 | 45 extern InputPlugin console_ip; |
147
6fe2bfbe6fc2
[svn] Move SPC-specific code into SPC-specific routines.
nenolod
parents:
146
diff
changeset
|
46 static int playing_type; |
100 | 47 |
94 | 48 static int is_our_file(gchar *filename) |
49 { | |
50 gchar *ext; | |
51 | |
52 ext = strrchr(filename, '.'); | |
53 | |
54 if (ext) | |
55 { | |
56 if (!strcasecmp(ext, ".spc")) | |
57 return 1; | |
58 } | |
59 | |
60 return 0; | |
61 } | |
62 | |
63 static gchar *get_title(gchar *filename) | |
64 { | |
65 gchar *title; | |
66 Emu_Std_Reader reader; | |
67 Spc_Emu::header_t header; | |
68 | |
69 reader.open(filename); | |
70 reader.read(&header, sizeof(header)); | |
71 | |
104 | 72 if (header.song) |
73 { | |
74 TitleInput *tinput; | |
75 | |
76 tinput = bmp_title_input_new(); | |
77 | |
105
18fe59468510
[svn] Use header.game, over header.author, as most SPC files do not contain the composer information.
nenolod
parents:
104
diff
changeset
|
78 tinput->performer = g_strdup(header.game); |
104 | 79 tinput->album_name = g_strdup(header.game); |
80 tinput->track_name = g_strdup(header.song); | |
94 | 81 |
104 | 82 tinput->file_name = g_path_get_basename(filename); |
83 tinput->file_path = g_path_get_dirname(filename); | |
84 | |
85 title = xmms_get_titlestring(xmms_get_gentitle_format(), | |
86 tinput); | |
87 | |
88 g_free(tinput); | |
89 } | |
90 else | |
91 title = g_strdup(filename); | |
99 | 92 |
94 | 93 return title; |
94 } | |
95 | 95 |
96 static void get_song_info(char *filename, char **title, int *length) | |
97 { | |
98 (*title) = get_title(filename); | |
145 | 99 |
100 if (audcfg.loop_length) | |
101 (*length) = audcfg.loop_length; | |
102 else | |
103 (*length) = -1; | |
95 | 104 } |
105 | |
147
6fe2bfbe6fc2
[svn] Move SPC-specific code into SPC-specific routines.
nenolod
parents:
146
diff
changeset
|
106 static void play_file_spc(char *filename) |
95 | 107 { |
106
d2b88d78ccd7
[svn] Tell the player that the decoder has fired up :)
nenolod
parents:
105
diff
changeset
|
108 gchar *name; |
95 | 109 Emu_Std_Reader reader; |
110 Spc_Emu::header_t header; | |
111 | |
112 reader.open(filename); | |
113 reader.read(&header, sizeof(header)); | |
114 | |
115 spc = new Spc_Emu; | |
101
59ba6595fdf1
[svn] More accurate sound reproduction, but there is warbling. Still locks up player on completion.
nenolod
parents:
100
diff
changeset
|
116 spc->init(32000); |
95 | 117 spc->load(header, reader); |
118 spc->start_track(0); | |
119 | |
103 | 120 console_ip_is_going = TRUE; |
121 | |
106
d2b88d78ccd7
[svn] Tell the player that the decoder has fired up :)
nenolod
parents:
105
diff
changeset
|
122 name = get_title(filename); |
d2b88d78ccd7
[svn] Tell the player that the decoder has fired up :)
nenolod
parents:
105
diff
changeset
|
123 |
145 | 124 if (audcfg.loop_length) |
125 console_ip.set_info(name, audcfg.loop_length * 1000, | |
146
4309d2df6586
[svn] Display the amount of DSP channels in the kbps box.
nenolod
parents:
145
diff
changeset
|
126 spc->voice_count() * 1000, 32000, 2); |
145 | 127 else |
128 console_ip.set_info(name, -1, spc->voice_count(), 32000, 2); | |
129 | |
106
d2b88d78ccd7
[svn] Tell the player that the decoder has fired up :)
nenolod
parents:
105
diff
changeset
|
130 |
d2b88d78ccd7
[svn] Tell the player that the decoder has fired up :)
nenolod
parents:
105
diff
changeset
|
131 g_free(name); |
d2b88d78ccd7
[svn] Tell the player that the decoder has fired up :)
nenolod
parents:
105
diff
changeset
|
132 |
102
de414e40f772
[svn] Normal sound decoding, now to just figure out how to stop the decode_thread when we need to.
nenolod
parents:
101
diff
changeset
|
133 if (!console_ip.output->open_audio(MY_FMT, 32000, 2)) |
100 | 134 return; |
133
3fb426494de8
[svn] Open the output channel before firing up the thread.
nenolod
parents:
109
diff
changeset
|
135 |
147
6fe2bfbe6fc2
[svn] Move SPC-specific code into SPC-specific routines.
nenolod
parents:
146
diff
changeset
|
136 playing_type = PLAY_TYPE_SPC; |
6fe2bfbe6fc2
[svn] Move SPC-specific code into SPC-specific routines.
nenolod
parents:
146
diff
changeset
|
137 |
6fe2bfbe6fc2
[svn] Move SPC-specific code into SPC-specific routines.
nenolod
parents:
146
diff
changeset
|
138 decode_thread = g_thread_create(play_loop_spc, spc, TRUE, NULL); |
6fe2bfbe6fc2
[svn] Move SPC-specific code into SPC-specific routines.
nenolod
parents:
146
diff
changeset
|
139 } |
6fe2bfbe6fc2
[svn] Move SPC-specific code into SPC-specific routines.
nenolod
parents:
146
diff
changeset
|
140 |
6fe2bfbe6fc2
[svn] Move SPC-specific code into SPC-specific routines.
nenolod
parents:
146
diff
changeset
|
141 static void play_file(char *filename) |
6fe2bfbe6fc2
[svn] Move SPC-specific code into SPC-specific routines.
nenolod
parents:
146
diff
changeset
|
142 { |
6fe2bfbe6fc2
[svn] Move SPC-specific code into SPC-specific routines.
nenolod
parents:
146
diff
changeset
|
143 gchar *ext; |
6fe2bfbe6fc2
[svn] Move SPC-specific code into SPC-specific routines.
nenolod
parents:
146
diff
changeset
|
144 |
6fe2bfbe6fc2
[svn] Move SPC-specific code into SPC-specific routines.
nenolod
parents:
146
diff
changeset
|
145 ext = strrchr(filename, '.'); |
6fe2bfbe6fc2
[svn] Move SPC-specific code into SPC-specific routines.
nenolod
parents:
146
diff
changeset
|
146 |
6fe2bfbe6fc2
[svn] Move SPC-specific code into SPC-specific routines.
nenolod
parents:
146
diff
changeset
|
147 if (ext) |
6fe2bfbe6fc2
[svn] Move SPC-specific code into SPC-specific routines.
nenolod
parents:
146
diff
changeset
|
148 { |
6fe2bfbe6fc2
[svn] Move SPC-specific code into SPC-specific routines.
nenolod
parents:
146
diff
changeset
|
149 if (!strcasecmp(ext, ".spc")) |
6fe2bfbe6fc2
[svn] Move SPC-specific code into SPC-specific routines.
nenolod
parents:
146
diff
changeset
|
150 play_file_spc(filename); |
6fe2bfbe6fc2
[svn] Move SPC-specific code into SPC-specific routines.
nenolod
parents:
146
diff
changeset
|
151 } |
95 | 152 } |
153 | |
96 | 154 static void seek(gint time) |
155 { | |
156 // XXX: Not yet implemented | |
157 } | |
158 | |
159 InputPlugin console_ip = { | |
160 NULL, | |
161 NULL, | |
162 NULL, | |
163 console_init, | |
109 | 164 console_aboutbox, |
96 | 165 NULL, |
166 is_our_file, | |
167 NULL, | |
168 play_file, | |
169 console_stop, | |
170 console_pause, | |
171 seek, | |
172 NULL, | |
173 get_time, | |
174 NULL, | |
175 NULL, | |
176 NULL, | |
177 NULL, | |
178 NULL, | |
179 NULL, | |
180 NULL, | |
104 | 181 get_song_info, |
96 | 182 NULL, |
183 NULL | |
184 }; | |
185 | |
186 static void console_stop(void) | |
187 { | |
103 | 188 console_ip_is_going = FALSE; |
96 | 189 g_thread_join(decode_thread); |
190 console_ip.output->close_audio(); | |
191 } | |
192 | |
98
e42694a28331
[svn] More progress -- now loads as an audacious module. :)
nenolod
parents:
96
diff
changeset
|
193 extern "C" InputPlugin *get_iplugin_info(void) |
96 | 194 { |
109 | 195 console_ip.description = g_strdup_printf(_("SPC, GYM, NSF, VGM and GBS module decoder")); |
96 | 196 return &console_ip; |
197 } | |
198 | |
199 static void console_pause(gshort p) | |
200 { | |
201 console_ip.output->pause(p); | |
202 } | |
203 | |
147
6fe2bfbe6fc2
[svn] Move SPC-specific code into SPC-specific routines.
nenolod
parents:
146
diff
changeset
|
204 static void *play_loop_spc(gpointer arg) |
95 | 205 { |
99 | 206 Spc_Emu *my_spc = (Spc_Emu *) arg; |
108 | 207 Music_Emu::sample_t buf[1024]; |
95 | 208 |
145 | 209 for (;;) |
210 { | |
211 if (!console_ip_is_going) | |
212 break; | |
213 | |
214 my_spc->play(1024, buf); | |
215 | |
216 if ((console_ip.output->output_time() / 1000) > | |
217 audcfg.loop_length && audcfg.loop_length != 0) | |
218 break; | |
100 | 219 console_ip.add_vis_pcm(console_ip.output->written_time(), |
108 | 220 MY_FMT, 1, 2048, buf); |
221 while(console_ip.output->buffer_free() < 2048) | |
101
59ba6595fdf1
[svn] More accurate sound reproduction, but there is warbling. Still locks up player on completion.
nenolod
parents:
100
diff
changeset
|
222 xmms_usleep(10000); |
108 | 223 console_ip.output->write_audio(buf, 2048); |
100 | 224 } |
95 | 225 |
96 | 226 delete spc; |
145 | 227 console_ip.output->close_audio(); |
228 console_ip_is_going = FALSE; | |
147
6fe2bfbe6fc2
[svn] Move SPC-specific code into SPC-specific routines.
nenolod
parents:
146
diff
changeset
|
229 playing_type = PLAY_TYPE_NONE; |
96 | 230 g_thread_exit(NULL); |
95 | 231 |
96 | 232 return NULL; |
95 | 233 } |
234 | |
96 | 235 static int get_time(void) |
236 { | |
145 | 237 if (console_ip_is_going == TRUE) |
238 return console_ip.output->output_time(); | |
239 else | |
240 return -1; | |
96 | 241 } |
95 | 242 |
100 | 243 static void console_init(void) |
244 { | |
245 | |
246 } | |
247 | |
109 | 248 extern "C" void console_aboutbox(void) |
249 { | |
250 xmms_show_message(_("About the Console Music Decoder"), | |
251 _("Console music decoder engine based on Game_Music_Emu 0.2.4.\n" | |
252 "Audacious implementation by: William Pitcock <nenolod@nenolod.net>"), | |
253 _("Ok"), | |
254 FALSE, NULL, NULL); | |
255 } |