actually complete the input config dialog

This commit is contained in:
Arisotura
2020-05-19 20:48:52 +02:00
parent 920ff9778d
commit 34506ff2bb
7 changed files with 434 additions and 95 deletions

View File

@ -20,11 +20,13 @@
#include <QLabel>
#include <QKeyEvent>
#include <SDL2/SDL.h>
#include "types.h"
#include "Config.h"
#include "PlatformConfig.h"
#include "main.h"
#include "Input.h"
#include "InputConfigDialog.h"
#include "ui_InputConfigDialog.h"
@ -93,6 +95,22 @@ InputConfigDialog::InputConfigDialog(QWidget* parent) : QDialog(parent), ui(new
populatePage(ui->tabInput, 12, dskeylabels, keypadKeyMap, keypadJoyMap);
populatePage(ui->tabAddons, 2, hk_addons_labels, addonsKeyMap, addonsJoyMap);
populatePage(ui->tabHotkeysGeneral, 6, hk_general_labels, hkGeneralKeyMap, hkGeneralJoyMap);
int njoy = SDL_NumJoysticks();
if (njoy > 0)
{
for (int i = 0; i < njoy; i++)
{
const char* name = SDL_JoystickNameForIndex(i);
ui->cbxJoystick->addItem(QString(name));
}
ui->cbxJoystick->setCurrentIndex(Input::JoystickID);
}
else
{
ui->cbxJoystick->addItem("(no joysticks available)");
ui->cbxJoystick->setEnabled(false);
}
}
InputConfigDialog::~InputConfigDialog()
@ -117,7 +135,7 @@ void InputConfigDialog::populatePage(QWidget* page, int num, const char** labels
for (int i = 0; i < num; i++)
{
QLabel* label = new QLabel(QString(labels[i])+":");
KeyMapButton* btn = new KeyMapButton(nullptr, &keymap[i], ishotkey);
KeyMapButton* btn = new KeyMapButton(&keymap[i], ishotkey);
group_layout->addWidget(label, i, 0);
group_layout->addWidget(btn, i, 1);
@ -133,15 +151,10 @@ void InputConfigDialog::populatePage(QWidget* page, int num, const char** labels
for (int i = 0; i < num; i++)
{
QLabel* label = new QLabel(QString(labels[i])+":");
QPushButton* btn = new QPushButton();
JoyMapButton* btn = new JoyMapButton(&joymap[i], ishotkey);
group_layout->addWidget(label, i, 0);
group_layout->addWidget(btn, i, 1);
btn->setText(joyMappingName(joymap[i]));
//btn->setProperty("mapping", QVariant(&joymap[i]));
//btn->setProperty("isHotkey", QVariant(ishotkey));
}
group_layout->setRowStretch(num, 1);
group->setLayout(group_layout);
@ -150,71 +163,48 @@ void InputConfigDialog::populatePage(QWidget* page, int num, const char** labels
page->setLayout(main_layout);
}
QString InputConfigDialog::joyMappingName(int id)
{
if (id < 0)
{
return "None";
}
bool hasbtn = ((id & 0xFFFF) != 0xFFFF);
QString str;
if (hasbtn)
{
if (id & 0x100)
{
int hatnum = ((id >> 4) & 0xF) + 1;
switch (id & 0xF)
{
case 0x1: str = "Hat %1 up"; break;
case 0x2: str = "Hat %1 right"; break;
case 0x4: str = "Hat %1 down"; break;
case 0x8: str = "Hat %1 left"; break;
}
str = str.arg(hatnum);
}
else
{
str = QString("Button %1").arg((id & 0xFFFF) + 1);
}
}
else
{
str = "";
}
if (id & 0x10000)
{
int axisnum = ((id >> 24) & 0xF) + 1;
if (hasbtn) str += " / ";
switch ((id >> 20) & 0xF)
{
case 0: str += QString("Axis %1 +").arg(axisnum); break;
case 1: str += QString("Axis %1 -").arg(axisnum); break;
case 2: str += QString("Trigger %1").arg(axisnum); break;
}
}
return str;
}
void InputConfigDialog::on_InputConfigDialog_accepted()
{
for (int i = 0; i < 12; i++)
{
Config::KeyMapping[dskeyorder[i]] = keypadKeyMap[i];
Config::JoyMapping[dskeyorder[i]] = keypadJoyMap[i];
}
for (int i = 0; i < 2; i++)
{
Config::HKKeyMapping[hk_addons[i]] = addonsKeyMap[i];
Config::HKJoyMapping[hk_addons[i]] = addonsJoyMap[i];
}
for (int i = 0; i < 6; i++)
{
Config::HKKeyMapping[hk_general[i]] = hkGeneralKeyMap[i];
Config::HKJoyMapping[hk_general[i]] = hkGeneralJoyMap[i];
}
Config::JoystickID = Input::JoystickID;
Config::Save();
closeDlg();
}
void InputConfigDialog::on_InputConfigDialog_rejected()
{
Input::JoystickID = Config::JoystickID;
Input::OpenJoystick();
closeDlg();
}
void InputConfigDialog::on_cbxJoystick_currentIndexChanged(int id)
{
Input::JoystickID = id;
Input::OpenJoystick();
}
KeyMapButton::KeyMapButton(QWidget* parent, int* mapping, bool hotkey) : QPushButton(parent)
KeyMapButton::KeyMapButton(int* mapping, bool hotkey) : QPushButton()
{
this->mapping = mapping;
this->isHotkey = hotkey;
@ -257,7 +247,7 @@ void KeyMapButton::keyPressEvent(QKeyEvent* event)
if (!ismod)
key |= mod;
else if (IsRightModKey(event))
else if (Input::IsRightModKey(event))
key |= (1<<31);
*mapping = key;
@ -314,3 +304,188 @@ QString KeyMapButton::mappingText()
return ret.replace("&", "&&");
}
JoyMapButton::JoyMapButton(int* mapping, bool hotkey) : QPushButton()
{
this->mapping = mapping;
this->isHotkey = hotkey;
setCheckable(true);
setText(mappingText());
connect(this, &JoyMapButton::clicked, this, &JoyMapButton::onClick);
timerID = 0;
}
JoyMapButton::~JoyMapButton()
{
}
void JoyMapButton::keyPressEvent(QKeyEvent* event)
{
if (!isChecked()) return QPushButton::keyPressEvent(event);
int key = event->key();
int mod = event->modifiers();
if (!mod)
{
if (key == Qt::Key_Escape) { click(); return; }
if (key == Qt::Key_Backspace) { *mapping = -1; click(); return; }
}
}
void JoyMapButton::focusOutEvent(QFocusEvent* event)
{
if (isChecked())
{
// if we lost the focus while mapping, consider it 'done'
click();
}
QPushButton::focusOutEvent(event);
}
void JoyMapButton::timerEvent(QTimerEvent* event)
{
SDL_Joystick* joy = Input::Joystick;
if (!joy) { click(); return; }
if (!SDL_JoystickGetAttached(joy)) { click(); return; }
int oldmap;
if (*mapping == -1) oldmap = 0xFFFF;
else oldmap = *mapping;
int nbuttons = SDL_JoystickNumButtons(joy);
for (int i = 0; i < nbuttons; i++)
{
if (SDL_JoystickGetButton(joy, i))
{
*mapping = (oldmap & 0xFFFF0000) | i;
click();
return;
}
}
int nhats = SDL_JoystickNumHats(joy);
if (nhats > 16) nhats = 16;
for (int i = 0; i < nhats; i++)
{
Uint8 blackhat = SDL_JoystickGetHat(joy, i);
if (blackhat)
{
if (blackhat & 0x1) blackhat = 0x1;
else if (blackhat & 0x2) blackhat = 0x2;
else if (blackhat & 0x4) blackhat = 0x4;
else blackhat = 0x8;
*mapping = (oldmap & 0xFFFF0000) | 0x100 | blackhat | (i << 4);
click();
return;
}
}
int naxes = SDL_JoystickNumAxes(joy);
if (naxes > 16) naxes = 16;
for (int i = 0; i < naxes; i++)
{
Sint16 axisval = SDL_JoystickGetAxis(joy, i);
int diff = abs(axisval - axesRest[i]);
if (axesRest[i] < -16384 && axisval >= 0)
{
*mapping = (oldmap & 0xFFFF) | 0x10000 | (2 << 20) | (i << 24);
click();
return;
}
else if (diff > 16384)
{
int axistype;
if (axisval > 0) axistype = 0;
else axistype = 1;
*mapping = (oldmap & 0xFFFF) | 0x10000 | (axistype << 20) | (i << 24);
click();
return;
}
}
}
void JoyMapButton::onClick()
{
if (isChecked())
{
setText("[press button/axis]");
timerID = startTimer(50);
memset(axesRest, 0, sizeof(axesRest));
if (Input::Joystick && SDL_JoystickGetAttached(Input::Joystick))
{
int naxes = SDL_JoystickNumAxes(Input::Joystick);
if (naxes > 16) naxes = 16;
for (int a = 0; a < naxes; a++)
{
axesRest[a] = SDL_JoystickGetAxis(Input::Joystick, a);
}
}
}
else
{
setText(mappingText());
if (timerID) { killTimer(timerID); timerID = 0; }
}
}
QString JoyMapButton::mappingText()
{
int id = *mapping;
if (id == -1) return "None";
bool hasbtn = ((id & 0xFFFF) != 0xFFFF);
QString str;
if (hasbtn)
{
if (id & 0x100)
{
int hatnum = ((id >> 4) & 0xF) + 1;
switch (id & 0xF)
{
case 0x1: str = "Hat %1 up"; break;
case 0x2: str = "Hat %1 right"; break;
case 0x4: str = "Hat %1 down"; break;
case 0x8: str = "Hat %1 left"; break;
}
str = str.arg(hatnum);
}
else
{
str = QString("Button %1").arg((id & 0xFFFF) + 1);
}
}
else
{
str = "";
}
if (id & 0x10000)
{
int axisnum = ((id >> 24) & 0xF) + 1;
if (hasbtn) str += " / ";
switch ((id >> 20) & 0xF)
{
case 0: str += QString("Axis %1 +").arg(axisnum); break;
case 1: str += QString("Axis %1 -").arg(axisnum); break;
case 2: str += QString("Trigger %1").arg(axisnum); break;
}
}
return str;
}