diff --git a/Source/Core/Core/ConfigManager.cpp b/Source/Core/Core/ConfigManager.cpp index 6ff2f314bc..f86db8aa46 100644 --- a/Source/Core/Core/ConfigManager.cpp +++ b/Source/Core/Core/ConfigManager.cpp @@ -265,6 +265,8 @@ void SConfig::SaveSlippiSettings(IniFile& ini) slippi->Set("PlaybackControls", m_slippiEnableSeek); slippi->Set("ForceNetplayPort", m_slippiForceNetplayPort); slippi->Set("NetplayPort", m_slippiNetplayPort); + slippi->Set("ForceLanIP", m_slippiForceLanIp); + slippi->Set("LanIP", m_slippiLanIp); } void SConfig::SaveMovieSettings(IniFile& ini) @@ -555,6 +557,8 @@ void SConfig::LoadSlippiSettings(IniFile& ini) m_strSlippiReplayDir = default_replay_dir; slippi->Get("ForceNetplayPort", &m_slippiForceNetplayPort, false); slippi->Get("NetplayPort", &m_slippiNetplayPort, 2626); + slippi->Get("ForceLanIP", &m_slippiForceLanIp, false); + slippi->Get("LanIP", &m_slippiLanIp, ""); } void SConfig::LoadMovieSettings(IniFile& ini) diff --git a/Source/Core/Core/ConfigManager.h b/Source/Core/Core/ConfigManager.h index a2ae4b379f..6ba8f1f148 100644 --- a/Source/Core/Core/ConfigManager.h +++ b/Source/Core/Core/ConfigManager.h @@ -163,9 +163,9 @@ struct SConfig // Slippi // enable Slippi Networking output - bool m_enableSpectator; + bool m_enableSpectator = true; int m_spectatorPort = 51441; - std::string m_strSlippiInput; + std::string m_strSlippiInput = ""; int m_slippiOnlineDelay = 2; bool m_slippiEnableSeek = true; bool m_slippiSaveReplays = true; @@ -175,6 +175,8 @@ struct SConfig bool m_blockingPipes = false; bool m_slippiForceNetplayPort = false; int m_slippiNetplayPort = 2626; + bool m_slippiForceLanIp = false; + std::string m_slippiLanIp = ""; // Interface settings bool bConfirmStop = false; diff --git a/Source/Core/Core/Slippi/SlippiMatchmaking.cpp b/Source/Core/Core/Slippi/SlippiMatchmaking.cpp index 8d6d2b3bfe..f8f2a6dd3f 100644 --- a/Source/Core/Core/Slippi/SlippiMatchmaking.cpp +++ b/Source/Core/Core/Slippi/SlippiMatchmaking.cpp @@ -365,6 +365,14 @@ void SlippiMatchmaking::startMatchmaking() } } + if (SConfig::GetInstance().m_slippiForceLanIp) + { + WARN_LOG(SLIPPI_ONLINE, "[Matchmaking] Overwriting LAN IP sent with configured address"); + sprintf(lan_addr, "%s:%d", SConfig::GetInstance().m_slippiLanIp.c_str(), m_hostPort); + } + + WARN_LOG_FMT(SLIPPI_ONLINE, "[Matchmaking] Sending LAN address: {}", lan_addr); + std::vector connectCodeBuf; connectCodeBuf.insert(connectCodeBuf.end(), m_searchSettings.connectCode.begin(), m_searchSettings.connectCode.end()); @@ -509,6 +517,8 @@ void SlippiMatchmaking::handleMatchmaking() auto lanIp = el.value("ipAddressLan", "1.1.1.1:123"); + WARN_LOG_FMT(SLIPPI_ONLINE, "LAN IP: {}", lanIp.c_str()); + if (exIpParts[0] != localExternalIp || lanIp.empty()) { // If external IPs are different, just use that address diff --git a/Source/Core/DolphinQt/Settings/SlippiPane.cpp b/Source/Core/DolphinQt/Settings/SlippiPane.cpp index 1640395c08..186a4ff4ed 100644 --- a/Source/Core/DolphinQt/Settings/SlippiPane.cpp +++ b/Source/Core/DolphinQt/Settings/SlippiPane.cpp @@ -82,6 +82,8 @@ void SlippiPane::CreateLayout() connect(delay_spin, qOverload(&QSpinBox::valueChanged), this, [](int delay) { SConfig::GetInstance().m_slippiOnlineDelay = delay; }); + // i'd like to note that I hate everything about how this is organized for the next two sections + // and a lot of the Qstring bullshit drives me up the wall. auto* netplay_port_spin = new QSpinBox(); netplay_port_spin->setFixedSize(60, 25); QSizePolicy sp_retain = netplay_port_spin->sizePolicy(); @@ -111,6 +113,41 @@ void SlippiPane::CreateLayout() online_settings_layout->addRow(netplay_port_layout); + auto* netplay_ip_edit = new QLineEdit(); + netplay_ip_edit->setFixedSize(100, 25); + sp_retain = netplay_ip_edit->sizePolicy(); + sp_retain.setRetainSizeWhenHidden(true); + netplay_ip_edit->setSizePolicy(sp_retain); + std::string ipRange = "(?:[0-1]?[0-9]?[0-9]|2[0-4][0-9]|25[0-5])"; + // You may want to use QRegularExpression for new code with Qt 5 (not mandatory). + QRegularExpression ipRegex(QString::fromStdString( + "^" + ipRange + "(\\." + ipRange + ")" + "(\\." + ipRange + ")" + "(\\." + ipRange + ")$")); + QRegularExpressionValidator* ipValidator = new QRegularExpressionValidator(ipRegex, this); + netplay_ip_edit->setValidator(ipValidator); + auto lan_ip = SConfig::GetInstance().m_slippiLanIp; + netplay_ip_edit->setText(QString::fromStdString(lan_ip)); + if (!SConfig::GetInstance().m_slippiForceLanIp) + { + netplay_ip_edit->hide(); + } + auto* enable_force_netplay_ip_checkbox = new QCheckBox(tr("Force Netplay IP:")); + enable_force_netplay_ip_checkbox->setToolTip( + tr("Enable this to force Slippi to use a specific LAN IP when connecting to users with a " + "matching WAN IP. Should not be required for most users.")); + + enable_force_netplay_ip_checkbox->setChecked(SConfig::GetInstance().m_slippiForceLanIp); + connect(enable_force_netplay_ip_checkbox, &QCheckBox::toggled, this, + [netplay_ip_edit](bool checked) { + SConfig::GetInstance().m_slippiForceLanIp = checked; + checked ? netplay_ip_edit->show() : netplay_ip_edit->hide(); + }); + auto* netplay_ip_layout = new QGridLayout(); + netplay_ip_layout->setColumnStretch(1, 1); + netplay_ip_layout->addWidget(enable_force_netplay_ip_checkbox, 0, 0); + netplay_ip_layout->addWidget(netplay_ip_edit, 0, 1, Qt::AlignLeft); + + online_settings_layout->addRow(netplay_ip_layout); + #else // Playback Settings auto* playback_settings = new QGroupBox(tr("Playback Settings"));