From 02a44b0247238240b22870a7e52b9f3132fb6736 Mon Sep 17 00:00:00 2001 From: Joshua Goins Date: Fri, 2 May 2025 15:17:32 -0400 Subject: [PATCH] Overhaul custom server settings, allow configuring more servers You can now configure the frontier server, the save data bank server and the data center travel server. The names of the existing settings should be clearer now, too. --- launcher/accountconfig.kcfg | 26 ++++-- launcher/include/launchercore.h | 5 +- launcher/src/gamerunner.cpp | 27 ++++-- launcher/src/launchercore.cpp | 6 +- launcher/src/squareenixlogin.cpp | 22 ++--- launcher/ui/Settings/AccountSettings.qml | 106 ++++++++++++++++------- 6 files changed, 130 insertions(+), 62 deletions(-) diff --git a/launcher/accountconfig.kcfg b/launcher/accountconfig.kcfg index 3d2dea6..7703cca 100644 --- a/launcher/accountconfig.kcfg +++ b/launcher/accountconfig.kcfg @@ -61,23 +61,35 @@ SPDX-License-Identifier: CC0-1.0 https - + - + - - 7000 + + - + ffxiv.com - + square-enix.com - + finalfantasyxiv.com + + + + + + + + + + + + diff --git a/launcher/include/launchercore.h b/launcher/include/launchercore.h index c094ef2..0c31aa3 100755 --- a/launcher/include/launchercore.h +++ b/launcher/include/launchercore.h @@ -46,10 +46,7 @@ struct LoginAuth { QString SID; int region = 2; // america? int maxExpansion = 1; - - // if empty, don't set on the client - QString lobbyHost, frontierHost; - int lobbyHostPort; + Account *account = nullptr; }; class LauncherCore : public QObject diff --git a/launcher/src/gamerunner.cpp b/launcher/src/gamerunner.cpp index 1ccffe4..8cd5213 100644 --- a/launcher/src/gamerunner.cpp +++ b/launcher/src/gamerunner.cpp @@ -250,12 +250,29 @@ QString GameRunner::getGameArgs(const Profile &profile, const std::optionalwinePrefixPath()); if (auth) { - if (!auth->lobbyHost.isEmpty()) { - gameArgs.push_back({QStringLiteral("DEV.GMServerHost"), auth->frontierHost}); - for (int i = 1; i < 9; i++) { - gameArgs.push_back({QStringLiteral("DEV.LobbyHost0%1").arg(QString::number(i)), auth->lobbyHost}); - gameArgs.push_back({QStringLiteral("DEV.LobbyPort0%1").arg(QString::number(i)), QString::number(auth->lobbyHostPort)}); + auto config = auth->account->config(); + if (!config->frontierServer().isEmpty()) { + gameArgs.push_back({QStringLiteral("DEV.GMServerHost"), config->frontierServer()}); + } + + if (!config->lobbyServer().isEmpty()) { + for (int i = 1; i < 13; i++) { + gameArgs.push_back({QStringLiteral("DEV.LobbyHost%1").arg(QString::number(i), 2, '0'_L1), config->lobbyServer()}); + gameArgs.push_back({QStringLiteral("DEV.LobbyPort%1").arg(QString::number(i), 2, '0'_L1), QString::number(config->lobbyPort())}); } + + // the special server!! + gameArgs.push_back({QStringLiteral("DEV.LobbyHost98"), config->lobbyServer()}); + gameArgs.push_back({QStringLiteral("DEV.LobbyPort98"), QString::number(config->lobbyPort())}); + } + + if (!config->saveDataBankServer().isEmpty()) { + gameArgs.push_back({QStringLiteral("DEV.SaveDataBankHost"), config->saveDataBankServer()}); + gameArgs.push_back({QStringLiteral("DEV.SaveDataBankPort"), QString::number(config->saveDataBankPort())}); + } + + if (!config->dataCenterTravelServer().isEmpty()) { + gameArgs.push_back({QStringLiteral("DEV.DktWebHost"), config->dataCenterTravelServer()}); } if (profile.account()->config()->license() == Account::GameLicense::WindowsSteam) { diff --git a/launcher/src/launchercore.cpp b/launcher/src/launchercore.cpp index f6cd257..32db888 100755 --- a/launcher/src/launchercore.cpp +++ b/launcher/src/launchercore.cpp @@ -185,7 +185,7 @@ void LauncherCore::fetchAvatar(Account *account) QUrl url; url.setScheme(account->config()->preferredProtocol()); - url.setHost(QStringLiteral("na.%1").arg(account->config()->mainServer())); // TODO: NA isnt the only thing in the world... + url.setHost(QStringLiteral("na.%1").arg(account->config()->newServer())); url.setPath(QStringLiteral("/lodestone/character/%1").arg(account->config()->lodestoneId())); const QNetworkRequest request(url); @@ -500,7 +500,7 @@ QCoro::Task<> LauncherCore::fetchNews() QUrl headlineUrl; headlineUrl.setScheme(currentProfile()->account()->config()->preferredProtocol()); - headlineUrl.setHost(QStringLiteral("frontier.%1").arg(currentProfile()->account()->config()->squareEnixServer())); + headlineUrl.setHost(QStringLiteral("frontier.%1").arg(currentProfile()->account()->config()->oldServer())); headlineUrl.setPath(QStringLiteral("/news/headline.json")); headlineUrl.setQuery(query); @@ -519,7 +519,7 @@ QCoro::Task<> LauncherCore::fetchNews() QUrl bannerUrl; bannerUrl.setScheme(currentProfile()->account()->config()->preferredProtocol()); - bannerUrl.setHost(QStringLiteral("frontier.%1").arg(currentProfile()->account()->config()->squareEnixServer())); + bannerUrl.setHost(QStringLiteral("frontier.%1").arg(currentProfile()->account()->config()->oldServer())); bannerUrl.setPath(QStringLiteral("/v2/topics/%1/banner.json").arg(QStringLiteral("en-us"))); bannerUrl.setQuery(query); diff --git a/launcher/src/squareenixlogin.cpp b/launcher/src/squareenixlogin.cpp index e2d5d12..baa0b6f 100644 --- a/launcher/src/squareenixlogin.cpp +++ b/launcher/src/squareenixlogin.cpp @@ -73,13 +73,7 @@ QCoro::Task> SquareEnixLogin::login(LoginInformation *i co_return std::nullopt; } - // Inject custom game server if set - if (!info->profile->account()->config()->lobbyHost().isEmpty()) { - m_auth.frontierHost = info->profile->account()->config()->gMServerHost(); - m_auth.lobbyHost = info->profile->account()->config()->lobbyHost(); - m_auth.lobbyHostPort = info->profile->account()->config()->lobbyHostPort(); - } - + m_auth.account = info->profile->account(); co_return m_auth; } @@ -90,7 +84,7 @@ QCoro::Task SquareEnixLogin::checkGateStatus() const QUrl url; url.setScheme(m_info->profile->account()->config()->preferredProtocol()); - url.setHost(QStringLiteral("frontier.%1").arg(m_info->profile->account()->config()->squareEnixServer())); + url.setHost(QStringLiteral("frontier.%1").arg(m_info->profile->account()->config()->oldServer())); url.setPath(QStringLiteral("/worldStatus/gate_status.json")); url.setQuery(QString::number(QDateTime::currentMSecsSinceEpoch())); @@ -131,7 +125,7 @@ QCoro::Task SquareEnixLogin::checkLoginStatus() const QUrl url; url.setScheme(m_info->profile->account()->config()->preferredProtocol()); - url.setHost(QStringLiteral("frontier.%1").arg(m_info->profile->account()->config()->squareEnixServer())); + url.setHost(QStringLiteral("frontier.%1").arg(m_info->profile->account()->config()->oldServer())); url.setPath(QStringLiteral("/worldStatus/login_status.json")); url.setQuery(QString::number(QDateTime::currentMSecsSinceEpoch())); @@ -173,7 +167,7 @@ QCoro::Task SquareEnixLogin::checkBootUpdates() QUrl url; url.setScheme(QStringLiteral("http")); - url.setHost(QStringLiteral("patch-bootver.%1").arg(m_info->profile->account()->config()->squareEnixServer())); + url.setHost(QStringLiteral("patch-bootver.%1").arg(m_info->profile->account()->config()->oldServer())); url.setPath(QStringLiteral("/http/%1/%2/%3/").arg(platform, bootUpdateChannel, m_info->profile->bootVersion())); url.setQuery(query); @@ -184,7 +178,7 @@ QCoro::Task SquareEnixLogin::checkBootUpdates() request.setHeader(QNetworkRequest::KnownHeaders::UserAgentHeader, patchUserAgent); } - request.setRawHeader(QByteArrayLiteral("Host"), QStringLiteral("patch-bootver.%1").arg(m_info->profile->account()->config()->squareEnixServer()).toUtf8()); + request.setRawHeader(QByteArrayLiteral("Host"), QStringLiteral("patch-bootver.%1").arg(m_info->profile->account()->config()->oldServer()).toUtf8()); Utility::printRequest(QStringLiteral("GET"), request); const auto reply = m_launcher.mgr()->get(request); @@ -248,7 +242,7 @@ QCoro::Task> SquareEnixLogin::getStor QUrl url; url.setScheme(m_info->profile->account()->config()->preferredProtocol()); - url.setHost(QStringLiteral("ffxiv-login.%1").arg(m_info->profile->account()->config()->squareEnixLoginServer())); + url.setHost(QStringLiteral("ffxiv-login.%1").arg(m_info->profile->account()->config()->loginServer())); url.setPath(QStringLiteral("/oauth/ffxivarr/login/top")); url.setQuery(query); @@ -306,7 +300,7 @@ QCoro::Task SquareEnixLogin::loginOAuth() QUrl url; url.setScheme(m_info->profile->account()->config()->preferredProtocol()); - url.setHost(QStringLiteral("ffxiv-login.%1").arg(m_info->profile->account()->config()->squareEnixLoginServer())); + url.setHost(QStringLiteral("ffxiv-login.%1").arg(m_info->profile->account()->config()->loginServer())); url.setPath(QStringLiteral("/oauth/ffxivarr/login/login.send")); QNetworkRequest request(url); @@ -367,7 +361,7 @@ QCoro::Task SquareEnixLogin::registerSession() QUrl url; url.setScheme(m_info->profile->account()->config()->preferredProtocol()); - url.setHost(QStringLiteral("patch-gamever.%1").arg(m_info->profile->account()->config()->squareEnixServer())); + url.setHost(QStringLiteral("patch-gamever.%1").arg(m_info->profile->account()->config()->oldServer())); url.setPath(QStringLiteral("/http/%1/%2/%3/%4").arg(platform, gameUpdateChannel, m_info->profile->baseGameVersion(), m_SID)); auto request = QNetworkRequest(url); diff --git a/launcher/ui/Settings/AccountSettings.qml b/launcher/ui/Settings/AccountSettings.qml index 7046460..7eca958 100644 --- a/launcher/ui/Settings/AccountSettings.qml +++ b/launcher/ui/Settings/AccountSettings.qml @@ -250,9 +250,10 @@ FormCard.FormCardPage { FormCard.FormTextFieldDelegate { id: squareMainServerDelegate - label: i18n("SE Main Server (ffxiv.com)") - text: page.account.config.squareEnixServer - onTextChanged: page.account.config.squareEnixServer = text + label: i18n("Old Server") + text: page.account.config.oldServer + placeholderText: "ffxiv.com" + onTextChanged: page.account.config.oldServer = text } FormCard.FormDelegateSeparator { @@ -263,9 +264,10 @@ FormCard.FormCardPage { FormCard.FormTextFieldDelegate { id: loginServerDelegate - label: i18n("SE Login Server (square-enix.com)") - text: page.account.config.squareEnixLoginServer - onTextChanged: page.account.config.squareEnixLoginServer = text + label: i18n("Login Server") + text: page.account.config.loginServer + placeholderText: "square-enix.com" + onTextChanged: page.account.config.loginServer = text } FormCard.FormDelegateSeparator { @@ -276,35 +278,24 @@ FormCard.FormCardPage { FormCard.FormTextFieldDelegate { id: mainServerDelegate - label: i18n("Main Server (finalfantasyxiv.com)") - text: page.account.config.mainServer - onTextChanged: page.account.config.mainServer = text + label: i18n("New Server") + text: page.account.config.newServer + placeholderText: "finalfantasyxiv.com" + onTextChanged: page.account.config.newServer = text } FormCard.FormDelegateSeparator { above: mainServerDelegate - below: gmServerDelegate - } - - FormCard.FormTextFieldDelegate { - id: gmServerDelegate - - label: i18n("GM Server (leave blank for default)") - text: page.account.config.gMServerHost - onTextChanged: page.account.config.gMServerHost = text - } - - FormCard.FormDelegateSeparator { - above: gmServerDelegate below: gameServerDelegate } FormCard.FormTextFieldDelegate { id: gameServerDelegate - label: i18n("Lobby Server (leave blank for default)") - text: page.account.config.lobbyHost - onTextChanged: page.account.config.lobbyHost = text + label: i18n("Lobby Server") + text: page.account.config.lobbyServer + placeholderText: i18nc("@info:placeholder", "(Default value in client)") + onTextChanged: page.account.config.lobbyServer = text } FormCard.FormDelegateSeparator { @@ -315,12 +306,69 @@ FormCard.FormCardPage { FormCard.FormSpinBoxDelegate { id: gameServerPortDelegate - label: i18n("Lobby Server Port") - value: page.account.config.lobbyHostPort - onValueChanged: page.account.config.lobbyHostPort = value - from: 1 + label: i18n("Lobby Port") + value: page.account.config.lobbyPort + onValueChanged: page.account.config.lobbyPort = value + from: 0 to: 999999 } + + FormCard.FormDelegateSeparator { + above: gameServerPortDelegate + below: frontierServerDelegate + } + + FormCard.FormTextFieldDelegate { + id: frontierServerDelegate + + label: i18n("Frontier Server") + text: page.account.config.frontierServer + placeholderText: i18nc("@info:placeholder", "(Default value in client)") + onTextChanged: page.account.config.frontierServer = text + } + + FormCard.FormDelegateSeparator { + above: frontierServerDelegate + below: saveDataBankServerDelegate + } + + FormCard.FormTextFieldDelegate { + id: saveDataBankServerDelegate + + label: i18n("Save Data Bank Server") + text: page.account.config.saveDataBankServer + placeholderText: i18nc("@info:placeholder", "(Default value in client)") + onTextChanged: page.account.config.saveDataBankServer = text + } + + FormCard.FormDelegateSeparator { + above: saveDataBankServerDelegate + below: saveDataBankPortDelegate + } + + FormCard.FormSpinBoxDelegate { + id: saveDataBankPortDelegate + + label: i18n("Save Data Bank Port") + value: page.account.config.saveDataBankPort + onValueChanged: page.account.config.saveDataBankPort = value + from: 0 + to: 999999 + } + + FormCard.FormDelegateSeparator { + above: saveDataBankPortDelegate + below: dataCenterTravelServerDelegate + } + + FormCard.FormTextFieldDelegate { + id: dataCenterTravelServerDelegate + + label: i18n("Data Center Travel Server") + text: page.account.config.dataCenterTravelServer + placeholderText: i18nc("@info:placeholder", "(Default value in client)") + onTextChanged: page.account.config.dataCenterTravelServer = text + } } Kirigami.PromptDialog {