From deaceb6b08517e0eb377afe9669dd0ab1de4352b Mon Sep 17 00:00:00 2001 From: FlatOutPS2 Date: Tue, 29 Nov 2016 20:31:22 +0100 Subject: [PATCH] LilyPad: Add skip deadzone option Adds a skip deadzone option to the Pad tabs. With the normal deadzone, if the control input value is below the deadzone threshold, the input is ignored. However, some controllers also benefit from shortening the input range by skipping a deadzone. --- plugins/LilyPad/Config.cpp | 50 +++++++++++++++++++++++--------- plugins/LilyPad/Global.h | 2 ++ plugins/LilyPad/InputManager.cpp | 7 ++--- plugins/LilyPad/InputManager.h | 1 + plugins/LilyPad/LilyPad.cpp | 12 ++++---- plugins/LilyPad/Tooltips.cpp | 3 ++ plugins/LilyPad/resource.h | 1 + 7 files changed, 51 insertions(+), 25 deletions(-) diff --git a/plugins/LilyPad/Config.cpp b/plugins/LilyPad/Config.cpp index 8629a0a091..1e766412dd 100644 --- a/plugins/LilyPad/Config.cpp +++ b/plugins/LilyPad/Config.cpp @@ -364,7 +364,7 @@ void CALLBACK PADsetSettingsDir(const char *dir) } int GetBinding(int port, int slot, int index, Device *&dev, Binding *&b, ForceFeedbackBinding *&ffb); -int BindCommand(Device *dev, unsigned int uid, unsigned int port, unsigned int slot, unsigned int padtype, int command, int sensitivity, int turbo, int deadZone); +int BindCommand(Device *dev, unsigned int uid, unsigned int port, unsigned int slot, unsigned int padtype, int command, int sensitivity, int turbo, int deadZone, int skipDeadZone); int CreateEffectBinding(Device *dev, wchar_t *effectName, unsigned int port, unsigned int slot, unsigned int padtype, unsigned int motor, ForceFeedbackBinding **binding); @@ -383,6 +383,7 @@ void SelChanged(int port, int slot) int turbo = -1; int sensitivity = 0; int deadZone = 0; + int skipDeadZone = 0; int nonButtons = 0; // Set if sensitivity != 0, but need to disable flip anyways. // Only used to relative axes. @@ -456,6 +457,7 @@ void SelChanged(int port, int slot) } if (((control->uid >> 16) & 0xFF) != PSHBTN && ((control->uid >> 16) & 0xFF) != TGLBTN) { deadZone += b->deadZone; + skipDeadZone += b->skipDeadZone; nonButtons++; } } else @@ -469,6 +471,7 @@ void SelChanged(int port, int slot) ffb = 0; turbo = -1; deadZone = 0; + skipDeadZone = 0; sensitivity = 0; disableFlip = 1; bFound = ffbFound = 0; @@ -477,6 +480,7 @@ void SelChanged(int port, int slot) sensitivity /= bFound; if (nonButtons) { deadZone /= nonButtons; + skipDeadZone /= nonButtons; } if (bFound > 1) disableFlip = 1; @@ -530,6 +534,7 @@ void SelChanged(int port, int slot) if (!ffb) { SetLogSliderVal(hWnd, IDC_SLIDER_SENSITIVITY, GetDlgItem(hWnd, IDC_AXIS_SENSITIVITY), sensitivity); SetLogSliderVal(hWnd, IDC_SLIDER_DEADZONE, GetDlgItem(hWnd, IDC_AXIS_DEADZONE), deadZone); + SetLogSliderVal(hWnd, IDC_SLIDER_SKIP_DEADZONE, GetDlgItem(hWnd, IDC_AXIS_SKIP_DEADZONE), skipDeadZone); if (disableFlip) EnableWindow(GetDlgItem(hWnd, IDC_FLIP), 0); @@ -693,7 +698,7 @@ int ListBoundEffect(int port, int slot, Device *dev, ForceFeedbackBinding *b) } // Only for use with control bindings. Affects all highlighted bindings. -void ChangeValue(int port, int slot, int *newSensitivity, int *newTurbo, int *newDeadZone) +void ChangeValue(int port, int slot, int *newSensitivity, int *newTurbo, int *newDeadZone, int *newSkipDeadZone) { int padtype = config.padConfigs[port][slot].type; if (!hWnds[port][slot][padtype]) @@ -724,6 +729,11 @@ void ChangeValue(int port, int slot, int *newSensitivity, int *newTurbo, int *ne b->deadZone = *newDeadZone; } } + if (newSkipDeadZone) { + if (b->skipDeadZone) { + b->skipDeadZone = *newSkipDeadZone; + } + } if (newTurbo) { b->turbo = *newTurbo; } @@ -886,7 +896,7 @@ int SaveSettings(wchar_t *file = 0) Binding *b = dev->pads[port][slot][padtype].bindings + j; VirtualControl *c = &dev->virtualControls[b->controlIndex]; wsprintfW(temp, L"Binding %i", bindingCount++); - wsprintfW(temp2, L"0x%08X, %i, %i, %i, %i, %i, %i, %i", c->uid, port, b->command, b->sensitivity, b->turbo, slot, b->deadZone, padtype); + wsprintfW(temp2, L"0x%08X, %i, %i, %i, %i, %i, %i, %i, %i", c->uid, port, b->command, b->sensitivity, b->turbo, slot, b->deadZone, b->skipDeadZone, padtype); noError &= WritePrivateProfileStringW(id, temp, temp2, file); } for (int j = 0; j < dev->pads[port][slot][padtype].numFFBindings; j++) { @@ -1013,7 +1023,7 @@ int LoadSettings(int force, wchar_t *file) } last = 1; unsigned int uid; - int port, command, sensitivity, turbo, slot = 0, deadZone = 0, padtype = 0; + int port, command, sensitivity, turbo, slot = 0, deadZone = 0, skipDeadZone = 0, padtype = 0; int w = 0; char string[1000]; while (temp2[w]) { @@ -1021,7 +1031,7 @@ int LoadSettings(int force, wchar_t *file) w++; } string[w] = 0; - int len = sscanf(string, " %i , %i , %i , %i , %i , %i , %i , %i", &uid, &port, &command, &sensitivity, &turbo, &slot, &deadZone, &padtype); + int len = sscanf(string, " %i , %i , %i , %i , %i , %i , %i , %i , %i", &uid, &port, &command, &sensitivity, &turbo, &slot, &deadZone, &skipDeadZone, &padtype); if (len >= 5 && type) { VirtualControl *c = dev->GetVirtualControl(uid); if (!c) @@ -1034,8 +1044,11 @@ int LoadSettings(int force, wchar_t *file) } else { padtype = 1; } + } else if (len == 8) { + padtype = skipDeadZone; + skipDeadZone = 0; } - BindCommand(dev, uid, port, slot, padtype, command, sensitivity, turbo, deadZone); + BindCommand(dev, uid, port, slot, padtype, command, sensitivity, turbo, deadZone, skipDeadZone); } } } @@ -1322,7 +1335,7 @@ int CreateEffectBinding(Device *dev, wchar_t *effectID, unsigned int port, unsig return ListBoundEffect(port, slot, dev, b); } -int BindCommand(Device *dev, unsigned int uid, unsigned int port, unsigned int slot, unsigned int padtype, int command, int sensitivity, int turbo, int deadZone) +int BindCommand(Device *dev, unsigned int uid, unsigned int port, unsigned int slot, unsigned int padtype, int command, int sensitivity, int turbo, int deadZone, int skipDeadZone) { // Checks needed because I use this directly when loading bindings. if (port > 1 || slot > 3 || padtype >= numPadTypes) @@ -1332,13 +1345,17 @@ int BindCommand(Device *dev, unsigned int uid, unsigned int port, unsigned int s sensitivity = BASE_SENSITIVITY; if ((uid >> 16) & (PSHBTN | TGLBTN)) { deadZone = 0; + skipDeadZone = 0; } else if (!deadZone) { if ((uid >> 16) & PRESSURE_BTN) { deadZone = 1; } else { deadZone = DEFAULT_DEADZONE; } + } else if (!skipDeadZone) { + skipDeadZone = 1; } + // Relative axes can have negative sensitivity. else if (((uid >> 16) & 0xFF) == RELAXIS) { sensitivity = abs(sensitivity); @@ -1363,6 +1380,7 @@ int BindCommand(Device *dev, unsigned int uid, unsigned int port, unsigned int s b->turbo = turbo; b->sensitivity = sensitivity; b->deadZone = deadZone; + b->skipDeadZone = skipDeadZone; // Where it appears in listview. int count = ListBoundCommand(port, slot, dev, b); @@ -1477,6 +1495,7 @@ INT_PTR CALLBACK DialogProc(HWND hWnd, unsigned int msg, WPARAM wParam, LPARAM l SendMessage(hWndList, LVM_SETEXTENDEDLISTVIEWSTYLE, 0, LVS_EX_FULLROWSELECT); SetupLogSlider(GetDlgItem(hWnd, IDC_SLIDER_SENSITIVITY)); SetupLogSlider(GetDlgItem(hWnd, IDC_SLIDER_DEADZONE)); + SetupLogSlider(GetDlgItem(hWnd, IDC_SLIDER_SKIP_DEADZONE)); if (port || slot) EnableWindow(GetDlgItem(hWnd, ID_IGNORE), 0); @@ -1489,6 +1508,7 @@ INT_PTR CALLBACK DialogProc(HWND hWnd, unsigned int msg, WPARAM wParam, LPARAM l AddTooltip(IDC_TURBO, hWnd); AddTooltip(IDC_FLIP, hWnd); AddTooltip(IDC_SLIDER_DEADZONE, hWnd); + AddTooltip(IDC_SLIDER_SKIP_DEADZONE, hWnd); AddTooltip(IDC_SLIDER_SENSITIVITY, hWnd); Populate(port, slot, padtype); @@ -1529,9 +1549,9 @@ INT_PTR CALLBACK DialogProc(HWND hWnd, unsigned int msg, WPARAM wParam, LPARAM l UnselectAll(hWndList); int index = -1; if (command == 0x7F && dev->api == IGNORE_KEYBOARD) { - index = BindCommand(dev, uid, 0, 0, 0, command, BASE_SENSITIVITY, 0, 0); + index = BindCommand(dev, uid, 0, 0, 0, command, BASE_SENSITIVITY, 0, 0, 0); } else if (command < 0x30) { - index = BindCommand(dev, uid, port, slot, padtype, command, BASE_SENSITIVITY, 0, 0); + index = BindCommand(dev, uid, port, slot, padtype, command, BASE_SENSITIVITY, 0, 0, 0); } if (index >= 0) { PropSheet_Changed(hWndProp, hWnds[port][slot][padtype]); @@ -1593,9 +1613,11 @@ INT_PTR CALLBACK DialogProc(HWND hWnd, unsigned int msg, WPARAM wParam, LPARAM l int id = GetDlgCtrlID((HWND)lParam); int val = GetLogSliderVal(hWnd, id); if (id == IDC_SLIDER_SENSITIVITY) { - ChangeValue(port, slot, &val, 0, 0); + ChangeValue(port, slot, &val, 0, 0, 0); } else if (id == IDC_SLIDER_DEADZONE) { - ChangeValue(port, slot, 0, 0, &val); + ChangeValue(port, slot, 0, 0, &val, 0); + } else if (id == IDC_SLIDER_SKIP_DEADZONE) { + ChangeValue(port, slot, 0, 0, 0, &val); } else { ChangeEffect(port, slot, id, &val, 0); } @@ -1615,7 +1637,7 @@ INT_PTR CALLBACK DialogProc(HWND hWnd, unsigned int msg, WPARAM wParam, LPARAM l uid = (uid & 0x00FFFFFF) | axisUIDs[cbsel]; Binding backup = *b; DeleteSelected(port, slot); - int index = BindCommand(dev, uid, port, slot, padtype, backup.command, backup.sensitivity, backup.turbo, backup.deadZone); + int index = BindCommand(dev, uid, port, slot, padtype, backup.command, backup.sensitivity, backup.turbo, backup.deadZone, backup.skipDeadZone); ListView_SetItemState(hWndList, index, LVIS_SELECTED, LVIS_SELECTED); PropSheet_Changed(hWndProp, hWnd); } @@ -1763,10 +1785,10 @@ INT_PTR CALLBACK DialogProc(HWND hWnd, unsigned int msg, WPARAM wParam, LPARAM l // Don't allow setting it back to indeterminate. SendMessage(GetDlgItem(hWnd, IDC_TURBO), BM_SETSTYLE, BS_AUTOCHECKBOX, 0); int turbo = (IsDlgButtonChecked(hWnd, IDC_TURBO) == BST_CHECKED); - ChangeValue(port, slot, 0, &turbo, 0); + ChangeValue(port, slot, 0, &turbo, 0, 0); } else if (cmd == IDC_FLIP) { int val = GetLogSliderVal(hWnd, IDC_SLIDER_SENSITIVITY); - ChangeValue(port, slot, &val, 0, 0); + ChangeValue(port, slot, &val, 0, 0, 0); } else if (cmd >= IDC_FF_AXIS1_ENABLED && cmd < IDC_FF_AXIS8_ENABLED + 16) { int index = (cmd - IDC_FF_AXIS1_ENABLED) / 16; int val = GetLogSliderVal(hWnd, 16 * index + IDC_FF_AXIS1); diff --git a/plugins/LilyPad/Global.h b/plugins/LilyPad/Global.h index bf4bed6c7a..e7bc57b785 100644 --- a/plugins/LilyPad/Global.h +++ b/plugins/LilyPad/Global.h @@ -104,6 +104,8 @@ extern Window GSwin; #ifdef _MSC_VER #define _WIN32_WINNT 0x0600 +#define NOMINMAX +#include #include #ifdef PCSX2_DEBUG diff --git a/plugins/LilyPad/InputManager.cpp b/plugins/LilyPad/InputManager.cpp index 10a4ea2b6b..fd6fcd05b7 100644 --- a/plugins/LilyPad/InputManager.cpp +++ b/plugins/LilyPad/InputManager.cpp @@ -240,12 +240,9 @@ void Device::CalcVirtualState() double angle = val * (3.141592653589793 / 18000.0); double East = sin(angle); double South = -cos(angle); -// Normalize so greatest direction is 1. -#ifdef __linux__ + // Normalize so greatest direction is 1. double mul = FULLY_DOWN / std::max(fabs(South), fabs(East)); -#else - double mul = FULLY_DOWN / max(fabs(South), fabs(East)); -#endif + iEast = (int)floor(East * mul + 0.5); iSouth = (int)floor(South * mul + 0.5); } diff --git a/plugins/LilyPad/InputManager.h b/plugins/LilyPad/InputManager.h index a0366fcdf7..5504d51c24 100644 --- a/plugins/LilyPad/InputManager.h +++ b/plugins/LilyPad/InputManager.h @@ -80,6 +80,7 @@ struct Binding int command; int sensitivity; int deadZone; + int skipDeadZone; unsigned char turbo; }; diff --git a/plugins/LilyPad/LilyPad.cpp b/plugins/LilyPad/LilyPad.cpp index b182b3481e..ecfe20542e 100644 --- a/plugins/LilyPad/LilyPad.cpp +++ b/plugins/LilyPad/LilyPad.cpp @@ -42,7 +42,7 @@ #define FORCE_UPDATE_LPARAM ((LPARAM)0x89437437) // LilyPad version. -#define VERSION ((0 << 8) | 11 | (0 << 24)) +#define VERSION ((0 << 8) | 12 | (0 << 24)) #ifdef __linux__ Display *GSdsp; @@ -384,8 +384,12 @@ void AddForce(ButtonSum *sum, u8 cmd, int delta = 255) void ProcessButtonBinding(Binding *b, ButtonSum *sum, int value) { - if (value < b->deadZone || !value) + if (value < b->deadZone || value == 0) { return; + } + if (b->skipDeadZone > b->deadZone) { + value = std::min((int)(((__int64)value * (FULLY_DOWN - (__int64)b->skipDeadZone)) / FULLY_DOWN) + b->skipDeadZone, FULLY_DOWN); + } if (config.turboKeyHack == 1) { // send a tabulator keypress to emulator //printf("%x\n", b->command); @@ -425,11 +429,7 @@ void CapSum(ButtonSum *sum) { int i; for (i = 0; i < 2; i++) { -#ifdef __linux__ int div = std::max(abs(sum->sticks[i].horiz), abs(sum->sticks[i].vert)); -#else - int div = max(abs(sum->sticks[i].horiz), abs(sum->sticks[i].vert)); -#endif if (div > 255) { sum->sticks[i].horiz = sum->sticks[i].horiz * 255 / div; sum->sticks[i].vert = sum->sticks[i].vert * 255 / div; diff --git a/plugins/LilyPad/Tooltips.cpp b/plugins/LilyPad/Tooltips.cpp index 112dd17a9f..f28b5ce0b0 100644 --- a/plugins/LilyPad/Tooltips.cpp +++ b/plugins/LilyPad/Tooltips.cpp @@ -93,6 +93,9 @@ LPWSTR dialog_message(int ID, bool *updateText) case IDC_SLIDER_DEADZONE: return L"Decreases or increases the range of an input where no input is recognised.\n\n" L"Increasing the dead zone requires the input to be pressed harder or moved more before it is applied, decreasing it makes it recognise a softer press or a shorter movement."; + case IDC_SKIP_DEADZONE: + return L"Skips and avoids the dead zone to detect input earlier.\n\n" + L"Note: This is useful when a controller input requires too much movement/pressure before there's a corresponding action in-game."; case IDC_SLIDER_SENSITIVITY: return L"Sets how hard an axis or button is pressed.\n\n" L"Note 1: What the default sensitivity value of \"1.00\" means depends on the device itself. The default is high enough that relative axes (which are primarily used by mice) are generally either considered fully up or down." diff --git a/plugins/LilyPad/resource.h b/plugins/LilyPad/resource.h index 8df65e5af6..ce3429acdf 100644 --- a/plugins/LilyPad/resource.h +++ b/plugins/LilyPad/resource.h @@ -62,6 +62,7 @@ #define IDC_AXIS_DEADZONE 0x1014 #define IDC_LABEL_SENSITIVITY 0x1020 #define IDC_LABEL_DEADZONE 0x1021 +#define IDC_SKIP_DEADZONE 0x1022 #define ID_LOCK_BUTTONS 0x10FC #define ID_LOCK_ALL_INPUT 0x10FD #define ID_LOCK_DIRECTION 0x10FE