X-Git-Url: https://notaz.gp2x.de/cgi-bin/gitweb.cgi?p=fceu.git;a=blobdiff_plain;f=drivers%2Fgp2x%2Finput.c;h=43da4b3b0af3e982ed862c8ca304cf18beb342ee;hp=cd25e97abb964e576f0530d3b71fe4d60afab2ff;hb=03497cf8eeda7f6d0ad91286819ed613e8d8f648;hpb=b2b95d2e0d1fd5e52d03c2152605b09b024c1d0e diff --git a/drivers/gp2x/input.c b/drivers/gp2x/input.c index cd25e97..43da4b3 100644 --- a/drivers/gp2x/input.c +++ b/drivers/gp2x/input.c @@ -1,7 +1,4 @@ /* FCE Ultra - NES/Famicom Emulator - * - * Copyright notice for this file: - * Copyright (C) 2002 Ben Parnell * * 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 @@ -18,362 +15,284 @@ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ -#define JOY_A 1 -#define JOY_B 2 -#define JOY_SELECT 4 -#define JOY_START 8 -#define JOY_UP 0x10 -#define JOY_DOWN 0x20 -#define JOY_LEFT 0x40 -#define JOY_RIGHT 0x80 - -#include "minimal.h" - -extern uint8 Exit; // exit emu loop - -extern int swapbuttons; -extern int scaled_display; -extern int FSkip_setting; - - +#include "../../state.h" +#include "../../general.h" +#include "../../input.h" +#include "../../svga.h" +#include "../../video.h" +#include "usbjoy.h" /* UsrInputType[] is user-specified. InputType[] is current - (game loading can override user settings) + (game loading can override user settings) */ static int UsrInputType[2]={SI_GAMEPAD,SI_GAMEPAD}; -static int InputType[2]; - static int UsrInputTypeFC={SI_NONE}; + +static int InputType[2]; static int InputTypeFC; static uint32 JSreturn; -int NoWaiting=0; static int powerpadsc[2][12]; static int powerpadside=0; - static uint32 MouseData[3]; static uint8 fkbkeys[0x48]; -unsigned long lastpad=0; - -extern void ResetNES(void); -extern void CleanSurface(void); -char soundvolmeter[21]; -int soundvolIndex=0; -int L_count=0; -int R_count=0; -extern int CurrentState; -int TurboFireOff=1; -int TurboFireTop=0; // 0 is none // 1 is A & X turbo // 2 is Y & B turbo -int TurboFireBottom=0; -int turbo_toggle_A=0; -int turbo_toggle_B=0; +static uint32 combo_acts = 0, combo_keys = 0; +static uint32 prev_emu_acts = 0; static void setsoundvol(int soundvolume) { - //FCEUI_SetSoundVolume(soundvol); - // draw on screen :D - gp2x_sound_volume(soundvolume, soundvolume); - int meterval=soundvolume/5; - for (soundvolIndex=0; soundvolIndex < 20; soundvolIndex++) - { - if (soundvolIndex < meterval) - { - soundvolmeter[soundvolIndex]='*'; - } - else - { - soundvolmeter[soundvolIndex]='_'; - } - } - soundvolmeter[20]=0; - FCEU_DispMessage("|%s|", soundvolmeter); + int soundvolIndex; + static char soundvolmeter[24]; + + // draw on screen :D + gp2x_sound_volume(soundvolume, soundvolume); + int meterval=soundvolume/5; + for (soundvolIndex = 0; soundvolIndex < 20; soundvolIndex++) + { + if (soundvolIndex < meterval) + { + soundvolmeter[soundvolIndex]='*'; + } + else + { + soundvolmeter[soundvolIndex]='_'; + } + } + soundvolmeter[20]=0; + FCEU_DispMessage("|%s|", soundvolmeter); } +static void do_emu_acts(uint32 acts) +{ + uint32 actsc = acts; + acts &= acts ^ prev_emu_acts; + prev_emu_acts = actsc; + + if (acts & (3 << 30)) + { + unsigned long keys; + int do_it = 1; + if (acts & (1 << 30)) + { + if (Settings.sstate_confirm & 2) + { + FCEU_DispMessage("LOAD STATE? (Y=yes, X=no)"); + FCEU_PutImage(); + FCEUD_Update(XBuf+8,NULL,0); + while( !((keys = gp2x_joystick_read(1)) & (GP2X_X|GP2X_Y)) ) usleep(50*1024); + if (keys & GP2X_X) do_it = 0; + FCEU_DispMessage(""); + } + if (do_it) FCEUI_LoadState(); + } + else + { + if (Settings.sstate_confirm & 1) + { + char *fname = FCEU_MakeFName(FCEUMKF_STATE,CurrentState,0); + FILE *st=fopen(fname,"rb"); + free(fname); + if (st) + { + fclose(st); + FCEU_DispMessage("OVERWRITE SAVE? (Y=yes, X=no)"); + FCEU_PutImage(); + FCEUD_Update(XBuf+8,NULL,0); + while( !((keys = gp2x_joystick_read(1)) & (GP2X_X|GP2X_Y)) ) usleep(50*1024); + if (keys & GP2X_X) do_it = 0; + FCEU_DispMessage(""); + } + } + if (do_it) FCEUI_SaveState(); + } + RefreshThrottleFPS(); + } + else if (acts & (3 << 28)) // state slot next/prev + { + FILE *st; + char *fname; + + CurrentState += (acts & (1 << 29)) ? 1 : -1; + if (CurrentState > 9) CurrentState = 0; + if (CurrentState < 0) CurrentState = 9; + + fname = FCEU_MakeFName(FCEUMKF_STATE,CurrentState,0); + st=fopen(fname,"rb"); + free(fname); + FCEU_DispMessage("[%s] State Slot %i", st ? "USED" : "FREE", CurrentState); + if (st) fclose(st); + } + else if (acts & (1 << 27)) // FDS insert/eject + { + if(FCEUGameInfo.type == GIT_FDS) + FCEU_DoSimpleCommand(FCEUNPCMD_FDSINSERT); + } + else if (acts & (1 << 26)) // FDS select + { + if(FCEUGameInfo.type == GIT_FDS) + FCEU_DoSimpleCommand(FCEUNPCMD_FDSSELECT); + } + else if (acts & (1 << 25)) // VS Unisystem insert coin + { + if(FCEUGameInfo.type == GIT_VSUNI) + FCEU_DoSimpleCommand(FCEUNPCMD_VSUNICOIN); + } +} + + +#define down(b) (keys & GP2X_##b) +static void do_fake_mouse(unsigned long keys) +{ + static int x=256/2, y=240/2; + int speed = 3; + + if (down(A)) speed = 1; + if (down(Y)) speed = 5; + + if (down(LEFT)) + { + x -= speed; + if (x < 0) x = 0; + } + else if (down(RIGHT)) + { + x += speed; + if (x > 255) x = 255; + } + + if (down(UP)) + { + y -= speed; + if (y < 0) y = 0; + } + else if (down(DOWN)) + { + y += speed; + if (y > 239) y = 239; + } + + MouseData[0] = x; + MouseData[1] = y; + MouseData[2] = 0; + if (down(B)) MouseData[2] |= 1; + if (down(X)) MouseData[2] |= 2; +} + void FCEUD_UpdateInput(void) { - long lastpad2=lastpad; - unsigned long pad=gp2x_joystick_read(1); // TODO: USB joys and stuff - uint32 JS=0; - -#define down(b) (pad & GP2X_##b) -#define last_down(b) (lastpad & GP2X_##b) -#define L_down (pad & GP2X_L) -#define R_down (pad & GP2X_R) -#define last_L_down (lastpad & GP2X_L) -#define last_R_down (lastpad & GP2X_R) -#define shift ((pad & GP2X_PUSH) || ((pad & (GP2X_VOL_UP|GP2X_VOL_DOWN)) == (GP2X_VOL_UP|GP2X_VOL_DOWN))) -#define last_shift ((lastpad & GP2X_PUSH) || ((lastpad & (GP2X_VOL_UP|GP2X_VOL_DOWN)) == (GP2X_VOL_UP|GP2X_VOL_DOWN))) - - if (L_down && R_down && !(pad & GP2X_PUSH) && !(last_R_down && last_L_down)) - { - ResetNES(); - puts("Reset"); - goto no_pad; - } - - if (down(VOL_UP) && !down(VOL_DOWN)) - { - soundvol+=1; - if (soundvol >= 100) soundvol=100; - //FCEUI_SetSoundVolume(soundvol); - setsoundvol(soundvol); - } - else if (down(VOL_DOWN) && !down(VOL_UP)) - { - soundvol-=1; - if (soundvol < 0) soundvol=0; - //FCEUI_SetSoundVolume(soundvol); - setsoundvol(soundvol); - } - else if (down(VOL_DOWN) && down(VOL_UP)) - { - Exit = 1; - } - - if (shift) - { - // only if it's something else then last time, and not moving around the joystick - if (!(pad & (GP2X_UP|GP2X_DOWN|GP2X_LEFT|GP2X_RIGHT))) - { - if (down(SELECT)) - { - if (last_down(SELECT) && last_shift) + static int volpushed_frames = 0; + static int turbo_rate_cnt_a[2] = {0,0}, turbo_rate_cnt_b[2] = {0,0}; + unsigned long keys = gp2x_joystick_read(0); + uint32 all_acts[2] = {0,0}; + int i; + + if ((down(VOL_DOWN) && down(VOL_UP)) || (keys & (GP2X_L|GP2X_L|GP2X_START)) == (GP2X_L|GP2X_L|GP2X_START)) + { + Exit = 1; + return; + } + else if (down(VOL_UP)) + { + /* wait for at least 10 updates, because user may be just trying to enter menu */ + if (volpushed_frames++ > 10) { + soundvol++; + if (soundvol > 100) soundvol=100; + //FCEUI_SetSoundVolume(soundvol); + setsoundvol(soundvol); + } + } + else if (down(VOL_DOWN)) { - // still pressed down from stretching from last one - goto no_pad; + if (volpushed_frames++ > 10) { + soundvol-=1; + if (soundvol < 0) soundvol=0; + //FCEUI_SetSoundVolume(soundvol); + setsoundvol(soundvol); + } } - scaled_display = !scaled_display; + else + { + volpushed_frames = 0; + } + + JSreturn = 0; // RLDU SEBA - if (scaled_display) + if (InputType[1] != SI_GAMEPAD) { - gp2x_video_RGB_setscaling(0, 256, 240); + /* try to feed fake mouse there */ + do_fake_mouse(keys); } - else + + for (i = 0; i < 32; i++) { - gp2x_video_RGB_setscaling(0, 320, 240); + if (keys & (1 << i)) + { + uint32 acts, u = 32; + acts = Settings.KeyBinds[i]; + if (!acts) continue; + if ((1 << i) & combo_keys) + { + // combo key detected, try to find if other is pressed + for (u = i+1; u < 32; u++) + { + if ((keys & (1 << u)) && (Settings.KeyBinds[u] & acts)) + { + keys &= ~(1 << u); + break; + } + } + } + if (u != 32) acts &= combo_acts; // other combo key pressed + else acts &= ~combo_acts; + all_acts[(acts>>16)&1] |= acts; + } } - goto no_pad; - } - else if (L_down && R_down) - { - FCEUI_CloseGame(); - puts("Quit"); - goto no_pad; - } - else if (R_down && !(last_R_down && last_shift)) - { - FCEUI_LoadState(); - goto no_pad; - } - else if (L_down && !(last_L_down && last_shift)) - { - FCEUI_SaveState(); - goto no_pad; - } - else if (down(A) && !(last_down(A) && last_shift)) - { - FSkip_setting--; - if (FSkip_setting < 0) { - FSkip_setting = -1; - FCEUI_DispMessage("Auto frameskip"); - } - else - FCEUI_DispMessage("Frameskip: %i", FSkip_setting); - goto no_pad; - } - else if (down(Y) && !(last_down(Y) && last_shift)) - { - FSkip_setting++; - if (FSkip_setting > 8) FSkip_setting = 8; - FCEUI_DispMessage("Frameskip: %i", FSkip_setting); - goto no_pad; - } - } - } - - // r is toggle savestate - if (R_down) - { - if (last_R_down) - { - R_count++; - if ((R_count & 31)== 31) - { - CurrentState=(CurrentState+1) % 10; - FCEUI_DispMessage("Now Using Save State %d", CurrentState); - } - } - } - else - { - R_count=0; - } - - // l is toggle turbo - if (L_down) - { - if (last_L_down) - { - L_count++; - if ((L_count & 31)== 31) - { - // 0 is none // 1 is Y & B turbo // 2 is X & A turbo - if ((!TurboFireTop) && (!TurboFireBottom)) - { - // was off - TurboFireTop=1; - TurboFireBottom=0; - if (swapbuttons) - { - FCEUI_DispMessage("Turbo A and Y"); - } - else - { - FCEUI_DispMessage("Turbo Y and B"); - } - } - else if (TurboFireTop) - { - TurboFireTop=0; - TurboFireBottom=1; - if (swapbuttons) - { - FCEUI_DispMessage("Turbo X and B"); - } - else - { - FCEUI_DispMessage("Turbo A and X"); - } - } - else - { - TurboFireTop=0; - TurboFireBottom=0; - FCEUI_DispMessage("Turbo Off"); - } - - } - } - } - else - { - L_count=0; - } - - //unsigned long padTmp=0; - // shift the bits in - // up - //padTmp=(pad & GP2X_UP) ; // 1 is 2^0, - JS |= ((pad & GP2X_UP) << (4-0)); // 0x10 is 2^4 - - //padTmp=(pad & GP2X_DOWN); // 0x10 is 2^4, - JS |= ((pad & GP2X_DOWN) << (5-4)); // 0x20 is 2^5 - - //padTmp=(pad & GP2X_LEFT); // 0x4 is 2^2, - JS |= ((pad & GP2X_LEFT) << (6-2)); // 0x40 is 2^6 - - //padTmp=(pad & GP2X_RIGHT); // 0x40 is 2^6, - JS |= ((pad & GP2X_RIGHT) << (7-6)); // 0x80 is 2^7 - - -#define A_down (pad & GP2X_A) -#define B_down (pad & GP2X_B) -#define X_down (pad & GP2X_X) -#define Y_down (pad & GP2X_Y) - - // should be 2 cycles held, 1 cycle release - turbo_toggle_A=(turbo_toggle_A+1) % 3; - turbo_toggle_B=(turbo_toggle_B+1) % 3; - - // 0 is none // 1 is Y & B turbo // 2 is X & A turbo - // B or X are both considered A - //padTmp=B_down >> 13; // 2^13, - - if (!(TurboFireTop && (!turbo_toggle_A))) - { - JS |= ((B_down >> 13) << 0); // 0x1 is 2^0 - } - // A or Y are both considered B - //padTmp=A_down >> 12; // 2^13, - if (!(TurboFireBottom && (!turbo_toggle_B))) - { - JS |= ((A_down >> 12) << 1); // 0x2 is 2^1 - } + // add joy inputs + if (num_of_joys > 0) + { + int joy; + gp2x_usbjoy_update(); + for (joy = 0; joy < num_of_joys; joy++) { + int keys = gp2x_usbjoy_check2(joy); + for (i = 0; i < 32; i++) { + if (keys & (1 << i)) { + int acts = Settings.JoyBinds[joy][i]; + all_acts[(acts>>16)&1] |= acts; + } + } + } + } - if (swapbuttons) - { - //padTmp=X_down >> 14; // 2^13, - if (!(TurboFireBottom && (!turbo_toggle_A))) - { -// JS |= ((X_down >> 14) << 0); // 0x1 is 2^0 - JS |= ((Y_down >> 15) << 0); // 0x1 is 2^0 - } + // player 1 + JSreturn |= all_acts[0] & 0xff; + if (all_acts[0] & 0x100) { // A turbo + turbo_rate_cnt_a[0] += Settings.turbo_rate_add; + JSreturn |= (turbo_rate_cnt_a[0] >> 24) & 1; + } + if (all_acts[0] & 0x200) { // B turbo + turbo_rate_cnt_b[0] += Settings.turbo_rate_add; + JSreturn |= (turbo_rate_cnt_b[0] >> 23) & 2; + } - //padTmp=Y_down >> 15; // 2^13, - if (!(TurboFireTop && (!turbo_toggle_B))) - { - JS |= ((X_down >> 14) << 1); // 0x2 is 2^1 - } - } - else - { - //padTmp=X_down >> 14; // 2^13, - if (!(TurboFireBottom && (!turbo_toggle_A))) - { - JS |= ((X_down >> 14) << 0); // 0x1 is 2^0 - } + // player 2 + JSreturn |= (all_acts[1] & 0xff) << 16; + if (all_acts[1] & 0x100) { // A turbo + turbo_rate_cnt_a[1] += Settings.turbo_rate_add; + JSreturn |= (turbo_rate_cnt_a[1] >> 8) & 0x10000; + } + if (all_acts[1] & 0x200) { // B turbo + turbo_rate_cnt_b[1] += Settings.turbo_rate_add; + JSreturn |= (turbo_rate_cnt_b[1] >> 7) & 0x20000; + } - //padTmp=Y_down >> 15; // 2^13, - if (!(TurboFireTop && (!turbo_toggle_B))) - { - JS |= ((Y_down >> 15) << 1); // 0x2 is 2^1 - } - } - - // select - //padTmp=(pad & GP2X_SELECT) >> 9; // 0x40 is 2^9, - JS |= (((pad & GP2X_SELECT) >> 9) << 2); // 0x4 is 2^2 - - // start - //padTmp=(pad & GP2X_START) >> 8; // 2^8, - JS |= (((pad & GP2X_START) >> 8) << 3); // 0x8 is 2^3 - - JSreturn = JS; - lastpad=pad; - - //JSreturn=(JS&0xFF000000)|(JS&0xFF)|((JS&0xFF0000)>>8)|((JS&0xFF00)<<8); - - - // JSreturn=(JSreturn&0xFF000000)|(JSreturn&0xFF)|((JSreturn&0xFF0000)>>8)|((JSreturn&0xFF00)<<8); - // TODO: make these bindable, use new interface - if(gametype==GIT_FDS) - { - NoWaiting&=~1; - if ((pad & GP2X_PUSH) && (!(pad & GP2X_SELECT)) && (!(pad & GP2X_L)) && (!(pad & GP2X_R)) && (!(lastpad2 & GP2X_PUSH))) - { - DriverInterface(DES_FDSSELECT,0); - } - else if ((pad & GP2X_L) && (!(pad & GP2X_SELECT)) && (!(pad & GP2X_PUSH)) && (!(pad & GP2X_R))&& (!(lastpad2 & GP2X_L))) - { - DriverInterface(DES_FDSINSERT,0); - } - else if ((pad & GP2X_R) && (!(pad & GP2X_SELECT)) && (!(pad & GP2X_L)) && (!(pad & GP2X_PUSH)) && (!(lastpad2 & GP2X_R))) - { - DriverInterface(DES_FDSEJECT,0); - } - } - return; - -no_pad: - JSreturn=0; - lastpad=pad; + do_emu_acts(all_acts[0]|all_acts[1]); } @@ -386,6 +305,9 @@ static void InitOtherInput(void) int x; int attrib; + printf("InitOtherInput: InputType[0]: %i, InputType[1]: %i, InputTypeFC: %i\n", + InputType[0], InputType[1], InputTypeFC); + for(t=0,x=0;x<2;x++) { attrib=0; @@ -415,9 +337,43 @@ static void InitOtherInput(void) FCEUI_SetInputFC(InputTypeFC,InputDPtr,attrib); FCEUI_DisableFourScore(eoptions&EO_NOFOURSCORE); - if(t && !(inited&16)) - { - InitMouse(); - inited|=16; - } + inited|=16; } + + +static void PrepareOtherInput(void) +{ + uint32 act, key, seen_acts; + + combo_acts = combo_keys = prev_emu_acts = seen_acts = 0; + + // find combo_acts + for (act = 1; act; act <<= 1) + { + for (key = 1; key < 32; key++) + { + if (Settings.KeyBinds[key] & act) + { + if (seen_acts & act) combo_acts |= act; + else seen_acts |= act; + } + } + } + + combo_acts &= ~0x00030000; // don't take player_id bits + + // find combo_keys + for (act = 1; act; act <<= 1) + { + for (key = 0; key < 32; key++) + { + if (Settings.KeyBinds[key] & combo_acts) + { + combo_keys |= 1 << key; + } + } + } + + // printf("generated combo_acts: %08x, combo_keys: %08x\n", combo_acts, combo_keys); +} +