mirror of
https://gitea.tendokyu.moe/TeamTofuShop/segatools.git
synced 2026-09-22 22:37:59 +03:00
* Rewrote the input handler Added support for dinput and xinput, full keyboard slider cell binding (#127), hold-takeovers, button alternation and auto-sliding (PS4 behaviour). See segatools.ini for a detailed description about everything. * Split touch handling into backends and added Wintouch touch emulation Now you can use actual touchscreens as well as mouse emulation was not the greatest when trying to use an actual touchscreen. * Fixed input issues gamebtns was always uninitialized, so good luck trying to do anything. How did nobody ever complain about this? lol * Fixed resolution issues caused by chaining both gfx hooks The diva-specific hook is the only one we need. Stacking both has strange effects. * Added support for the MITSUBISHI CP9550DS printer Q: Why? A: /shrug  I am not particularly good at this game (or the pass requirements are insane, 23+12 misses out of ~550 is a fail!?), so if someone could test how this feels as opposed to the PS4 version, that would help a lot!  Also something that happens but that I can't reliably reproduce is that my aime card reader randomly becomes NG after a dozen game starts until I delete eeprom.bin. If that is the case, the only packet sent is SEND_HEX_DATA. Reviewed-on: https://gitea.tendokyu.moe/TeamTofuShop/segatools/pulls/129 Co-authored-by: kyoubate-haruka <46010460+kyoubate-haruka@users.noreply.github.com> Co-committed-by: kyoubate-haruka <46010460+kyoubate-haruka@users.noreply.github.com>
129 lines
3.2 KiB
C
129 lines
3.2 KiB
C
#include <windows.h>
|
|
#include <xinput.h>
|
|
|
|
#include <assert.h>
|
|
#include <stdbool.h>
|
|
#include <stdint.h>
|
|
|
|
#include "divaio/config.h"
|
|
#include "divaio/input/backend.h"
|
|
#include "divaio/input/xi.h"
|
|
|
|
#include "util/dprintf.h"
|
|
|
|
static void diva_xi_get_gamebtns(struct diva_button_states* states);
|
|
static void diva_xi_get_opbtns(uint8_t* opbtn);
|
|
static void diva_xi_get_auto_status(bool* left, bool* right);
|
|
|
|
static HRESULT diva_xi_config_apply(const struct diva_xi_config* cfg);
|
|
|
|
|
|
static const struct diva_io_backend diva_xi_backend = {
|
|
.get_gamebtns = diva_xi_get_gamebtns,
|
|
.get_opbtns = diva_xi_get_opbtns,
|
|
.get_auto_status = diva_xi_get_auto_status,
|
|
};
|
|
|
|
static bool diva_xi_test_enabled;
|
|
|
|
static XINPUT_STATE xi = {0};
|
|
|
|
HRESULT diva_xi_init(const struct diva_xi_config* cfg, const struct diva_io_backend** backend) {
|
|
assert(cfg != NULL);
|
|
assert(backend != NULL);
|
|
|
|
HRESULT hr = diva_xi_config_apply(cfg);
|
|
|
|
if (FAILED(hr)) {
|
|
return hr;
|
|
}
|
|
|
|
dprintf("XInput: Using XInput controller\n");
|
|
*backend = &diva_xi_backend;
|
|
|
|
return S_OK;
|
|
}
|
|
|
|
static HRESULT diva_xi_config_apply(const struct diva_xi_config* cfg) {
|
|
dprintf("XInput: --- Begin configuration ---\n");
|
|
dprintf("XInput: Test Button : %i\n", cfg->use_select_as_test);
|
|
dprintf("XInput: --- End configuration ---\n");
|
|
|
|
diva_xi_test_enabled = cfg->use_select_as_test;
|
|
|
|
return S_OK;
|
|
}
|
|
|
|
static void diva_xi_get_gamebtns(struct diva_button_states* states) {
|
|
|
|
assert(states != NULL);
|
|
|
|
memset(&xi, 0, sizeof(xi));
|
|
XInputGetState(0, &xi);
|
|
|
|
const WORD xb = xi.Gamepad.wButtons;
|
|
|
|
states->start = xb & XINPUT_GAMEPAD_START;
|
|
states->cross.primary = xb & XINPUT_GAMEPAD_A;
|
|
states->cross.secondary = xb & XINPUT_GAMEPAD_DPAD_DOWN;
|
|
states->circle.primary = xb & XINPUT_GAMEPAD_B;
|
|
states->circle.secondary = xb & XINPUT_GAMEPAD_DPAD_RIGHT;
|
|
states->triangle.primary = xb & XINPUT_GAMEPAD_Y;
|
|
states->triangle.secondary = xb & XINPUT_GAMEPAD_DPAD_UP;
|
|
states->square.primary = xb & XINPUT_GAMEPAD_X;
|
|
states->square.secondary = xb & XINPUT_GAMEPAD_DPAD_LEFT;
|
|
}
|
|
|
|
void diva_xi_get_opbtns(uint8_t* opbtn) {
|
|
assert(opbtn != NULL);
|
|
|
|
uint8_t opbtn_out = 0;
|
|
|
|
if (diva_xi_test_enabled && xi.Gamepad.wButtons & XINPUT_GAMEPAD_BACK) {
|
|
opbtn_out |= DIVA_IO_OPBTN_TEST;
|
|
}
|
|
|
|
*opbtn = opbtn_out;
|
|
}
|
|
|
|
void diva_xi_get_auto_status(bool* left, bool* right) {
|
|
assert(left != NULL);
|
|
assert(right != NULL);
|
|
|
|
*left = false;
|
|
*right = false;
|
|
|
|
const int left_x = xi.Gamepad.sThumbLX;
|
|
const int right_x = xi.Gamepad.sThumbRX;
|
|
|
|
if (left_x < -XINPUT_GAMEPAD_LEFT_THUMB_DEADZONE * 2) {
|
|
*left |= true;
|
|
} else if (left_x > XINPUT_GAMEPAD_LEFT_THUMB_DEADZONE * 2) {
|
|
*right |= true;
|
|
}
|
|
|
|
if (right_x < -XINPUT_GAMEPAD_LEFT_THUMB_DEADZONE * 2) {
|
|
*left |= true;
|
|
} else if (right_x > XINPUT_GAMEPAD_LEFT_THUMB_DEADZONE * 2) {
|
|
*right |= true;
|
|
}
|
|
|
|
const WORD xb = xi.Gamepad.wButtons;
|
|
|
|
if (xb & XINPUT_GAMEPAD_LEFT_SHOULDER) {
|
|
*left |= true;
|
|
}
|
|
|
|
if (xb & XINPUT_GAMEPAD_RIGHT_SHOULDER) {
|
|
*right |= true;
|
|
}
|
|
|
|
if (xi.Gamepad.bLeftTrigger > 64) {
|
|
*left |= true;
|
|
}
|
|
|
|
if (xi.Gamepad.bRightTrigger > 64) {
|
|
*right |= true;
|
|
}
|
|
}
|