diff --git a/desmume/src/windows/DeSmuME_2005.vcproj b/desmume/src/windows/DeSmuME_2005.vcproj
index 7e0c475aa..d9270d545 100644
--- a/desmume/src/windows/DeSmuME_2005.vcproj
+++ b/desmume/src/windows/DeSmuME_2005.vcproj
@@ -572,6 +572,10 @@
/>
+
+
diff --git a/desmume/src/windows/inputdx.cpp b/desmume/src/windows/inputdx.cpp
index 5029bf7fb..a98a855ec 100644
--- a/desmume/src/windows/inputdx.cpp
+++ b/desmume/src/windows/inputdx.cpp
@@ -1,511 +1,303 @@
-/* Copyright (C) 2006 yopyop
- yopyop156@ifrance.com
- yopyop156.ifrance.com
-
- Copyright (C) 2006-2009 DeSmuME team
-
- This file is part of DeSmuME
-
- DeSmuME 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.
-
- DeSmuME 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 DeSmuME; if not, write to the Free Software
- Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
-*/
+///* This file is part of DeSmuME, derived from several files in Snes9x 1.51 which are
+// licensed under the terms supplied at the end of this file (for the terms are very long!)
+// Differences from that baseline version are:
+//
+// Copyright (C) 2009 DeSmuME team
+//
+// DeSmuME 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.
+//
+// DeSmuME 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 DeSmuME; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+//*/
+
+
+
+#ifdef __MINGW32__
+#define _WIN32_IE 0x0501
+#define _WIN32_WINNT 0x0501
+#endif
+
+#define STRICT
+#include
+#include
+#include
+
+#if (((defined(_MSC_VER) && _MSC_VER >= 1300)) || defined(__MINGW32__))
+ // both MINGW and VS.NET use fstream instead of fstream.h which is deprecated
+ #include
+ using namespace std;
+#else
+ // for VC++ 6
+ #include
+#endif
+
+#include "inputdx.h"
+
+#include "main.h"
+#include "resource.h"
+#include "common.h"
+#include "../addons.h"
+#include "../NDSSystem.h"
+
#define DIRECTINPUT_VERSION 0x0800
+#include "../common.h"
+#include "../types.h"
+#include "directx/dinput.h"
+
+// Gamepad Dialog Strings
+#define INPUTCONFIG_TITLE "Input Configuration"
+#define INPUTCONFIG_JPTOGGLE "Enabled"
+//#define INPUTCONFIG_DIAGTOGGLE "Toggle Diagonals"
+//#define INPUTCONFIG_OK "&OK"
+//#define INPUTCONFIG_CANCEL "&Cancel"
+#define INPUTCONFIG_JPCOMBO "Joypad #%d"
+#define INPUTCONFIG_LABEL_UP "Up"
+#define INPUTCONFIG_LABEL_DOWN "Down"
+#define INPUTCONFIG_LABEL_LEFT "Left"
+#define INPUTCONFIG_LABEL_RIGHT "Right"
+#define INPUTCONFIG_LABEL_A "A"
+#define INPUTCONFIG_LABEL_B "B"
+#define INPUTCONFIG_LABEL_X "X"
+#define INPUTCONFIG_LABEL_Y "Y"
+#define INPUTCONFIG_LABEL_L "L"
+#define INPUTCONFIG_LABEL_R "R"
+#define INPUTCONFIG_LABEL_START "Start"
+#define INPUTCONFIG_LABEL_SELECT "Select"
+#define INPUTCONFIG_LABEL_UPLEFT "Up Left"
+#define INPUTCONFIG_LABEL_UPRIGHT "Up Right"
+#define INPUTCONFIG_LABEL_DOWNRIGHT "Dn Right"
+#define INPUTCONFIG_LABEL_DOWNLEFT "Dn Left"
+#define INPUTCONFIG_LABEL_BLUE "Blue means the button is already mapped.\nPink means it conflicts with a custom hotkey.\nRed means it's reserved by Windows.\nButtons can be disabled using Escape.\nGrayed buttons arent supported yet (sorry!)"
+#define INPUTCONFIG_LABEL_UNUSED ""
+#define INPUTCONFIG_LABEL_CLEAR_TOGGLES_AND_TURBO "Clear All"
+#define INPUTCONFIG_LABEL_MAKE_TURBO "TempTurbo"
+#define INPUTCONFIG_LABEL_MAKE_HELD "Autohold"
+#define INPUTCONFIG_LABEL_MAKE_TURBO_HELD "Autofire"
+#define INPUTCONFIG_LABEL_CONTROLLER_TURBO_PANEL_MOD " Turbo"
+
+// Hotkeys Dialog Strings
+#define HOTKEYS_TITLE "Hotkey Configuration"
+#define HOTKEYS_CONTROL_MOD "Ctrl + "
+#define HOTKEYS_SHIFT_MOD "Shift + "
+#define HOTKEYS_ALT_MOD "Alt + "
+#define HOTKEYS_LABEL_BLUE "Blue means the hotkey is already mapped.\nPink means it conflicts with a game button.\nRed means it's reserved by Windows.\nA hotkey can be disabled using Escape."
+#define HOTKEYS_HKCOMBO "Page %d"
+#define HOTKEYS_LABEL_1_1 "speed +"
+#define HOTKEYS_LABEL_1_2 "speed -"
+#define HOTKEYS_LABEL_1_3 "pause"
+#define HOTKEYS_LABEL_1_4 "frame advance"
+#define HOTKEYS_LABEL_1_5 "fast forward"
+#define HOTKEYS_LABEL_1_6 "skip +"
+#define HOTKEYS_LABEL_1_7 "skip -"
+#define HOTKEYS_LABEL_1_8 "superscope turbo"
+#define HOTKEYS_LABEL_1_9 "superscope pause"
+#define HOTKEYS_LABEL_1_10 "show pressed keys"
+#define HOTKEYS_LABEL_1_11 "movie frame count"
+#define HOTKEYS_LABEL_1_12 "movie read-only"
+#define HOTKEYS_LABEL_1_13 "save screenshot"
+#define HOTKEYS_LABEL_2_1 "Graphics Layer 1"
+#define HOTKEYS_LABEL_2_2 "Graphics Layer 2"
+#define HOTKEYS_LABEL_2_3 "Graphics Layer 3"
+#define HOTKEYS_LABEL_2_4 "Graphics Layer 4"
+#define HOTKEYS_LABEL_2_5 "Sprites Layer"
+#define HOTKEYS_LABEL_2_6 "Clipping Windows"
+#define HOTKEYS_LABEL_2_7 "Transparency"
+#define HOTKEYS_LABEL_2_8 "HDMA Emulation"
+#define HOTKEYS_LABEL_2_9 "GLCube Mode"
+#define HOTKEYS_LABEL_2_10 "Switch Controllers"
+#define HOTKEYS_LABEL_2_11 "Joypad Swap"
+#define HOTKEYS_LABEL_2_12 "Reset Game"
+#define HOTKEYS_LABEL_2_13 "Toggle Cheats"
+#define HOTKEYS_LABEL_3_1 "Turbo A mode"
+#define HOTKEYS_LABEL_3_2 "Turbo B mode"
+#define HOTKEYS_LABEL_3_3 "Turbo Y mode"
+#define HOTKEYS_LABEL_3_4 "Turbo X mode"
+#define HOTKEYS_LABEL_3_5 "Turbo L mode"
+#define HOTKEYS_LABEL_3_6 "Turbo R mode"
+#define HOTKEYS_LABEL_3_7 "Turbo Start mode"
+#define HOTKEYS_LABEL_3_8 "Turbo Select mode"
+#define HOTKEYS_LABEL_3_9 "Turbo Left mode"
+#define HOTKEYS_LABEL_3_10 "Turbo Up mode"
+#define HOTKEYS_LABEL_3_11 "Turbo Right mode"
+#define HOTKEYS_LABEL_3_12 "Turbo Down mode"
+//#define HOTKEYS_LABEL_4_12 "Interpolate Mode 7"
+//#define HOTKEYS_LABEL_4_13 "BG Layering hack"
+
+// gaming buttons and axes
+#define GAMEDEVICE_JOYNUMPREFIX "(J%x)" // don't change this
+#define GAMEDEVICE_JOYBUTPREFIX "#[%d]" // don't change this
+#define GAMEDEVICE_XNEG "Left"
+#define GAMEDEVICE_XPOS "Right"
+#define GAMEDEVICE_YPOS "Up"
+#define GAMEDEVICE_YNEG "Down"
+#define GAMEDEVICE_POVLEFT "POV Left"
+#define GAMEDEVICE_POVRIGHT "POV Right"
+#define GAMEDEVICE_POVUP "POV Up"
+#define GAMEDEVICE_POVDOWN "POV Down"
+#define GAMEDEVICE_POVDNLEFT "POV Dn Left"
+#define GAMEDEVICE_POVDNRIGHT "POV Dn Right"
+#define GAMEDEVICE_POVUPLEFT "POV Up Left"
+#define GAMEDEVICE_POVUPRIGHT "POV Up Right"
+#define GAMEDEVICE_ZPOS "Z Up"
+#define GAMEDEVICE_ZNEG "Z Down"
+#define GAMEDEVICE_RPOS "R Up"
+#define GAMEDEVICE_RNEG "R Down"
+#define GAMEDEVICE_UPOS "U Up"
+#define GAMEDEVICE_UNEG "U Down"
+#define GAMEDEVICE_VPOS "V Up"
+#define GAMEDEVICE_VNEG "V Down"
+#define GAMEDEVICE_BUTTON "Button %d"
+
+// gaming general
+#define GAMEDEVICE_DISABLED "Disabled"
+
+// gaming keys
+#define GAMEDEVICE_KEY "#%d"
+#define GAMEDEVICE_NUMPADPREFIX "Numpad-%c"
+#define GAMEDEVICE_VK_TAB "Tab"
+#define GAMEDEVICE_VK_BACK "Backspace"
+#define GAMEDEVICE_VK_CLEAR "Delete"
+#define GAMEDEVICE_VK_RETURN "Enter"
+#define GAMEDEVICE_VK_LSHIFT "LShift"
+#define GAMEDEVICE_VK_RSHIFT "RShift"
+#define GAMEDEVICE_VK_LCONTROL "LCtrl"
+#define GAMEDEVICE_VK_RCONTROL "RCtrl"
+#define GAMEDEVICE_VK_LMENU "LAlt"
+#define GAMEDEVICE_VK_RMENU "RAlt"
+#define GAMEDEVICE_VK_PAUSE "Pause"
+#define GAMEDEVICE_VK_CAPITAL "Capslock"
+#define GAMEDEVICE_VK_ESCAPE "Disabled"
+#define GAMEDEVICE_VK_SPACE "Space"
+#define GAMEDEVICE_VK_PRIOR "PgUp"
+#define GAMEDEVICE_VK_NEXT "PgDn"
+#define GAMEDEVICE_VK_HOME "Home"
+#define GAMEDEVICE_VK_END "End"
+#define GAMEDEVICE_VK_LEFT "Left"
+#define GAMEDEVICE_VK_RIGHT "Right"
+#define GAMEDEVICE_VK_UP "Up"
+#define GAMEDEVICE_VK_DOWN "Down"
+#define GAMEDEVICE_VK_SELECT "Select"
+#define GAMEDEVICE_VK_PRINT "Print"
+#define GAMEDEVICE_VK_EXECUTE "Execute"
+#define GAMEDEVICE_VK_SNAPSHOT "SnapShot"
+#define GAMEDEVICE_VK_INSERT "Insert"
+#define GAMEDEVICE_VK_DELETE "Delete"
+#define GAMEDEVICE_VK_HELP "Help"
+#define GAMEDEVICE_VK_LWIN "LWinKey"
+#define GAMEDEVICE_VK_RWIN "RWinKey"
+#define GAMEDEVICE_VK_APPS "AppKey"
+#define GAMEDEVICE_VK_MULTIPLY "Numpad *"
+#define GAMEDEVICE_VK_ADD "Numpad +"
+#define GAMEDEVICE_VK_SEPARATOR "Separator"
+#define GAMEDEVICE_VK_OEM_1 "Semi-Colon"
+#define GAMEDEVICE_VK_OEM_7 "Apostrophe"
+#define GAMEDEVICE_VK_OEM_COMMA "Comma"
+#define GAMEDEVICE_VK_OEM_PERIOD "Period"
+#define GAMEDEVICE_VK_SUBTRACT "Numpad -"
+#define GAMEDEVICE_VK_DECIMAL "Numpad ."
+#define GAMEDEVICE_VK_DIVIDE "Numpad /"
+#define GAMEDEVICE_VK_NUMLOCK "Num-lock"
+#define GAMEDEVICE_VK_SCROLL "Scroll-lock"
+#define GAMEDEVICE_VK_OEM_MINUS "-"
+#define GAMEDEVICE_VK_OEM_PLUS "="
+#define GAMEDEVICE_VK_SHIFT "Shift"
+#define GAMEDEVICE_VK_CONTROL "Control"
+#define GAMEDEVICE_VK_MENU "Alt"
+#define GAMEDEVICE_VK_OEM_4 "["
+#define GAMEDEVICE_VK_OEM_6 "]"
+#define GAMEDEVICE_VK_OEM_5 "\\"
+#define GAMEDEVICE_VK_OEM_2 "/"
+#define GAMEDEVICE_VK_OEM_3 "`"
+#define GAMEDEVICE_VK_F1 "F1"
+#define GAMEDEVICE_VK_F2 "F2"
+#define GAMEDEVICE_VK_F3 "F3"
+#define GAMEDEVICE_VK_F4 "F4"
+#define GAMEDEVICE_VK_F5 "F5"
+#define GAMEDEVICE_VK_F6 "F6"
+#define GAMEDEVICE_VK_F7 "F7"
+#define GAMEDEVICE_VK_F8 "F8"
+#define GAMEDEVICE_VK_F9 "F9"
+#define GAMEDEVICE_VK_F10 "F10"
+#define GAMEDEVICE_VK_F11 "F11"
+#define GAMEDEVICE_VK_F12 "F12"
+#define BUTTON_OK "&OK"
+#define BUTTON_CANCEL "&Cancel"
+
+static TCHAR szClassName[] = _T("InputCustom");
+static TCHAR szHotkeysClassName[] = _T("InputCustomHot");
+
+static LRESULT CALLBACK InputCustomWndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam);
+static LRESULT CALLBACK HotInputCustomWndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam);
+
+SJoyState Joystick [16];
+SJoyState JoystickF [16];
+SJoypad ToggleJoypadStorage[8];
+SJoypad TurboToggleJoypadStorage[8];
+u32 joypads [8];
+SCustomKeys CustomKeys;
+
+//the main input configuration:
+SJoypad DefaultJoypad[16] = {
+ {
+ true, /* Joypad 1 enabled */
+ VK_LEFT, VK_RIGHT, VK_UP, VK_DOWN, /* Left, Right, Up, Down */
+ 0, 0, 0, 0, /* Left_Up, Left_Down, Right_Up, Right_Down */
+ VK_RETURN, VK_RSHIFT, /* Start, Select */
+ 0, 0, /* Lid, Debug */
+ 'X', 'Z', /* A B */
+ 'S', 'A', /* X Y */
+ 'W', 'Q' /* L R */
+ },
+ { false, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+ { false, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+ { false, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+ { false, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+ { false, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+ { false, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+ { false, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+ { false, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+ { false, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+ { false, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+ { false, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+ { false, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+ { false, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+ { false, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
+ { false, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }
+};
+
+SJoypad Joypad[16];
+
+extern volatile BOOL paused;
+
+#define MAXKEYPAD 15
-#include "inputdx.h"
-#include "directx\dinput.h"
-#include "..\mem.h"
-#include "..\debug.h"
-#include "..\MMU.h"
-#include "..\common.h"
-#include "..\addons.h"
-#include "resource.h"
-#include "NDSSystem.h"
-
-// ==================================================== emu input
-// =======================================================================
-#define IDD_INPUT_TIMER 1000000
-
-const char *DIkeysNames[0xEF] =
-{
- "N/A",
- // Main keyboard 0x01
- "ESC", "1", "2", "3", "4", "5", "6", "7", "8", "9", "0", "-", "=", "BSPACE",
- "Tab", "Q", "W", "E", "R", "T", "Y", "U", "I", "O", "P", "[", "]", "Enter",
- "LCtrl", "A", "S", "D", "F", "G", "H", "J", "K", "L", ";", "\'", "GRAVE", "LShift", "\\",
- "Z", "X", "C", "V", "B", "N", "M", ",", ".", "/", "RShift",
- // Numeric keypad 0x37
- "Num *",
- // Main keyboard 0x38
- "LAlt", "SPACE", "~CAP",
- "F1", "F2", "F3", "F4", "F5", "F6", "F7", "F8", "F9", "F10",
- // Numeric keypad 0x45
- "NumLock", "Scrool", "Num 7", "Num 8", "Num 9",
- "Num -", "Num 4", "Num 5", "Num 6", "Num +",
- "Num 1", "Num 2", "Num 3", "Num 0", "Num .",
- // Reserved 0x54
- "", "",
- // non US keyboards 0x56
- "oem",
- // func keyboard 0x57
- "F11", "F12",
- // Reserved 0x59
- "", "", "", "", "", "", "", "", "", "", "",
- // PC98 0x64
- "F13", "F14", "F15",
- // Reserved 0x67
- "", "", "", "", "", "", "", "", "",
- // Japanise 0x70
- "KANA",
- // Reserved 0x71
- "", "",
- // Brazilian 0x73
- "ABNT_C1",
- // Reserved 0x74
- "", "", "", "", "",
- // Japanise 0x79
- "Convert",
- // Reserved 0x7A
- "",
- // Japanise 0x7B
- "Noconvert",
- // Reserved 0x7C
- "",
- // Japanise 0x7D
- "Yen",
- // Brazilian 0x7E
- "ABNT_C2",
- // Reserved 0x7F
- "", "", "", "", "", "", "", "", "", "", "", "", "", "",
- // PC98 0x8D
- "N =",
- // Reserved 0x8E
- "", "",
- // ext 0x90
- "PTrack",
- // PC98 0x91
- "AT", "Colon", "Underline",
- // Japanise 0x94
- "Kanji",
- // PC98 0x95
- "Stop",
- // Japanise 0x96
- "AX", "Unlab",
- // Reseved 0x98
- "",
- // ext 0x99
- "NTrack",
- // Reserved 0x9A
- "", "",
- // Numeric keypad 0x9C
- "Num enter", "RCtrl",
- // Reserved 0x9E
- "", "",
- // ext 0xA0
- "Mute", "Calc", "Play",
- // Reserved 0xA3
- "",
- // ext 0xA4
- "Stop",
- // Reserved 0xA5
- "", "", "", "", "", "", "", "", "",
- // ext 0xAE
- "Vol-",
- // Reserved 0xAF
- "",
- // ext 0xB0
- "Vol+",
- // Reserved 0xB1
- "",
- // Web 0xB2
- "Web Home",
- // Numeric keypad (PC98) 0xB3
- "Num ,",
- // Reserved 0xB4
- "",
- // Numeric keypad 0xB5
- "Num /",
- // Reserved 0xB6
- "",
- // Main keyboard 0xB7
- "SysRq", "RAlt",
- // Reserved 0xB9
- "", "", "", "", "", "", "", "", "", "", "", "",
- // Main keyboard 0xC5
- "Pause",
- // Reserved 0xC6
- "",
- // Main keyboard 0xC7
- "Home", "Up", "PgUp",
- // Reserved 0xCA
- "",
- // Main keyboard 0xCB
- "Left",
- // Reserved 0xCC
- "",
- // Main keyboard 0xCD
- "Right",
- // Reserved 0xCE
- "",
- // Main keyboard 0xCF
- "End", "Down", "PgDn", "Insert", "Delete",
- // Reserved 0xD4
- "", "", "", "", "", "", "", "",
- // Main keyboard 0xDB
- "LWin", "RWin", "App", "Power", "Sleep",
- // Reversed 0xE0
- "", "", "",
- // Main keyboard 0xE3
- "Wake",
- // Reversed 0xE4
- "",
- // Web 0xE5
- "Web Search", "Web Favorites", "Web Refresh", "Web Stop", "Web Forward", "Web Back",
- "My Computer", "Mail", "Media Select"
- // 0xEE
-};
-const char *DIJoyNames[0x04] = { "JUp", "JDown", "JLeft", "JRight" };
-
-#define KEY_A 0
-#define KEY_B 1
-#define KEY_SELECT 2
-#define KEY_START 3
-#define KEY_RIGHT 4
-#define KEY_LEFT 5
-#define KEY_UP 6
-#define KEY_DOWN 7
-#define KEY_R 8
-#define KEY_L 9
-#define KEY_X 10
-#define KEY_Y 11
-#define KEY_DEBUG 12
-#define KEY_FOLD 13
-#define KEY_POWER 14
-
-
-char *keyPadNames [MAXKEYPAD] = { "A", "B", "SELECT", "START",
- "RIGHT", "LEFT", "UP", "DOWN",
- "R", "L", "X", "Y", "DEBUG", "FOLD", "POWER" };
-
-u16 keyPadDefs[MAXKEYPAD] = {DIK_X, DIK_Z, DIK_RSHIFT, DIK_RETURN, DIK_RIGHT,
- DIK_LEFT, DIK_UP, DIK_DOWN, DIK_W, DIK_Q,
- DIK_S, DIK_A, 0x00, DIK_BACKSPACE, DIK_PAUSE};
-
-const int inputIDs[15]={ IDC_EDIT06, IDC_EDIT05, IDC_EDIT11, IDC_EDIT12, IDC_EDIT03, IDC_EDIT02, IDC_EDIT01,
- IDC_EDIT04, IDC_EDIT10, IDC_EDIT09, IDC_EDIT08, IDC_EDIT07, IDC_EDIT14, IDC_EDIT13,
- IDC_EDIT15};
-
-
-u16 keyPad[15];
-extern INPUTCLASS *input;
-
-void NDS_inputFeedback(BOOL enable);
-
-// ==================================================== Config Input
-INPUTCLASS *inputCfg = NULL;
-HWND g_hWnd = NULL;
-static int pressed;
-static bool tab;
-u16 tempKeyPad[MAXKEYPAD];
-
-void InputConfigDIProc(BOOL paused, LPSTR buf)
-{
- int t;
- int i;
-
- if (pressed == 0)
- {
- for (t=0; t<512; t++)
- {
- if (t == DIK_ESCAPE) continue;
- if (t == DIK_TAB) continue;
- if (t == DIK_LMENU) continue;
- if (t == DIK_F1) continue;
- if (t == DIK_F2) continue;
- if (t == DIK_F3) continue;
- if (t == DIK_F4) continue;
- if (t == DIK_F5) continue;
- if (t == DIK_F6) continue;
- if (t == DIK_F7) continue;
- if (t == DIK_F8) continue;
- if (t == DIK_F9) continue;
- if (t == DIK_F10) continue;
- if (t == DIK_F11) continue;
- if (t == DIK_F12) continue;
- if (t == DIK_NUMLOCK) continue;
-
- if (buf[t] & 0x80)
- {
- pressed = t;
- break;
- }
- }
- }
- else
- {
- if ((pressed == DIK_LSHIFT) && ((buf[DIK_TAB] & 0x80))) tab = true;
- if ((pressed == DIK_RSHIFT) && ((buf[DIK_TAB] & 0x80))) tab = true;
-
- if (!(buf[pressed] & 0x80))
- {
- if (!tab)
- {
- if (pressed>255)
- {
- if (pressed>255 && pressed<260)
- {
- SetWindowText(GetFocus(), DIJoyNames[pressed-256]);
- }
- else
- {
- char buf[20];
- memset(buf, 0, sizeof(buf));
- wsprintf(buf, "JB%02i", pressed-259);
- SetWindowText(GetFocus(), buf);
- }
- }
- else
- {
- SetWindowText(GetFocus(), DIkeysNames[pressed]);
- }
- for (i=0; i255)
- {
- if (tempKeyPad[i]>255 && tempKeyPad[i]<260)
- {
- SetWindowText(GetDlgItem(hDlg, inputIDs[i]), DIJoyNames[tempKeyPad[i]-256]);
- }
- else
- {
- char buf[20];
- memset(buf, 0, sizeof(buf));
- wsprintf(buf, "JB%02i", tempKeyPad[i]-259);
- SetWindowText(GetDlgItem(hDlg, inputIDs[i]), buf);
- }
- }
- else
- SetWindowText(GetDlgItem(hDlg, inputIDs[i]), DIkeysNames[tempKeyPad[i]]);
- }
-
- if (!inputCfg->Init(hDlg, &InputConfigDIProc))
- INFO("Input config: Error initialize DirectInput\n");
- SetTimer(hDlg, IDD_INPUT_TIMER, 100, NULL);
- return true;
-
- case WM_TIMER:
- inputCfg->process();
- return true;
-
- case WM_COMMAND:
- switch(LOWORD(wParam))
- {
- case IDOK:
- if (GetFocus() == GetDlgItem(hDlg, IDOK))
- {
- for (int t=0; t255)
- {
- if (!input->JoystickEnabled())
- {
- keyPad[i] = keyPadDefs[i];
- }
- }
- }
-
- FeedbackON = NDS_inputFeedback;
-}
-
-void NDS_inputPost(BOOL paused, LPSTR buf)
-{
- if (paused) return;
-
- bool R = (buf[keyPad[KEY_RIGHT]] & 0x80)!=0;
- bool L = (buf[keyPad[KEY_LEFT]] & 0x80)!=0;
- bool D = (buf[keyPad[KEY_DOWN]] & 0x80)!=0;
- bool U = (buf[keyPad[KEY_UP]] & 0x80)!=0;
- bool T = (buf[keyPad[KEY_START]] & 0x80)!=0;
- bool S = (buf[keyPad[KEY_SELECT]] & 0x80)!=0;
- bool B = (buf[keyPad[KEY_B]] & 0x80)!=0;
- bool A = (buf[keyPad[KEY_A]] & 0x80)!=0;
- bool Y = (buf[keyPad[KEY_Y]] & 0x80)!=0;
- bool X = (buf[keyPad[KEY_X]] & 0x80)!=0;
- bool W = (buf[keyPad[KEY_L]] & 0x80)!=0;
- bool E = (buf[keyPad[KEY_R]] & 0x80)!=0;
- bool G = (buf[keyPad[KEY_DEBUG]] & 0x80)!=0;
- bool F = (buf[keyPad[KEY_FOLD]] & 0x80)!=0;
-
- NDS_setPad( R, L, D, U, T, S, B, A, Y, X, W, E, G, F);
-}
-
-void NDS_inputFeedback(BOOL enable)
-{
- input->JoystickFeedback(enable);
-}
-
-// TODO
-// ==================================================== GUI input
-// =======================================================================
-
-
-// ==================================================== INPUTCLASS
-// ===============================================================
-// ===============================================================
-// ===============================================================
+typedef char TcDIBuf[512];
+
+TcDIBuf cDIBuf;
+LPDIRECTINPUT8 pDI;
+LPDIRECTINPUTDEVICE8 pJoystick;
+DIDEVCAPS DIJoycap;
+LPDIRECTINPUTEFFECT pEffect;
+char JoystickName[255];
+BOOL Feedback;
+
+
static LPDIRECTINPUT8 tmp_pDI = NULL;
static BOOL tmp_Feedback = FALSE;
static char tmp_device_name[255] = { 0 };
static LPDIRECTINPUTDEVICE8 tmp_Device = NULL;
-static LPDIRECTINPUTDEVICE8 tmp_Joystick = NULL;
-
-INPUTCLASS::INPUTCLASS()
-: pEffect(NULL)
-, hParentWnd(0)
-, inputProc(NULL)
-, pKeyboard(NULL)
-, pJoystick(NULL)
-, pDI(NULL)
-{
-}
-
-INPUTCLASS::~INPUTCLASS()
-{
- if (pDI != NULL)
- {
- if (pKeyboard != NULL)
- {
- pKeyboard->Unacquire();
- pKeyboard->Release();
- pKeyboard = NULL;
- }
-
- if (pJoystick != NULL)
- {
- if (pEffect)
- {
- pEffect->Stop();
- pEffect->Release();
- pEffect = NULL;
- }
- pJoystick->Unacquire();
- pJoystick->Release();
- pJoystick = NULL;
- }
- pDI->Release();
- }
-}
-
-extern BOOL CALLBACK EnumCallback(LPCDIDEVICEINSTANCE lpddi, LPVOID pvRef)
-{
- DI_CLASS *tmp = (DI_CLASS *)lpddi;
- return tmp->EnumCallback(lpddi, pvRef);
-}
-
-LPDIRECTINPUTDEVICE8 DI_CLASS::EnumDevices(LPDIRECTINPUT8 pDI)
-{
- tmp_pDI = pDI;
- tmp_Feedback = FALSE;
- memset(tmp_device_name, 0, 255);
- if( FAILED( pDI->EnumDevices(DI8DEVCLASS_GAMECTRL,
- ::EnumCallback,
- NULL,
- DIEDFL_ATTACHEDONLY) ) )
- return NULL;
- Feedback = tmp_Feedback;
- strcpy(JoystickName, tmp_device_name);
- return tmp_Device;
-}
-
-BOOL DI_CLASS::EnumCallback(LPCDIDEVICEINSTANCE lpddi, LPVOID pvRef)
+static LPDIRECTINPUTDEVICE8 tmp_Joystick = NULL;
+
+BOOL CALLBACK EnumCallback(LPCDIDEVICEINSTANCE lpddi, LPVOID pvRef)
{
if ( FAILED( tmp_pDI->CreateDevice(lpddi->guidInstance, &tmp_Device, NULL) ) )
{
@@ -517,14 +309,24 @@ BOOL DI_CLASS::EnumCallback(LPCDIDEVICEINSTANCE lpddi, LPVOID pvRef)
if (lpddi->guidFFDriver.Data1) tmp_Feedback = TRUE;
return DIENUM_STOP;
}
-
-extern BOOL CALLBACK EnumObjects(const DIDEVICEOBJECTINSTANCE* pdidoi,VOID* pContext)
+
+
+LPDIRECTINPUTDEVICE8 EnumDevices(LPDIRECTINPUT8 pDI)
{
- DI_CLASS *tmp = (DI_CLASS *)pdidoi;
- return tmp->EnumObjects(pdidoi, pContext);
+ tmp_pDI = pDI;
+ tmp_Feedback = FALSE;
+ memset(tmp_device_name, 0, 255);
+ if( FAILED( pDI->EnumDevices(DI8DEVCLASS_GAMECTRL,
+ EnumCallback,
+ NULL,
+ DIEDFL_ATTACHEDONLY) ) )
+ return NULL;
+ Feedback = tmp_Feedback;
+ strcpy(JoystickName, tmp_device_name);
+ return tmp_Device;
}
-BOOL CALLBACK DI_CLASS::EnumObjects(const DIDEVICEOBJECTINSTANCE* pdidoi,VOID* pContext)
+BOOL CALLBACK EnumObjects(const DIDEVICEOBJECTINSTANCE* pdidoi,VOID* pContext)
{
if( pdidoi->dwType & DIDFT_AXIS )
{
@@ -533,8 +335,8 @@ BOOL CALLBACK DI_CLASS::EnumObjects(const DIDEVICEOBJECTINSTANCE* pdidoi,VOID* p
diprg.diph.dwHeaderSize = sizeof(DIPROPHEADER);
diprg.diph.dwHow = DIPH_BYID;
diprg.diph.dwObj = pdidoi->dwType;
- diprg.lMin = -3;
- diprg.lMax = 3;
+ diprg.lMin = -10000;
+ diprg.lMax = 10000;
if( FAILED(tmp_Joystick->SetProperty(DIPROP_RANGE, &diprg.diph)) )
return DIENUM_STOP;
@@ -542,15 +344,55 @@ BOOL CALLBACK DI_CLASS::EnumObjects(const DIDEVICEOBJECTINSTANCE* pdidoi,VOID* p
return DIENUM_CONTINUE;
}
-BOOL INPUTCLASS::Init(HWND hParentWnd, INPUTPROC inputProc)
+static void ReadControl(const char* name, WORD& output)
{
- if (hParentWnd == NULL) return FALSE;
- if (inputProc == NULL) return FALSE;
+ UINT temp;
+ temp = GetPrivateProfileInt("Controls",name,-1,IniName);
+ if(temp != -1) {
+ output = temp;
+ }
+}
- this->hParentWnd = hParentWnd;
+static void LoadConfig()
+{
+ memcpy(&Joypad,&DefaultJoypad,sizeof(Joypad));
+
+ //read from configuration file
+ Joypad[0].Enabled = true;
+#define DO(X) ReadControl(#X,Joypad[0] . X);
+ DO(Left); DO(Right); DO(Up); DO(Down);
+ DO(Left_Up); DO(Left_Down); DO(Right_Up); DO(Right_Down);
+ DO(Start); DO(Select);
+ DO(Lid); DO(Debug);
+ DO(A); DO(B); DO(X); DO(Y);
+ DO(L); DO(R);
+#undef DO
+}
+
+static void WriteControl(char* name, WORD val)
+{
+ WritePrivateProfileInt("Controls",name,val,IniName);
+}
+
+static void SaveConfig()
+{
+#define DO(X) WriteControl(#X,Joypad[0] . X);
+ DO(Left); DO(Right); DO(Up); DO(Down);
+ DO(Left_Up); DO(Left_Down); DO(Right_Up); DO(Right_Down);
+ DO(Start); DO(Select);
+ DO(Lid); DO(Debug);
+ DO(A); DO(B); DO(X); DO(Y);
+ DO(L); DO(R);
+#undef DO
+}
+
+BOOL di_init()
+{
+ HWND hParentWnd = MainWindow->getHWnd();
+
+ LoadConfig();
pDI = NULL;
- pKeyboard = NULL;
pJoystick = NULL;
Feedback = FALSE;
memset(cDIBuf, 0, sizeof(cDIBuf));
@@ -559,22 +401,6 @@ BOOL INPUTCLASS::Init(HWND hParentWnd, INPUTPROC inputProc)
if(FAILED(DirectInput8Create(GetModuleHandle(NULL),DIRECTINPUT_VERSION,IID_IDirectInput8,(void**)&pDI,NULL)))
return FALSE;
- if (!FAILED(pDI->CreateDevice(GUID_SysKeyboard,&pKeyboard,NULL)))
- {
- if (!FAILED(pKeyboard->SetDataFormat(&c_dfDIKeyboard)))
- {
- if (FAILED(pKeyboard->SetCooperativeLevel(hParentWnd,DISCL_FOREGROUND|DISCL_NONEXCLUSIVE)))
- {
- pKeyboard->Release();
- pKeyboard = NULL;
- }
- }
- else
- {
- pKeyboard->Release();
- pKeyboard = NULL;
- }
- }
pJoystick = EnumDevices(pDI);
@@ -582,7 +408,7 @@ BOOL INPUTCLASS::Init(HWND hParentWnd, INPUTPROC inputProc)
{
if(!FAILED(pJoystick->SetDataFormat(&c_dfDIJoystick2)))
{
- if(FAILED(pJoystick->SetCooperativeLevel(hParentWnd,DISCL_FOREGROUND|DISCL_EXCLUSIVE)))
+ if(FAILED(pJoystick->SetCooperativeLevel(hParentWnd,DISCL_BACKGROUND|DISCL_EXCLUSIVE)))
{
pJoystick->Release();
pJoystick = NULL;
@@ -643,12 +469,7 @@ BOOL INPUTCLASS::Init(HWND hParentWnd, INPUTPROC inputProc)
Feedback = FALSE;
}
- if (pKeyboard == NULL && pJoystick == NULL) return FALSE;
-
- this->inputProc = inputProc;
-
INFO("DirectX Input: \n");
- if (pKeyboard != NULL) INFO(" - keyboard successfully inited\n");
if (pJoystick != NULL)
{
INFO(" - gamecontrol successfully inited: %s\n", JoystickName);
@@ -660,69 +481,1945 @@ BOOL INPUTCLASS::Init(HWND hParentWnd, INPUTPROC inputProc)
return TRUE;
}
-BOOL INPUTCLASS::JoystickEnabled()
+BOOL JoystickEnabled()
{
return (pJoystick==NULL?FALSE:TRUE);
}
-
-void INPUTCLASS::process()
-{
- HRESULT hr;
-
- if (paused) return;
- if (inputProc == NULL) return;
-
- if (pKeyboard)
- {
- hr=pKeyboard->GetDeviceState(256,cDIBuf);
- if (FAILED(hr))
- pKeyboard->Acquire();
- }
-
+
+
+HWND funky;
+//WPARAM tid;
+
+//
+void JoystickChanged( short ID, short Movement)
+{
+ // don't allow two changes to happen too close together in time
+ {
+ static bool first = true;
+ static DWORD lastTime = 0;
+ if(first || timeGetTime() - lastTime > 300) // 0.3 seconds
+ {
+ first = false;
+ lastTime = timeGetTime();
+ }
+ else
+ {
+ return; // too soon after last change
+ }
+ }
+
+ WORD JoyKey;
+
+ JoyKey = 0x8000;
+ JoyKey |= (WORD)(ID << 8);
+ JoyKey |= Movement;
+ SendMessage(funky,WM_USER+45,JoyKey,0);
+// KillTimer(funky,tid);
+}
+
+int FunkyNormalize(int cur, int min, int max)
+{
+ int Result = 0;
+
+ if ((max - min) == 0)
+
+ return (Result);
+
+ Result = cur - min;
+ Result = (Result * 200) / (max - min);
+ Result -= 100;
+
+ return Result;
+}
+
+
+
+#define S9X_JOY_NEUTRAL 60
+
+void CheckAxis (short joy, short control, int val,
+ int min, int max,
+ bool &first, bool &second)
+{
+
+
+
+ if (FunkyNormalize (val, min, max) < -S9X_JOY_NEUTRAL)
+
+ {
+ second = false;
+ if (!first)
+ {
+ JoystickChanged (joy, control);
+ first = true;
+
+ }
+ }
+ else
+ first = false;
+
+ if (FunkyNormalize (val, min, max) > S9X_JOY_NEUTRAL)
+ {
+ first = false;
+ if (!second)
+ {
+ JoystickChanged (joy, (short) (control + 1));
+ second = true;
+ }
+ }
+ else
+ second = false;
+}
+
+
+void CheckAxis_game (int val, int min, int max, bool &first, bool &second)
+{
+ if (FunkyNormalize (val, min, max) < -S9X_JOY_NEUTRAL)
+ {
+ second = false;
+ first = true;
+ }
+ else
+ first = false;
+
+ if (FunkyNormalize (val, min, max) > S9X_JOY_NEUTRAL)
+ {
+ first = false;
+ second = true;
+ }
+ else
+ second = false;
+}
+
+void S9xUpdateJoyState()
+{
+ memset(&Joystick[0],0,sizeof(Joystick[0]));
+
+ int C = 0;
if (pJoystick)
- {
+ {
DIJOYSTATE2 JoyStatus;
- hr=pJoystick->Poll();
+ HRESULT hr=pJoystick->Poll();
if (FAILED(hr))
pJoystick->Acquire();
else
- {
+ {
hr=pJoystick->GetDeviceState(sizeof(JoyStatus),&JoyStatus);
if (FAILED(hr)) hr=pJoystick->Acquire();
else
{
- memset(cDIBuf+255, 0, sizeof(cDIBuf)-255);
+ CheckAxis_game(JoyStatus.lX,-10000,10000,Joystick[0].Left,Joystick[0].Right);
+ CheckAxis_game(JoyStatus.lY,-10000,10000,Joystick[0].Down,Joystick[0].Up);
+
+ switch (JoyStatus.rgdwPOV[0])
+ {
+ case JOY_POVBACKWARD:
+ Joystick[C].PovDown = true;
+ break;
+ case 4500:
+ Joystick[C].PovUpRight = true;
+ break;
+ case 13500:
+ Joystick[C].PovDnRight = true;
+ break;
+ case 22500:
+ Joystick[C].PovDnLeft = true;
+ break;
+ case 31500:
+ Joystick[C].PovUpLeft = true;
+ break;
+
+ case JOY_POVFORWARD:
+ Joystick[C].PovUp = true;
+ break;
+
+ case JOY_POVLEFT:
+ Joystick[C].PovLeft = true;
+ break;
+
+ case JOY_POVRIGHT:
+ Joystick[C].PovRight = true;
+ break;
+
+ default:
+ break;
+ }
+
+ for(int B=0;B<128;B++)
+ if( JoyStatus.rgbButtons[B] )
+ Joystick[C].Button[B] = true;
+
+ }
+ }
+ }
+}
- if (JoyStatus.lX<-1) cDIBuf[258]=-128;
- if (JoyStatus.lX>1) cDIBuf[259]=-128;
- if (JoyStatus.lY<-1) cDIBuf[256]=-128;
- if (JoyStatus.lY>1) cDIBuf[257]=-128;
-
- if (JoyStatus.rgdwPOV[0]==0) cDIBuf[256]=-128;
- if (JoyStatus.rgdwPOV[0]==4500) { cDIBuf[256]=-128; cDIBuf[259]=-128;}
- if (JoyStatus.rgdwPOV[0]==9000) cDIBuf[259]=-128;
- if (JoyStatus.rgdwPOV[0]==13500) { cDIBuf[259]=-128; cDIBuf[257]=-128;}
- if (JoyStatus.rgdwPOV[0]==18000) cDIBuf[257]=-128;
- if (JoyStatus.rgdwPOV[0]==22500) { cDIBuf[257]=-128; cDIBuf[258]=-128;}
- if (JoyStatus.rgdwPOV[0]==27000) cDIBuf[258]=-128;
- if (JoyStatus.rgdwPOV[0]==31500) { cDIBuf[258]=-128; cDIBuf[256]=-128;}
- memcpy(cDIBuf+260, JoyStatus.rgbButtons, sizeof(JoyStatus.rgbButtons));
- }
- }
- }
+void di_poll_scan()
+{
+ int C = 0;
+ if (pJoystick)
+ {
+ DIJOYSTATE2 JoyStatus;
- this->inputProc(paused, (LPSTR)&cDIBuf);
-}
+ HRESULT hr=pJoystick->Poll();
+ if (FAILED(hr))
+ pJoystick->Acquire();
+ else
+ {
+ hr=pJoystick->GetDeviceState(sizeof(JoyStatus),&JoyStatus);
+ if (FAILED(hr)) hr=pJoystick->Acquire();
+ else
+ {
+ CheckAxis(0,0,JoyStatus.lX,-10000,10000,Joystick[0].Left,Joystick[0].Right);
+ CheckAxis(0,2,JoyStatus.lY,-10000,10000,Joystick[0].Down,Joystick[0].Up);
+
+ switch (JoyStatus.rgdwPOV[0])
+ {
+ case JOY_POVBACKWARD:
+ if( !JoystickF[C].PovDown)
+ { JoystickChanged( C, 7); }
+
+ JoystickF[C].PovDown = true;
+ JoystickF[C].PovUp = false;
+ JoystickF[C].PovLeft = false;
+ JoystickF[C].PovRight = false;
+ JoystickF[C].PovDnLeft = false;
+ JoystickF[C].PovDnRight = false;
+ JoystickF[C].PovUpLeft = false;
+ JoystickF[C].PovUpRight = false;
+ break;
+ case 4500:
+ if( !JoystickF[C].PovUpRight)
+ { JoystickChanged( C, 52); }
+ JoystickF[C].PovDown = false;
+ JoystickF[C].PovUp = false;
+ JoystickF[C].PovLeft = false;
+ JoystickF[C].PovRight = false;
+ JoystickF[C].PovDnLeft = false;
+ JoystickF[C].PovDnRight = false;
+ JoystickF[C].PovUpLeft = false;
+ JoystickF[C].PovUpRight = true;
+ break;
+ case 13500:
+ if( !JoystickF[C].PovDnRight)
+ { JoystickChanged( C, 50); }
+ JoystickF[C].PovDown = false;
+ JoystickF[C].PovUp = false;
+ JoystickF[C].PovLeft = false;
+ JoystickF[C].PovRight = false;
+ JoystickF[C].PovDnLeft = false;
+ JoystickF[C].PovDnRight = true;
+ JoystickF[C].PovUpLeft = false;
+ JoystickF[C].PovUpRight = false;
+ break;
+ case 22500:
+ if( !JoystickF[C].PovDnLeft)
+ { JoystickChanged( C, 49); }
+ JoystickF[C].PovDown = false;
+ JoystickF[C].PovUp = false;
+ JoystickF[C].PovLeft = false;
+ JoystickF[C].PovRight = false;
+ JoystickF[C].PovDnLeft = true;
+ JoystickF[C].PovDnRight = false;
+ JoystickF[C].PovUpLeft = false;
+ JoystickF[C].PovUpRight = false;
+ break;
+ case 31500:
+ if( !JoystickF[C].PovUpLeft)
+ { JoystickChanged( C, 51); }
+ JoystickF[C].PovDown = false;
+ JoystickF[C].PovUp = false;
+ JoystickF[C].PovLeft = false;
+ JoystickF[C].PovRight = false;
+ JoystickF[C].PovDnLeft = false;
+ JoystickF[C].PovDnRight = false;
+ JoystickF[C].PovUpLeft = true;
+ JoystickF[C].PovUpRight = false;
+ break;
+
+ case JOY_POVFORWARD:
+ if( !JoystickF[C].PovUp)
+ { JoystickChanged( C, 6); }
+
+ JoystickF[C].PovDown = false;
+ JoystickF[C].PovUp = true;
+ JoystickF[C].PovLeft = false;
+ JoystickF[C].PovRight = false;
+ JoystickF[C].PovDnLeft = false;
+ JoystickF[C].PovDnRight = false;
+ JoystickF[C].PovUpLeft = false;
+ JoystickF[C].PovUpRight = false;
+ break;
+
+ case JOY_POVLEFT:
+ if( !JoystickF[C].PovLeft)
+ { JoystickChanged( C, 4); }
+
+ JoystickF[C].PovDown = false;
+ JoystickF[C].PovUp = false;
+ JoystickF[C].PovLeft = true;
+ JoystickF[C].PovRight = false;
+ JoystickF[C].PovDnLeft = false;
+ JoystickF[C].PovDnRight = false;
+ JoystickF[C].PovUpLeft = false;
+ JoystickF[C].PovUpRight = false;
+ break;
+
+ case JOY_POVRIGHT:
+ if( !JoystickF[C].PovRight)
+ { JoystickChanged( C, 5); }
+
+ JoystickF[C].PovDown = false;
+ JoystickF[C].PovUp = false;
+ JoystickF[C].PovLeft = false;
+ JoystickF[C].PovRight = true;
+ JoystickF[C].PovDnLeft = false;
+ JoystickF[C].PovDnRight = false;
+ JoystickF[C].PovUpLeft = false;
+ JoystickF[C].PovUpRight = false;
+ break;
+
+ default:
+ JoystickF[C].PovDown = false;
+ JoystickF[C].PovUp = false;
+ JoystickF[C].PovLeft = false;
+ JoystickF[C].PovRight = false;
+ JoystickF[C].PovDnLeft = false;
+ JoystickF[C].PovDnRight = false;
+ JoystickF[C].PovUpLeft = false;
+ JoystickF[C].PovUpRight = false;
+ break;
+ }
+
+ for(int B=0;B<128;B++)
+ if( JoyStatus.rgbButtons[B] )
+ {
+ if( !JoystickF[C].Button[B])
+ {
+ JoystickChanged( C, (short)(8+B));
+ JoystickF[C].Button[B] = true;
+ }
+ }
+ else
+ { JoystickF[C].Button[B] = false; }
+
+
+ }
+ }
+ }
+
+}
+
+
+void FunkyJoyStickTimer()
+{
+ di_poll_scan();
+}
+
+void TranslateKey(WORD keyz,char *out)
+{
+// sprintf(out,"%d",keyz);
+// return;
+
+ char temp[128];
+ if(keyz&0x8000)
+ {
+ sprintf(out,GAMEDEVICE_JOYNUMPREFIX,((keyz>>8)&0xF));
+ switch(keyz&0xFF)
+ {
+ case 0: strcat(out,GAMEDEVICE_XNEG); break;
+ case 1: strcat(out,GAMEDEVICE_XPOS); break;
+ case 2: strcat(out,GAMEDEVICE_YPOS); break;
+ case 3: strcat(out,GAMEDEVICE_YNEG); break;
+ case 4: strcat(out,GAMEDEVICE_POVLEFT); break;
+ case 5: strcat(out,GAMEDEVICE_POVRIGHT); break;
+ case 6: strcat(out,GAMEDEVICE_POVUP); break;
+ case 7: strcat(out,GAMEDEVICE_POVDOWN); break;
+ case 49: strcat(out,GAMEDEVICE_POVDNLEFT); break;
+ case 50: strcat(out,GAMEDEVICE_POVDNRIGHT); break;
+ case 51: strcat(out,GAMEDEVICE_POVUPLEFT); break;
+ case 52: strcat(out,GAMEDEVICE_POVUPRIGHT); break;
+ case 41: strcat(out,GAMEDEVICE_ZPOS); break;
+ case 42: strcat(out,GAMEDEVICE_ZNEG); break;
+ case 43: strcat(out,GAMEDEVICE_RPOS); break;
+ case 44: strcat(out,GAMEDEVICE_RNEG); break;
+ case 45: strcat(out,GAMEDEVICE_UPOS); break;
+ case 46: strcat(out,GAMEDEVICE_UNEG); break;
+ case 47: strcat(out,GAMEDEVICE_VPOS); break;
+ case 48: strcat(out,GAMEDEVICE_VNEG); break;
+ default:
+ if ((keyz & 0xff) > 40)
+ {
+ sprintf(temp,GAMEDEVICE_JOYBUTPREFIX,keyz&0xFF);
+ strcat(out,temp);
+ break;
+ }
+
+ sprintf(temp,GAMEDEVICE_BUTTON,(keyz&0xFF)-8);
+ strcat(out,temp);
+ break;
+
+ }
+ return;
+ }
+ sprintf(out,GAMEDEVICE_KEY,keyz);
+ if((keyz>='0' && keyz<='9')||(keyz>='A' &&keyz<='Z'))
+ {
+ sprintf(out,"%c",keyz);
+ return;
+ }
+
+ if( keyz >= VK_NUMPAD0 && keyz <= VK_NUMPAD9)
+ {
+
+ sprintf(out,GAMEDEVICE_NUMPADPREFIX,'0'+(keyz-VK_NUMPAD0));
+
+ return ;
+ }
+ switch(keyz)
+ {
+ case 0: sprintf(out,GAMEDEVICE_DISABLED); break;
+ case VK_TAB: sprintf(out,GAMEDEVICE_VK_TAB); break;
+ case VK_BACK: sprintf(out,GAMEDEVICE_VK_BACK); break;
+ case VK_CLEAR: sprintf(out,GAMEDEVICE_VK_CLEAR); break;
+ case VK_RETURN: sprintf(out,GAMEDEVICE_VK_RETURN); break;
+ case VK_LSHIFT: sprintf(out,GAMEDEVICE_VK_LSHIFT); break;
+ case VK_RSHIFT: sprintf(out,GAMEDEVICE_VK_RSHIFT); break;
+ case VK_LCONTROL: sprintf(out,GAMEDEVICE_VK_LCONTROL); break;
+ case VK_RCONTROL: sprintf(out,GAMEDEVICE_VK_RCONTROL); break;
+ case VK_LMENU: sprintf(out,GAMEDEVICE_VK_LMENU); break;
+ case VK_RMENU: sprintf(out,GAMEDEVICE_VK_RMENU); break;
+ case VK_PAUSE: sprintf(out,GAMEDEVICE_VK_PAUSE); break;
+ case VK_CANCEL: sprintf(out,GAMEDEVICE_VK_PAUSE); break; // the Pause key can resolve to either "Pause" or "Cancel" depending on when it's pressed
+ case VK_CAPITAL: sprintf(out,GAMEDEVICE_VK_CAPITAL); break;
+ case VK_ESCAPE: sprintf(out,GAMEDEVICE_VK_ESCAPE); break;
+ case VK_SPACE: sprintf(out,GAMEDEVICE_VK_SPACE); break;
+ case VK_PRIOR: sprintf(out,GAMEDEVICE_VK_PRIOR); break;
+ case VK_NEXT: sprintf(out,GAMEDEVICE_VK_NEXT); break;
+ case VK_HOME: sprintf(out,GAMEDEVICE_VK_HOME); break;
+ case VK_END: sprintf(out,GAMEDEVICE_VK_END); break;
+ case VK_LEFT: sprintf(out,GAMEDEVICE_VK_LEFT ); break;
+ case VK_RIGHT: sprintf(out,GAMEDEVICE_VK_RIGHT); break;
+ case VK_UP: sprintf(out,GAMEDEVICE_VK_UP); break;
+ case VK_DOWN: sprintf(out,GAMEDEVICE_VK_DOWN); break;
+ case VK_SELECT: sprintf(out,GAMEDEVICE_VK_SELECT); break;
+ case VK_PRINT: sprintf(out,GAMEDEVICE_VK_PRINT); break;
+ case VK_EXECUTE: sprintf(out,GAMEDEVICE_VK_EXECUTE); break;
+ case VK_SNAPSHOT: sprintf(out,GAMEDEVICE_VK_SNAPSHOT); break;
+ case VK_INSERT: sprintf(out,GAMEDEVICE_VK_INSERT); break;
+ case VK_DELETE: sprintf(out,GAMEDEVICE_VK_DELETE); break;
+ case VK_HELP: sprintf(out,GAMEDEVICE_VK_HELP); break;
+ case VK_LWIN: sprintf(out,GAMEDEVICE_VK_LWIN); break;
+ case VK_RWIN: sprintf(out,GAMEDEVICE_VK_RWIN); break;
+ case VK_APPS: sprintf(out,GAMEDEVICE_VK_APPS); break;
+ case VK_MULTIPLY: sprintf(out,GAMEDEVICE_VK_MULTIPLY); break;
+ case VK_ADD: sprintf(out,GAMEDEVICE_VK_ADD); break;
+ case VK_SEPARATOR: sprintf(out,GAMEDEVICE_VK_SEPARATOR); break;
+ case /*VK_OEM_1*/0xBA: sprintf(out,GAMEDEVICE_VK_OEM_1); break;
+ case /*VK_OEM_2*/0xBF: sprintf(out,GAMEDEVICE_VK_OEM_2); break;
+ case /*VK_OEM_3*/0xC0: sprintf(out,GAMEDEVICE_VK_OEM_3); break;
+ case /*VK_OEM_4*/0xDB: sprintf(out,GAMEDEVICE_VK_OEM_4); break;
+ case /*VK_OEM_5*/0xDC: sprintf(out,GAMEDEVICE_VK_OEM_5); break;
+ case /*VK_OEM_6*/0xDD: sprintf(out,GAMEDEVICE_VK_OEM_6); break;
+ case /*VK_OEM_7*/0xDE: sprintf(out,GAMEDEVICE_VK_OEM_7); break;
+ case /*VK_OEM_COMMA*/0xBC: sprintf(out,GAMEDEVICE_VK_OEM_COMMA );break;
+ case /*VK_OEM_PERIOD*/0xBE: sprintf(out,GAMEDEVICE_VK_OEM_PERIOD);break;
+ case VK_SUBTRACT: sprintf(out,GAMEDEVICE_VK_SUBTRACT); break;
+ case VK_DECIMAL: sprintf(out,GAMEDEVICE_VK_DECIMAL); break;
+ case VK_DIVIDE: sprintf(out,GAMEDEVICE_VK_DIVIDE); break;
+ case VK_NUMLOCK: sprintf(out,GAMEDEVICE_VK_NUMLOCK); break;
+ case VK_SCROLL: sprintf(out,GAMEDEVICE_VK_SCROLL); break;
+ case /*VK_OEM_MINUS*/0xBD: sprintf(out,GAMEDEVICE_VK_OEM_MINUS); break;
+ case /*VK_OEM_PLUS*/0xBB: sprintf(out,GAMEDEVICE_VK_OEM_PLUS); break;
+ case VK_SHIFT: sprintf(out,GAMEDEVICE_VK_SHIFT); break;
+ case VK_CONTROL: sprintf(out,GAMEDEVICE_VK_CONTROL); break;
+ case VK_MENU: sprintf(out,GAMEDEVICE_VK_MENU); break;
+ case VK_F1: sprintf(out,GAMEDEVICE_VK_F1); break;
+ case VK_F2: sprintf(out,GAMEDEVICE_VK_F2); break;
+ case VK_F3: sprintf(out,GAMEDEVICE_VK_F3); break;
+ case VK_F4: sprintf(out,GAMEDEVICE_VK_F4); break;
+ case VK_F5: sprintf(out,GAMEDEVICE_VK_F5); break;
+ case VK_F6: sprintf(out,GAMEDEVICE_VK_F6); break;
+ case VK_F7: sprintf(out,GAMEDEVICE_VK_F7); break;
+ case VK_F8: sprintf(out,GAMEDEVICE_VK_F8); break;
+ case VK_F9: sprintf(out,GAMEDEVICE_VK_F9); break;
+ case VK_F10: sprintf(out,GAMEDEVICE_VK_F10); break;
+ case VK_F11: sprintf(out,GAMEDEVICE_VK_F11); break;
+ case VK_F12: sprintf(out,GAMEDEVICE_VK_F12); break;
+ }
+
+ return ;
+
+
+
+}
+
+bool IsReserved (WORD Key, int modifiers)
+{
+ // keys that do other stuff in Windows
+ if(Key == VK_CAPITAL || Key == VK_NUMLOCK || Key == VK_SCROLL || Key == VK_SNAPSHOT
+ || Key == VK_LWIN || Key == VK_RWIN || Key == VK_APPS || Key == /*VK_SLEEP*/0x5F
+ || (Key == VK_F4 && (modifiers & CUSTKEY_ALT_MASK) != 0)) // alt-f4 (behaves unlike accelerators)
+ return true;
+
+ // menu shortcuts (accelerators) -- TODO: should somehow parse GUI.Accelerators for this information
+ if(modifiers == CUSTKEY_CTRL_MASK
+ && (Key == 'O')
+ || modifiers == CUSTKEY_ALT_MASK
+ && (Key == VK_F5 || Key == VK_F7 || Key == VK_F8 || Key == VK_F9
+ || Key == 'R' || Key == 'T' || Key == /*VK_OEM_4*/0xDB || Key == /*VK_OEM_6*/0xDD
+ || Key == 'E' || Key == 'A' || Key == VK_RETURN || Key == VK_DELETE)
+ || Key == VK_MENU || Key == VK_CONTROL)
+ return true;
+
+ return false;
+}
+
+int GetNumHotKeysAssignedTo (WORD Key, int modifiers)
+{
+ int count = 0;
+ {
+ #define MATCHES_KEY(k) \
+ (Key != 0 && Key != VK_ESCAPE \
+ && ((Key == CustomKeys.k.key && modifiers == CustomKeys.k.modifiers) \
+ || (Key == VK_SHIFT && CustomKeys.k.modifiers & CUSTKEY_SHIFT_MASK) \
+ || (Key == VK_MENU && CustomKeys.k.modifiers & CUSTKEY_ALT_MASK) \
+ || (Key == VK_CONTROL && CustomKeys.k.modifiers & CUSTKEY_CTRL_MASK) \
+ || (CustomKeys.k.key == VK_SHIFT && modifiers & CUSTKEY_SHIFT_MASK) \
+ || (CustomKeys.k.key == VK_MENU && modifiers & CUSTKEY_ALT_MASK) \
+ || (CustomKeys.k.key == VK_CONTROL && modifiers & CUSTKEY_CTRL_MASK)))
+
+ if(MATCHES_KEY(SpeedUp)) count++;
+ if(MATCHES_KEY(SpeedDown)) count++;
+ if(MATCHES_KEY(Pause)) count++;
+ if(MATCHES_KEY(FrameAdvance)) count++;
+ if(MATCHES_KEY(SkipUp)) count++;
+ if(MATCHES_KEY(SkipDown)) count++;
+ if(MATCHES_KEY(ScopeTurbo)) count++;
+ if(MATCHES_KEY(ScopePause)) count++;
+ if(MATCHES_KEY(FrameCount)) count++;
+ if(MATCHES_KEY(ReadOnly)) count++;
+ for(int i = 0 ; i < 10 ; i++) {
+ if(MATCHES_KEY(Save[i])) count++;
+ if(MATCHES_KEY(Load[i])) count++;
+ if(MATCHES_KEY(SelectSave[i])) count++;
+ }
+ if(MATCHES_KEY(FastForward)) count++;
+ if(MATCHES_KEY(ShowPressed)) count++;
+ if(MATCHES_KEY(SaveScreenShot)) count++;
+ if(MATCHES_KEY(SlotPlus)) count++;
+ if(MATCHES_KEY(SlotMinus)) count++;
+ if(MATCHES_KEY(SlotSave)) count++;
+ if(MATCHES_KEY(SlotLoad)) count++;
+ if(MATCHES_KEY(BGL1)) count++;
+ if(MATCHES_KEY(BGL2)) count++;
+ if(MATCHES_KEY(BGL3)) count++;
+ if(MATCHES_KEY(BGL4)) count++;
+ if(MATCHES_KEY(BGL5)) count++;
+ if(MATCHES_KEY(ClippingWindows)) count++;
+// if(MATCHES_KEY(BGLHack)) count++;
+ if(MATCHES_KEY(Transparency)) count++;
+ if(MATCHES_KEY(GLCube)) count++;
+// if(MATCHES_KEY(InterpMode7)) count++;
+ if(MATCHES_KEY(JoypadSwap)) count++;
+ if(MATCHES_KEY(SwitchControllers)) count++;
+ if(MATCHES_KEY(TurboA)) count++;
+ if(MATCHES_KEY(TurboB)) count++;
+ if(MATCHES_KEY(TurboY)) count++;
+ if(MATCHES_KEY(TurboX)) count++;
+ if(MATCHES_KEY(TurboL)) count++;
+ if(MATCHES_KEY(TurboR)) count++;
+ if(MATCHES_KEY(TurboStart)) count++;
+ if(MATCHES_KEY(TurboSelect)) count++;
+ if(MATCHES_KEY(TurboLeft)) count++;
+ if(MATCHES_KEY(TurboUp)) count++;
+ if(MATCHES_KEY(TurboRight)) count++;
+ if(MATCHES_KEY(TurboDown)) count++;
+ if(MATCHES_KEY(ResetGame)) count++;
+ if(MATCHES_KEY(ToggleCheats)) count++;
+ for(int i = 0 ; i < 8 ; i++) {
+ if(MATCHES_KEY(ToggleSound[i])) count++;
+ }
+ for(int i = 0 ; i < 8 ; i++) {
+ if(MATCHES_KEY(ToggleMacro[i])) count++;
+ }
+ if(MATCHES_KEY(EditMacro)) count++;
+
+ #undef MATCHES_KEY
+ }
+ return count;
+}
+
+int GetNumButtonsAssignedTo (WORD Key)
+{
+ int count = 0;
+ for(int J = 0; J < 5*2; J++)
+ {
+ // don't want to report conflicts with disabled keys
+ if(!Joypad[J%5].Enabled || Key == 0 || Key == VK_ESCAPE)
+ continue;
+
+ if(Key == Joypad[J].Left) count++;
+ if(Key == Joypad[J].Right) count++;
+ if(Key == Joypad[J].Left_Up) count++;
+ if(Key == Joypad[J].Left_Down) count++;
+ if(Key == Joypad[J].Right_Up) count++;
+ if(Key == Joypad[J].Right_Down) count++;
+ if(Key == Joypad[J].Up) count++;
+ if(Key == Joypad[J].Down) count++;
+ if(Key == Joypad[J].Start) count++;
+ if(Key == Joypad[J].Select) count++;
+ if(Key == Joypad[J].A) count++;
+ if(Key == Joypad[J].B) count++;
+ if(Key == Joypad[J].X) count++;
+ if(Key == Joypad[J].Y) count++;
+ if(Key == Joypad[J].L) count++;
+ if(Key == Joypad[J].R) count++;
+ if(Key == Joypad[J].Lid) count++;
+ if(Key == Joypad[J].Debug) count++;
+ }
+ return count;
+}
+
+COLORREF CheckButtonKey( WORD Key)
+{
+ COLORREF red,magenta,blue,white;
+ red =RGB(255,0,0);
+ magenta =RGB(255,0,255);
+ blue = RGB(0,0,255);
+ white = RGB(255,255,255);
+
+ // Check for conflict with reserved windows keys
+ if(IsReserved(Key,0))
+ return red;
+
+ // Check for conflict with Snes9X hotkeys
+ if(GetNumHotKeysAssignedTo(Key,0) > 0)
+ return magenta;
+
+ // Check for duplicate button keys
+ if(GetNumButtonsAssignedTo(Key) > 1)
+ return blue;
+
+ return white;
+}
+
+COLORREF CheckHotKey( WORD Key, int modifiers)
+{
+ COLORREF red,magenta,blue,white;
+ red =RGB(255,0,0);
+ magenta =RGB(255,0,255);
+ blue = RGB(0,0,255);
+ white = RGB(255,255,255);
+
+ // Check for conflict with reserved windows keys
+ if(IsReserved(Key,modifiers))
+ return red;
+
+ // Check for conflict with button keys
+ if(modifiers == 0 && GetNumButtonsAssignedTo(Key) > 0)
+ return magenta;
+
+ // Check for duplicate Snes9X hotkeys
+ if(GetNumHotKeysAssignedTo(Key,modifiers) > 1)
+ return blue;
+
+ return white;
+}
+
+void InitInputCustomControl()
+{
+
+ WNDCLASSEX wc;
+
+ wc.cbSize = sizeof(wc);
+ wc.lpszClassName = szClassName;
+ wc.hInstance = GetModuleHandle(0);
+ wc.lpfnWndProc = InputCustomWndProc;
+ wc.hCursor = LoadCursor (NULL, IDC_ARROW);
+ wc.hIcon = 0;
+ wc.lpszMenuName = 0;
+ wc.hbrBackground = (HBRUSH)GetSysColorBrush(COLOR_BTNFACE);
+ wc.style = 0;
+ wc.cbClsExtra = 0;
+ wc.cbWndExtra = sizeof(InputCust *);
+ wc.hIconSm = 0;
+
+
+ RegisterClassEx(&wc);
+
+}
+void InitKeyCustomControl()
+{
+
+ WNDCLASSEX wc;
+
+ wc.cbSize = sizeof(wc);
+ wc.lpszClassName = szHotkeysClassName;
+ wc.hInstance = GetModuleHandle(0);
+ wc.lpfnWndProc = HotInputCustomWndProc;
+ wc.hCursor = LoadCursor (NULL, IDC_ARROW);
+ wc.hIcon = 0;
+ wc.lpszMenuName = 0;
+ wc.hbrBackground = (HBRUSH)GetSysColorBrush(COLOR_BTNFACE);
+ wc.style = 0;
+ wc.cbClsExtra = 0;
+ wc.cbWndExtra = sizeof(InputCust *);
+ wc.hIconSm = 0;
+
+
+ RegisterClassEx(&wc);
+
+}
+//HWND CreateInputCustom(HWND hwndParent)
+//{
+// HWND hwndCtrl;
+//
+// hwndCtrl = CreateWindowEx(
+// WS_EX_CLIENTEDGE, // give it a standard border
+// szClassName,
+// _T("A custom control"),
+// WS_VISIBLE | WS_CHILD,
+// 0, 0, 100, 100,
+// hwndParent,
+// NULL, GetModuleHandle(0), NULL
+// );
+//
+// return hwndCtrl;
+//}
+InputCust * GetInputCustom(HWND hwnd)
+{
+ return (InputCust *)GetWindowLong(hwnd, 0);
+}
+
+void SetInputCustom(HWND hwnd, InputCust *icp)
+{
+ SetWindowLong(hwnd, 0, (LONG)icp);
+}
+
+LRESULT InputCustom_OnPaint(InputCust *ccp, WPARAM wParam, LPARAM lParam)
+{
+ HDC hdc;
+ PAINTSTRUCT ps;
+ HANDLE hOldFont;
+ TCHAR szText[200];
+ RECT rect;
+ SIZE sz;
+ int x,y;
+
+ // Get a device context for this window
+ hdc = BeginPaint(ccp->hwnd, &ps);
+
+ // Set the font we are going to use
+ hOldFont = SelectObject(hdc, ccp->hFont);
+
+ // Set the text colours
+ SetTextColor(hdc, ccp->crForeGnd);
+ SetBkColor (hdc, ccp->crBackGnd);
+
+ // Find the text to draw
+ GetWindowText(ccp->hwnd, szText, sizeof(szText));
+
+ // Work out where to draw
+ GetClientRect(ccp->hwnd, &rect);
+
+
+ // Find out how big the text will be
+ GetTextExtentPoint32(hdc, szText, lstrlen(szText), &sz);
+
+ // Center the text
+ x = (rect.right - sz.cx) / 2;
+ y = (rect.bottom - sz.cy) / 2;
+
+ // Draw the text
+ ExtTextOut(hdc, x, y, ETO_OPAQUE, &rect, szText, lstrlen(szText), 0);
+
+ // Restore the old font when we have finished
+ SelectObject(hdc, hOldFont);
+
+ // Release the device context
+ EndPaint(ccp->hwnd, &ps);
+
+ return 0;
+}
+
+static LRESULT CALLBACK InputCustomWndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
+{
+ // retrieve the custom structure POINTER for THIS window
+ InputCust *icp = GetInputCustom(hwnd);
+ HWND pappy = (HWND__ *)GetWindowLongPtr(hwnd,GWL_HWNDPARENT);
+ funky= hwnd;
+
+ static HWND selectedItem = NULL;
+
+ char temp[100];
+ COLORREF col;
+ switch(msg)
+ {
+
+ case WM_GETDLGCODE:
+ return DLGC_WANTARROWS|DLGC_WANTALLKEYS|DLGC_WANTCHARS;
+ break;
+
+
+ case WM_NCCREATE:
+
+ // Allocate a new CustCtrl structure for this window.
+ icp = (InputCust *) malloc( sizeof(InputCust) );
+
+ // Failed to allocate, stop window creation.
+ if(icp == NULL) return FALSE;
+
+ // Initialize the CustCtrl structure.
+ icp->hwnd = hwnd;
+ icp->crForeGnd = GetSysColor(COLOR_WINDOWTEXT);
+ icp->crBackGnd = GetSysColor(COLOR_WINDOW);
+ icp->hFont = (HFONT__ *) GetStockObject(DEFAULT_GUI_FONT);
+
+ // Assign the window text specified in the call to CreateWindow.
+ SetWindowText(hwnd, ((CREATESTRUCT *)lParam)->lpszName);
+
+ // Attach custom structure to this window.
+ SetInputCustom(hwnd, icp);
+
+ InvalidateRect(icp->hwnd, NULL, FALSE);
+ UpdateWindow(icp->hwnd);
+
+ selectedItem = NULL;
+
+ SetTimer(hwnd,777,125,NULL);
+
+ // Continue with window creation.
+ return TRUE;
+
+ // Clean up when the window is destroyed.
+ case WM_NCDESTROY:
+ free(icp);
+ break;
+ case WM_PAINT:
+ return InputCustom_OnPaint(icp,wParam,lParam);
+ break;
+ case WM_ERASEBKGND:
+ return 1;
+ case WM_USER+45:
+ case WM_KEYDOWN:
+ TranslateKey(wParam,temp);
+ col = CheckButtonKey(wParam);
+
+ icp->crForeGnd = ((~col) & 0x00ffffff);
+ icp->crBackGnd = col;
+ SetWindowText(hwnd,temp);
+ InvalidateRect(icp->hwnd, NULL, FALSE);
+ UpdateWindow(icp->hwnd);
+ SendMessage(pappy,WM_USER+43,wParam,(LPARAM)hwnd);
+
+ break;
+ case WM_USER+44:
+
+ TranslateKey(wParam,temp);
+ if(IsWindowEnabled(hwnd))
+ {
+ col = CheckButtonKey(wParam);
+ }
+ else
+ {
+ col = RGB( 192,192,192);
+ }
+ icp->crForeGnd = ((~col) & 0x00ffffff);
+ icp->crBackGnd = col;
+ SetWindowText(hwnd,temp);
+ InvalidateRect(icp->hwnd, NULL, FALSE);
+ UpdateWindow(icp->hwnd);
+
+ break;
+
+ case WM_SETFOCUS:
+ {
+ selectedItem = hwnd;
+ col = RGB( 0,255,0);
+ icp->crForeGnd = ((~col) & 0x00ffffff);
+ icp->crBackGnd = col;
+ InvalidateRect(icp->hwnd, NULL, FALSE);
+ UpdateWindow(icp->hwnd);
+// tid = wParam;
+
+ break;
+ }
+ case WM_KILLFOCUS:
+ {
+ selectedItem = NULL;
+ SendMessage(pappy,WM_USER+46,wParam,(LPARAM)hwnd); // refresh fields on deselect
+ break;
+ }
+
+ case WM_TIMER:
+ if(hwnd == selectedItem)
+ {
+ FunkyJoyStickTimer();
+ }
+ SetTimer(hwnd,777,125,NULL);
+ break;
+ case WM_LBUTTONDOWN:
+ SetFocus(hwnd);
+ break;
+ case WM_ENABLE:
+ COLORREF col;
+ if(wParam)
+ {
+ col = RGB( 255,255,255);
+ icp->crForeGnd = ((~col) & 0x00ffffff);
+ icp->crBackGnd = col;
+ }
+ else
+ {
+ col = RGB( 192,192,192);
+ icp->crForeGnd = ((~col) & 0x00ffffff);
+ icp->crBackGnd = col;
+ }
+ InvalidateRect(icp->hwnd, NULL, FALSE);
+ UpdateWindow(icp->hwnd);
+ return true;
+ default:
+ break;
+ }
+
+ return DefWindowProc(hwnd, msg, wParam, lParam);
+}
+
+static void TranslateKeyWithModifiers(int wParam, int modifiers, char * outStr)
+{
+
+ // if the key itself is a modifier, special case output:
+ if(wParam == VK_SHIFT)
+ strcpy(outStr, "Shift");
+ else if(wParam == VK_MENU)
+ strcpy(outStr, "Alt");
+ else if(wParam == VK_CONTROL)
+ strcpy(outStr, "Control");
+ else
+ {
+ // otherwise, prepend the modifier(s)
+ if(wParam != VK_ESCAPE && wParam != 0)
+ {
+ if((modifiers & CUSTKEY_CTRL_MASK) != 0)
+ {
+ sprintf(outStr,HOTKEYS_CONTROL_MOD);
+ outStr += strlen(HOTKEYS_CONTROL_MOD);
+ }
+ if((modifiers & CUSTKEY_ALT_MASK) != 0)
+ {
+ sprintf(outStr,HOTKEYS_ALT_MOD);
+ outStr += strlen(HOTKEYS_ALT_MOD);
+ }
+ if((modifiers & CUSTKEY_SHIFT_MASK) != 0)
+ {
+ sprintf(outStr,HOTKEYS_SHIFT_MOD);
+ outStr += strlen(HOTKEYS_SHIFT_MOD);
+ }
+ }
+
+ // and append the translated non-modifier key
+ TranslateKey(wParam,outStr);
+ }
+}
+
+static bool keyPressLock = false;
+
+static LRESULT CALLBACK HotInputCustomWndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
+{
+ // retrieve the custom structure POINTER for THIS window
+ InputCust *icp = GetInputCustom(hwnd);
+ HWND pappy = (HWND__ *)GetWindowLongPtr(hwnd,GWL_HWNDPARENT);
+ funky= hwnd;
+
+ static HWND selectedItem = NULL;
+
+ char temp[100];
+ COLORREF col;
+ switch(msg)
+ {
+
+ case WM_GETDLGCODE:
+ return DLGC_WANTARROWS|DLGC_WANTALLKEYS|DLGC_WANTCHARS;
+ break;
+
+
+ case WM_NCCREATE:
+
+ // Allocate a new CustCtrl structure for this window.
+ icp = (InputCust *) malloc( sizeof(InputCust) );
+
+ // Failed to allocate, stop window creation.
+ if(icp == NULL) return FALSE;
+
+ // Initialize the CustCtrl structure.
+ icp->hwnd = hwnd;
+ icp->crForeGnd = GetSysColor(COLOR_WINDOWTEXT);
+ icp->crBackGnd = GetSysColor(COLOR_WINDOW);
+ icp->hFont = (HFONT__ *) GetStockObject(DEFAULT_GUI_FONT);
+
+ // Assign the window text specified in the call to CreateWindow.
+ SetWindowText(hwnd, ((CREATESTRUCT *)lParam)->lpszName);
+
+ // Attach custom structure to this window.
+ SetInputCustom(hwnd, icp);
+
+ InvalidateRect(icp->hwnd, NULL, FALSE);
+ UpdateWindow(icp->hwnd);
+
+ keyPressLock = false;
+
+ selectedItem = NULL;
+
+ SetTimer(hwnd,747,125,NULL);
+
+ // Continue with window creation.
+ return TRUE;
+
+ // Clean up when the window is destroyed.
+ case WM_NCDESTROY:
+ free(icp);
+ break;
+ case WM_PAINT:
+ return InputCustom_OnPaint(icp,wParam,lParam);
+ break;
+ case WM_ERASEBKGND:
+ return 1;
+/*
+ case WM_KEYUP:
+ {
+ int count = 0;
+ for(int i=0;i<256;i++)
+ if(GetAsyncKeyState(i) & 1)
+ count++;
+
+ if(count < 2)
+ {
+ int p = count;
+ }
+ if(count < 1)
+ {
+ int p = count;
+ }
+
+ TranslateKey(wParam,temp);
+ col = CheckButtonKey(wParam);
+
+ icp->crForeGnd = ((~col) & 0x00ffffff);
+ icp->crBackGnd = col;
+ SetWindowText(hwnd,temp);
+ InvalidateRect(icp->hwnd, NULL, FALSE);
+ UpdateWindow(icp->hwnd);
+ SendMessage(pappy,WM_USER+43,wParam,(LPARAM)hwnd);
+ }
+ break;
+*/
+ case WM_SYSKEYDOWN:
+ case WM_KEYDOWN:
+
+ {
+ int count = 0;
+ for(int i=2;i<256;i++)
+ {
+ if(i >= VK_LSHIFT && i <= VK_RMENU)
+ continue;
+ if(GetAsyncKeyState(i) & 1)
+ count++;
+ }
+
+ if(count <= 1)
+ {
+ keyPressLock = false;
+ }
+ }
+
+ // no break
+
+ case WM_USER+45:
+ // assign a hotkey:
+ {
+ // don't assign pure modifiers on key-down (they're assigned on key-up)
+ if(wParam == VK_SHIFT || wParam == VK_MENU || wParam == VK_CONTROL)
+ break;
+
+ int modifiers = 0;
+ if(GetAsyncKeyState(VK_MENU))
+ modifiers |= CUSTKEY_ALT_MASK;
+ if(GetAsyncKeyState(VK_CONTROL))
+ modifiers |= CUSTKEY_CTRL_MASK;
+ if(GetAsyncKeyState(VK_SHIFT))
+ modifiers |= CUSTKEY_SHIFT_MASK;
+
+ TranslateKeyWithModifiers(wParam, modifiers, temp);
+
+ col = CheckHotKey(wParam,modifiers);
+/// if(col == RGB(255,0,0)) // un-redify
+/// col = RGB(255,255,255);
+
+ icp->crForeGnd = ((~col) & 0x00ffffff);
+ icp->crBackGnd = col;
+ SetWindowText(hwnd,temp);
+ InvalidateRect(icp->hwnd, NULL, FALSE);
+ UpdateWindow(icp->hwnd);
+ SendMessage(pappy,WM_USER+43,wParam,(LPARAM)hwnd);
+
+ keyPressLock = true;
+
+ }
+ break;
+ case WM_SYSKEYUP:
+ case WM_KEYUP:
+ if(!keyPressLock)
+ {
+ int count = 0;
+ for(int i=2;i<256;i++)
+ {
+ if(i >= VK_LSHIFT && i <= VK_RMENU)
+ continue;
+ if(GetAsyncKeyState(i) & 1) // &1 seems to solve an weird non-zero return problem, don't know why
+ count++;
+ }
+ if(count <= 1)
+ {
+ if(wParam == VK_SHIFT || wParam == VK_MENU || wParam == VK_CONTROL)
+ {
+ if(wParam == VK_SHIFT)
+ sprintf(temp, "Shift");
+ if(wParam == VK_MENU)
+ sprintf(temp, "Alt");
+ if(wParam == VK_CONTROL)
+ sprintf(temp, "Control");
+
+ col = CheckHotKey(wParam,0);
+
+ icp->crForeGnd = ((~col) & 0x00ffffff);
+ icp->crBackGnd = col;
+ SetWindowText(hwnd,temp);
+ InvalidateRect(icp->hwnd, NULL, FALSE);
+ UpdateWindow(icp->hwnd);
+ SendMessage(pappy,WM_USER+43,wParam,(LPARAM)hwnd);
+ }
+ }
+ }
+ break;
+ case WM_USER+44:
+
+ // set a hotkey field:
+ {
+ int modifiers = lParam;
+
+ TranslateKeyWithModifiers(wParam, modifiers, temp);
+
+ if(IsWindowEnabled(hwnd))
+ {
+ col = CheckHotKey(wParam,modifiers);
+/// if(col == RGB(255,0,0)) // un-redify
+/// col = RGB(255,255,255);
+ }
+ else
+ {
+ col = RGB( 192,192,192);
+ }
+ icp->crForeGnd = ((~col) & 0x00ffffff);
+ icp->crBackGnd = col;
+ SetWindowText(hwnd,temp);
+ InvalidateRect(icp->hwnd, NULL, FALSE);
+ UpdateWindow(icp->hwnd);
+ }
+ break;
+
+ case WM_SETFOCUS:
+ {
+ selectedItem = hwnd;
+ col = RGB( 0,255,0);
+ icp->crForeGnd = ((~col) & 0x00ffffff);
+ icp->crBackGnd = col;
+ InvalidateRect(icp->hwnd, NULL, FALSE);
+ UpdateWindow(icp->hwnd);
+// tid = wParam;
+
+ break;
+ }
+ case WM_KILLFOCUS:
+ {
+ selectedItem = NULL;
+ SendMessage(pappy,WM_USER+46,wParam,(LPARAM)hwnd); // refresh fields on deselect
+ break;
+ }
+
+ case WM_TIMER:
+ if(hwnd == selectedItem)
+ {
+ //FunkyJoyStickTimer();
+ }
+ SetTimer(hwnd,747,125,NULL);
+ break;
+ case WM_LBUTTONDOWN:
+ SetFocus(hwnd);
+ break;
+ case WM_ENABLE:
+ COLORREF col;
+ if(wParam)
+ {
+ col = RGB( 255,255,255);
+ icp->crForeGnd = ((~col) & 0x00ffffff);
+ icp->crBackGnd = col;
+ }
+ else
+ {
+ col = RGB( 192,192,192);
+ icp->crForeGnd = ((~col) & 0x00ffffff);
+ icp->crBackGnd = col;
+ }
+ InvalidateRect(icp->hwnd, NULL, FALSE);
+ UpdateWindow(icp->hwnd);
+ return true;
+ default:
+ break;
+ }
+
+ return DefWindowProc(hwnd, msg, wParam, lParam);
+}
+
+static void set_buttoninfo(int index, HWND hDlg)
+{
+ SendDlgItemMessage(hDlg,IDC_UP,WM_USER+44,Joypad[index].Up,0);
+ SendDlgItemMessage(hDlg,IDC_LEFT,WM_USER+44,Joypad[index].Left,0);
+ SendDlgItemMessage(hDlg,IDC_DOWN,WM_USER+44,Joypad[index].Down,0);
+ SendDlgItemMessage(hDlg,IDC_RIGHT,WM_USER+44,Joypad[index].Right,0);
+ SendDlgItemMessage(hDlg,IDC_A,WM_USER+44,Joypad[index].A,0);
+ SendDlgItemMessage(hDlg,IDC_B,WM_USER+44,Joypad[index].B,0);
+ SendDlgItemMessage(hDlg,IDC_X,WM_USER+44,Joypad[index].X,0);
+ SendDlgItemMessage(hDlg,IDC_Y,WM_USER+44,Joypad[index].Y,0);
+ SendDlgItemMessage(hDlg,IDC_L,WM_USER+44,Joypad[index].L,0);
+ SendDlgItemMessage(hDlg,IDC_R,WM_USER+44,Joypad[index].R,0);
+ SendDlgItemMessage(hDlg,IDC_START,WM_USER+44,Joypad[index].Start,0);
+ SendDlgItemMessage(hDlg,IDC_SELECT,WM_USER+44,Joypad[index].Select,0);
+ SendDlgItemMessage(hDlg,IDC_LID,WM_USER+44,Joypad[index].Lid,0);
+ SendDlgItemMessage(hDlg,IDC_DEBUG,WM_USER+44,Joypad[index].Debug,0);
+ if(index < 5)
+ {
+ SendDlgItemMessage(hDlg,IDC_UPLEFT,WM_USER+44,Joypad[index].Left_Up,0);
+ SendDlgItemMessage(hDlg,IDC_UPRIGHT,WM_USER+44,Joypad[index].Right_Up,0);
+ SendDlgItemMessage(hDlg,IDC_DWNLEFT,WM_USER+44,Joypad[index].Left_Down,0);
+ SendDlgItemMessage(hDlg,IDC_DWNRIGHT,WM_USER+44,Joypad[index].Right_Down,0);
+ }
+}
+
+void EnableDisableKeyFields (int index, HWND hDlg)
+{
+ bool enableUnTurboable;
+ if(index < 5)
+ {
+ SetDlgItemText(hDlg,IDC_LABEL_RIGHT,INPUTCONFIG_LABEL_RIGHT);
+ SetDlgItemText(hDlg,IDC_LABEL_UPLEFT,INPUTCONFIG_LABEL_UPLEFT);
+ SetDlgItemText(hDlg,IDC_LABEL_UPRIGHT,INPUTCONFIG_LABEL_UPRIGHT);
+ SetDlgItemText(hDlg,IDC_LABEL_DOWNRIGHT,INPUTCONFIG_LABEL_DOWNRIGHT);
+ SetDlgItemText(hDlg,IDC_LABEL_UP,INPUTCONFIG_LABEL_UP);
+ SetDlgItemText(hDlg,IDC_LABEL_LEFT,INPUTCONFIG_LABEL_LEFT);
+ SetDlgItemText(hDlg,IDC_LABEL_DOWN,INPUTCONFIG_LABEL_DOWN);
+ SetDlgItemText(hDlg,IDC_LABEL_DOWNLEFT,INPUTCONFIG_LABEL_DOWNLEFT);
+ enableUnTurboable = true;
+ }
+ else
+ {
+ SetDlgItemText(hDlg,IDC_LABEL_UP,INPUTCONFIG_LABEL_MAKE_TURBO);
+ SetDlgItemText(hDlg,IDC_LABEL_LEFT,INPUTCONFIG_LABEL_MAKE_HELD);
+ SetDlgItemText(hDlg,IDC_LABEL_DOWN,INPUTCONFIG_LABEL_MAKE_TURBO_HELD);
+ SetDlgItemText(hDlg,IDC_LABEL_RIGHT,INPUTCONFIG_LABEL_CLEAR_TOGGLES_AND_TURBO);
+ SetDlgItemText(hDlg,IDC_LABEL_UPLEFT,INPUTCONFIG_LABEL_UNUSED);
+ SetDlgItemText(hDlg,IDC_LABEL_UPRIGHT,INPUTCONFIG_LABEL_UNUSED);
+ SetDlgItemText(hDlg,IDC_LABEL_DOWNLEFT,INPUTCONFIG_LABEL_UNUSED);
+ SetDlgItemText(hDlg,IDC_LABEL_DOWNRIGHT,INPUTCONFIG_LABEL_UNUSED);
+ SetDlgItemText(hDlg,IDC_UPLEFT,INPUTCONFIG_LABEL_UNUSED);
+ SetDlgItemText(hDlg,IDC_UPRIGHT,INPUTCONFIG_LABEL_UNUSED);
+ SetDlgItemText(hDlg,IDC_DWNLEFT,INPUTCONFIG_LABEL_UNUSED);
+ SetDlgItemText(hDlg,IDC_DWNRIGHT,INPUTCONFIG_LABEL_UNUSED);
+ enableUnTurboable = false;
+ }
+
+ EnableWindow(GetDlgItem(hDlg,IDC_UPLEFT), false);
+ EnableWindow(GetDlgItem(hDlg,IDC_UPRIGHT), false);
+ EnableWindow(GetDlgItem(hDlg,IDC_DWNRIGHT), false);
+ EnableWindow(GetDlgItem(hDlg,IDC_DWNLEFT), false);
+ EnableWindow(GetDlgItem(hDlg,IDC_DEBUG), false);
+ EnableWindow(GetDlgItem(hDlg,IDC_LID), false);
+}
+
+INT_PTR CALLBACK DlgInputConfig(HWND hDlg, UINT msg, WPARAM wParam, LPARAM lParam)
+{
+ char temp[256];
+ short C;
+ int i, which;
+ static int index=0;
+
+
+ static SJoypad savepad[10];
+
+
+ //HBRUSH g_hbrBackground;
+
+ InitInputCustomControl();
+switch(msg)
+ {
+ case WM_INITDIALOG:
+ //if(DirectX.Clipped) S9xReRefresh();
+ SetWindowText(hDlg,INPUTCONFIG_TITLE);
+ //SetDlgItemText(hDlg,IDC_JPTOGGLE,INPUTCONFIG_JPTOGGLE);
+ SetDlgItemText(hDlg,IDOK,BUTTON_OK);
+ SetDlgItemText(hDlg,IDCANCEL,BUTTON_CANCEL);
+/// SetDlgItemText(hDlg,IDC_DIAGTOGGLE,INPUTCONFIG_DIAGTOGGLE);
+ SetDlgItemText(hDlg,IDC_LABEL_UP,INPUTCONFIG_LABEL_UP);
+ SetDlgItemText(hDlg,IDC_LABEL_DOWN,INPUTCONFIG_LABEL_DOWN);
+ SetDlgItemText(hDlg,IDC_LABEL_LEFT,INPUTCONFIG_LABEL_LEFT);
+ SetDlgItemText(hDlg,IDC_LABEL_A,INPUTCONFIG_LABEL_A);
+ SetDlgItemText(hDlg,IDC_LABEL_B,INPUTCONFIG_LABEL_B);
+ SetDlgItemText(hDlg,IDC_LABEL_X,INPUTCONFIG_LABEL_X);
+ SetDlgItemText(hDlg,IDC_LABEL_Y,INPUTCONFIG_LABEL_Y);
+ SetDlgItemText(hDlg,IDC_LABEL_L,INPUTCONFIG_LABEL_L);
+ SetDlgItemText(hDlg,IDC_LABEL_R,INPUTCONFIG_LABEL_R);
+ SetDlgItemText(hDlg,IDC_LABEL_START,INPUTCONFIG_LABEL_START);
+ SetDlgItemText(hDlg,IDC_LABEL_SELECT,INPUTCONFIG_LABEL_SELECT);
+ SetDlgItemText(hDlg,IDC_LABEL_UPRIGHT,INPUTCONFIG_LABEL_UPRIGHT);
+ SetDlgItemText(hDlg,IDC_LABEL_UPLEFT,INPUTCONFIG_LABEL_UPLEFT);
+ SetDlgItemText(hDlg,IDC_LABEL_DOWNRIGHT,INPUTCONFIG_LABEL_DOWNRIGHT);
+ SetDlgItemText(hDlg,IDC_LABEL_DOWNLEFT,INPUTCONFIG_LABEL_DOWNLEFT);
+ SetDlgItemText(hDlg,IDC_LABEL_BLUE,INPUTCONFIG_LABEL_BLUE);
+
+ for(i=5;i<10;i++)
+ Joypad[i].Left_Up = Joypad[i].Right_Up = Joypad[i].Left_Down = Joypad[i].Right_Down = 0;
+
+ memcpy(savepad, Joypad, 10*sizeof(SJoypad));
+
+ for( i=0;i<256;i++)
+ GetAsyncKeyState(i);
+
+ //for( C = 0; C != 16; C ++)
+ // JoystickF[C].Attached = joyGetDevCaps( JOYSTICKID1+C, &JoystickF[C].Caps, sizeof( JOYCAPS)) == JOYERR_NOERROR;
+
+ memset(&JoystickF[0],0,sizeof(JoystickF[0]));
+ JoystickF[0].Attached = pJoystick != NULL;
+
+
+ //for(i=1;i<6;i++)
+ //{
+ // sprintf(temp,INPUTCONFIG_JPCOMBO,i);
+ // SendDlgItemMessage(hDlg,IDC_JPCOMBO,CB_ADDSTRING,0,(LPARAM)(LPCTSTR)temp);
+ //}
+
+ //for(i=6;i<11;i++)
+ //{
+ // sprintf(temp,INPUTCONFIG_JPCOMBO INPUTCONFIG_LABEL_CONTROLLER_TURBO_PANEL_MOD,i-5);
+ // SendDlgItemMessage(hDlg,IDC_JPCOMBO,CB_ADDSTRING,0,(LPARAM)(LPCTSTR)temp);
+ //}
+
+ //SendDlgItemMessage(hDlg,IDC_JPCOMBO,CB_SETCURSEL,(WPARAM)0,0);
+
+ //SendDlgItemMessage(hDlg,IDC_JPTOGGLE,BM_SETCHECK, Joypad[index].Enabled ? (WPARAM)BST_CHECKED : (WPARAM)BST_UNCHECKED, 0);
+ //SendDlgItemMessage(hDlg,IDC_ALLOWLEFTRIGHT,BM_SETCHECK, Settings.UpAndDown ? (WPARAM)BST_CHECKED : (WPARAM)BST_UNCHECKED, 0);
+
+ set_buttoninfo(index,hDlg);
+
+ EnableDisableKeyFields(index,hDlg);
+
+ //PostMessage(hDlg,WM_COMMAND, CBN_SELCHANGE<<16, 0);
+
+ //SetFocus(GetDlgItem(hDlg,IDC_JPCOMBO));
+
+ return true;
+ break;
+ case WM_CLOSE:
+ EndDialog(hDlg, 0);
+ return TRUE;
+ case WM_USER+46:
+ // refresh command, for clicking away from a selected field
+ //index = SendDlgItemMessage(hDlg,IDC_JPCOMBO,CB_GETCURSEL,0,0);
+ //if(index > 4) index += 3; // skip controllers 6, 7, and 8 in the input dialog
+ set_buttoninfo(index,hDlg);
+ return TRUE;
+ case WM_USER+43:
+ //MessageBox(hDlg,"USER+43 CAUGHT","moo",MB_OK);
+ which = GetDlgCtrlID((HWND)lParam);
+ switch(which)
+ {
+ case IDC_UP:
+ Joypad[index].Up = wParam;
+
+ break;
+ case IDC_DOWN:
+ Joypad[index].Down = wParam;
+
+ break;
+ case IDC_LEFT:
+ Joypad[index].Left = wParam;
+
+ break;
+ case IDC_RIGHT:
+ Joypad[index].Right = wParam;
+
+ break;
+ case IDC_A:
+ Joypad[index].A = wParam;
+
+ break;
+ case IDC_B:
+ Joypad[index].B = wParam;
+
+ break;
+ case IDC_X:
+ Joypad[index].X = wParam;
+
+ break;
+ case IDC_Y:
+ Joypad[index].Y = wParam;
+
+ break;
+ case IDC_L:
+ Joypad[index].L = wParam;
+ break;
+
+ case IDC_R:
+ Joypad[index].R = wParam;
+
+ break;
+ case IDC_SELECT:
+ Joypad[index].Select = wParam;
+
+ break;
+ case IDC_START:
+ Joypad[index].Start = wParam;
+
+ break;
+ case IDC_UPLEFT:
+ Joypad[index].Left_Up = wParam;
+
+ break;
+ case IDC_UPRIGHT:
+ Joypad[index].Right_Up = wParam;
+
+ break;
+ case IDC_DWNLEFT:
+ Joypad[index].Left_Down = wParam;
+
+ break;
+ case IDC_DWNRIGHT:
+ Joypad[index].Right_Down = wParam;
+
+ case IDC_LID:
+ Joypad[index].Lid = wParam;
+
+ case IDC_DEBUG:
+ Joypad[index].Debug = wParam;
+
+ break;
+
+ }
+
+ set_buttoninfo(index,hDlg);
+
+ PostMessage(hDlg,WM_NEXTDLGCTL,0,0);
+ return true;
+ case WM_COMMAND:
+ switch(LOWORD(wParam))
+ {
+ case IDCANCEL:
+ memcpy(Joypad, savepad, 10*sizeof(SJoypad));
+ EndDialog(hDlg,0);
+ break;
+
+ case IDOK:
+ //Settings.UpAndDown = IsDlgButtonChecked(hDlg, IDC_ALLOWLEFTRIGHT);
+ //WinSaveConfigFile(); //TODO
+ SaveConfig();
+ EndDialog(hDlg,0);
+ break;
+
+ //case IDC_JPTOGGLE: // joypad Enable toggle
+ // index = SendDlgItemMessage(hDlg,IDC_JPCOMBO,CB_GETCURSEL,0,0);
+ // if(index > 4) index += 3; // skip controllers 6, 7, and 8 in the input dialog
+ // Joypad[index].Enabled=IsDlgButtonChecked(hDlg,IDC_JPTOGGLE);
+ // set_buttoninfo(index, hDlg); // update display of conflicts
+ // break;
+
+ }
+ switch(HIWORD(wParam))
+ {
+ //case CBN_SELCHANGE:
+ // index = SendDlgItemMessage(hDlg,IDC_JPCOMBO,CB_GETCURSEL,0,0);
+ // SendDlgItemMessage(hDlg,IDC_JPCOMBO,CB_SETCURSEL,(WPARAM)index,0);
+ // if(index > 4) index += 3; // skip controllers 6, 7, and 8 in the input dialog
+ // if(index < 8)
+ // {
+ // SendDlgItemMessage(hDlg,IDC_JPTOGGLE,BM_SETCHECK, Joypad[index].Enabled ? (WPARAM)BST_CHECKED : (WPARAM)BST_UNCHECKED, 0);
+ // EnableWindow(GetDlgItem(hDlg,IDC_JPTOGGLE),TRUE);
+ // }
+ // else
+ // {
+ // SendDlgItemMessage(hDlg,IDC_JPTOGGLE,BM_SETCHECK, Joypad[index-8].Enabled ? (WPARAM)BST_CHECKED : (WPARAM)BST_UNCHECKED, 0);
+ // EnableWindow(GetDlgItem(hDlg,IDC_JPTOGGLE),FALSE);
+ // }
+
+ // set_buttoninfo(index,hDlg);
+
+ // EnableDisableKeyFields(index,hDlg);
+
+ // break;
+ }
+ return FALSE;
+
+ }
+
+ return FALSE;
+}
+
-void INPUTCLASS::JoystickFeedback(BOOL on)
+bool S9xGetState (WORD KeyIdent)
+{
+ if(KeyIdent == 0 || KeyIdent == VK_ESCAPE) // if it's the 'disabled' key, it's never pressed
+ return true;
+
+ //if(!GUI.BackgroundKeyGamekeys && GUI.hWnd != GetForegroundWindow())
+ // return true;
+
+ if (KeyIdent & 0x8000) // if it's a joystick 'key':
+ {
+ int j = (KeyIdent >> 8) & 15;
+
+ //S9xUpdateJoyState();
+
+ switch (KeyIdent & 0xff)
+ {
+ case 0: return !Joystick [j].Left;
+ case 1: return !Joystick [j].Right;
+ case 2: return !Joystick [j].Up;
+ case 3: return !Joystick [j].Down;
+ case 4: return !Joystick [j].PovLeft;
+ case 5: return !Joystick [j].PovRight;
+ case 6: return !Joystick [j].PovUp;
+ case 7: return !Joystick [j].PovDown;
+ case 49:return !Joystick [j].PovDnLeft;
+ case 50:return !Joystick [j].PovDnRight;
+ case 51:return !Joystick [j].PovUpLeft;
+ case 52:return !Joystick [j].PovUpRight;
+ case 41:return !Joystick [j].ZUp;
+ case 42:return !Joystick [j].ZDown;
+ case 43:return !Joystick [j].RUp;
+ case 44:return !Joystick [j].RDown;
+ case 45:return !Joystick [j].UUp;
+ case 46:return !Joystick [j].UDown;
+ case 47:return !Joystick [j].VUp;
+ case 48:return !Joystick [j].VDown;
+
+ default:
+ if ((KeyIdent & 0xff) > 40)
+ return true; // not pressed
+
+ return !Joystick [j].Button [(KeyIdent & 0xff) - 8];
+ }
+ }
+
+ // the pause key is special, need this to catch all presses of it
+ // Both GetKeyState and GetAsyncKeyState cannot catch it anyway,
+ // so this should be handled in WM_KEYDOWN message.
+ if(KeyIdent == VK_PAUSE)
+ {
+ return true; // not pressed
+// if(GetAsyncKeyState(VK_PAUSE)) // not &'ing this with 0x8000 is intentional and necessary
+// return false;
+ }
+
+ SHORT gks = GetKeyState (KeyIdent);
+ return ((gks & 0x80) == 0);
+}
+
+void S9xWinScanJoypads ()
+{
+ u32 PadState;
+
+ S9xUpdateJoyState();
+
+ for (int J = 0; J < 8; J++)
+ {
+ if (Joypad [J].Enabled)
+ {
+ // toggle checks
+ {
+ PadState = 0;
+ PadState |= ToggleJoypadStorage[J].Left||TurboToggleJoypadStorage[J].Left ? LEFT_MASK : 0;
+ PadState |= ToggleJoypadStorage[J].Right||TurboToggleJoypadStorage[J].Right ? RIGHT_MASK : 0;
+ PadState |= ToggleJoypadStorage[J].Up||TurboToggleJoypadStorage[J].Up ? UP_MASK : 0;
+ PadState |= ToggleJoypadStorage[J].Down||TurboToggleJoypadStorage[J].Down ? DOWN_MASK : 0;
+ PadState |= ToggleJoypadStorage[J].Start||TurboToggleJoypadStorage[J].Start ? START_MASK : 0;
+ PadState |= ToggleJoypadStorage[J].Select||TurboToggleJoypadStorage[J].Select ? SELECT_MASK : 0;
+ PadState |= ToggleJoypadStorage[J].Lid||TurboToggleJoypadStorage[J].Lid ? LID_MASK : 0;
+ PadState |= ToggleJoypadStorage[J].Debug||TurboToggleJoypadStorage[J].Debug ? DEBUG_MASK : 0;
+ PadState |= ToggleJoypadStorage[J].A||TurboToggleJoypadStorage[J].A ? A_MASK : 0;
+ PadState |= ToggleJoypadStorage[J].B||TurboToggleJoypadStorage[J].B ? B_MASK : 0;
+ PadState |= ToggleJoypadStorage[J].X||TurboToggleJoypadStorage[J].X ? X_MASK : 0;
+ PadState |= ToggleJoypadStorage[J].Y||TurboToggleJoypadStorage[J].Y ? Y_MASK : 0;
+ PadState |= ToggleJoypadStorage[J].L||TurboToggleJoypadStorage[J].L ? L_MASK : 0;
+ PadState |= ToggleJoypadStorage[J].R||TurboToggleJoypadStorage[J].R ? R_MASK : 0;
+ }
+ // auto-hold AND regular key/joystick presses
+ if(S9xGetState(Joypad[J+8].Left))
+ {
+ if(!S9xGetState(Joypad[J].Start))
+ {
+ int zzz=9;
+ }
+ PadState ^= (!S9xGetState(Joypad[J].R)||!S9xGetState(Joypad[J+8].R)) ? R_MASK : 0;
+ PadState ^= (!S9xGetState(Joypad[J].L)||!S9xGetState(Joypad[J+8].L)) ? L_MASK : 0;
+ PadState ^= (!S9xGetState(Joypad[J].X)||!S9xGetState(Joypad[J+8].X)) ? X_MASK : 0;
+ PadState ^= (!S9xGetState(Joypad[J].A)||!S9xGetState(Joypad[J+8].A)) ? A_MASK : 0;
+ PadState ^= (!S9xGetState(Joypad[J].Right)) ? RIGHT_MASK : 0;
+ PadState ^= (!S9xGetState(Joypad[J].Right_Up)) ? RIGHT_MASK + UP_MASK : 0;
+ PadState ^= (!S9xGetState(Joypad[J].Right_Down)) ? RIGHT_MASK + DOWN_MASK : 0;
+ PadState ^= (!S9xGetState(Joypad[J].Left)) ? LEFT_MASK : 0;
+ PadState ^= (!S9xGetState(Joypad[J].Left_Up)) ? LEFT_MASK + UP_MASK : 0;
+ PadState ^= (!S9xGetState(Joypad[J].Left_Down)) ? LEFT_MASK + DOWN_MASK : 0;
+ PadState ^= (!S9xGetState(Joypad[J].Down)) ? DOWN_MASK : 0;
+ PadState ^= (!S9xGetState(Joypad[J].Up)) ? UP_MASK : 0;
+ PadState ^= (!S9xGetState(Joypad[J].Start)||!S9xGetState(Joypad[J+8].Start)) ? START_MASK : 0;
+ PadState ^= (!S9xGetState(Joypad[J].Select)||!S9xGetState(Joypad[J+8].Select)) ? SELECT_MASK : 0;
+ PadState ^= (!S9xGetState(Joypad[J].Y)||!S9xGetState(Joypad[J+8].Y)) ? Y_MASK : 0;
+ PadState ^= (!S9xGetState(Joypad[J].B)||!S9xGetState(Joypad[J+8].B)) ? B_MASK : 0;
+ PadState ^= (!S9xGetState(Joypad[J].Lid)||!S9xGetState(Joypad[J+8].Lid)) ? LID_MASK : 0;
+ PadState ^= (!S9xGetState(Joypad[J].Debug)||!S9xGetState(Joypad[J+8].Debug)) ? DEBUG_MASK : 0;
+ }
+
+ bool turbofy = !S9xGetState(Joypad[J+8].Up); // All Mod for turbo
+
+ u32 TurboMask = 0;
+
+ //handle turbo case! (autofire / auto-fire)
+ if(turbofy || ((TurboMask&A_MASK))&&(PadState&A_MASK) || !S9xGetState(Joypad[J+8].A )) PadState^=(joypads[J]&A_MASK);
+ if(turbofy || ((TurboMask&B_MASK))&&(PadState&B_MASK) || !S9xGetState(Joypad[J+8].B )) PadState^=(joypads[J]&B_MASK);
+ if(turbofy || ((TurboMask&Y_MASK))&&(PadState&Y_MASK) || !S9xGetState(Joypad[J+8].Y )) PadState^=(joypads[J]&Y_MASK);
+ if(turbofy || ((TurboMask&X_MASK))&&(PadState&X_MASK) || !S9xGetState(Joypad[J+8].X )) PadState^=(joypads[J]&X_MASK);
+ if(turbofy || ((TurboMask&L_MASK))&&(PadState&L_MASK) || !S9xGetState(Joypad[J+8].L )) PadState^=(joypads[J]&L_MASK);
+ if(turbofy || ((TurboMask&R_MASK))&&(PadState&R_MASK) || !S9xGetState(Joypad[J+8].R )) PadState^=(joypads[J]&R_MASK);
+ if(turbofy || ((TurboMask&START_MASK))&&(PadState&START_MASK) || !S9xGetState(Joypad[J+8].Start )) PadState^=(joypads[J]&START_MASK);
+ if(turbofy || ((TurboMask&SELECT_MASK))&&(PadState&SELECT_MASK) || !S9xGetState(Joypad[J+8].Select)) PadState^=(joypads[J]&SELECT_MASK);
+ if(turbofy || ((TurboMask&DEBUG_MASK))&&(PadState&DEBUG_MASK) || !S9xGetState(Joypad[J+8].Debug)) PadState^=(joypads[J]&DEBUG_MASK);
+ if( ((TurboMask&LEFT_MASK))&&(PadState&LEFT_MASK) ) PadState^=(joypads[J]&LEFT_MASK);
+ if( ((TurboMask&UP_MASK))&&(PadState&UP_MASK) ) PadState^=(joypads[J]&UP_MASK);
+ if( ((TurboMask&RIGHT_MASK))&&(PadState&RIGHT_MASK) ) PadState^=(joypads[J]&RIGHT_MASK);
+ if( ((TurboMask&DOWN_MASK))&&(PadState&DOWN_MASK) ) PadState^=(joypads[J]&DOWN_MASK);
+ if( ((TurboMask&LID_MASK))&&(PadState&LID_MASK) ) PadState^=(joypads[J]&LID_MASK);
+
+ if(TurboToggleJoypadStorage[J].A ) PadState^=(joypads[J]&A_MASK);
+ if(TurboToggleJoypadStorage[J].B ) PadState^=(joypads[J]&B_MASK);
+ if(TurboToggleJoypadStorage[J].Y ) PadState^=(joypads[J]&Y_MASK);
+ if(TurboToggleJoypadStorage[J].X ) PadState^=(joypads[J]&X_MASK);
+ if(TurboToggleJoypadStorage[J].L ) PadState^=(joypads[J]&L_MASK);
+ if(TurboToggleJoypadStorage[J].R ) PadState^=(joypads[J]&R_MASK);
+ if(TurboToggleJoypadStorage[J].Start ) PadState^=(joypads[J]&START_MASK);
+ if(TurboToggleJoypadStorage[J].Select) PadState^=(joypads[J]&SELECT_MASK);
+ if(TurboToggleJoypadStorage[J].Left ) PadState^=(joypads[J]&LEFT_MASK);
+ if(TurboToggleJoypadStorage[J].Up ) PadState^=(joypads[J]&UP_MASK);
+ if(TurboToggleJoypadStorage[J].Right ) PadState^=(joypads[J]&RIGHT_MASK);
+ if(TurboToggleJoypadStorage[J].Down ) PadState^=(joypads[J]&DOWN_MASK);
+ if(TurboToggleJoypadStorage[J].Lid ) PadState^=(joypads[J]&LID_MASK);
+ if(TurboToggleJoypadStorage[J].Debug ) PadState^=(joypads[J]&DEBUG_MASK);
+ //end turbo case...
+
+
+ // enforce left+right/up+down disallowance here to
+ // avoid recording unused l+r/u+d that will cause desyncs
+ // when played back with l+r/u+d is allowed
+ //if(!Settings.UpAndDown)
+ //{
+ // if((PadState[1] & 2) != 0)
+ // PadState[1] &= ~(1);
+ // if((PadState[1] & 8) != 0)
+ // PadState[1] &= ~(4);
+ //}
+
+ joypads [J] = PadState | 0x80000000;
+ }
+ else
+ joypads [J] = 0;
+ }
+
+ // input from macro
+ //for (int J = 0; J < 8; J++)
+ //{
+ // if(MacroIsEnabled(J))
+ // {
+ // uint16 userPadState = joypads[J] & 0xFFFF;
+ // uint16 macroPadState = MacroInput(J);
+ // uint16 newPadState;
+
+ // switch(GUI.MacroInputMode)
+ // {
+ // case MACRO_INPUT_MOV:
+ // newPadState = macroPadState;
+ // break;
+ // case MACRO_INPUT_OR:
+ // newPadState = macroPadState | userPadState;
+ // break;
+ // case MACRO_INPUT_XOR:
+ // newPadState = macroPadState ^ userPadState;
+ // break;
+ // default:
+ // newPadState = userPadState;
+ // break;
+ // }
+
+ // PadState[0] = (uint8) ( newPadState & 0xFF);
+ // PadState[1] = (uint8) ((newPadState >> 8) & 0xFF);
+
+ // // enforce left+right/up+down disallowance here to
+ // // avoid recording unused l+r/u+d that will cause desyncs
+ // // when played back with l+r/u+d is allowed
+ // if(!Settings.UpAndDown)
+ // {
+ // if((PadState[1] & 2) != 0)
+ // PadState[1] &= ~(1);
+ // if((PadState[1] & 8) != 0)
+ // PadState[1] &= ~(4);
+ // }
+
+ // joypads [J] = PadState [0] | (PadState [1] << 8) | 0x80000000;
+ // }
+ //}
+
+//#ifdef NETPLAY_SUPPORT
+// if (Settings.NetPlay)
+// {
+// // Send joypad position update to server
+// S9xNPSendJoypadUpdate (joypads [GUI.NetplayUseJoypad1 ? 0 : NetPlay.Player-1]);
+//
+// // set input from network
+// for (int J = 0; J < NP_MAX_CLIENTS; J++)
+// joypads[J] = S9xNPGetJoypad (J);
+// }
+//#endif
+}
+
+//void NDS_inputInit()
+//{
+// int i;
+// memset(keyPad, 0, sizeof(keyPad));
+//
+// for (i=0; i < MAXKEYPAD; i++)
+// {
+// char buf[64];
+// memset(buf, 0, sizeof(buf));
+// wsprintf(buf,"Key_%s", keyPadNames[i]);
+// keyPad[i] = GetPrivateProfileInt("NDS_Input",buf,keyPadDefs[i], IniName);
+// if (keyPad[i]>255)
+// {
+// if (!input->JoystickEnabled())
+// {
+// keyPad[i] = keyPadDefs[i];
+// }
+// }
+// }
+//
+// FeedbackON = NDS_inputFeedback;
+//}
+
+void input_feedback(BOOL enable)
{
- if (!Feedback) return;
- if (!pEffect) return;
+ //input->JoystickFeedback(enable);
+}
+
+
+void input_init()
+{
+ di_init();
+ FeedbackON = input_feedback;
+}
+
+void input_process()
+{
+ S9xWinScanJoypads();
+
+ if (paused) return;
- if (on)
- pEffect->Start(2, 0);
- else
- pEffect->Stop();
-}
-// ==================================================== END INPUTCLASS
+ bool R = joypads[0] & RIGHT_MASK;
+ bool L = joypads[0] & LEFT_MASK;
+ bool D = joypads[0] & DOWN_MASK;
+ bool U = joypads[0] & UP_MASK;
+ bool T = joypads[0] & START_MASK;
+ bool S = joypads[0] & SELECT_MASK;
+ bool B = joypads[0] & B_MASK;
+ bool A = joypads[0] & A_MASK;
+ bool Y = joypads[0] & Y_MASK;
+ bool X = joypads[0] & X_MASK;
+ bool W = joypads[0] & L_MASK;
+ bool E = joypads[0] & R_MASK;
+ bool G = joypads[0] & DEBUG_MASK;
+ bool F = joypads[0] & LID_MASK;
+
+ NDS_setPad( R, L, D, U, T, S, B, A, Y, X, W, E, G, F);
+}
+
+
+void RunInputConfig()
+{
+
+ DialogBox(hAppInst, MAKEINTRESOURCE(IDD_INPUTCONFIG), MainWindow->getHWnd(), DlgInputConfig);
+}
+
+
+/**********************************************************************************
+ Snes9x - Portable Super Nintendo Entertainment System (TM) emulator.
+
+ (c) Copyright 1996 - 2002 Gary Henderson (gary.henderson@ntlworld.com),
+ Jerremy Koot (jkoot@snes9x.com)
+
+ (c) Copyright 2002 - 2004 Matthew Kendora
+
+ (c) Copyright 2002 - 2005 Peter Bortas (peter@bortas.org)
+
+ (c) Copyright 2004 - 2005 Joel Yliluoma (http://iki.fi/bisqwit/)
+
+ (c) Copyright 2001 - 2006 John Weidman (jweidman@slip.net)
+
+ (c) Copyright 2002 - 2006 funkyass (funkyass@spam.shaw.ca),
+ Kris Bleakley (codeviolation@hotmail.com)
+
+ (c) Copyright 2002 - 2007 Brad Jorsch (anomie@users.sourceforge.net),
+ Nach (n-a-c-h@users.sourceforge.net),
+ zones (kasumitokoduck@yahoo.com)
+
+ (c) Copyright 2006 - 2007 nitsuja
+
+
+ BS-X C emulator code
+ (c) Copyright 2005 - 2006 Dreamer Nom,
+ zones
+
+ C4 x86 assembler and some C emulation code
+ (c) Copyright 2000 - 2003 _Demo_ (_demo_@zsnes.com),
+ Nach,
+ zsKnight (zsknight@zsnes.com)
+
+ C4 C++ code
+ (c) Copyright 2003 - 2006 Brad Jorsch,
+ Nach
+
+ DSP-1 emulator code
+ (c) Copyright 1998 - 2006 _Demo_,
+ Andreas Naive (andreasnaive@gmail.com)
+ Gary Henderson,
+ Ivar (ivar@snes9x.com),
+ John Weidman,
+ Kris Bleakley,
+ Matthew Kendora,
+ Nach,
+ neviksti (neviksti@hotmail.com)
+
+ DSP-2 emulator code
+ (c) Copyright 2003 John Weidman,
+ Kris Bleakley,
+ Lord Nightmare (lord_nightmare@users.sourceforge.net),
+ Matthew Kendora,
+ neviksti
+
+
+ DSP-3 emulator code
+ (c) Copyright 2003 - 2006 John Weidman,
+ Kris Bleakley,
+ Lancer,
+ z80 gaiden
+
+ DSP-4 emulator code
+ (c) Copyright 2004 - 2006 Dreamer Nom,
+ John Weidman,
+ Kris Bleakley,
+ Nach,
+ z80 gaiden
+
+ OBC1 emulator code
+ (c) Copyright 2001 - 2004 zsKnight,
+ pagefault (pagefault@zsnes.com),
+ Kris Bleakley,
+ Ported from x86 assembler to C by sanmaiwashi
+
+ SPC7110 and RTC C++ emulator code
+ (c) Copyright 2002 Matthew Kendora with research by
+ zsKnight,
+ John Weidman,
+ Dark Force
+
+ S-DD1 C emulator code
+ (c) Copyright 2003 Brad Jorsch with research by
+ Andreas Naive,
+ John Weidman
+
+ S-RTC C emulator code
+ (c) Copyright 2001-2006 byuu,
+ John Weidman
+
+ ST010 C++ emulator code
+ (c) Copyright 2003 Feather,
+ John Weidman,
+ Kris Bleakley,
+ Matthew Kendora
+
+ Super FX x86 assembler emulator code
+ (c) Copyright 1998 - 2003 _Demo_,
+ pagefault,
+ zsKnight,
+
+ Super FX C emulator code
+ (c) Copyright 1997 - 1999 Ivar,
+ Gary Henderson,
+ John Weidman
+
+ Sound DSP emulator code is derived from SNEeSe and OpenSPC:
+ (c) Copyright 1998 - 2003 Brad Martin
+ (c) Copyright 1998 - 2006 Charles Bilyue'
+
+ SH assembler code partly based on x86 assembler code
+ (c) Copyright 2002 - 2004 Marcus Comstedt (marcus@mc.pp.se)
+
+ 2xSaI filter
+ (c) Copyright 1999 - 2001 Derek Liauw Kie Fa
+
+ HQ2x, HQ3x, HQ4x filters
+ (c) Copyright 2003 Maxim Stepin (maxim@hiend3d.com)
+
+ Win32 GUI code
+ (c) Copyright 2003 - 2006 blip,
+ funkyass,
+ Matthew Kendora,
+ Nach,
+ nitsuja
+
+ Mac OS GUI code
+ (c) Copyright 1998 - 2001 John Stiles
+ (c) Copyright 2001 - 2007 zones
+
+
+ Specific ports contains the works of other authors. See headers in
+ individual files.
+
+
+ Snes9x homepage: http://www.snes9x.com
+
+ Permission to use, copy, modify and/or distribute Snes9x in both binary
+ and source form, for non-commercial purposes, is hereby granted without
+ fee, providing that this license information and copyright notice appear
+ with all copies and any derived work.
+
+ This software is provided 'as-is', without any express or implied
+ warranty. In no event shall the authors be held liable for any damages
+ arising from the use of this software or it's derivatives.
+
+ Snes9x is freeware for PERSONAL USE only. Commercial users should
+ seek permission of the copyright holders first. Commercial use includes,
+ but is not limited to, charging money for Snes9x or software derived from
+ Snes9x, including Snes9x or derivatives in commercial game bundles, and/or
+ using Snes9x as a promotion for your commercial product.
+
+ The copyright holders request that bug fixes and improvements to the code
+ should be forwarded to them so everyone can benefit from the modifications
+ in future versions.
+
+ Super NES and Super Nintendo Entertainment System are trademarks of
+ Nintendo Co., Limited and its subsidiary companies.
+**********************************************************************************/
diff --git a/desmume/src/windows/inputdx.h b/desmume/src/windows/inputdx.h
index 00a4120cd..e19d665bd 100644
--- a/desmume/src/windows/inputdx.h
+++ b/desmume/src/windows/inputdx.h
@@ -1,78 +1,325 @@
-/* Copyright (C) 2006 yopyop
- yopyop156@ifrance.com
- yopyop156.ifrance.com
-
- Copyright (C) 2006-2008 DeSmuME team
-
- This file is part of DeSmuME
-
- DeSmuME 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.
-
- DeSmuME 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 DeSmuME; if not, write to the Free Software
- Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
-*/
-
-#ifndef _INPUT_DX_
-#define _INPUT_DX_
-
-#define DIRECTINPUT_VERSION 0x0800
-#include "../common.h"
-#include "../types.h"
-#include "directx/dinput.h"
-
-#define MAXKEYPAD 15
-
-typedef void (*INPUTPROC)(BOOL, LPSTR);
-
-class DI_CLASS
-{
- friend BOOL CALLBACK EnumCallback(LPCDIDEVICEINSTANCE lpddi, LPVOID pvRef);
- friend BOOL CALLBACK EnumObjects(const DIDEVICEOBJECTINSTANCE* pdidoi,VOID* pContext);
-public:
- char JoystickName[255];
- BOOL Feedback;
- LPDIRECTINPUTDEVICE8 EnumDevices(LPDIRECTINPUT8 pDI);
-protected:
- BOOL CALLBACK EnumCallback(LPCDIDEVICEINSTANCE lpddi, LPVOID pvRef);
- BOOL CALLBACK EnumObjects(const DIDEVICEOBJECTINSTANCE* pdidoi,VOID* pContext);
-};
-
-class INPUTCLASS : private DI_CLASS
-{
-private:
- HWND hParentWnd;
- BOOL paused;
-
- char cDIBuf[512];
- LPDIRECTINPUT8 pDI;
- LPDIRECTINPUTDEVICE8 pKeyboard;
- LPDIRECTINPUTDEVICE8 pJoystick;
- DIDEVCAPS DIJoycap;
- LPDIRECTINPUTEFFECT pEffect;
-
- INPUTPROC inputProc;
-
-public:
- INPUTCLASS();
- ~INPUTCLASS();
- BOOL Init(HWND hParentWnd, INPUTPROC inputProc);
- BOOL JoystickEnabled();
- void JoystickFeedback(BOOL on);
- void process();
-};
-
-// ========== emu input
-extern void InputConfig(HWND hwnd);
-extern void NDS_inputInit();
-extern void NDS_inputPost(BOOL paused, LPSTR buf);
-extern u16 keyPad[MAXKEYPAD];
-#endif
\ No newline at end of file
+///* This file is part of DeSmuME, derived from several files in Snes9x 1.51 which are
+// licensed under the terms supplied at the end of this file (for the terms are very long!)
+// Differences from that baseline version are:
+//
+// Copyright (C) 2009 DeSmuME team
+//
+// DeSmuME 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.
+//
+// DeSmuME 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 DeSmuME; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+//*/
+
+
+#ifndef INPUTDX_INCLUDED
+#define INPUTDX_INCLUDED
+
+void InitInputCustomControl(void);
+HWND CreateInputCustom(HWND hwndParent);
+void InitKeyCustomControl(void);
+HWND CreateKeyCustom(HWND hwndParent);
+
+typedef struct
+{
+ COLORREF crForeGnd; // Foreground text colour
+ COLORREF crBackGnd; // Background text colour
+ HFONT hFont; // The font
+ HWND hwnd; // The control's window handle
+} InputCust;
+COLORREF CheckButtonKey( WORD Key);
+COLORREF CheckHotKey( WORD Key, int modifiers);
+InputCust * GetInputCustom(HWND hwnd);
+
+#define CUSTKEY_ALT_MASK 0x01
+#define CUSTKEY_CTRL_MASK 0x02
+#define CUSTKEY_SHIFT_MASK 0x04
+
+struct SCustomKey {
+ WORD key;
+ WORD modifiers;
+};
+
+struct SCustomKeys {
+ SCustomKey SpeedUp;
+ SCustomKey SpeedDown;
+ SCustomKey Pause;
+ SCustomKey FrameAdvance;
+ SCustomKey SkipUp;
+ SCustomKey SkipDown;
+ SCustomKey ScopeTurbo;
+ SCustomKey ScopePause;
+ SCustomKey FrameCount;
+ SCustomKey ReadOnly;
+ SCustomKey Save [10];
+ SCustomKey Load [10];
+ SCustomKey FastForward;
+ SCustomKey ShowPressed;
+ SCustomKey SaveScreenShot;
+ SCustomKey SlotPlus;
+ SCustomKey SlotMinus;
+ SCustomKey SlotSave;
+ SCustomKey SlotLoad;
+ SCustomKey BGL1;
+ SCustomKey BGL2;
+ SCustomKey BGL3;
+ SCustomKey BGL4;
+ SCustomKey BGL5;
+ SCustomKey ClippingWindows;
+// SCustomKey BGLHack;
+ SCustomKey Transparency;
+ SCustomKey HDMA;
+ SCustomKey GLCube;
+// SCustomKey InterpMode7;
+ SCustomKey JoypadSwap;
+ SCustomKey SwitchControllers;
+ SCustomKey TurboA, TurboB, TurboY, TurboX, TurboL, TurboR, TurboStart, TurboSelect, TurboLeft, TurboUp, TurboRight, TurboDown;
+ SCustomKey SelectSave [10];
+ SCustomKey ResetGame;
+ SCustomKey ToggleCheats;
+ SCustomKey ToggleSound [8];
+ SCustomKey ToggleMacro [8];
+ SCustomKey EditMacro;
+};
+
+struct SJoypad {
+ BOOL Enabled;
+ WORD Left;
+ WORD Right;
+ WORD Up;
+ WORD Down;
+ WORD Left_Up;
+ WORD Left_Down;
+ WORD Right_Up;
+ WORD Right_Down;
+ WORD Start;
+ WORD Select;
+ WORD Lid;
+ WORD Debug;
+ WORD A;
+ WORD B;
+ WORD X;
+ WORD Y;
+ WORD L;
+ WORD R;
+};
+
+#define LEFT_MASK 0x0001
+#define RIGHT_MASK 0x0002
+#define UP_MASK 0x0004
+#define DOWN_MASK 0x0008
+#define START_MASK 0x0010
+#define SELECT_MASK 0x0020
+#define LID_MASK 0x0040
+#define DEBUG_MASK 0x0080
+#define A_MASK 0x0100
+#define B_MASK 0x0200
+#define X_MASK 0x0400
+#define Y_MASK 0x0800
+#define L_MASK 0x1000
+#define R_MASK 0x2000
+
+
+struct SJoyState{
+ bool Attached;
+ //JOYCAPS Caps;
+ int Threshold;
+ bool Left;
+ bool Right;
+ bool Up;
+ bool Down;
+ bool PovLeft;
+ bool PovRight;
+ bool PovUp;
+ bool PovDown;
+ bool PovDnLeft;
+ bool PovDnRight;
+ bool PovUpLeft;
+ bool PovUpRight;
+ bool RUp;
+ bool RDown;
+ bool UUp;
+ bool UDown;
+ bool VUp;
+ bool VDown;
+ bool ZUp;
+ bool ZDown;
+ bool Button[32];
+};
+
+extern SJoypad Joypad[16];
+extern SJoypad ToggleJoypadStorage[8];
+extern SCustomKeys CustomKeys;
+extern SJoypad TurboToggleJoypadStorage[8];
+
+
+#endif
+
+
+/**********************************************************************************
+ Snes9x - Portable Super Nintendo Entertainment System (TM) emulator.
+
+ (c) Copyright 1996 - 2002 Gary Henderson (gary.henderson@ntlworld.com),
+ Jerremy Koot (jkoot@snes9x.com)
+
+ (c) Copyright 2002 - 2004 Matthew Kendora
+
+ (c) Copyright 2002 - 2005 Peter Bortas (peter@bortas.org)
+
+ (c) Copyright 2004 - 2005 Joel Yliluoma (http://iki.fi/bisqwit/)
+
+ (c) Copyright 2001 - 2006 John Weidman (jweidman@slip.net)
+
+ (c) Copyright 2002 - 2006 funkyass (funkyass@spam.shaw.ca),
+ Kris Bleakley (codeviolation@hotmail.com)
+
+ (c) Copyright 2002 - 2007 Brad Jorsch (anomie@users.sourceforge.net),
+ Nach (n-a-c-h@users.sourceforge.net),
+ zones (kasumitokoduck@yahoo.com)
+
+ (c) Copyright 2006 - 2007 nitsuja
+
+
+ BS-X C emulator code
+ (c) Copyright 2005 - 2006 Dreamer Nom,
+ zones
+
+ C4 x86 assembler and some C emulation code
+ (c) Copyright 2000 - 2003 _Demo_ (_demo_@zsnes.com),
+ Nach,
+ zsKnight (zsknight@zsnes.com)
+
+ C4 C++ code
+ (c) Copyright 2003 - 2006 Brad Jorsch,
+ Nach
+
+ DSP-1 emulator code
+ (c) Copyright 1998 - 2006 _Demo_,
+ Andreas Naive (andreasnaive@gmail.com)
+ Gary Henderson,
+ Ivar (ivar@snes9x.com),
+ John Weidman,
+ Kris Bleakley,
+ Matthew Kendora,
+ Nach,
+ neviksti (neviksti@hotmail.com)
+
+ DSP-2 emulator code
+ (c) Copyright 2003 John Weidman,
+ Kris Bleakley,
+ Lord Nightmare (lord_nightmare@users.sourceforge.net),
+ Matthew Kendora,
+ neviksti
+
+
+ DSP-3 emulator code
+ (c) Copyright 2003 - 2006 John Weidman,
+ Kris Bleakley,
+ Lancer,
+ z80 gaiden
+
+ DSP-4 emulator code
+ (c) Copyright 2004 - 2006 Dreamer Nom,
+ John Weidman,
+ Kris Bleakley,
+ Nach,
+ z80 gaiden
+
+ OBC1 emulator code
+ (c) Copyright 2001 - 2004 zsKnight,
+ pagefault (pagefault@zsnes.com),
+ Kris Bleakley,
+ Ported from x86 assembler to C by sanmaiwashi
+
+ SPC7110 and RTC C++ emulator code
+ (c) Copyright 2002 Matthew Kendora with research by
+ zsKnight,
+ John Weidman,
+ Dark Force
+
+ S-DD1 C emulator code
+ (c) Copyright 2003 Brad Jorsch with research by
+ Andreas Naive,
+ John Weidman
+
+ S-RTC C emulator code
+ (c) Copyright 2001-2006 byuu,
+ John Weidman
+
+ ST010 C++ emulator code
+ (c) Copyright 2003 Feather,
+ John Weidman,
+ Kris Bleakley,
+ Matthew Kendora
+
+ Super FX x86 assembler emulator code
+ (c) Copyright 1998 - 2003 _Demo_,
+ pagefault,
+ zsKnight,
+
+ Super FX C emulator code
+ (c) Copyright 1997 - 1999 Ivar,
+ Gary Henderson,
+ John Weidman
+
+ Sound DSP emulator code is derived from SNEeSe and OpenSPC:
+ (c) Copyright 1998 - 2003 Brad Martin
+ (c) Copyright 1998 - 2006 Charles Bilyue'
+
+ SH assembler code partly based on x86 assembler code
+ (c) Copyright 2002 - 2004 Marcus Comstedt (marcus@mc.pp.se)
+
+ 2xSaI filter
+ (c) Copyright 1999 - 2001 Derek Liauw Kie Fa
+
+ HQ2x, HQ3x, HQ4x filters
+ (c) Copyright 2003 Maxim Stepin (maxim@hiend3d.com)
+
+ Win32 GUI code
+ (c) Copyright 2003 - 2006 blip,
+ funkyass,
+ Matthew Kendora,
+ Nach,
+ nitsuja
+
+ Mac OS GUI code
+ (c) Copyright 1998 - 2001 John Stiles
+ (c) Copyright 2001 - 2007 zones
+
+
+ Specific ports contains the works of other authors. See headers in
+ individual files.
+
+
+ Snes9x homepage: http://www.snes9x.com
+
+ Permission to use, copy, modify and/or distribute Snes9x in both binary
+ and source form, for non-commercial purposes, is hereby granted without
+ fee, providing that this license information and copyright notice appear
+ with all copies and any derived work.
+
+ This software is provided 'as-is', without any express or implied
+ warranty. In no event shall the authors be held liable for any damages
+ arising from the use of this software or it's derivatives.
+
+ Snes9x is freeware for PERSONAL USE only. Commercial users should
+ seek permission of the copyright holders first. Commercial use includes,
+ but is not limited to, charging money for Snes9x or software derived from
+ Snes9x, including Snes9x or derivatives in commercial game bundles, and/or
+ using Snes9x as a promotion for your commercial product.
+
+ The copyright holders request that bug fixes and improvements to the code
+ should be forwarded to them so everyone can benefit from the modifications
+ in future versions.
+
+ Super NES and Super Nintendo Entertainment System are trademarks of
+ Nintendo Co., Limited and its subsidiary companies.
+**********************************************************************************/
diff --git a/desmume/src/windows/main.cpp b/desmume/src/windows/main.cpp
index 8c72cd920..adf18de07 100644
--- a/desmume/src/windows/main.cpp
+++ b/desmume/src/windows/main.cpp
@@ -116,7 +116,7 @@ LPDIRECTDRAWCLIPPER lpDDClipPrimary=NULL;
LPDIRECTDRAWCLIPPER lpDDClipBack=NULL;
//===================== Input vars
-INPUTCLASS *input = NULL;
+//INPUTCLASS *input = NULL;
#ifndef EXPERIMENTAL_GBASLOT
/* The compact flash disk image file */
@@ -814,7 +814,10 @@ DWORD WINAPI run()
// if (!skipnextframe)
// {
- input->process();
+ //input->process();
+ //TODO INPUT
+ void input_process();
+ input_process();
if (FpsDisplay) osd->addFixed(0, 5, "%02d Fps", fps);
osd->update();
@@ -1141,6 +1144,8 @@ int WINAPI WinMain (HINSTANCE hThisInstance,
}
InitializeCriticalSection(&win_sync);
+ InitInputCustomControl();
+ InitKeyCustomControl();
#ifdef GDB_STUB
gdbstub_handle_t arm9_gdb_stub;
@@ -1282,13 +1287,16 @@ int WINAPI WinMain (HINSTANCE hThisInstance,
LOG("Init NDS\n");
- input = new INPUTCLASS();
- if (!input->Init(MainWindow->getHWnd(), &NDS_inputPost))
- {
- MessageBox(NULL, "Error DXInput init\n", "DeSmuME", MB_OK);
- exit(-1);
- }
- NDS_inputInit();
+ //input = new INPUTCLASS();
+ //if (!input->Init(MainWindow->getHWnd(), &NDS_inputPost))
+ //{
+ // MessageBox(NULL, "Error DXInput init\n", "DeSmuME", MB_OK);
+ // exit(-1);
+ //}
+ //NDS_inputInit();
+
+ void input_init();
+ input_init();
ViewDisasm_ARM7 = new TOOLSCLASS(hThisInstance, IDD_DESASSEMBLEUR_VIEWER7, (DLGPROC) ViewDisasm_ARM7Proc);
ViewDisasm_ARM9 = new TOOLSCLASS(hThisInstance, IDD_DESASSEMBLEUR_VIEWER9, (DLGPROC) ViewDisasm_ARM9Proc);
@@ -1456,7 +1464,7 @@ int WINAPI WinMain (HINSTANCE hThisInstance,
#ifdef DEBUG
//LogStop();
#endif
- if (input!=NULL) delete input;
+ //if (input!=NULL) delete input;
if (ViewLights!=NULL) delete ViewLights;
if (ViewMatrices!=NULL) delete ViewMatrices;
if (ViewOAM!=NULL) delete ViewOAM;
@@ -2418,7 +2426,9 @@ LRESULT CALLBACK WindowProcedure (HWND hwnd, UINT message, WPARAM wParam, LPARAM
tpaused=true;
NDS_Pause();
}
- InputConfig(hwnd);
+ //InputConfig(hwnd);
+ void RunInputConfig();
+ RunInputConfig();
if (tpaused)
NDS_UnPause();
}
diff --git a/desmume/src/windows/main.h b/desmume/src/windows/main.h
new file mode 100644
index 000000000..c790c96e4
--- /dev/null
+++ b/desmume/src/windows/main.h
@@ -0,0 +1,7 @@
+#ifndef _MAIN_H_
+#define _MAIN_H_
+
+#include "CWindow.h"
+extern WINCLASS *MainWindow;
+
+#endif
diff --git a/desmume/src/windows/resource.h b/desmume/src/windows/resource.h
index 87f35209b..df198ee9d 100644
--- a/desmume/src/windows/resource.h
+++ b/desmume/src/windows/resource.h
@@ -16,7 +16,6 @@
#define IDC_AUTO_UPDATE 108
#define IDM_MEMORY 109
#define IDM_DISASSEMBLER 110
-#define IDC_AUTO_UPDATE2 111
#define IDD_3DSETTINGS 111
#define IDM_GAME_INFO 111
#define IDD_GBASLOT 113
@@ -208,7 +207,6 @@
#define IDC_AUTOUPDATE_ASM 1018
#define IDC_BGMAP_PRIO 1018
#define IDC_BGMAP_PAL 1019
-#define IDC_VISIBLE 1019
#define IDC_BGMAP_SIZE 1020
#define IDC_IPCFIFO9 1020
#define IDC_BGMAP_SCROLL 1021
@@ -382,7 +380,6 @@
#define IDC_LIGHT_VIEWER_LIGHT3COLOR_COLORCTRL 1332
#define IDC_LIGHT_VIEWER_LIGHT3COLOR_EDIT 1333
#define IDC_LIGHT_VIEWER_LIGHT3VECTOR_EDIT 1334
-#define IDM_ABOUT 40003
#define ACCEL_P 40004
#define ACCEL_SPACEBAR 40005
#define ACCEL_N 40007
@@ -403,7 +400,6 @@
#define ACCEL_9 40030
#define ACCEL_CTRL_O 40032
#define ID_FILE_RECENTROM 40034
-#define IDC_SAVETYPE7 40037
#define IDM_DEFSIZE 40038
#define IDM_3DCONFIG 40040
#define IDM_GBASLOT 40042
@@ -411,3 +407,46 @@
#define IDC_BGMAP_ROTSCALEPARAMS 40051
#define IDM_CHEATS_SEARCH 40051
#define IDC_BGMAP_ROTSCALE 40052
+#define IDC_LABEL_UP 50000
+#define IDC_LABEL_RIGHT 50001
+#define IDC_LABEL_LEFT 50002
+#define IDC_LABEL_DOWN 50003
+#define IDC_LABEL_A 50004
+#define IDC_LABEL_X 50005
+#define IDC_LABEL_B 50006
+#define IDC_LABEL_Y 50007
+#define IDC_LABEL_L 50008
+#define IDC_LABEL_START 50009
+#define IDC_LABEL_R 50010
+#define IDC_LABEL_SELECT 50011
+#define IDC_LABEL_UPLEFT 50012
+#define IDC_LABEL_DOWNRIGHT 50013
+#define IDC_LABEL_UPRIGHT 50014
+#define IDC_LABEL_DOWNLEFT 50015
+#define IDC_ALLOWLEFTRIGHT 50016
+#define IDC_LABEL_X3 50017
+#define IDC_LABEL_X2 50018
+#define IDC_DEBUG 50019
+#define IDC_UP 50020
+#define IDC_LEFT 50021
+#define IDC_DOWN 50022
+#define IDC_RIGHT 50023
+#define IDC_B 50024
+#define IDC_A 50025
+#define IDC_Y 50026
+#define IDC_X 50027
+#define IDC_START 50028
+#define IDC_SELECT 50029
+#define IDC_L 50030
+#define IDC_R 50031
+#define IDC_UPLEFT 50032
+#define IDC_UPRIGHT 50033
+#define IDC_DWNRIGHT 50034
+#define IDC_DWNLEFT 50035
+#define IDC_LABEL_BLUE 50036
+#define IDC_LID 50037
+#define IDD_INPUTCONFIG 50038
+#define IDC_SAVETYPE7 40037
+#define IDC_AUTO_UPDATE2 111
+#define IDC_VISIBLE 1019
+#define IDM_ABOUT 40003
diff --git a/desmume/src/windows/resources.rc b/desmume/src/windows/resources.rc
index 01e6b60ca..d47d86fac 100644
--- a/desmume/src/windows/resources.rc
+++ b/desmume/src/windows/resources.rc
@@ -2271,6 +2271,53 @@ BEGIN
LTEXT "secs", IDC_STATIC, 428, 167, 16, 8, SS_LEFT
END
+IDD_INPUTCONFIG DIALOGEX 0, 0, 339, 148
+STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | WS_POPUP | WS_CAPTION | WS_SYSMENU
+CAPTION "Control Config"
+FONT 8, "MS Shell Dlg", 400, 0, 0x1
+BEGIN
+ CONTROL "WOG!",IDC_UP,"InputCustom",WS_TABSTOP,52,15,71,12,WS_EX_CLIENTEDGE
+ CONTROL "",IDC_LEFT,"InputCustom",WS_TABSTOP,52,29,71,12,WS_EX_CLIENTEDGE
+ CONTROL "",IDC_DOWN,"InputCustom",WS_TABSTOP,52,42,71,12,WS_EX_CLIENTEDGE
+ CONTROL "",IDC_RIGHT,"InputCustom",WS_TABSTOP,52,55,71,12,WS_EX_CLIENTEDGE
+ CONTROL "",IDC_B,"InputCustom",WS_TABSTOP,52,68,71,12,WS_EX_CLIENTEDGE
+ CONTROL "",IDC_A,"InputCustom",WS_TABSTOP,52,81,71,12,WS_EX_CLIENTEDGE
+ CONTROL "",IDC_Y,"InputCustom",WS_TABSTOP,52,94,71,12,WS_EX_CLIENTEDGE
+ CONTROL "",IDC_X,"InputCustom",WS_TABSTOP,52,107,71,12,WS_EX_CLIENTEDGE
+ CONTROL " ",IDC_START,"InputCustom",WS_TABSTOP,163,15,71,12,WS_EX_CLIENTEDGE
+ CONTROL " ",IDC_SELECT,"InputCustom",WS_TABSTOP,163,29,71,12,WS_EX_CLIENTEDGE
+ CONTROL " ",IDC_L,"InputCustom",WS_TABSTOP,163,42,71,12,WS_EX_CLIENTEDGE
+ CONTROL " ",IDC_R,"InputCustom",WS_TABSTOP,163,55,71,12,WS_EX_CLIENTEDGE
+ CONTROL " ",IDC_UPLEFT,"InputCustom",WS_DISABLED | WS_TABSTOP,163,68,71,12,WS_EX_CLIENTEDGE
+ CONTROL " ",IDC_UPRIGHT,"InputCustom",WS_DISABLED | WS_TABSTOP,163,81,71,12,WS_EX_CLIENTEDGE
+ CONTROL " ",IDC_DWNRIGHT,"InputCustom",WS_DISABLED | WS_TABSTOP,163,94,71,12,WS_EX_CLIENTEDGE
+ CONTROL " ",IDC_DWNLEFT,"InputCustom",WS_DISABLED | WS_TABSTOP,163,107,71,12,WS_EX_CLIENTEDGE
+ PUSHBUTTON "Cancel",IDCANCEL,293,119,39,14
+ PUSHBUTTON "OK",IDOK,245,119,41,14
+ LTEXT "Blue means the button is already mapped.\nPink means it conflicts with a custom hotkey.\nRed means it's reserved by Windows.\nButtons can be disabled using Escape.\nGrayed buttons arent supported yet (sorry!)",IDC_LABEL_BLUE,246,10,80,88
+ RTEXT "UP",IDC_LABEL_UP,10,18,38,8
+ RTEXT "RIGHT",IDC_LABEL_RIGHT,8,58,41,8
+ RTEXT "LEFT",IDC_LABEL_LEFT,11,31,37,8
+ RTEXT "DOWN",IDC_LABEL_DOWN,10,45,39,8
+ RTEXT "A",IDC_LABEL_A,10,83,38,8
+ RTEXT "X",IDC_LABEL_X,8,109,39,8
+ RTEXT "B",IDC_LABEL_B,11,71,37,8
+ RTEXT "Y",IDC_LABEL_Y,8,97,40,8
+ RTEXT "L",IDC_LABEL_L,136,44,24,8
+ RTEXT "START",IDC_LABEL_START,136,18,24,8
+ RTEXT "R",IDC_LABEL_R,136,57,24,8
+ RTEXT "SELECT",IDC_LABEL_SELECT,132,31,28,8
+ RTEXT "UP LEFT",IDC_LABEL_UPLEFT,130,71,30,8
+ RTEXT "DN RIGHT",IDC_LABEL_DOWNRIGHT,124,97,36,8
+ RTEXT "UP RIGHT",IDC_LABEL_UPRIGHT,124,84,36,8
+ RTEXT "DN LEFT",IDC_LABEL_DOWNLEFT,129,109,31,8
+ CONTROL "Allow Left+Rt/Up+Dn",IDC_ALLOWLEFTRIGHT,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,245,102,87,11
+ GROUPBOX "Buttons",IDC_STATIC,7,7,234,129,0,WS_EX_TRANSPARENT
+ CONTROL "",IDC_LID,"InputCustom",WS_TABSTOP,52,120,71,12,WS_EX_CLIENTEDGE
+ RTEXT "LID",IDC_LABEL_X2,8,121,39,8
+ RTEXT "DEBUG",IDC_LABEL_X3,127,123,29,8
+ CONTROL " ",IDC_DEBUG,"InputCustom",WS_DISABLED | WS_TABSTOP,163,120,71,12,WS_EX_CLIENTEDGE
+END
//