| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,70 @@ | ||
| // Copyright 2017 Dolphin Emulator Project | ||
| // Licensed under GPLv2+ | ||
| // Refer to the license.txt file included. | ||
|
|
||
| #include "DolphinQt2/NetPlay/GameListDialog.h" | ||
|
|
||
| #include <QDialogButtonBox> | ||
| #include <QListWidget> | ||
| #include <QVBoxLayout> | ||
|
|
||
| #include "DolphinQt2/GameList/GameListModel.h" | ||
| #include "DolphinQt2/Settings.h" | ||
|
|
||
| GameListDialog::GameListDialog(QWidget* parent) : QDialog(parent) | ||
| { | ||
| setWindowFlags(windowFlags() & ~Qt::WindowContextHelpButtonHint); | ||
|
|
||
| CreateWidgets(); | ||
| ConnectWidgets(); | ||
| } | ||
|
|
||
| void GameListDialog::CreateWidgets() | ||
| { | ||
| m_main_layout = new QVBoxLayout; | ||
| m_game_list = new QListWidget; | ||
| m_button_box = new QDialogButtonBox(QDialogButtonBox::Ok); | ||
| m_button_box->setEnabled(false); | ||
|
|
||
| m_main_layout->addWidget(m_game_list); | ||
| m_main_layout->addWidget(m_button_box); | ||
|
|
||
| setLayout(m_main_layout); | ||
| } | ||
|
|
||
| void GameListDialog::ConnectWidgets() | ||
| { | ||
| connect(m_game_list, &QListWidget::itemSelectionChanged, [this] { | ||
| int row = m_game_list->currentRow(); | ||
|
|
||
| m_button_box->setEnabled(row != -1); | ||
| m_game_id = m_game_list->currentItem()->text(); | ||
| }); | ||
| connect(m_button_box, &QDialogButtonBox::accepted, this, &GameListDialog::accept); | ||
| } | ||
|
|
||
| void GameListDialog::PopulateGameList() | ||
| { | ||
| auto* game_list_model = Settings::Instance().GetGameListModel(); | ||
|
|
||
| m_game_list->clear(); | ||
|
|
||
| for (int i = 0; i < game_list_model->rowCount(QModelIndex()); i++) | ||
| { | ||
| auto* item = new QListWidgetItem(game_list_model->GetUniqueID(i)); | ||
| m_game_list->addItem(item); | ||
| } | ||
|
|
||
| m_game_list->sortItems(); | ||
| } | ||
|
|
||
| const QString& GameListDialog::GetSelectedUniqueID() | ||
| { | ||
| return m_game_id; | ||
| } | ||
|
|
||
| int GameListDialog::exec() | ||
| { | ||
| PopulateGameList(); | ||
| return QDialog::exec(); | ||
| } |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,32 @@ | ||
| // Copyright 2017 Dolphin Emulator Project | ||
| // Licensed under GPLv2+ | ||
| // Refer to the license.txt file included. | ||
|
|
||
| #pragma once | ||
|
|
||
| #include <QDialog> | ||
|
|
||
| class GameListModel; | ||
| class QVBoxLayout; | ||
| class QListWidget; | ||
| class QDialogButtonBox; | ||
|
|
||
| class GameListDialog : public QDialog | ||
| { | ||
| Q_OBJECT | ||
| public: | ||
| explicit GameListDialog(QWidget* parent); | ||
|
|
||
| int exec(); | ||
| const QString& GetSelectedUniqueID(); | ||
|
|
||
| private: | ||
| void CreateWidgets(); | ||
| void ConnectWidgets(); | ||
| void PopulateGameList(); | ||
|
|
||
| QVBoxLayout* m_main_layout; | ||
| QListWidget* m_game_list; | ||
| QDialogButtonBox* m_button_box; | ||
| QString m_game_id; | ||
| }; |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,134 @@ | ||
| // Copyright 2017 Dolphin Emulator Project | ||
| // Licensed under GPLv2+ | ||
| // Refer to the license.txt file included. | ||
|
|
||
| #include "MD5Dialog.h" | ||
|
|
||
| #include "DolphinQt2/Settings.h" | ||
|
|
||
| #include <QDialogButtonBox> | ||
| #include <QGroupBox> | ||
| #include <QLabel> | ||
| #include <QProgressBar> | ||
| #include <QVBoxLayout> | ||
|
|
||
| static QString GetPlayerNameFromPID(int pid) | ||
| { | ||
| QString player_name = QObject::tr("Invalid Player ID"); | ||
| for (const auto* player : Settings::Instance().GetNetPlayClient()->GetPlayers()) | ||
| { | ||
| if (player->pid == pid) | ||
| { | ||
| player_name = QString::fromStdString(player->name); | ||
| break; | ||
| } | ||
| } | ||
| return player_name; | ||
| } | ||
|
|
||
| MD5Dialog::MD5Dialog(QWidget* parent) : QDialog(parent) | ||
| { | ||
| CreateWidgets(); | ||
| ConnectWidgets(); | ||
| setWindowTitle(tr("MD5 Checksum")); | ||
| } | ||
|
|
||
| void MD5Dialog::CreateWidgets() | ||
| { | ||
| m_main_layout = new QVBoxLayout; | ||
| m_progress_box = new QGroupBox; | ||
| m_progress_layout = new QVBoxLayout; | ||
| m_button_box = new QDialogButtonBox(QDialogButtonBox::Close); | ||
| m_check_label = new QLabel; | ||
|
|
||
| m_progress_box->setLayout(m_progress_layout); | ||
|
|
||
| m_main_layout->addWidget(m_progress_box); | ||
| m_main_layout->addWidget(m_check_label); | ||
| m_main_layout->addWidget(m_button_box); | ||
| setLayout(m_main_layout); | ||
| } | ||
|
|
||
| void MD5Dialog::ConnectWidgets() | ||
| { | ||
| connect(m_button_box, &QDialogButtonBox::rejected, this, &MD5Dialog::reject); | ||
| } | ||
|
|
||
| void MD5Dialog::show(const QString& title) | ||
| { | ||
| m_progress_box->setTitle(title); | ||
|
|
||
| for (auto& pair : m_progress_bars) | ||
| { | ||
| m_progress_layout->removeWidget(pair.second); | ||
| pair.second->deleteLater(); | ||
| } | ||
|
|
||
| for (auto& pair : m_status_labels) | ||
| { | ||
| m_progress_layout->removeWidget(pair.second); | ||
| pair.second->deleteLater(); | ||
| } | ||
|
|
||
| m_progress_bars.clear(); | ||
| m_status_labels.clear(); | ||
|
|
||
| for (const auto* player : Settings::Instance().GetNetPlayClient()->GetPlayers()) | ||
| { | ||
| m_progress_bars[player->pid] = new QProgressBar; | ||
| m_status_labels[player->pid] = new QLabel; | ||
|
|
||
| m_progress_layout->addWidget(m_progress_bars[player->pid]); | ||
| m_progress_layout->addWidget(m_status_labels[player->pid]); | ||
| } | ||
|
|
||
| m_last_result = ""; | ||
|
|
||
| QDialog::show(); | ||
| } | ||
|
|
||
| void MD5Dialog::SetProgress(int pid, int progress) | ||
| { | ||
| QString player_name = GetPlayerNameFromPID(pid); | ||
|
|
||
| if (!m_status_labels.count(pid)) | ||
| return; | ||
|
|
||
| m_status_labels[pid]->setText( | ||
| tr("%1[%2]: %3 %").arg(player_name, QString::number(pid), QString::number(progress))); | ||
| m_progress_bars[pid]->setValue(progress); | ||
| } | ||
|
|
||
| void MD5Dialog::SetResult(int pid, const std::string& result) | ||
| { | ||
| QString player_name = GetPlayerNameFromPID(pid); | ||
|
|
||
| if (!m_status_labels.count(pid)) | ||
| return; | ||
|
|
||
| m_status_labels[pid]->setText( | ||
| tr("%1[%2]: %3").arg(player_name, QString::number(pid), QString::fromStdString(result))); | ||
|
|
||
| if (m_last_result == "") | ||
| { | ||
| m_check_label->setText(tr("The hashes match!")); | ||
| return; | ||
| } | ||
|
|
||
| if (m_last_result != result) | ||
| { | ||
| m_check_label->setText(tr("The hashes do not match!")); | ||
| } | ||
|
|
||
| m_last_result = result; | ||
| } | ||
|
|
||
| void MD5Dialog::reject() | ||
| { | ||
| auto* server = Settings::Instance().GetNetPlayServer(); | ||
|
|
||
| if (server) | ||
| server->AbortMD5(); | ||
|
|
||
| QDialog::reject(); | ||
| } |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,42 @@ | ||
| // Copyright 2017 Dolphin Emulator Project | ||
| // Licensed under GPLv2+ | ||
| // Refer to the license.txt file included. | ||
|
|
||
| #pragma once | ||
|
|
||
| #include <QDialog> | ||
|
|
||
| class QDialogButtonBox; | ||
| class QGroupBox; | ||
| class QLabel; | ||
| class QProgressBar; | ||
| class QVBoxLayout; | ||
| class QWidget; | ||
|
|
||
| class MD5Dialog : public QDialog | ||
| { | ||
| Q_OBJECT | ||
| public: | ||
| MD5Dialog(QWidget* parent); | ||
|
|
||
| void show(const QString& title); | ||
| void SetProgress(int pid, int progress); | ||
| void SetResult(int pid, const std::string& md5); | ||
|
|
||
| void reject() override; | ||
|
|
||
| private: | ||
| void CreateWidgets(); | ||
| void ConnectWidgets(); | ||
|
|
||
| std::map<int, QProgressBar*> m_progress_bars; | ||
| std::map<int, QLabel*> m_status_labels; | ||
|
|
||
| std::string m_last_result; | ||
|
|
||
| QGroupBox* m_progress_box; | ||
| QVBoxLayout* m_progress_layout; | ||
| QVBoxLayout* m_main_layout; | ||
| QLabel* m_check_label; | ||
| QDialogButtonBox* m_button_box; | ||
| }; |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,110 @@ | ||
| // Copyright 2017 Dolphin Emulator Project | ||
| // Licensed under GPLv2+ | ||
| // Refer to the license.txt file included. | ||
|
|
||
| #pragma once | ||
|
|
||
| #include <QDialog> | ||
|
|
||
| #include "Core/NetPlayClient.h" | ||
| #include "VideoCommon/OnScreenDisplay.h" | ||
|
|
||
| class MD5Dialog; | ||
| class GameListModel; | ||
| class NetPlayServer; | ||
| class PadMappingDialog; | ||
| class QCheckBox; | ||
| class QComboBox; | ||
| class QGridLayout; | ||
| class QGroupBox; | ||
| class QLabel; | ||
| class QLineEdit; | ||
| class QListWidget; | ||
| class QPushButton; | ||
| class QSpinBox; | ||
| class QTextEdit; | ||
|
|
||
| class NetPlayDialog : public QDialog, public NetPlayUI | ||
| { | ||
| Q_OBJECT | ||
| public: | ||
| NetPlayDialog(QWidget* parent); | ||
|
|
||
| void show(std::string nickname, bool use_traversal); | ||
| void reject() override; | ||
|
|
||
| // NetPlayUI methods | ||
| void BootGame(const std::string& filename) override; | ||
| void StopGame() override; | ||
|
|
||
| void Update() override; | ||
| void AppendChat(const std::string& msg) override; | ||
|
|
||
| void OnMsgChangeGame(const std::string& filename) override; | ||
| void OnMsgStartGame() override; | ||
| void OnMsgStopGame() override; | ||
| void OnPadBufferChanged(u32 buffer) override; | ||
| void OnDesync(u32 frame, const std::string& player) override; | ||
| void OnConnectionLost() override; | ||
| void OnTraversalError(int error) override; | ||
| bool IsRecording() override; | ||
| std::string FindGame(const std::string& game) override; | ||
| void ShowMD5Dialog(const std::string& file_identifier) override; | ||
| void SetMD5Progress(int pid, int progress) override; | ||
| void SetMD5Result(int pid, const std::string& result) override; | ||
| void AbortMD5() override; | ||
| signals: | ||
| void EmulationStopped(); | ||
| void Boot(const QString& filename); | ||
| void Stop(); | ||
|
|
||
| private: | ||
| void CreateChatLayout(); | ||
| void CreatePlayersLayout(); | ||
| void CreateMainLayout(); | ||
| void ConnectWidgets(); | ||
| void OnChat(); | ||
| void OnStart(); | ||
| void OnMD5Combo(int index); | ||
| void DisplayMessage(const QString& msg, const std::string& color, | ||
| int duration = OSD::Duration::NORMAL); | ||
| void UpdateGUI(); | ||
| void GameStatusChanged(bool running); | ||
|
|
||
| void SetGame(const QString& game_path); | ||
|
|
||
| // Chat | ||
| QGroupBox* m_chat_box; | ||
| QTextEdit* m_chat_edit; | ||
| QLineEdit* m_chat_type_edit; | ||
| QPushButton* m_chat_send_button; | ||
|
|
||
| // Players | ||
| QGroupBox* m_players_box; | ||
| QComboBox* m_room_box; | ||
| QLabel* m_hostcode_label; | ||
| QPushButton* m_hostcode_action_button; | ||
| QListWidget* m_players_list; | ||
| QPushButton* m_kick_button; | ||
| QPushButton* m_assign_ports_button; | ||
|
|
||
| // Other | ||
| QPushButton* m_game_button; | ||
| QComboBox* m_md5_box; | ||
| QPushButton* m_start_button; | ||
| QLabel* m_buffer_label; | ||
| QSpinBox* m_buffer_size_box; | ||
| QCheckBox* m_save_sd_box; | ||
| QCheckBox* m_load_wii_box; | ||
| QCheckBox* m_record_input_box; | ||
| QPushButton* m_quit_button; | ||
|
|
||
| QGridLayout* m_main_layout; | ||
| MD5Dialog* m_md5_dialog; | ||
| PadMappingDialog* m_pad_mapping; | ||
| std::string m_current_game; | ||
| std::string m_nickname; | ||
| GameListModel* m_game_list_model = nullptr; | ||
| bool m_use_traversal = false; | ||
| bool m_is_copy_button_retry = false; | ||
| }; |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,267 @@ | ||
| // Copyright 2017 Dolphin Emulator Project | ||
| // Licensed under GPLv2+ | ||
| // Refer to the license.txt file included. | ||
|
|
||
| #include "DolphinQt2/NetPlay/NetPlaySetupDialog.h" | ||
|
|
||
| #include "Core/Config/NetplaySettings.h" | ||
| #include "DolphinQt2/GameList/GameListModel.h" | ||
| #include "DolphinQt2/Settings.h" | ||
|
|
||
| #include <QCheckBox> | ||
| #include <QComboBox> | ||
| #include <QDialogButtonBox> | ||
| #include <QGridLayout> | ||
| #include <QLabel> | ||
| #include <QLineEdit> | ||
| #include <QListWidget> | ||
| #include <QMessageBox> | ||
| #include <QPushButton> | ||
| #include <QSettings> | ||
| #include <QSpinBox> | ||
| #include <QTabWidget> | ||
|
|
||
| NetPlaySetupDialog::NetPlaySetupDialog(QWidget* parent) | ||
| : QDialog(parent), m_game_list_model(Settings::Instance().GetGameListModel()) | ||
| { | ||
| setWindowTitle(tr("Dolphin NetPlay Setup")); | ||
|
|
||
| CreateMainLayout(); | ||
|
|
||
| std::string nickname = Config::Get(Config::NETPLAY_NICKNAME); | ||
| std::string traversal_choice = Config::Get(Config::NETPLAY_TRAVERSAL_CHOICE); | ||
| int connect_port = Config::Get(Config::NETPLAY_CONNECT_PORT); | ||
| int host_port = Config::Get(Config::NETPLAY_HOST_PORT); | ||
| int host_listen_port = Config::Get(Config::NETPLAY_LISTEN_PORT); | ||
| #ifdef USE_UPNP | ||
| bool use_upnp = Config::Get(Config::NETPLAY_USE_UPNP); | ||
|
|
||
| m_host_upnp->setChecked(use_upnp); | ||
| #endif | ||
|
|
||
| m_nickname_edit->setText(QString::fromStdString(nickname)); | ||
| m_connection_type->setCurrentIndex(traversal_choice == "direct" ? 0 : 1); | ||
| m_connect_port_box->setValue(connect_port); | ||
| m_host_port_box->setValue(host_port); | ||
|
|
||
| m_host_force_port_check->setChecked(false); | ||
| m_host_force_port_box->setValue(host_listen_port); | ||
| m_host_force_port_box->setEnabled(false); | ||
|
|
||
| OnConnectionTypeChanged(m_connection_type->currentIndex()); | ||
|
|
||
| int selected_game = QSettings().value(QStringLiteral("netplay/hostgame"), 0).toInt(); | ||
|
|
||
| if (selected_game >= m_host_games->count()) | ||
| selected_game = 0; | ||
|
|
||
| m_host_games->setCurrentItem(m_host_games->item(selected_game)); | ||
|
|
||
| ConnectWidgets(); | ||
| } | ||
|
|
||
| void NetPlaySetupDialog::CreateMainLayout() | ||
| { | ||
| m_main_layout = new QGridLayout; | ||
| m_button_box = new QDialogButtonBox(QDialogButtonBox::Cancel); | ||
| m_nickname_edit = new QLineEdit; | ||
| m_connection_type = new QComboBox; | ||
| m_reset_traversal_button = new QPushButton(tr("Reset Traversal Settings")); | ||
| m_tab_widget = new QTabWidget; | ||
|
|
||
| // Connection widget | ||
| auto* connection_widget = new QWidget; | ||
| auto* connection_layout = new QGridLayout; | ||
|
|
||
| m_ip_label = new QLabel; | ||
| m_ip_edit = new QLineEdit; | ||
| m_connect_port_label = new QLabel(tr("Port:")); | ||
| m_connect_port_box = new QSpinBox; | ||
| m_connect_button = new QPushButton(tr("Connect")); | ||
|
|
||
| m_connect_port_box->setMaximum(65535); | ||
|
|
||
| connection_layout->addWidget(m_ip_label, 0, 0); | ||
| connection_layout->addWidget(m_ip_edit, 0, 1); | ||
| connection_layout->addWidget(m_connect_port_label, 0, 2); | ||
| connection_layout->addWidget(m_connect_port_box, 0, 3); | ||
| connection_layout->addWidget( | ||
| new QLabel(tr( | ||
| "ALERT:\n\n" | ||
| "All players must use the same Dolphin version.\n" | ||
| "All memory cards, SD cards and cheats must be identical between players or disabled.\n" | ||
| "If DSP LLE is used, DSP ROMs must be identical between players.\n" | ||
| "If connecting directly, the host must have the chosen UDP port open/forwarded!\n" | ||
| "\n" | ||
| "Wii Remote support in netplay is experimental and should not be expected to work.\n")), | ||
| 1, 0, -1, -1); | ||
| connection_layout->addWidget(m_connect_button, 3, 3, Qt::AlignRight); | ||
|
|
||
| connection_widget->setLayout(connection_layout); | ||
|
|
||
| // Host widget | ||
| auto* host_widget = new QWidget; | ||
| auto* host_layout = new QGridLayout; | ||
| m_host_port_label = new QLabel(tr("Port:")); | ||
| m_host_port_box = new QSpinBox; | ||
| m_host_force_port_check = new QCheckBox(tr("Force Listen Port:")); | ||
| m_host_force_port_box = new QSpinBox; | ||
|
|
||
| #ifdef USE_UPNP | ||
| m_host_upnp = new QCheckBox(tr("Forward port (UPnP)")); | ||
| #endif | ||
| m_host_games = new QListWidget; | ||
| m_host_button = new QPushButton(tr("Host")); | ||
|
|
||
| m_host_port_box->setMaximum(65535); | ||
| m_host_force_port_box->setMaximum(65535); | ||
|
|
||
| host_layout->addWidget(m_host_port_label, 0, 0); | ||
| host_layout->addWidget(m_host_port_box, 0, 1); | ||
| #ifdef USE_UPNP | ||
| host_layout->addWidget(m_host_upnp, 0, 2); | ||
| #endif | ||
| host_layout->addWidget(m_host_games, 1, 0, 1, -1); | ||
| host_layout->addWidget(m_host_force_port_check, 2, 0); | ||
| host_layout->addWidget(m_host_force_port_box, 2, 1, Qt::AlignLeft); | ||
| host_layout->addWidget(m_host_button, 2, 2, Qt::AlignRight); | ||
|
|
||
| host_widget->setLayout(host_layout); | ||
|
|
||
| m_connection_type->addItem(tr("Direct Connection")); | ||
| m_connection_type->addItem(tr("Traversal Server")); | ||
|
|
||
| m_main_layout->addWidget(new QLabel(tr("Connection Type:")), 0, 0); | ||
| m_main_layout->addWidget(m_connection_type, 0, 1); | ||
| m_main_layout->addWidget(m_reset_traversal_button, 0, 2); | ||
| m_main_layout->addWidget(new QLabel(tr("Nickname:")), 1, 0); | ||
| m_main_layout->addWidget(m_nickname_edit, 1, 1); | ||
| m_main_layout->addWidget(m_tab_widget, 2, 0, 1, -1); | ||
| m_main_layout->addWidget(m_button_box, 3, 0, 1, -1); | ||
|
|
||
| // Tabs | ||
| m_tab_widget->addTab(connection_widget, tr("Connect")); | ||
| m_tab_widget->addTab(host_widget, tr("Host")); | ||
|
|
||
| setLayout(m_main_layout); | ||
| } | ||
|
|
||
| void NetPlaySetupDialog::ConnectWidgets() | ||
| { | ||
| connect(m_connection_type, static_cast<void (QComboBox::*)(int)>(&QComboBox::currentIndexChanged), | ||
| this, &NetPlaySetupDialog::OnConnectionTypeChanged); | ||
| connect(m_nickname_edit, &QLineEdit::textChanged, this, &NetPlaySetupDialog::SaveSettings); | ||
|
|
||
| // Connect widget | ||
| connect(m_ip_edit, &QLineEdit::textChanged, this, &NetPlaySetupDialog::SaveSettings); | ||
| connect(m_connect_port_box, static_cast<void (QSpinBox::*)(int)>(&QSpinBox::valueChanged), this, | ||
| &NetPlaySetupDialog::SaveSettings); | ||
| // Host widget | ||
| connect(m_host_port_box, static_cast<void (QSpinBox::*)(int)>(&QSpinBox::valueChanged), this, | ||
| &NetPlaySetupDialog::SaveSettings); | ||
| connect(m_host_games, static_cast<void (QListWidget::*)(int)>(&QListWidget::currentRowChanged), | ||
| [](int index) { QSettings().setValue(QStringLiteral("netplay/hostgame"), index); }); | ||
| connect(m_host_force_port_check, &QCheckBox::toggled, | ||
| [this](int value) { m_host_force_port_box->setEnabled(value); }); | ||
| #ifdef USE_UPNP | ||
| connect(m_host_upnp, &QCheckBox::stateChanged, this, &NetPlaySetupDialog::SaveSettings); | ||
| #endif | ||
|
|
||
| connect(m_connect_button, &QPushButton::clicked, this, &QDialog::accept); | ||
| connect(m_host_button, &QPushButton::clicked, this, &QDialog::accept); | ||
| connect(m_button_box, &QDialogButtonBox::rejected, this, &QDialog::reject); | ||
| connect(m_reset_traversal_button, &QPushButton::clicked, this, | ||
| &NetPlaySetupDialog::ResetTraversalHost); | ||
| } | ||
|
|
||
| void NetPlaySetupDialog::SaveSettings() | ||
| { | ||
| Config::SetBaseOrCurrent(Config::NETPLAY_NICKNAME, m_nickname_edit->text().toStdString()); | ||
| Config::SetBaseOrCurrent(Config::NETPLAY_HOST_CODE, m_ip_edit->text().toStdString()); | ||
| Config::SetBaseOrCurrent(Config::NETPLAY_CONNECT_PORT, | ||
| static_cast<u16>(m_connect_port_box->value())); | ||
| Config::SetBaseOrCurrent(Config::NETPLAY_HOST_PORT, static_cast<u16>(m_host_port_box->value())); | ||
| Config::SetBaseOrCurrent(Config::NETPLAY_USE_UPNP, m_host_upnp->isChecked()); | ||
|
|
||
| if (m_host_force_port_check->isChecked()) | ||
| Config::SetBaseOrCurrent(Config::NETPLAY_LISTEN_PORT, | ||
| static_cast<u16>(m_host_force_port_box->value())); | ||
| } | ||
|
|
||
| void NetPlaySetupDialog::OnConnectionTypeChanged(int index) | ||
| { | ||
| m_connect_port_box->setHidden(index != 0); | ||
| m_connect_port_label->setHidden(index != 0); | ||
|
|
||
| m_host_port_label->setHidden(index != 0); | ||
| m_host_port_box->setHidden(index != 0); | ||
| m_host_upnp->setHidden(index != 0); | ||
| m_host_force_port_check->setHidden(index == 0); | ||
| m_host_force_port_box->setHidden(index == 0); | ||
|
|
||
| m_reset_traversal_button->setHidden(index == 0); | ||
|
|
||
| std::string address = Config::Get(Config::NETPLAY_HOST_CODE); | ||
|
|
||
| m_ip_label->setText(index == 0 ? tr("IP Address:") : tr("Host Code:")); | ||
| m_ip_edit->setText(QString::fromStdString(address)); | ||
|
|
||
| Config::SetBaseOrCurrent(Config::NETPLAY_TRAVERSAL_CHOICE, | ||
| std::string(index == 0 ? "direct" : "traversal")); | ||
| } | ||
|
|
||
| void NetPlaySetupDialog::show() | ||
| { | ||
| PopulateGameList(); | ||
| QDialog::show(); | ||
| } | ||
|
|
||
| void NetPlaySetupDialog::accept() | ||
| { | ||
| SaveSettings(); | ||
| if (m_tab_widget->currentIndex() == 0) | ||
| { | ||
| emit Join(); | ||
| } | ||
| else | ||
| { | ||
| auto items = m_host_games->selectedItems(); | ||
| if (items.size() == 0) | ||
| { | ||
| QMessageBox::critical(this, tr("Error"), tr("You must select a game to host!")); | ||
| return; | ||
| } | ||
|
|
||
| emit Host(items[0]->text()); | ||
| } | ||
| } | ||
|
|
||
| void NetPlaySetupDialog::PopulateGameList() | ||
| { | ||
| m_host_games->clear(); | ||
| for (int i = 0; i < m_game_list_model->rowCount(QModelIndex()); i++) | ||
| { | ||
| auto title = m_game_list_model->GetUniqueID(i); | ||
| auto path = m_game_list_model->GetPath(i); | ||
|
|
||
| auto* item = new QListWidgetItem(title); | ||
| item->setData(Qt::UserRole, path); | ||
| m_host_games->addItem(item); | ||
| } | ||
|
|
||
| m_host_games->sortItems(); | ||
| } | ||
|
|
||
| void NetPlaySetupDialog::ResetTraversalHost() | ||
| { | ||
| Config::SetBaseOrCurrent(Config::NETPLAY_TRAVERSAL_SERVER, | ||
| Config::NETPLAY_TRAVERSAL_SERVER.default_value); | ||
| Config::SetBaseOrCurrent(Config::NETPLAY_TRAVERSAL_PORT, | ||
| Config::NETPLAY_TRAVERSAL_PORT.default_value); | ||
|
|
||
| QMessageBox::information( | ||
| this, tr("Reset Traversal Server"), | ||
| tr("Reset Traversal Server to %1:%2") | ||
| .arg(QString::fromStdString(Config::NETPLAY_TRAVERSAL_SERVER.default_value), | ||
| QString::number(Config::NETPLAY_TRAVERSAL_PORT.default_value))); | ||
| } |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,72 @@ | ||
| // Copyright 2017 Dolphin Emulator Project | ||
| // Licensed under GPLv2+ | ||
| // Refer to the license.txt file included. | ||
|
|
||
| #pragma once | ||
|
|
||
| #include <QDialog> | ||
|
|
||
| class GameListModel; | ||
| class QCheckBox; | ||
| class QComboBox; | ||
| class QDialogButtonBox; | ||
| class QLabel; | ||
| class QLineEdit; | ||
| class QListWidget; | ||
| class QGridLayout; | ||
| class QPushButton; | ||
| class QSpinBox; | ||
| class QTabWidget; | ||
|
|
||
| class NetPlaySetupDialog : public QDialog | ||
| { | ||
| Q_OBJECT | ||
| public: | ||
| NetPlaySetupDialog(QWidget* parent); | ||
|
|
||
| void accept() override; | ||
| void show(); | ||
|
|
||
| signals: | ||
| bool Join(); | ||
| bool Host(const QString& game_identifier); | ||
|
|
||
| private: | ||
| void CreateMainLayout(); | ||
| void ConnectWidgets(); | ||
| void PopulateGameList(); | ||
| void ResetTraversalHost(); | ||
|
|
||
| void SaveSettings(); | ||
|
|
||
| void OnConnectionTypeChanged(int index); | ||
|
|
||
| // Main Widget | ||
| QDialogButtonBox* m_button_box; | ||
| QComboBox* m_connection_type; | ||
| QLineEdit* m_nickname_edit; | ||
| QGridLayout* m_main_layout; | ||
| QTabWidget* m_tab_widget; | ||
| QPushButton* m_reset_traversal_button; | ||
|
|
||
| // Connection Widget | ||
| QLabel* m_ip_label; | ||
| QLineEdit* m_ip_edit; | ||
| QLabel* m_connect_port_label; | ||
| QSpinBox* m_connect_port_box; | ||
| QPushButton* m_connect_button; | ||
|
|
||
| // Host Widget | ||
| QLabel* m_host_port_label; | ||
| QSpinBox* m_host_port_box; | ||
| QListWidget* m_host_games; | ||
| QPushButton* m_host_button; | ||
| QCheckBox* m_host_force_port_check; | ||
| QSpinBox* m_host_force_port_box; | ||
|
|
||
| #ifdef USE_UPNP | ||
| QCheckBox* m_host_upnp; | ||
| #endif | ||
|
|
||
| GameListModel* m_game_list_model; | ||
| }; |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,94 @@ | ||
| // Copyright 2017 Dolphin Emulator Project | ||
| // Licensed under GPLv2+ | ||
| // Refer to the license.txt file included. | ||
|
|
||
| #include "DolphinQt2/NetPlay/PadMappingDialog.h" | ||
| #include "DolphinQt2/Settings.h" | ||
|
|
||
| #include "Core/NetPlayClient.h" | ||
|
|
||
| #include <QComboBox> | ||
| #include <QDialogButtonBox> | ||
| #include <QGridLayout> | ||
| #include <QLabel> | ||
|
|
||
| PadMappingDialog::PadMappingDialog(QWidget* parent) : QDialog(parent) | ||
| { | ||
| setWindowFlags(windowFlags() & ~Qt::WindowContextHelpButtonHint); | ||
|
|
||
| CreateWidgets(); | ||
| ConnectWidgets(); | ||
| } | ||
|
|
||
| void PadMappingDialog::CreateWidgets() | ||
| { | ||
| m_main_layout = new QGridLayout; | ||
| m_button_box = new QDialogButtonBox(QDialogButtonBox::Ok); | ||
|
|
||
| for (unsigned int i = 0; i < m_wii_boxes.size(); i++) | ||
| { | ||
| m_gc_boxes[i] = new QComboBox; | ||
| m_wii_boxes[i] = new QComboBox; | ||
|
|
||
| m_main_layout->addWidget(new QLabel(tr("GC Port %1").arg(i + 1)), 0, i); | ||
| m_main_layout->addWidget(new QLabel(tr("Wii Remote Port %1").arg(i + 1)), 0, 4 + i); | ||
| m_main_layout->addWidget(m_gc_boxes[i], 1, i); | ||
| m_main_layout->addWidget(m_wii_boxes[i], 1, 4 + i); | ||
| } | ||
|
|
||
| m_main_layout->addWidget(m_button_box, 2, 0, 1, -1); | ||
|
|
||
| setLayout(m_main_layout); | ||
| } | ||
|
|
||
| void PadMappingDialog::ConnectWidgets() | ||
| { | ||
| connect(m_button_box, &QDialogButtonBox::accepted, this, &QDialog::accept); | ||
| } | ||
|
|
||
| int PadMappingDialog::exec() | ||
| { | ||
| m_players = Settings::Instance().GetNetPlayClient()->GetPlayers(); | ||
|
|
||
| QStringList players; | ||
|
|
||
| players.append(tr("None")); | ||
|
|
||
| for (const auto& player : m_players) | ||
| players.append(QString::fromStdString(player->name)); | ||
|
|
||
| for (auto& combo_group : {m_gc_boxes, m_wii_boxes}) | ||
| { | ||
| for (auto& combo : combo_group) | ||
| { | ||
| combo->clear(); | ||
| combo->addItems(players); | ||
| connect(combo, static_cast<void (QComboBox::*)(int)>(&QComboBox::currentIndexChanged), this, | ||
| &PadMappingDialog::OnMappingChanged); | ||
| } | ||
| } | ||
|
|
||
| return QDialog::exec(); | ||
| } | ||
|
|
||
| PadMappingArray PadMappingDialog::GetGCPadArray() | ||
| { | ||
| return m_pad_mapping; | ||
| } | ||
|
|
||
| PadMappingArray PadMappingDialog::GetWiimoteArray() | ||
| { | ||
| return m_wii_mapping; | ||
| } | ||
|
|
||
| void PadMappingDialog::OnMappingChanged() | ||
| { | ||
| for (unsigned int i = 0; i < m_wii_boxes.size(); i++) | ||
| { | ||
| int gc_id = m_gc_boxes[i]->currentIndex(); | ||
| int wii_id = m_wii_boxes[i]->currentIndex(); | ||
|
|
||
| m_pad_mapping[i] = gc_id > 0 ? m_players[gc_id - 1]->pid : -1; | ||
| m_wii_mapping[i] = wii_id > 0 ? m_players[wii_id - 1]->pid : -1; | ||
| } | ||
| } |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,41 @@ | ||
| // Copyright 2017 Dolphin Emulator Project | ||
| // Licensed under GPLv2+ | ||
| // Refer to the license.txt file included. | ||
|
|
||
| #pragma once | ||
|
|
||
| #include <QDialog> | ||
|
|
||
| #include "Core/NetPlayProto.h" | ||
|
|
||
| class NetPlayClient; | ||
| class Player; | ||
| class QGridLayout; | ||
| class QComboBox; | ||
| class QDialogButtonBox; | ||
|
|
||
| class PadMappingDialog : public QDialog | ||
| { | ||
| Q_OBJECT | ||
| public: | ||
| explicit PadMappingDialog(QWidget* widget); | ||
|
|
||
| int exec(); | ||
|
|
||
| PadMappingArray GetGCPadArray(); | ||
| PadMappingArray GetWiimoteArray(); | ||
|
|
||
| private: | ||
| void CreateWidgets(); | ||
| void ConnectWidgets(); | ||
| void OnMappingChanged(); | ||
|
|
||
| PadMappingArray m_pad_mapping; | ||
| PadMappingArray m_wii_mapping; | ||
|
|
||
| QGridLayout* m_main_layout; | ||
| std::array<QComboBox*, 4> m_gc_boxes; | ||
| std::array<QComboBox*, 4> m_wii_boxes; | ||
| std::vector<const Player*> m_players; | ||
| QDialogButtonBox* m_button_box; | ||
| }; |