1 /* $Id: ipret.c,v 1.10 2006/09/16 10:17:33 toad32767 Exp $ */
2 /**
3 ** 2005, 2006 by Marco Trillo
4 ** This file is part of UModPlayer, and is released by
5 ** its autors to the Public Domain.
6 ** In case it's not legally possible, its autors grant
7 ** anyone the right to use, redistribute and modify
8 ** this software for any purpose, without any conditions,
9 ** unless such conditions are required by law.
10 **
11 ** THIS FILE COMES WITHOUT ANY WARRANTY. THE AUTHORS
12 ** SHALL NOT BE LIABLE FOR ANY DAMAGE RESULTING BY THE
13 ** USE OR MISUSE OF THIS SOFTWARE.
14 **/
15
16 #include <umodplayer.h>
17 #include <text.h>
18 #include <messages.h>
19 #include <coresound.h>
20 #include <file_read.h>
21 #include <options.h>
22 #include <file_parse.h>
23 #include <notes.h>
24
25 /*
26 * User commands
27 */
28 void
CommandOpen(char * filenam)29 CommandOpen(char *filenam)
30 {
31 if (filenam == NULL || *filenam == '\0') {
32 fputs("usage: open <file>\n", stderr);
33 return;
34 }
35 /* free the current file */
36 UFreeFile();
37 file.name = strcopyof(filenam);
38 if (file.name == NULL) {
39 error("%s", MESSAGE_NO_MEMORY);
40 return;
41 }
42 file.malloc = TRUE;
43 ULoadFile();
44 }
45
46 void
CommandConfig(char * unused)47 CommandConfig(char *unused)
48 {
49 WTable table;
50
51 rr = (char **) malloc(8 * sizeof(char *));
52
53 rr[0] = "Sampling Rate:";
54 rr[1] = "Resampling Mode:";
55 rr[2] = "Noise Reduction:";
56 rr[3] = "Reverb:";
57 rr[4] = "Megabass:";
58 rr[5] = "Surround:";
59 rr[6] = "Channels:";
60 rr[7] = "Master Volume:";
61
62 TableSetOptions(&table, 0, 8, 2, CalcLen(rr, 8) + 1, 0, TABLE_LEFT_ALIGN);
63 TableUseTheme(&table, sets.appareance);
64 TableInitCallback(&table, MyTextCallback);
65 DrawTable(table);
66 free(rr);
67 }
68
69 void
CommandHelp(char * unused)70 CommandHelp(char *unused)
71 {
72 puts("Commands available on interactive mode:");
73 puts(" quit config play");
74 puts(" position noise reverb");
75 puts(" megabass surround reset");
76 puts(" loadconfig saveconfig info");
77 puts(" list / ls message samples");
78 puts(" instruments export advanced");
79 puts(" setadvanced playlist volume");
80 puts(" display <X>-<Y> goto <ORDER> samplerate <F>");
81 puts(" open <FILE> volume <V> savemessage <FILE>");
82 puts(" resampling <M> channels (1|2) cd <DIRECTORY>");
83 puts(" exec <command> version");
84 puts("");
85 puts("Hint: The '!' command prints the last executed command,");
86 puts(" and the '!!' command (without quotes) runs it.");
87 }
88
89 void
CommandVolume(char * volstr)90 CommandVolume(char *volstr)
91 {
92 if (volstr == NULL || *volstr == '\0') {
93 printf("volume: %u\n", sets.vol);
94 } else {
95 sets.vol = (unsigned int) strtoul(volstr, NULL, 10);
96 if (sets.vol > 768) /* XXX - what's the ModPlug limit ? */
97 sets.vol = 768;
98 else if (sets.vol < 1)
99 sets.vol = 1;
100 }
101 }
102
103 void
CommandDisplay(char * range)104 CommandDisplay(char *range)
105 {
106 if (range == NULL || *range == '\0') {
107 NoteDisplay_Start(-1, -1);
108 } else {
109 int x, y;
110
111 GetRangeValues(range, &x, &y);
112 NoteDisplay_Start(x, y);
113 }
114 }
115
116 void
CommandSampleRate(char * rate)117 CommandSampleRate(char *rate)
118 {
119 int r;
120
121 if (rate == NULL || *rate == '\0')
122 fputs("usage: samplerate <rate>\n", stderr);
123 else {
124 r = (int) strtoul(rate, NULL, 10);
125
126 switch (r) {
127 case 11025:
128 case 16000:
129 case 22050:
130 case 24000:
131 case 32000:
132 case 44100:
133 sets.samplerate = r;
134
135 /* XXX -- hack for ModPlug 0.7/0.8 configuration oddness (bug or feature?) */
136 if (file.name != NULL) {
137 CoreSound_InitOptions();
138 }
139
140 break;
141 default:
142 warning("invalid sampling rate -- %d. not changing.\n", r);
143 }
144 }
145 }
146
147 void
CommandReSampling(char * mode)148 CommandReSampling(char *mode)
149 {
150 if (mode == NULL) {
151 usage:
152 fputs("usage: resampling (NO_INTERPOLATE|LINEAR|SPLINE|FIR_FILTER)\n", stderr);
153 return;
154 }
155 if (strcasecmp(mode, "NO_INTERPOLATE") == 0 ||
156 strcmp(mode, "RESAMPLE") == 0) /* deprecated, compat. only */
157 sets.resampling = 0;
158 else if (strcasecmp(mode, "LINEAR") == 0)
159 sets.resampling = 1;
160 else if (strcasecmp(mode, "SPLINE") == 0)
161 sets.resampling = 2;
162 else if (strcasecmp(mode, "FIR_FILTER") == 0)
163 sets.resampling = 3;
164 else
165 goto usage;
166 }
167
168 void
CommandChannels(char * ch)169 CommandChannels(char *ch)
170 {
171 if (ch == NULL || *ch == '\0') {
172 fputs("usage: channels (1|2)\n", stderr);
173 } else {
174 if (*ch == '1')
175 sets.channels = 1;
176 else
177 sets.channels = 2;
178 }
179 }
180
181 void
CommandGoTo(char * to)182 CommandGoTo(char *to)
183 {
184 if (to == NULL || *to == '\0') {
185 usage:
186 fputs("usage: goto <order>\n", stderr);
187 } else {
188 int pos;
189
190 pos = atoi(to);
191 if (pos > -1) {
192 ModPlug_SeekOrder(file.mod, pos);
193 } else {
194 goto usage;
195 }
196 }
197 }
198
199 void
CommandChDir(char * dir)200 CommandChDir(char *dir)
201 {
202 if (dir == NULL || *dir == '\0') {
203 char *home = getenv("HOME");
204 if (home != NULL) {
205 chdir(home);
206 }
207 } else {
208 chdir(dir);
209 }
210 }
211
212
213 void
CommandQuit(char * unused)214 CommandQuit(char *unused)
215 {
216 exit(UM_OK);
217 }
218 void
CommandInfo(char * unused)219 CommandInfo(char *unused)
220 {
221 DrawInfoTable();
222 }
223 void
CommandPlay(char * unused)224 CommandPlay(char *unused)
225 {
226 (void) CoreSound_StartMonitor();
227 }
228 void
CommandPosition(char * unused)229 CommandPosition(char *unused)
230 {
231 DisplayCurPos();
232 }
233 void
CommandNoise(char * unused)234 CommandNoise(char *unused)
235 {
236 sets.flags ^= MODPLUG_ENABLE_NOISE_REDUCTION;
237 }
238 void
CommandReverb(char * unused)239 CommandReverb(char *unused)
240 {
241 sets.flags ^= MODPLUG_ENABLE_REVERB;
242 }
243 void
CommandMegabass(char * unused)244 CommandMegabass(char *unused)
245 {
246 sets.flags ^= MODPLUG_ENABLE_MEGABASS;
247 }
248 void
CommandSurround(char * unused)249 CommandSurround(char *unused)
250 {
251 sets.flags ^= MODPLUG_ENABLE_SURROUND;
252 }
253 void
CommandReset(char * unused)254 CommandReset(char *unused)
255 {
256 DefaultOptions(&sets);
257 }
258 void
CommandLoadConfig(char * unused)259 CommandLoadConfig(char *unused)
260 {
261 InitOptions(&sets);
262 }
263 void
CommandSaveConfig(char * unused)264 CommandSaveConfig(char *unused)
265 {
266 SaveOptions(&sets);
267 }
268 void
CommandList(char * unused)269 CommandList(char *unused)
270 {
271 SongList();
272 }
273 void
CommandMessage(char * unused)274 CommandMessage(char *unused)
275 {
276 DisplaySongComments();
277 }
278 void
CommandInstruments(char * unused)279 CommandInstruments(char *unused)
280 {
281 DisplayInstruments(0);
282 }
283 void
CommandSamples(char * unused)284 CommandSamples(char *unused)
285 {
286 DisplaySamples(0);
287 }
288 void
CommandExport(char * unused)289 CommandExport(char *unused)
290 {
291 ExportSong();
292 }
293 void
CommandAdvanced(char * unused)294 CommandAdvanced(char *unused)
295 {
296 AdvancedConfig();
297 }
298 void
CommandSetAdvanced(char * unused)299 CommandSetAdvanced(char *unused)
300 {
301 AdvancedConfig();
302 SetAdvancedConfig();
303 }
304 void
CommandPlayList(char * unused)305 CommandPlayList(char *unused)
306 {
307 PlayList();
308 }
309
310 void
CommandExec(char * command)311 CommandExec(char *command)
312 {
313 if (command == NULL || *command == '\0')
314 fputs("usage: exec <system command>\n", stderr);
315 else
316 system(command);
317 }
318
319 void
CommandVersion(char * unused)320 CommandVersion(char *unused)
321 {
322 PrintBanner();
323 }
324
325
326 /*
327 * Command interpreter
328 */
329 struct command {
330 char *name;
331 int moduleNeeded;
332 void (*action) (char *);
333 };
334
335 LOCAL struct command commands[] = {
336 {"open", 0, CommandOpen},
337 {"load", 0, CommandOpen},
338 {"config", 0, CommandConfig},
339 {"help", 0, CommandHelp},
340 {"?", 0, CommandHelp},
341 {"volume", 0, CommandVolume},
342 {"display", 1, CommandDisplay},
343 {"samplerate", 0, CommandSampleRate},
344 {"resampling", 0, CommandReSampling},
345 {"channels", 0, CommandChannels},
346 {"goto", 1, CommandGoTo},
347 {"chdir", 0, CommandChDir},
348 {"cd", 0, CommandChDir},
349 {"quit", 0, CommandQuit},
350 {"exit", 0, CommandQuit},
351 {"info", 1, CommandInfo},
352 {"play", 1, CommandPlay},
353 {"position", 1, CommandPosition},
354 {"noise", 0, CommandNoise},
355 {"reverb", 0, CommandReverb},
356 {"megabass", 0, CommandMegabass},
357 {"surround", 0, CommandSurround},
358 {"reset", 0, CommandReset},
359 {"loadconfig", 0, CommandLoadConfig},
360 {"saveconfig", 0, CommandSaveConfig},
361 {"list", 0, CommandList},
362 {"ls", 0, CommandList},
363 {"message", 1, CommandMessage},
364 {"instruments", 1, CommandInstruments},
365 {"samples", 1, CommandSamples},
366 {"export", 1, CommandExport},
367 {"advanced", 0, CommandAdvanced},
368 {"setadvanced", 0, CommandSetAdvanced},
369 {"playlist", 0, CommandPlayList},
370 {"exec", 0, CommandExec},
371 {"version", 0, CommandVersion},
372 {NULL, 0, NULL}
373
374 };
375
376 struct cline {
377 char *command;
378 char *params;
379 };
380
381 LOCAL struct cline *
ParseCommandLine(char * com)382 ParseCommandLine(char *com)
383 {
384 char *t;
385 static struct cline cl;
386
387 TrimString(com);
388 t = com;
389
390 while (*t != '\0' && *t != ' ' && *t != '\t' && *t != '#') {
391 ++t;
392 }
393
394 if (*t == '#') { /* skip comments */
395 *t = '\0';
396 cl.command = com;
397 cl.params = NULL;
398 } else if (t > com && (*t == ' ' || *t == '\t')) {
399 *t = '\0';
400
401 do
402 ++t;
403 while (*t == ' ' || *t == '\t');
404
405 cl.command = com;
406 cl.params = t;
407 } else {
408 cl.command = com;
409 cl.params = NULL;
410 }
411
412 return &cl;
413 }
414
415 LOCAL void
RunCommand(char * line)416 RunCommand(char *line)
417 {
418 struct cline *l;
419 struct command *c;
420
421 l = ParseCommandLine(line);
422
423 /* null command */
424 if (l->command[0] == '\0')
425 return;
426
427 for (c = commands; c->name != NULL; ++c) {
428 if (strcmp(c->name, l->command) == 0) {
429 if (c->moduleNeeded && file.name == NULL) {
430 warning("%s: no module loaded\n", l->command);
431 } else {
432 c->action(l->params);
433 }
434 return;
435 }
436 }
437
438 warning("%s: invalid command\nTry: `help'\n", l->command);
439 }
440
441
442 EXPORT void
CommandInterpreter()443 CommandInterpreter()
444 {
445 char *str, *last = NULL, pathbuf[1024];
446
447 for (;;) {
448 getcwd(pathbuf, 1024);
449 printf("umodplayer[%s]%% ", pathbuf);
450 fflush(stdout);
451
452 str = ReadString();
453 if (str == NULL) {
454 fputs(MESSAGE_NO_MEMORY, stderr);
455 continue;
456 }
457 if (str[0] == '!') {
458 if (last != NULL) {
459 if (str[1] == '!') {
460 RunCommand(last);
461 } else {
462 puts(last);
463 }
464 }
465 free(str);
466 } else {
467 if (last != NULL)
468 free(last);
469 last = strcopyof(str); /* RunCommand() modifies 'str' */
470 RunCommand(str);
471 free(str);
472 }
473 }
474 }
475