Merge pull request #179 from retro-wertz/input

refactor input devices
This commit is contained in:
Twinaphex
2017-11-14 08:22:04 +01:00
committed by GitHub

View File

@@ -26,6 +26,10 @@
#include "libretro-common/include/streams/memory_stream.h" #include "libretro-common/include/streams/memory_stream.h"
#define MAX_PLAYERS 4 /* max supported players */
#define MAX_PORTS 2 /* max controller ports,
* port 0 for player 1/3, port 1 for player 2/4 */
#define RETRO_DEVICE_GAMEPAD RETRO_DEVICE_SUBCLASS(RETRO_DEVICE_JOYPAD, 0) #define RETRO_DEVICE_GAMEPAD RETRO_DEVICE_SUBCLASS(RETRO_DEVICE_JOYPAD, 0)
#define RETRO_DEVICE_ZAPPER RETRO_DEVICE_SUBCLASS(RETRO_DEVICE_MOUSE, 0) #define RETRO_DEVICE_ZAPPER RETRO_DEVICE_SUBCLASS(RETRO_DEVICE_MOUSE, 0)
@@ -50,10 +54,10 @@ static bool overscan_v;
#endif #endif
static bool use_raw_palette; static bool use_raw_palette;
static bool use_par; static bool use_par;
int turbo_enabler; static unsigned turbo_enabler[MAX_PLAYERS] = {0};
int turbo_delay; static unsigned turbo_delay = 0;
static int t[2] = { 0, 0 }; static unsigned nes_device[MAX_PLAYERS] = {0};
static int zapper_mode = 0; /* 0=absolute 1=relative */ static unsigned zapper_mode = 0; /* 0=absolute 1=relative */
/* emulator-specific variables */ /* emulator-specific variables */
@@ -539,45 +543,41 @@ void retro_set_input_state(retro_input_state_t cb)
void retro_set_controller_port_device(unsigned port, unsigned device) void retro_set_controller_port_device(unsigned port, unsigned device)
{ {
unsigned arg = 0; if (port < MAX_PORTS) /* port #0 = player1/player3, port #1 = player2/player4 */
void *InputDPtr;
if (port < 2) /* port #0 = player1/player3, port #1 = player2/player4 */
{ {
switch(device) switch(device)
{ {
case RETRO_DEVICE_NONE: case RETRO_DEVICE_NONE:
t[port] = SI_NONE; nes_device[port] = RETRO_DEVICE_NONE;
InputDPtr = NULL; FCEUI_SetInput(port, SI_NONE, NULL, 0);
FCEU_printf(" Player %u: None\n", port + 1);
break; break;
case RETRO_DEVICE_GAMEPAD: case RETRO_DEVICE_GAMEPAD:
t[port] = SI_GAMEPAD; nes_device[port] = RETRO_DEVICE_GAMEPAD;
InputDPtr = &JSReturn; FCEUI_SetInput(port, SI_GAMEPAD, &JSReturn, 0);
FCEU_printf(" Player %u: Gamepad\n", port + 1);
break; break;
case RETRO_DEVICE_ZAPPER: case RETRO_DEVICE_ZAPPER:
arg = 1; nes_device[port] = RETRO_DEVICE_ZAPPER;
t[port] = SI_ZAPPER; FCEUI_SetInput(port, SI_ZAPPER, MouseData, 1);
InputDPtr = &MouseData[0]; FCEU_printf(" Player %u: Zapper\n", port + 1);
break; break;
case RETRO_DEVICE_JOYPAD: case RETRO_DEVICE_JOYPAD: /* Assigned to auto configure devices */
default: default: /* based on database */
if (GameInfo->input[port] == SI_ZAPPER) if (GameInfo->input[port] == SI_ZAPPER)
{ {
arg = 1; nes_device[port] = RETRO_DEVICE_ZAPPER;
t[port] = SI_ZAPPER; FCEUI_SetInput(port, SI_ZAPPER, MouseData, 1);
InputDPtr = &MouseData[0]; FCEU_printf(" Player %u: Zapper\n", port + 1);
} }
else else
{ {
t[port] = SI_GAMEPAD; nes_device[port] = RETRO_DEVICE_GAMEPAD;
InputDPtr = &JSReturn; FCEUI_SetInput(port, SI_GAMEPAD, &JSReturn, 0);
FCEU_printf(" Player %u: Gamepad\n", port + 1);
} }
break; break;
} }
FCEUI_SetInput(port, t[port], InputDPtr, arg);
FCEU_printf("Player %d: %s\n", port + 1,
t[port] == SI_GAMEPAD ? "Gamepad" :
t[port] == SI_ZAPPER ? "Zapper" : "None");
} }
} }
@@ -607,9 +607,10 @@ void retro_set_environment(retro_environment_t cb)
}; };
static const struct retro_controller_description pads[] = { static const struct retro_controller_description pads[] = {
{ "Auto", RETRO_DEVICE_JOYPAD }, { "Auto (Gamepad/Zapper)", RETRO_DEVICE_JOYPAD },
{ "Gamepad", RETRO_DEVICE_GAMEPAD }, { "Gamepad", RETRO_DEVICE_GAMEPAD },
{ "Zapper", RETRO_DEVICE_ZAPPER }, { "Zapper", RETRO_DEVICE_ZAPPER },
{ NULL, 0 },
}; };
static const struct retro_controller_info ports[] = { static const struct retro_controller_info ports[] = {
@@ -985,21 +986,19 @@ static void check_variables(bool startup)
if (environ_cb(RETRO_ENVIRONMENT_GET_VARIABLE, &var) && var.value) if (environ_cb(RETRO_ENVIRONMENT_GET_VARIABLE, &var) && var.value)
{ {
if (!strcmp(var.value, "None")) unsigned i;
{
turbo_enabler = 0; for (i = 0; i < MAX_PLAYERS; i++)
} turbo_enabler[i] = 0;
else if (!strcmp(var.value, "Player 1"))
{ if (!strcmp(var.value, "Player 1"))
turbo_enabler = 1; turbo_enabler[0] = 1;
}
else if (!strcmp(var.value, "Player 2")) else if (!strcmp(var.value, "Player 2"))
{ turbo_enabler[1] = 1;
turbo_enabler = 2;
}
else if (!strcmp(var.value, "Both")) else if (!strcmp(var.value, "Both"))
{ {
turbo_enabler = 3; turbo_enabler[0] = 1;
turbo_enabler[1] = 1;
} }
} }
@@ -1082,10 +1081,10 @@ static void check_variables(bool startup)
static int mzx = 0, mzy = 0, mzb = 0; static int mzx = 0, mzy = 0, mzb = 0;
void GetMouseData(uint32_t *zapdata) void GetMouseData(unsigned port, uint32_t *zapdata)
{ {
bool adjx = false, adjy = false; bool adjx = false, adjy = false;
int right, bottom, port; int right, bottom;
#ifdef PSP #ifdef PSP
adjx = adjy = use_overscan ? 1 : 0; adjx = adjy = use_overscan ? 1 : 0;
@@ -1093,7 +1092,6 @@ void GetMouseData(uint32_t *zapdata)
adjx = overscan_h ? 1 : 0; adjx = overscan_h ? 1 : 0;
adjy = overscan_v ? 1 : 0; adjy = overscan_v ? 1 : 0;
#endif #endif
port = (GameInfo->type == GIT_VSUNI) ? 0 : 1;
right = 256; right = 256;
bottom = 240; bottom = 240;
mzb = 0; mzb = 0;
@@ -1131,94 +1129,75 @@ void GetMouseData(uint32_t *zapdata)
/* /*
* Flags to keep track of whether turbo * Flags to keep track of whether turbo
* was toggled on or off * buttons toggled on or off.
* p0 - Player 1 *
* p1 - Player 2
* There are two values in array * There are two values in array
* for Turbo A and Turbo B for * for Turbo A and Turbo B for
* each player * each player
*/ */
unsigned char turbo_p0_toggle[] = { 0, 0 }; #define TURBO_BUTTONS 2
unsigned char turbo_p1_toggle[] = { 0, 0 }; unsigned char turbo_button_toggle[MAX_PLAYERS][TURBO_BUTTONS] = { {0} };
static void FCEUD_UpdateInput(void) static void FCEUD_UpdateInput(void)
{ {
unsigned p, i; unsigned player, i;
unsigned char pad[4]; unsigned char pad[4];
pad[0] = pad[1] = pad[2] = pad[3] = 0; for (player = 0; player < MAX_PLAYERS; player++)
pad[player] = 0; /* reset pads */
poll_cb(); poll_cb();
for (p = 0; p < 4; p++) for (player = 0; player < MAX_PLAYERS; player++)
{ {
for ( i = 0; i < 8; i++) switch (nes_device[player])
pad[p] |= input_cb(p, RETRO_DEVICE_JOYPAD, 0, bindmap[i].retro) ? bindmap[i].nes : 0;
}
/*
* Turbo A and Turbo B buttons are
* mapped to Joypad X and Joypad Y
* in RetroArch joypad.
*
* We achieve this by keeping track of
* the number of times it increments
* the toggle counter and fire or not fire
* depending on whether the delay value has
* been reached.
*/
if (turbo_enabler == 1 || turbo_enabler == 3)
{
/* Handle turbo buttons - player 1 */
for ( i = 8; i < 10; i++)
{ {
if (input_cb(0, RETRO_DEVICE_JOYPAD, 0, bindmap[i].retro)) case RETRO_DEVICE_GAMEPAD:
{ for (i = 0; i < 8; i++)
if (turbo_p0_toggle[i-8] == 0) pad[player] |= input_cb(player, RETRO_DEVICE_JOYPAD, 0,
pad[0] |= bindmap[i].nes; bindmap[i].retro) ? bindmap[i].nes : 0;
turbo_p0_toggle[i-8]++;
if (turbo_p0_toggle[i-8] > turbo_delay) /* Turbo A and Turbo B buttons are
* mapped to Joypad X and Joypad Y
* in RetroArch joypad.
*
* We achieve this by keeping track of
* the number of times it increments
* the toggle counter and fire or not fire
* depending on whether the delay value has
* been reached.
*/
if (turbo_enabler[player] == 1)
{ {
/* Reset the toggle if /* Handle Turbo A & B buttons */
* delay value is reached */ for (i = 8; i < 10; i++)
pad[0] |= bindmap[i].nes; {
turbo_p0_toggle[i-8] = 0; if (input_cb(player, RETRO_DEVICE_JOYPAD, 0, bindmap[i].retro))
{
if (turbo_button_toggle[player][i-8] == 0)
pad[player] |= bindmap[i].nes;
turbo_button_toggle[player][i-8]++;
if (turbo_button_toggle[player][i-8] > turbo_delay)
/* Reset the toggle if delay value is reached */
turbo_button_toggle[player][i-8] = 0;
}
else
/* If the button is not pressed, just reset the toggle */
turbo_button_toggle[player][i-8] = 0;
}
} }
}
else JSReturn = (pad[0] & 0xff) | ((pad[1] & 0xff) << 8) |
/* If the button is not pressed, just reset the toggle */ ((pad[2] & 0xff) << 16) | ((pad[3] & 0xff) << 24);
turbo_p0_toggle[i-8] = 0; break; /* RETRO_DEVICE_GAMEPAD */
case RETRO_DEVICE_ZAPPER:
GetMouseData(player, MouseData);
break; /* RETRO_DEVICE_ZAPPER */
} }
} }
if (turbo_enabler == 2 || turbo_enabler == 3)
{
/* Handle turbo buttons - player 2 */
for ( i = 8; i < 10; i++)
{
if (input_cb(1, RETRO_DEVICE_JOYPAD, 0, bindmap[i].retro))
{
if (turbo_p1_toggle[i-8] == 0)
pad[1] |= bindmap[i].nes;
turbo_p1_toggle[i-8]++;
if (turbo_p1_toggle[i-8] > turbo_delay)
{
/* Reset the toggle if
* delay value is reached */
pad[1] |= bindmap[i].nes;
turbo_p1_toggle[i-8] = 0;
}
}
else
/* If the button is not pressed, just reset the toggle */
turbo_p1_toggle[i-8] = 0;
}
}
JSReturn = pad[0] | (pad[1] << 8) | (pad[2] << 16) | (pad[3] << 24);
if (t[0] == SI_ZAPPER || t[1] == SI_ZAPPER)
GetMouseData(&MouseData[0]);
if (input_cb(0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_R2)) if (input_cb(0, RETRO_DEVICE_JOYPAD, 0, RETRO_DEVICE_ID_JOYPAD_R2))
FCEU_VSUniCoin(); /* Insert Coin VS System */ FCEU_VSUniCoin(); /* Insert Coin VS System */
@@ -1774,6 +1753,10 @@ bool retro_load_game(const struct retro_game_info *game)
return false; return false;
} }
nes_device[0] = RETRO_DEVICE_GAMEPAD;
nes_device[1] = RETRO_DEVICE_GAMEPAD;
nes_device[2] = RETRO_DEVICE_NONE;
nes_device[3] = RETRO_DEVICE_NONE;
FCEUI_SetInput(0, SI_GAMEPAD, &JSReturn, 0); FCEUI_SetInput(0, SI_GAMEPAD, &JSReturn, 0);
FCEUI_SetInput(1, SI_GAMEPAD, &JSReturn, 0); FCEUI_SetInput(1, SI_GAMEPAD, &JSReturn, 0);
@@ -1800,6 +1783,8 @@ bool retro_load_game(const struct retro_game_info *game)
if (fourscore_db_list[i].crc == iNESGameCRC32) if (fourscore_db_list[i].crc == iNESGameCRC32)
{ {
FCEUI_DisableFourScore(0); FCEUI_DisableFourScore(0);
nes_device[2] = RETRO_DEVICE_GAMEPAD;
nes_device[3] = RETRO_DEVICE_GAMEPAD;
break; break;
} }
} }
@@ -1809,6 +1794,8 @@ bool retro_load_game(const struct retro_game_info *game)
if (famicom_4p_db_list[i].crc == iNESGameCRC32) if (famicom_4p_db_list[i].crc == iNESGameCRC32)
{ {
FCEUI_SetInputFC(SIFC_4PLAYER, &JSReturn, 0); FCEUI_SetInputFC(SIFC_4PLAYER, &JSReturn, 0);
nes_device[2] = RETRO_DEVICE_GAMEPAD;
nes_device[3] = RETRO_DEVICE_GAMEPAD;
break; break;
} }
} }
@@ -1911,3 +1898,4 @@ size_t retro_get_memory_size(unsigned type)
return size; return size;
} }