revert add launcher folder and some checks to it
This commit is contained in:
2026-08-22 23:39:46 +00:00
parent af4230500e
commit 2c51c4736a
13 changed files with 169 additions and 328 deletions
+35 -53
View File
@@ -3,7 +3,6 @@
#include "authservice.h"
#include "gamelauncher.h"
#include "javalocator.h"
#include "launcherpaths.h"
#include <QDesktopServices>
#include <QDir>
@@ -12,7 +11,7 @@
#include <QJsonDocument>
#include <QJsonObject>
#include <QRegularExpression>
#include <QTimer>
#include <QStandardPaths>
#include <QUrl>
#include <algorithm>
@@ -33,16 +32,13 @@ int settingInt(const QVariantMap &settings, const QString &key, int fallback)
LauncherBackend::LauncherBackend(QObject *parent)
: QObject(parent)
, m_dataDir(QStandardPaths::writableLocation(QStandardPaths::AppDataLocation))
, m_auth(new AuthService(this))
, m_launcher(new GameLauncher(this))
{
// Папка лаунчера создаётся при первом запуске и проверяется при каждом
// следующем — если её удалили, она появится снова.
LauncherPaths::ensureRootExists(&m_storageError);
QDir().mkpath(m_dataDir);
loadSettings();
loadData();
ensureDataFiles();
connect(m_auth, &AuthService::progress, this, &LauncherBackend::launchProgress);
connect(m_launcher, &GameLauncher::progress, this, &LauncherBackend::launchProgress);
@@ -55,13 +51,6 @@ LauncherBackend::LauncherBackend(QObject *parent)
emit gameRunningChanged();
emit gameFinished(exitCode, crashed);
});
// Интерфейс подключается к сигналам уже после конструктора — сообщаем отложенно.
if (!m_storageError.isEmpty()) {
QTimer::singleShot(0, this, [this] {
emit launchError(tr("Не удалось создать папку лаунчера: %1").arg(m_storageError));
});
}
}
LauncherBackend::~LauncherBackend() = default;
@@ -109,9 +98,7 @@ void LauncherBackend::addProfile(const QString &name,
emit profilesChanged();
}
void LauncherBackend::addVersion(const QString &name,
const QString &serverUrl,
const QString &versionId)
void LauncherBackend::addVersion(const QString &name, const QString &serverUrl, const QString &versionId)
{
m_versions.append({m_nextVersionId++, name, serverUrl, versionId});
saveVersions();
@@ -247,11 +234,11 @@ void LauncherBackend::launchGame(int profileIndex, int versionIndex)
const QString id = versionIdOf(m_versions[versionIndex]);
const QStringList installed = VersionLoader::installedVersions(directory);
if (!installed.contains(id)) {
emit launchError(installed.isEmpty() ? tr("В %1 нет ни одной установленной версии")
.arg(QDir::toNativeSeparators(
directory + QStringLiteral("/versions")))
: tr("Версия «%1» не установлена. Доступны: %2")
.arg(id, installed.join(QStringLiteral(", "))));
emit launchError(installed.isEmpty()
? tr("В %1 нет ни одной установленной версии")
.arg(QDir::toNativeSeparators(directory + QStringLiteral("/versions")))
: tr("Версия «%1» не установлена. Доступны: %2")
.arg(id, installed.join(QStringLiteral(", "))));
return;
}
@@ -304,10 +291,9 @@ void LauncherBackend::beginAuthentication()
// Ely.by работает только вместе с authlib-injector — без него игра пойдёт
// в сессионный сервер Mojang и токен окажется недействительным.
m_auth->ensureAuthlibInjector(LauncherPaths::runtimeDir(),
[this](const QString &path, const QString &error) {
m_auth->ensureAuthlibInjector(m_dataDir, [this](const QString &path, const QString &error) {
if (m_pendingProfile < 0)
return; // запуск отменили, пока качался инжектор
return; // запуск отменили, пока качался инжектор
if (!error.isEmpty()) {
failLaunch(error);
return;
@@ -459,11 +445,21 @@ void LauncherBackend::setBusy(bool busy)
emit busyChanged();
}
QString LauncherBackend::defaultMinecraftDir() const
{
#if defined(Q_OS_WIN)
return QDir::homePath() + QStringLiteral("/AppData/Roaming/.minecraft");
#elif defined(Q_OS_MACOS)
return QDir::homePath() + QStringLiteral("/Library/Application Support/minecraft");
#else // Linux и прочие Unix-системы
return QDir::homePath() + QStringLiteral("/.minecraft");
#endif
}
QString LauncherBackend::gameDir() const
{
const QString configured = m_settings.value(QStringLiteral("gameDir")).toString().trimmed();
return configured.isEmpty() ? LauncherPaths::defaultMinecraftDir()
: QDir::fromNativeSeparators(configured);
return configured.isEmpty() ? defaultMinecraftDir() : QDir::fromNativeSeparators(configured);
}
QVariantMap LauncherBackend::settings() const
@@ -526,7 +522,7 @@ void LauncherBackend::loadData()
handler(val.toObject());
};
loadFile(LauncherPaths::profilesFile(), [this](const QJsonObject &o) {
loadFile(m_dataDir + "/profiles.json", [this](const QJsonObject &o) {
Profile profile;
profile.id = o["id"].toInt();
profile.name = o["name"].toString();
@@ -544,32 +540,18 @@ void LauncherBackend::loadData()
if (profile.id >= m_nextProfileId)
m_nextProfileId = profile.id + 1;
});
std::sort(m_profiles.begin(), m_profiles.end(), [](const Profile &a, const Profile &b) {
return a.id < b.id;
});
std::sort(m_profiles.begin(), m_profiles.end(),
[](const Profile &a, const Profile &b) { return a.id < b.id; });
loadFile(LauncherPaths::versionsFile(), [this](const QJsonObject &o) {
loadFile(m_dataDir + "/versions.json", [this](const QJsonObject &o) {
const int id = o["id"].toInt();
m_versions.append(
{id, o["name"].toString(), o["serverUrl"].toString(), o.value("versionId").toString()});
m_versions.append({id, o["name"].toString(), o["serverUrl"].toString(),
o.value("versionId").toString()});
if (id >= m_nextVersionId)
m_nextVersionId = id + 1;
});
std::sort(m_versions.begin(), m_versions.end(), [](const Version &a, const Version &b) {
return a.id < b.id;
});
}
// Файлы могли не появиться при первом запуске или быть удалены — создаём заново,
// чтобы папка лаунчера всегда была укомплектована.
void LauncherBackend::ensureDataFiles()
{
if (!QFile::exists(LauncherPaths::settingsFile()))
saveSettings();
if (!QFile::exists(LauncherPaths::profilesFile()))
saveProfiles();
if (!QFile::exists(LauncherPaths::versionsFile()))
saveVersions();
std::sort(m_versions.begin(), m_versions.end(),
[](const Version &a, const Version &b) { return a.id < b.id; });
}
void LauncherBackend::saveProfiles()
@@ -587,7 +569,7 @@ void LauncherBackend::saveProfiles()
{"resolvedName", p.resolvedName},
{"userType", p.userType}});
QFile f(LauncherPaths::profilesFile());
QFile f(m_dataDir + "/profiles.json");
if (f.open(QIODevice::WriteOnly))
f.write(QJsonDocument(arr).toJson());
}
@@ -601,7 +583,7 @@ void LauncherBackend::saveVersions()
{"serverUrl", v.serverUrl},
{"versionId", v.versionId}});
QFile f(LauncherPaths::versionsFile());
QFile f(m_dataDir + "/versions.json");
if (f.open(QIODevice::WriteOnly))
f.write(QJsonDocument(arr).toJson());
}
@@ -619,7 +601,7 @@ void LauncherBackend::loadSettings()
{QStringLiteral("launcherName"), QStringLiteral("KishkaLauncher")},
{QStringLiteral("launcherVersion"), QStringLiteral("1.0")}};
QFile f(LauncherPaths::settingsFile());
QFile f(m_dataDir + "/settings.json");
if (!f.open(QIODevice::ReadOnly))
return;
@@ -630,7 +612,7 @@ void LauncherBackend::loadSettings()
void LauncherBackend::saveSettings()
{
QFile f(LauncherPaths::settingsFile());
QFile f(m_dataDir + "/settings.json");
if (f.open(QIODevice::WriteOnly))
f.write(QJsonDocument(QJsonObject::fromVariantMap(m_settings)).toJson());
}