Genesis-Plus-GX/source/ngc/gui/menu.c
ekeeke31 217ca8de3f
2007-08-10 20:34:06 +00:00

624 lines
15 KiB
C

/****************************************************************************
* Genesis Plus 1.2a
*
* Copyright (C) 1998, 1999, 2000, 2001, 2002, 2003 Charles Mac Donald
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*
* Nintendo Gamecube Menus
*
* Please put any user menus here! - softdev March 12 2006
***************************************************************************/
#include "shared.h"
#include "dvd.h"
#include "rominfo.h"
#include "font.h"
#define PSOSDLOADID 0x7c6000a6
/***************************************************************************
* drawmenu
*
* As it says, simply draws the menu with a highlight on the currently
* selected item :)
***************************************************************************/
char menutitle[60] = { "" };
int menu = 0;
void drawmenu (char items[][20], int maxitems, int selected)
{
int i;
int ypos;
ypos = (310 - (fheight * maxitems)) >> 1;
ypos += 130;
ClearScreen ();
WriteCentre (134, menutitle);
for (i = 0; i < maxitems; i++)
{
if (i == selected) WriteCentre_HL (i * fheight + ypos, (char *) items[i]);
else WriteCentre (i * fheight + ypos, (char *) items[i]);
}
SetScreen ();
}
/****************************************************************************
* domenu
*
* Returns index into menu array when A is pressed, -1 for B
****************************************************************************/
int domenu (char items[][20], int maxitems)
{
int redraw = 1;
int quit = 0;
short p;
int ret = 0;
signed char a,b;
while (quit == 0)
{
if (redraw)
{
drawmenu (&items[0], maxitems, menu);
redraw = 0;
}
p = PAD_ButtonsDown (0);
a = PAD_StickY (0);
b = PAD_StickX (0);
/*** Look for up ***/
if ((p & PAD_BUTTON_UP) || (a > 70))
{
redraw = 1;
menu--;
if (menu < 0) menu = maxitems - 1;
}
/*** Look for down ***/
if ((p & PAD_BUTTON_DOWN) || (a < -70))
{
redraw = 1;
menu++;
if (menu == maxitems) menu = 0;
}
if ((p & PAD_BUTTON_A) || (b > 40) || (p & PAD_BUTTON_RIGHT))
{
quit = 1;
ret = menu;
}
if ((b < -40) || (p & PAD_BUTTON_LEFT))
{
quit = 1;
ret = 0 - 2 - menu;
}
if (p & PAD_BUTTON_B)
{
quit = 1;
ret = -1;
}
}
return ret;
}
/****************************************************************************
* Sound Option menu
*
****************************************************************************/
double psg_preamp = 3.0;
double fm_preamp = 1.0;
u8 boost = 1;
uint8 clipping = 2;
uint8 hq_fm = 1;
uint8 FM_GENS = 0;
uint8 PSG_MAME = 0;
void soundmenu ()
{
int ret;
int quit = 0;
int prevmenu = menu;
int count = 7;
char items[7][20];
strcpy (menutitle, "Sound Options");
sprintf (items[0], "PSG Volume : %1.2f", psg_preamp);
sprintf (items[1], "FM Volume : %1.2f", fm_preamp);
sprintf (items[2], "Volume Boost: %dX", boost);
sprintf (items[3], "HQ YM2612: %s", hq_fm ? "Y" : "N");
sprintf (items[4], "FM core : %s", FM_GENS ? "GENS" : "MAME");
sprintf (items[5], "PSG core: %s", PSG_MAME ? "MAME" : "SMSP");
strcpy (items[6], "Return to previous");
menu = 0;
while (quit == 0)
{
ret = domenu (&items[0], count);
switch (ret)
{
case 0:
case -2:
if (ret<0) psg_preamp -= 0.01;
else psg_preamp += 0.01;
if (psg_preamp < 0.0) psg_preamp = 5.0;
if (psg_preamp > 5.0) psg_preamp = 0.0;
sprintf (items[0], "PSG Volume : %1.2f", psg_preamp);
break;
case 1:
case -3:
if (ret<0) fm_preamp -= 0.01;
else fm_preamp += 0.01;
if (fm_preamp < 0.0) fm_preamp = 5.0;
if (fm_preamp > 5.0) fm_preamp = 0.0;
sprintf (items[1], "FM Volume : %1.2f", fm_preamp);
break;
case 2:
boost ++;
if (boost > 4) boost = 0;
sprintf (items[2], "Volume Boost: %dX", boost);
break;
case 3:
hq_fm ^= 1;
sprintf (items[3], "HQ YM2612: %s", hq_fm ? "Y" : "N");
if (genromsize)
{ audio_init(48000);
fm_restore();
}
break;
case 4:
FM_GENS ^= 1;
psg_preamp = PSG_MAME ? (FM_GENS ? 0.85 : 0.50) : (FM_GENS ? 4.0 : 3.0);
fm_preamp = 1.0;
sprintf (items[0], "PSG Volume : %1.2f", psg_preamp);
sprintf (items[1], "FM Volume : %1.2f", fm_preamp);
sprintf (items[4], "FM core : %s", FM_GENS ? "GENS" : "MAME");
if (genromsize)
{
audio_init(48000);
fm_restore();
}
break;
case 5:
PSG_MAME ^= 1;
psg_preamp = PSG_MAME ? (FM_GENS ? 0.85 : 0.50) : (FM_GENS ? 4.0 : 3.0);
fm_preamp = 1.0;
sprintf (items[0], "PSG Volume : %1.2f", psg_preamp);
sprintf (items[1], "FM Volume : %1.2f", fm_preamp);
sprintf (items[5], "PSG core: %s", PSG_MAME ? "MAME" : "SMSP");
if (genromsize) audio_init(48000);
break;
case 6:
case -1:
quit = 1;
break;
}
}
menu = prevmenu;
}
/****************************************************************************
* Misc Option menu
*
****************************************************************************/
extern void reloadrom ();
extern s16 square[];
extern int oldvwidth, oldvheight;
extern uint8 alttiming;
extern uint8 dmatiming;
extern uint8 vdptiming;
uint8 autoload = 0;
uint8 region_detect = 0;
uint8 cpu_detect = 0;
void miscmenu ()
{
int ret;
int quit = 0;
int prevmenu = menu;
int count = 9;
char items[9][20];
sprintf (items[0], "Scale X: %02d", square[3]);
sprintf (items[1], "Scale Y: %02d", square[1]);
sprintf (items[2], "Vdp Latency: %s", vdptiming ? "Y" : "N");
sprintf (items[3], "Dma Timing : %s", dmatiming ? "Y" : "N");
sprintf (items[4], "Alt Timing : %s", alttiming ? "Y" : "N");
if (cpu_detect == 0) sprintf (items[5], "Cpu Mode: AUTO");
else if (cpu_detect == 1) sprintf (items[5], "Cpu Mode: NTSC");
else if (cpu_detect == 2) sprintf (items[5], "Cpu Mode: PAL");
if (region_detect == 0) sprintf (items[6], "Region: AUTO");
else if (region_detect == 1) sprintf (items[6], "Region: USA");
else if (region_detect == 2) sprintf (items[6], "Region: EUR");
else if (region_detect == 3) sprintf (items[6], "Region: JAP-NTSC");
else if (region_detect == 4) sprintf (items[6], "Region: JAP-PAL");
sprintf (items[7], "SRAM autoload: %s", autoload ? "Y" : "N");
strcpy (items[8], "Return to previous");
menu = 0;
while (quit == 0)
{
strcpy (menutitle, "");
ret = domenu (&items[0], count);
switch (ret)
{
case 0: /*** Scale X ***/
case -2:
if (ret<0) square[3] -= 2;
else square[3] += 2;
if (square[3] < 40) square[3] = 80;
if (square[3] > 80) square[3] = 40;
square[6] = square[3];
square[0] = square[9] = -square[3];
oldvwidth = -1;
sprintf (items[0], "Scale X: %02d", square[3]);
break;
case 1: /*** Scale Y ***/
case -3:
if (ret<0) square[1] -= 2;
else square[1] += 2;
if (square[1] < 30) square[1] = 60;
if (square[1] > 60) square[1] = 30;
square[4] = square[1];
square[7] = square[10] = -square[1];
oldvheight = -1;
sprintf (items[1], "Scale Y: %02d", square[1]);
break;
case 2: /*** VDP access latency ***/
vdptiming ^= 1;
sprintf (items[2], "Vdp Latency: %s", vdptiming ? "Y" : "N");
break;
case 3: /*** DMA timing fix ***/
dmatiming ^= 1;
sprintf (items[3], "Dma Timing : %s", dmatiming ? "Y" : "N");
break;
case 4: /*** Alternate rendering timing ***/
alttiming ^= 1;
sprintf (items[4], "Alt Timing : %s", alttiming ? "Y" : "N");
break;
case 5: /*** Cpu mode : PAL (50hz) or NTSC (60Hz) ***/
cpu_detect ++;
if (cpu_detect > 2) cpu_detect = 0;
if (cpu_detect == 0) sprintf (items[5], "Cpu Mode: AUTO");
else if (cpu_detect == 1) sprintf (items[5], "Cpu Mode: NTSC");
else if (cpu_detect == 2) sprintf (items[5], "Cpu Mode: PAL");
if (genromsize) reloadrom();
break;
case 6: /* region detection */
region_detect ++;
if (region_detect > 4) region_detect = 0;
if (region_detect == 0) sprintf (items[6], "Region: AUTO");
else if (region_detect == 1) sprintf (items[6], "Region: USA");
else if (region_detect == 2) sprintf (items[6], "Region: EUR");
else if (region_detect == 3) sprintf (items[6], "Region: JAP-NTSC");
else if (region_detect == 4) sprintf (items[6], "Region: JAP-PAL");
if (genromsize) reloadrom();
break;
case 7: /*** VDP access latency ***/
autoload ^= 1;
sprintf (items[7], "SRAM autoload: %s", autoload ? "Y" : "N");
break;
case 8:
case -1:
quit = 1;
break;
}
}
menu = prevmenu;
}
/****************************************************************************
* Main Option menu
*
****************************************************************************/
extern void ConfigureJoypads();
extern void GetGGEntries();
void optionmenu ()
{
int ret;
int quit = 0;
int prevmenu = menu;
int count = 5;
char items[5][20] = {
"Misc. Options",
"Sound Options",
"Configure Joypads",
"Game Genie Codes",
"Return to previous"
};
menu = 0;
while (quit == 0)
{
strcpy (menutitle, "");
ret = domenu (&items[0], count);
switch (ret)
{
case 0:
miscmenu();
break;
case 1:
soundmenu();
break;
case 2:
ConfigureJoypads();
break;
case 3:
GetGGEntries();
break;
case 4:
case -1:
quit = 1;
break;
}
}
menu = prevmenu;
}
/****************************************************************************
* Generic Load/Save menu
*
****************************************************************************/
int CARDSLOT = CARD_SLOTB;
int use_SDCARD = 0;
extern int ManageSRAM (int direction);
extern int ManageState (int direction);
int loadsavemenu (int which)
{
int prevmenu = menu;
int quit = 0;
int ret;
int count = 5;
char items[5][20];
strcpy (menutitle, "");
if (use_SDCARD) sprintf(items[0], "Device: SDCARD");
else sprintf(items[0], "Device: MCARD");
if (CARDSLOT == CARD_SLOTA) sprintf(items[1], "Use: SLOT A");
else sprintf(items[1], "Use: SLOT B");
if (which)
{
sprintf(items[2], "Save State");
sprintf(items[3], "Load State");
}
else
{
sprintf(items[2], "Save SRAM");
sprintf(items[3], "Load SRAM");
}
sprintf(items[4], "Return to previous");
menu = 2;
while (quit == 0)
{
ret = domenu (&items[0], count);
switch (ret)
{
case -1:
case 4:
quit = 1;
break;
case 0:
use_SDCARD ^= 1;
if (use_SDCARD) sprintf(items[0], "Device: SDCARD");
else sprintf(items[0], "Device: MCARD");
break;
case 1:
CARDSLOT ^= 1;
if (CARDSLOT == CARD_SLOTA) sprintf(items[1], "Use: SLOT A");
else sprintf(items[1], "Use: SLOT B");
break;
case 2:
case 3:
if (which) quit = ManageState(ret-2);
else quit = ManageSRAM(ret-2);
if (quit) return 1;
break;
}
}
menu = prevmenu;
return 0;
}
/****************************************************************************
* File Manager menu
*
****************************************************************************/
int filemenu ()
{
int prevmenu = menu;
int ret;
int quit = 0;
uint32 crccheck;
int count = 3;
char items[3][20] = {
{"SRAM Manager"},
{"STATE Manager"},
{"Return to previous"}
};
crccheck = crc32 (0, &sram.sram[0], 0x10000);
if (genromsize && (crccheck != sram.crc)) strcpy (menutitle, "*** SRAM has been modified ***");
else strcpy (menutitle, "");
menu = 0;
while (quit == 0)
{
ret = domenu (&items[0], count);
switch (ret)
{
case -1: /*** Button B ***/
case 2: /*** Quit ***/
ret = 0;
quit = 1;
break;
case 0: /*** SRAM Manager ***/
case 1: /*** SaveState Manager ***/
if (loadsavemenu(ret)) return 1;
break;
}
}
menu = prevmenu;
return 0;
}
/****************************************************************************
* Load Rom menu
*
****************************************************************************/
extern void OpenDVD ();
extern int OpenSD ();
extern u8 UseSDCARD;
void loadmenu ()
{
int prevmenu = menu;
int ret;
int quit = 0;
int count = 3;
char item[3][20] = {
{"Load from DVD"},
{"Load from SDCARD"},
{"Return to previous"}
};
menu = UseSDCARD ? 1 : 0;
while (quit == 0)
{
strcpy (menutitle, "");
ret = domenu (&item[0], count);
switch (ret)
{
case -1: /*** Button B ***/
case 2: /*** Quit ***/
quit = 1;
menu = prevmenu;
break;
case 0: /*** Load from DVD ***/
OpenDVD ();
quit = 1;
break;
case 1: /*** Load from SCDARD ***/
OpenSD ();
quit = 1;
break;
}
}
}
/****************************************************************************
* Main menu
*
****************************************************************************/
void MainMenu ()
{
menu = 0;
int ret;
int quit = 0;
int *psoid = (int *) 0x80001800;
void (*PSOReload) () = (void (*)()) 0x80001800; /*** Stock PSO/SD Reload call ***/
int count = 8;
char items[8][20] = {
{"Play Game"},
{"Game Infos"},
{"Reset Game"},
{"Load New Game"},
{"File Management"},
{"Emulator Options"},
{"Stop DVD Motor"},
{"System Reboot"}
};
while (quit == 0)
{
strcpy (menutitle, "");
ret = domenu (&items[0], count);
switch (ret)
{
case -1: /*** Button B ***/
case 0: /*** Play Game ***/
quit = 1;
break;
case 1: /*** ROM Information ***/
showrominfo ();
break;
case 2: /*** Emulator Reset ***/
system_reset ();
quit = 1;
break;
case 3: /*** Load ROM Menu ***/
loadmenu();
menu = 0;
break;
case 4: /*** Memory Manager ***/
quit = filemenu ();
break;
case 5: /*** Emulator Options */
optionmenu ();
break;
case 6: /*** Stop DVD Motor ***/
ShowAction("Stopping DVD Motor ...");
dvd_motor_off();
break;
case 7: /*** SD/PSO Reload ***/
if (psoid[0] == PSOSDLOADID) PSOReload ();
else SYS_ResetSystem(SYS_HOTRESET,0,FALSE);
break;
}
}
/*** Remove any still held buttons ***/
while(PAD_ButtonsHeld(0)) VIDEO_WaitVSync();
/*** Stop the DVD from causing clicks while playing ***/
uselessinquiry ();
}