all repos — mgba @ 67905d281bfecbb06f51f2ca5ac939df378734a5

mGBA Game Boy Advance Emulator

src/platform/qt/ShortcutView.cpp (view raw)

  1/* Copyright (c) 2013-2015 Jeffrey Pfau
  2 *
  3 * This Source Code Form is subject to the terms of the Mozilla Public
  4 * License, v. 2.0. If a copy of the MPL was not distributed with this
  5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
  6#include "ShortcutView.h"
  7
  8#include "GamepadButtonEvent.h"
  9#include "InputController.h"
 10#include "ShortcutController.h"
 11
 12#include <QKeyEvent>
 13
 14using namespace QGBA;
 15
 16ShortcutView::ShortcutView(QWidget* parent)
 17	: QWidget(parent)
 18	, m_controller(nullptr)
 19	, m_input(nullptr)
 20{
 21	m_ui.setupUi(this);
 22	m_ui.keyEdit->setValueKey(0);
 23
 24	connect(m_ui.gamepadButton, &QAbstractButton::pressed, [this]() {
 25		bool signalsBlocked = m_ui.keyEdit->blockSignals(true);
 26		m_ui.keyEdit->setValueButton(-1);
 27		m_ui.keyEdit->blockSignals(signalsBlocked);
 28	});
 29	connect(m_ui.keyboardButton, &QAbstractButton::pressed, [this]() {
 30		bool signalsBlocked = m_ui.keyEdit->blockSignals(true);
 31		m_ui.keyEdit->setValueKey(0);
 32		m_ui.keyEdit->blockSignals(signalsBlocked);
 33	});
 34	connect(m_ui.keyEdit, SIGNAL(valueChanged(int)), this, SLOT(updateButton(int)));
 35	connect(m_ui.keyEdit, SIGNAL(axisChanged(int, int)), this, SLOT(updateAxis(int, int)));
 36	connect(m_ui.shortcutTable, SIGNAL(doubleClicked(const QModelIndex&)), this, SLOT(load(const QModelIndex&)));
 37	connect(m_ui.clearButton, SIGNAL(clicked()), this, SLOT(clear()));
 38}
 39
 40ShortcutView::~ShortcutView() {
 41	m_input->releaseFocus(this);
 42}
 43
 44void ShortcutView::setController(ShortcutController* controller) {
 45	m_controller = controller;
 46	m_ui.shortcutTable->setModel(controller);
 47}
 48
 49void ShortcutView::setInputController(InputController* controller) {
 50	if (m_input) {
 51		m_input->releaseFocus(this);
 52	}
 53	m_input = controller;
 54	m_input->stealFocus(this);
 55}
 56
 57void ShortcutView::load(const QModelIndex& index) {
 58	if (!m_controller) {
 59		return;
 60	}
 61	if (m_controller->isMenuAt(index)) {
 62		return;
 63	}
 64	int shortcut = m_controller->shortcutAt(index);
 65	if (index.column() == 1) {
 66		m_ui.keyboardButton->click();
 67	} else if (index.column() == 2) {
 68		m_ui.gamepadButton->click();
 69	}
 70	bool blockSignals = m_ui.keyEdit->blockSignals(true);
 71	m_ui.keyEdit->setFocus(Qt::MouseFocusReason);
 72	if (m_ui.gamepadButton->isChecked()) {
 73		m_ui.keyEdit->setValueButton(-1); // There are no default bindings
 74	} else {
 75		m_ui.keyEdit->setValueKey(shortcut);
 76	}
 77	m_ui.keyEdit->blockSignals(blockSignals);
 78}
 79
 80void ShortcutView::clear() {
 81	if (!m_controller) {
 82		return;
 83	}
 84	QModelIndex index = m_ui.shortcutTable->selectionModel()->currentIndex();
 85	if (m_controller->isMenuAt(index)) {
 86		return;
 87	}
 88	if (m_ui.gamepadButton->isChecked()) {
 89		m_controller->clearButton(index);
 90		m_ui.keyEdit->setValueButton(-1);
 91	} else {
 92		m_controller->clearKey(index);
 93		m_ui.keyEdit->setValueKey(-1);
 94	}
 95}
 96
 97void ShortcutView::updateButton(int button) {
 98	if (!m_controller || m_controller->isMenuAt(m_ui.shortcutTable->selectionModel()->currentIndex())) {
 99		return;
100	}
101	if (m_ui.gamepadButton->isChecked()) {
102		m_controller->updateButton(m_ui.shortcutTable->selectionModel()->currentIndex(), button);
103	} else {
104		m_controller->updateKey(m_ui.shortcutTable->selectionModel()->currentIndex(), button);
105	}
106}
107
108void ShortcutView::updateAxis(int axis, int direction) {
109	if (!m_controller || m_controller->isMenuAt(m_ui.shortcutTable->selectionModel()->currentIndex())) {
110		return;
111	}
112	m_controller->updateAxis(m_ui.shortcutTable->selectionModel()->currentIndex(), axis,
113	                         static_cast<GamepadAxisEvent::Direction>(direction));
114}
115
116void ShortcutView::closeEvent(QCloseEvent*) {
117	if (m_input) {
118		m_input->releaseFocus(this);
119	}
120}
121
122bool ShortcutView::event(QEvent* event) {
123	if (m_input) {
124		QEvent::Type type = event->type();
125		if (type == QEvent::WindowActivate || type == QEvent::Show) {
126			m_input->stealFocus(this);
127		} else if (type == QEvent::WindowDeactivate || type == QEvent::Hide) {
128			m_input->releaseFocus(this);
129		}
130	}
131	return QWidget::event(event);
132}