1 /*---------------------------------------------------------------------------*
2 Project: Chorus (expanded version) Test
3 File: expchorus.c
4
5 Copyright (C)2006 Nintendo All Rights Reserved.
6
7 These coded instructions, statements, and computer programs contain
8 proprietary information of Nintendo of America Inc. and/or Nintendo
9 Company Ltd., and are protected by Federal copyright law. They may
10 not be disclosed to third parties or copied or duplicated in any form,
11 in whole or in part, without the prior written consent of Nintendo.
12
13 $Log: expchorus.c,v $
14 Revision 1.1 06/08/2006 08:16:15 aka
15 Imported new demos for new AXFX made by Kawamura-san (EAD).
16
17 $NoKeywords: $
18 *---------------------------------------------------------------------------*/
19
20
21 /*---------------------------------------------------------------------------*
22 * Includes
23 *---------------------------------------------------------------------------*/
24
25 #include <demo.h>
26 #include <demo/DEMOWin.h>
27 #include <revolution.h>
28 #include <revolution/mix.h>
29 #include <revolution/sp.h>
30 #include <revolution/axfx.h>
31 #include <revolution/axfx_presets.h>
32 #include <revolution/mem.h>
33 #include <string.h>
34
35 #include "dpl2reverb.h"
36
37 /*---------------------------------------------------------------------------*
38 * SP data
39 *---------------------------------------------------------------------------*/
40
41 #define SPT_FILE "/axdemo/dpl2/dpl2reverb.spt"
42 #define SPD_FILE "/axdemo/dpl2/dpl2reverb.spd"
43
44 // use only a single SP sound table
45 static SPSoundTable *sp_table;
46 static u8 *sp_data;
47
48 /*---------------------------------------------------------------------------*
49 * Exp Heap
50 *---------------------------------------------------------------------------*/
51 static MEMHeapHandle hExpHeap;
52
53 /*---------------------------------------------------------------------------*
54 * Zero Buffer
55 *---------------------------------------------------------------------------*/
56
57 #define ZEROBUFFER_BYTES 256
58
59 /*---------------------------------------------------------------------------*
60 * AX and Application-layer voice abstraction
61 *---------------------------------------------------------------------------*/
62
63 // Max number of voices we will support in the abstraction layer
64 #define MAX_DEMO_VOICES 64
65
66 // Checks SP entry 'type' to see if the voice is looped or not
67 #define mISLOOPED(x) ((x->type)&0x1)
68
69 int panX; // pan value for left/right
70 int panY; // pan value for front/back
71
72 // Each voice has an associated AX parameter block and an SP entry
73 typedef struct
74 {
75 AXVPB *ax_voice;
76 SPSoundEntry *sp_entry;
77
78 } DEMO_VOICE;
79
80 DEMO_VOICE demo_voices[MAX_DEMO_VOICES];
81
82 // Constructs for Aux-bus effects
83 static AXFX_CHORUS_EXP chorus;
84
85 // AX profiling structures
86
87 // store up to 8 frames, just to be safe
88 #define NUM_AX_PROFILE_FRAMES 8
89
90 static AXPROFILE ax_profile[NUM_AX_PROFILE_FRAMES];
91
92 /*---------------------------------------------------------------------------*
93 * Prototypes
94 *---------------------------------------------------------------------------*/
95
96 // for AX and voice abstraction layer
97 static void ax_demo_callback (void);
98 static void ax_drop_voice_callback (void *p);
99 static void stop_all_voices (void);
100 static void stop_voice (DEMO_VOICE *v);
101 static DEMO_VOICE *play_sfx (u32 sfx);
102
103 // for UI menus
104 static void MNU_sound (DEMOWinMenuInfo *menu, u32 item, u32 *result);
105 static void MNU_position (DEMOWinMenuInfo *menu, u32 item, u32 *result);
106 static void MNU_stop_sfx (DEMOWinMenuInfo *menu, u32 item, u32 *result);
107 static void MNU_auxa (DEMOWinMenuInfo *menu, u32 item, u32 *result);
108 static void MNU_compressor (DEMOWinMenuInfo *menu, u32 item, u32 *result);
109 static void MNU_kill_all (DEMOWinMenuInfo *menu, u32 item, u32 *result);
110
111 /*---------------------------------------------------------------------------*
112 * User Interface stuff
113 *---------------------------------------------------------------------------*/
114
115 static u32 soundIndex = 0; // current sound effect to play
116 static u32 positionIndex = 0; // current panning
117 static u32 auxaIndex = 0; // current effect to apply to AuxA bus
118 static u32 compressFlag = 0; // current compressor state
119
120 DEMOWinInfo *DebugWin;
121 DEMOWinInfo *PositionWin;
122
123 DEMOWinMenuItem MenuItem[] =
124 {
125 { "Sound : (none)", DEMOWIN_ITM_NONE, MNU_sound, NULL },
126 { "AuxA : (none)", DEMOWIN_ITM_NONE, MNU_auxa, NULL },
127 { "", DEMOWIN_ITM_SEPARATOR, NULL, NULL },
128 { "Position: C Stick", DEMOWIN_ITM_NONE, MNU_position, NULL },
129 { "", DEMOWIN_ITM_SEPARATOR, NULL, NULL },
130 { "Compress: No", DEMOWIN_ITM_NONE, MNU_compressor, NULL },
131 { "", DEMOWIN_ITM_SEPARATOR, NULL, NULL },
132 { "Kill All Voices", DEMOWIN_ITM_NONE, MNU_kill_all, NULL },
133 { "", DEMOWIN_ITM_TERMINATOR, NULL, NULL }
134
135 };
136
137 DEMOWinMenuInfo Menu =
138 {
139 "AX ChorusExp Test", // title
140 NULL, // window handle
141 MenuItem, // list of menu items
142 9, // max num of items to display at a time
143 DEMOWIN_MNU_NONE, // attribute flags
144
145 // user callbacks
146 NULL, // callback for menu open event
147 NULL, // callback for cursor move event
148 NULL, // callback for item select event
149 NULL, // callback for cancel event
150
151 // private members
152 0, 0, 0, 0, 0
153 };
154
155 DEMOWinMenuInfo *MenuPtr;
156
157 /*===========================================================================*
158 * F U N C T I O N D E F I N I T I O N S
159 *===========================================================================*/
160
161
162 /*---------------------------------------------------------------------------*
163 * VOICE ABSTRACTION LAYER STUFF
164 /*---------------------------------------------------------------------------*
165
166
167 /*---------------------------------------------------------------------------*
168 * Name :
169 * Description :
170 * Arguments :
171 * Returns :
172 *---------------------------------------------------------------------------*/
173
174
stop_voice(DEMO_VOICE * v)175 static void stop_voice(DEMO_VOICE *v)
176 {
177
178 u32 i;
179 BOOL old;
180
181 old = OSDisableInterrupts();
182
183 for (i=0; i<MAX_DEMO_VOICES; i++)
184 {
185 if (v == &demo_voices[i])
186 {
187 if (demo_voices[i].ax_voice)
188 {
189 if (mISLOOPED(demo_voices[i].sp_entry))
190 {
191 SPPrepareEnd(demo_voices[i].sp_entry, demo_voices[i].ax_voice);
192 }
193 else
194 {
195 AXSetVoiceState(demo_voices[i].ax_voice, AX_PB_STATE_STOP);
196 }
197
198 break;
199 }
200
201 }
202 }
203
204 (void)OSRestoreInterrupts(old);
205
206
207 } // end stop_voice()
208
209 /*---------------------------------------------------------------------------*
210 * Name :
211 * Description :
212 * Arguments :
213 * Returns :
214 *---------------------------------------------------------------------------*/
215
stop_all_voices(void)216 static void stop_all_voices(void)
217 {
218
219 u32 i;
220 BOOL old;
221
222
223
224 old = OSDisableInterrupts();
225
226 for (i=0; i<MAX_DEMO_VOICES; i++)
227 {
228 if (demo_voices[i].ax_voice)
229 {
230 if (mISLOOPED(demo_voices[i].sp_entry))
231 {
232 SPPrepareEnd(demo_voices[i].sp_entry, demo_voices[i].ax_voice);
233 }
234 else
235 {
236 AXSetVoiceState(demo_voices[i].ax_voice, AX_PB_STATE_STOP);
237 }
238
239 }
240
241 }
242
243 (void)OSRestoreInterrupts(old);
244
245
246 } // end stop_voice()
247
248 /*---------------------------------------------------------------------------*
249 * Name :
250 * Description :
251 * Arguments :
252 * Returns :
253 *---------------------------------------------------------------------------*/
254
255
play_sfx(u32 sfx)256 static DEMO_VOICE *play_sfx(u32 sfx)
257 {
258
259 AXVPB *ax_v;
260 DEMO_VOICE *v;
261
262 BOOL old;
263
264
265 old = OSDisableInterrupts();
266
267 ax_v = AXAcquireVoice(15, ax_drop_voice_callback, 0);
268
269 if (ax_v)
270 {
271 // use AX voice index to reference a voice in the demo abstraction layer
272 demo_voices[ax_v->index].ax_voice = ax_v;
273
274 // assign a pointer for convenience
275 v = &demo_voices[ax_v->index];
276
277 // grab the requested sound from the SP table
278 v->sp_entry = SPGetSoundEntry(sp_table, sfx);
279
280 SPPrepareSound(v->sp_entry, v->ax_voice, (v->sp_entry)->sampleRate);
281
282
283 MIXInitChannel(v->ax_voice, 0, 0, 0, -960, -960, panX, 127-panY, 0);
284 AXSetVoiceState(v->ax_voice, AX_PB_STATE_RUN);
285
286 (void)OSRestoreInterrupts(old);
287 }
288 else
289 {
290 v = NULL;
291 (void)OSRestoreInterrupts(old);
292 DEMOWinLogPrintf(DebugWin, "ERROR: AX voice allocation failed.\n");
293
294 }
295
296 return(v);
297
298 } // end play_sfx()
299
300
301 /*---------------------------------------------------------------------------*
302 * Name :
303 * Description :
304 * Arguments : None.
305 * Returns : None.
306 *---------------------------------------------------------------------------*/
ax_demo_callback(void)307 static void ax_demo_callback(void)
308 {
309
310 u32 i;
311
312 // check for voices which have stopped and remove them from the
313 // abstraction layer
314 for (i=0; i<MAX_DEMO_VOICES; i++)
315 {
316 if (demo_voices[i].ax_voice)
317 {
318 if ( AX_PB_STATE_STOP == ((demo_voices[i].ax_voice)->pb.state))
319 {
320 // if the voice has stopped, clear it from the abstraction layer
321 MIXReleaseChannel(demo_voices[i].ax_voice);
322 AXFreeVoice(demo_voices[i].ax_voice);
323 demo_voices[i].ax_voice = NULL;
324 }
325 else
326 {
327 // otherwise, update the panning
328 MIXSetPan(demo_voices[i].ax_voice, panX);
329 MIXSetSPan(demo_voices[i].ax_voice, 127 - panY);
330 MIXUpdateSettings();
331 }
332 }
333 }
334
335 } // end ax_demo_callback()
336
337
338 /*---------------------------------------------------------------------------*
339 * Name : ax_drop_voice_callback()
340 * Description : Invoked by AX when a voice has been forciby dropped.
341 * Must delete references to the voice from our abstraction layer
342 * and release the associated MIXer channel.
343 * Arguments : None.
344 * Returns : None.
345 *---------------------------------------------------------------------------*/
ax_drop_voice_callback(void * p)346 static void ax_drop_voice_callback(void *p)
347 {
348
349 AXVPB *v;
350
351 v = (AXVPB *)p;
352
353 MIXReleaseChannel(demo_voices[v->index].ax_voice);
354 demo_voices[v->index].ax_voice = NULL;
355 demo_voices[v->index].sp_entry = NULL;
356
357 } // end ax_demo_callback()
358
359
360
361 /*---------------------------------------------------------------------------*
362 * MENU FUNCTIONS
363 /*---------------------------------------------------------------------------*
364
365 /*---------------------------------------------------------------------------*
366 * Name :
367 * Description :
368 * Arguments :
369 * Returns :
370 *---------------------------------------------------------------------------*/
371
MNU_compressor(DEMOWinMenuInfo * menu,u32 item,u32 * result)372 static void MNU_compressor(DEMOWinMenuInfo *menu, u32 item, u32 *result)
373 {
374 #pragma unused(menu, item, result)
375
376 BOOL old;
377
378 old = OSDisableInterrupts();
379
380 compressFlag ^= 1;
381 AXSetCompressor(compressFlag);
382
383 (void)OSRestoreInterrupts(old);
384
385 if (compressFlag)
386 {
387 menu->items[item].name = "Compress: YES";
388 }
389 else
390 {
391 menu->items[item].name = "Compress: NO ";
392 }
393
394
395 } // end MNU_compressor()
396
397 /*---------------------------------------------------------------------------*
398 * Name :
399 * Description :
400 * Arguments :
401 * Returns :
402 *---------------------------------------------------------------------------*/
403
MNU_kill_all(DEMOWinMenuInfo * menu,u32 item,u32 * result)404 static void MNU_kill_all(DEMOWinMenuInfo *menu, u32 item, u32 *result)
405 {
406 #pragma unused(menu, item, result)
407
408
409 u32 i;
410 BOOL old;
411
412 old = OSDisableInterrupts();
413
414 for (i=0; i<MAX_DEMO_VOICES; i++)
415 {
416 if (demo_voices[i].ax_voice)
417 {
418 AXSetVoiceState(demo_voices[i].ax_voice, AX_PB_STATE_STOP);
419 }
420 }
421
422 (void)OSRestoreInterrupts(old);
423
424
425 } // end MNU_kill_all()
426
427
428
429 /*---------------------------------------------------------------------------*
430 * Name :
431 * Description :
432 * Arguments :
433 * Returns :
434 *---------------------------------------------------------------------------*/
435
MNU_auxa(DEMOWinMenuInfo * menu,u32 item,u32 * result)436 static void MNU_auxa(DEMOWinMenuInfo *menu, u32 item, u32 *result)
437 {
438 #pragma unused(menu, item, result)
439
440 auxaIndex++;
441
442 auxaIndex %= 10;
443
444 switch (auxaIndex)
445 {
446 case 0:
447 AXFXChorusExpShutdown(&chorus);
448 AXRegisterAuxACallback(NULL, NULL);
449 menu->items[item].name = "Chorus : (none)";
450 break;
451 case 1:
452 AXFX_PRESET_CHORUS_EXP_TYPE1(&chorus);
453 AXFXChorusExpSettings(&chorus);
454 AXRegisterAuxACallback((void*)&AXFXChorusExpCallback, (void*)&chorus);
455 menu->items[item].name = "Chorus : Type 1";
456 break;
457
458
459 case 2:
460 AXFX_PRESET_CHORUS_EXP_TYPE2(&chorus);
461 AXFXChorusExpSettings(&chorus);
462 AXRegisterAuxACallback((void*)&AXFXChorusExpCallback, (void*)&chorus);
463 menu->items[item].name = "Chorus : Type 2";
464 break;
465
466 case 3:
467 AXFX_PRESET_CHORUS_EXP_TYPE3(&chorus);
468 AXFXChorusExpSettings(&chorus);
469 AXRegisterAuxACallback((void*)&AXFXChorusExpCallback, (void*)&chorus);
470 menu->items[item].name = "Chorus : Type 3";
471 break;
472
473 case 4:
474 AXFX_PRESET_CHORUS_EXP_FLANGER1(&chorus);
475 AXFXChorusExpSettings(&chorus);
476 AXRegisterAuxACallback((void*)&AXFXChorusExpCallback, (void*)&chorus);
477 menu->items[item].name = "Flanger : Type 1";
478 break;
479
480 case 5:
481 AXFX_PRESET_CHORUS_EXP_FLANGER2(&chorus);
482 AXFXChorusExpSettings(&chorus);
483 AXRegisterAuxACallback((void*)&AXFXChorusExpCallback, (void*)&chorus);
484 menu->items[item].name = "Flanger : Type 2";
485 break;
486
487 case 6:
488 AXFX_PRESET_CHORUS_EXP_ECHO1(&chorus);
489 AXFXChorusExpSettings(&chorus);
490 AXRegisterAuxACallback((void*)&AXFXChorusExpCallback, (void*)&chorus);
491 menu->items[item].name = "ChorEcho : Type 1";
492 break;
493
494 case 7:
495 AXFX_PRESET_CHORUS_EXP_ECHO2(&chorus);
496 AXFXChorusExpSettings(&chorus);
497 AXRegisterAuxACallback((void*)&AXFXChorusExpCallback, (void*)&chorus);
498 menu->items[item].name = "ChorEcho : Type 2";
499 break;
500
501 case 8:
502 AXFX_PRESET_CHORUS_EXP_WOBBLE1(&chorus);
503 AXFXChorusExpSettings(&chorus);
504 AXRegisterAuxACallback((void*)&AXFXChorusExpCallback, (void*)&chorus);
505 menu->items[item].name = "ChorWobble : Type 1";
506 break;
507
508 case 9:
509 AXFX_PRESET_CHORUS_EXP_WOBBLE2(&chorus);
510 AXFXChorusExpSettings(&chorus);
511 AXRegisterAuxACallback((void*)&AXFXChorusExpCallback, (void*)&chorus);
512 menu->items[item].name = "ChorWobble : Type 2";
513 break;
514
515
516 }
517
518
519 } // end MNU_auxa()
520
521
522 /*---------------------------------------------------------------------------*
523 * Name :
524 * Description :
525 * Arguments :
526 * Returns :
527 *---------------------------------------------------------------------------*/
528
MNU_sound(DEMOWinMenuInfo * menu,u32 item,u32 * result)529 static void MNU_sound(DEMOWinMenuInfo *menu, u32 item, u32 *result)
530 {
531 #pragma unused(result)
532
533 soundIndex++;
534 soundIndex %= 5;
535
536
537 stop_all_voices();
538
539 switch (soundIndex)
540 {
541 case 0: // None
542
543 menu->items[item].name = "Sound : None";
544 break;
545
546 case 1:
547
548 play_sfx(SFX_TICK);
549 menu->items[item].name = "Sound : TICK";
550
551 break;
552
553 case 2:
554
555 play_sfx(SFX_EXPLODE);
556 menu->items[item].name = "Sound : EXPLOSION";
557
558 break;
559
560 case 3:
561
562 play_sfx(SFX_MACHINEGUN);
563 menu->items[item].name = "Sound : MACHINEGUN";
564
565 break;
566
567 case 4:
568
569 play_sfx(SFX_SYNTH);
570 menu->items[item].name = "Sound : SYNTH";
571
572 break;
573
574 } // end switch()
575
576 } // end MNU_sound
577
578
579
580
581
582 /*---------------------------------------------------------------------------*
583 * Name :
584 * Description :
585 * Arguments :
586 * Returns :
587 *---------------------------------------------------------------------------*/
588
MNU_position(DEMOWinMenuInfo * menu,u32 item,u32 * result)589 static void MNU_position(DEMOWinMenuInfo *menu, u32 item, u32 *result)
590 {
591 #pragma unused(result)
592
593 positionIndex++;
594 positionIndex %= 7;
595
596 switch (positionIndex)
597 {
598 case 0:
599
600 menu->items[item].name = "Position: C Stick";
601
602 break;
603
604 case 1:
605
606 panX = 0;
607 panY = 0;
608 menu->items[item].name = "Position: L";
609
610 break;
611
612 case 2:
613
614 panX = 63;
615 panY = 0;
616 menu->items[item].name = "Position: C";
617
618 break;
619
620 case 3:
621
622 panX = 127;
623 panY = 0;
624 menu->items[item].name = "Position: R";
625
626 break;
627
628 case 4:
629
630 panX = 0;
631 panY = 127;
632 menu->items[item].name = "Position: Ls";
633
634 break;
635
636 case 5:
637
638 panX = 127;
639 panY = 127;
640 menu->items[item].name = "Position: Rs";
641
642 break;
643
644 case 6:
645
646 panX = 63;
647 panY = 127;
648 menu->items[item].name = "Position: Bs";
649
650 break;
651
652 }
653
654 } // end MNU_position()
655
656
657 /*---------------------------------------------------------------------------*
658 * Name : position_win_update()
659 * Description : refresh callback for position window
660 * Arguments :
661 * Returns :
662 *---------------------------------------------------------------------------*/
663
position_win_update(DEMOWinInfo * window)664 static void position_win_update(DEMOWinInfo *window)
665 {
666
667
668 int substickX;
669 int substickY;
670
671 BOOL old;
672
673 u32 i;
674
675 u32 cpuCycles;
676 u32 userCycles;
677 u32 axCycles;
678 u32 voices;
679
680 u32 maxCpuCycles =0;
681 u32 maxUserCycles=0;
682 u32 maxAxCycles =0;
683 u32 maxVoices =0;
684
685
686 substickX = (MenuPtr->handle)->pad.pads[0].substickX;
687 substickY = (MenuPtr->handle)->pad.pads[0].substickY;
688
689 // Update panning position
690 if (positionIndex == 0)
691 {
692
693 // if positionIndex is zero, then get panning information from
694 // the C-stick
695 panX = substickX + 63;
696 panY = (substickY - 63) * -1;
697
698 }
699
700 DEMOWinPrintfXY(window, 0, 1, "Pan : %1.2f ", (f32)panX/127);
701 DEMOWinPrintfXY(window, 0, 2, "SPan : %1.2f ", (f32)panY/127);
702
703 old = OSDisableInterrupts();
704
705 i = AXGetProfile();
706
707 if (i)
708 {
709 // up to 4 audio frames can complete within a 60Hz video frame
710 // so spin thru the accumulated audio frame profiles and find the peak values
711 while (i)
712 {
713 i--;
714
715 cpuCycles = (u32)(ax_profile[i].axFrameEnd - ax_profile[i].axFrameStart);
716 userCycles = (u32)(ax_profile[i].userCallbackEnd - ax_profile[i].userCallbackStart);
717 axCycles = cpuCycles - userCycles;
718 voices = ax_profile[i].axNumVoices;
719
720 // find peak values over the last i audio frames
721 if (cpuCycles > maxCpuCycles) maxCpuCycles = cpuCycles;
722 if (userCycles > maxUserCycles) maxUserCycles = userCycles;
723 if (axCycles > maxAxCycles) maxAxCycles = axCycles;
724 if (voices > maxVoices) maxVoices = voices;
725
726 }
727 (void)OSRestoreInterrupts(old);
728
729 DEMOWinPrintfXY(window, 0, 4, "Total CPU : %5.2f\n", (f32)OSTicksToNanoseconds(maxCpuCycles) / 50000);
730 DEMOWinPrintfXY(window, 0, 6, "User : %5.2f\n", (f32)OSTicksToNanoseconds(maxUserCycles) / 50000);
731 DEMOWinPrintfXY(window, 0, 7, "AX : %5.2f\n", (f32)OSTicksToNanoseconds(maxAxCycles) / 50000);
732 DEMOWinPrintfXY(window, 0, 9, "Voices : %5d", maxVoices);
733
734 }
735
736 (void)OSRestoreInterrupts(old);
737
738 }
739
740 /*---------------------------------------------------------------------------*
741 *---------------------------------------------------------------------------*/
LoadFileIntoRam(char * path)742 static void* LoadFileIntoRam(char *path)
743 {
744 DVDFileInfo handle;
745 u32 round_length;
746 s32 read_length;
747 void *buffer;
748
749 // Open File
750 if (!DVDOpen(path, &handle))
751 {
752 OSReport("WARNING! Failed to open %s\n", path);
753 return NULL;
754 }
755
756 // Make sure file length is not 0
757 if (DVDGetLength(&handle) == 0)
758 {
759 OSReport("WARNING! File length is 0\n");
760 return NULL;
761 }
762
763 round_length = OSRoundUp32B(DVDGetLength(&handle));
764 buffer = MEMAllocFromExpHeapEx(hExpHeap, round_length, 32);
765
766 // Make sure we got a buffer
767 if (buffer == NULL)
768 {
769 OSReport("WARNING! Unable to allocate buffer\n");
770 return NULL;
771 }
772
773 // Read Files
774 read_length = DVDRead(&handle, buffer, (s32)(round_length), 0);
775
776 // Make sure we read the file correctly
777 if (read_length <= 0)
778 {
779 OSReport("WARNING! File lenght is wrong\n");
780 return NULL;
781 }
782
783 return buffer;
784 }
785
786 /*---------------------------------------------------------------------------*
787 *---------------------------------------------------------------------------*/
PrivateAlloc(u32 size)788 static void* PrivateAlloc(u32 size)
789 {
790 return MEMAllocFromExpHeapEx(hExpHeap, size, 32);
791 }
792
793 /*---------------------------------------------------------------------------*
794 *---------------------------------------------------------------------------*/
PrivateFree(void * addr)795 static void PrivateFree(void* addr)
796 {
797 MEMFreeToExpHeap(hExpHeap, addr);
798 }
799
800 /*---------------------------------------------------------------------------*
801 * Name : main()
802 * Description : Hold on to your seatbelts!
803 * Arguments : None.
804 * Returns : None.
805 *---------------------------------------------------------------------------*/
main(void)806 void main(void)
807 {
808 void *arenaMem2Lo;
809 void *arenaMem2Hi;
810 u8 *zeroBuffer;
811
812 // initialize system
813 DEMOInit(NULL);
814 DEMOWinInit();
815
816 SISetSamplingRate(5);
817
818 arenaMem2Lo = OSGetMEM2ArenaLo();
819 arenaMem2Hi = OSGetMEM2ArenaHi();
820 hExpHeap = MEMCreateExpHeap(arenaMem2Lo, (u32)arenaMem2Hi - (u32) arenaMem2Lo);
821
822 // initialize AI subsystem
823 AIInit(NULL);
824
825 // initialize AX audio system and MIXer application
826 AXInit();
827 MIXInit();
828
829 AXSetMode(AX_MODE_SURROUND);
830 MIXSetSoundMode(MIX_SOUND_MODE_SURROUND);
831
832 // -----------------------------------------------------------
833 // Load SP data!
834 // -----------------------------------------------------------
835
836 // Load sound table
837 sp_table = LoadFileIntoRam(SPT_FILE);
838
839 // Load sound effects
840 sp_data = LoadFileIntoRam(SPD_FILE);
841
842 // -----------------------------------------------------------
843 // Prepare Zero Buffer
844 // -----------------------------------------------------------
845 zeroBuffer = MEMAllocFromExpHeapEx(hExpHeap, ZEROBUFFER_BYTES, 8);
846 memset(zeroBuffer, 0, ZEROBUFFER_BYTES);
847 DCFlushRange(zeroBuffer, ZEROBUFFER_BYTES);
848
849 // -----------------------------------------------------------
850 // initialize sound table!
851 // -----------------------------------------------------------
852 SPInitSoundTable(sp_table, sp_data, zeroBuffer);
853
854 // -----------------------------------------------------------
855 // Initialize demo voice abstraction layer
856 // -----------------------------------------------------------
857 AXRegisterCallback(ax_demo_callback);
858
859 // -----------------------------------------------------------
860 // Initialize AUX-bus effects
861 // -----------------------------------------------------------
862 AXFXSetHooks((AXFXAlloc)PrivateAlloc, (AXFXFree)PrivateFree);
863 AXFX_PRESET_CHORUS_EXP_TYPE1(&chorus);
864 AXFXChorusExpInit(&chorus);
865
866 // -----------------------------------------------------------
867 // initialize profiling for AX
868 // -----------------------------------------------------------
869 AXInitProfile(ax_profile, NUM_AX_PROFILE_FRAMES);
870
871 // -----------------------------------------------------------
872 // Invoke menu system!
873 // -----------------------------------------------------------
874 MenuPtr = DEMOWinCreateMenuWindow(
875 &Menu,
876 20,
877 120
878 );
879
880 DebugWin = DEMOWinCreateWindow(
881 (u16)(MenuPtr->handle->x2+10),
882 20,
883 620,
884 440,
885 "Debug",
886 1024,
887 NULL
888 );
889
890 PositionWin = DEMOWinCreateWindow(
891 (u16)(MenuPtr->handle->x1),
892 (u16)(MenuPtr->handle->y2+10),
893 (u16)(MenuPtr->handle->x2),
894 (u16)(MenuPtr->handle->y2+120),
895 "Position",
896 0,
897 position_win_update
898 );
899
900 DEMOWinOpenWindow(DebugWin);
901 DEMOWinOpenWindow(PositionWin);
902
903 DEMOWinLogPrintf(DebugWin, "------------------------------\n");
904 DEMOWinLogPrintf(DebugWin, "Chorus (expanded version) Test\n");
905 DEMOWinLogPrintf(DebugWin, "------------------------------\n");
906
907 DEMOWinLogPrintf(DebugWin, "\n");
908
909 DEMOWinLogPrintf(DebugWin, "AX_MODE_SURROUND.\n");
910
911 while (1)
912 {
913
914 DEMOWinMenu(MenuPtr);
915
916 }
917
918 } // end main()
919