diff options
32 files changed, 443 insertions, 487 deletions
diff --git a/CMakeLists.txt b/CMakeLists.txt index e69422b9..11b64c3d 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -314,8 +314,6 @@ logic/auth/flows/RefreshTask.cpp logic/auth/flows/RefreshTask.cpp logic/auth/flows/ValidateTask.h logic/auth/flows/ValidateTask.cpp -logic/auth/flows/InvalidateTask.h -logic/auth/flows/InvalidateTask.cpp # legacy instances logic/LegacyInstance.h diff --git a/gui/MainWindow.cpp b/gui/MainWindow.cpp index 854091c6..fd35e94e 100644 --- a/gui/MainWindow.cpp +++ b/gui/MainWindow.cpp @@ -69,10 +69,6 @@ #include "logic/lists/IconList.h" #include "logic/lists/JavaVersionList.h" -#include "logic/auth/flows/AuthenticateTask.h" -#include "logic/auth/flows/RefreshTask.h" -#include "logic/auth/flows/ValidateTask.h" - #include "logic/BaseInstance.h" #include "logic/InstanceFactory.h" #include "logic/MinecraftProcess.h" @@ -210,9 +206,9 @@ MainWindow::MainWindow(QWidget *parent) : QMainWindow(parent), ui(new Ui::MainWi for(AccountProfile profile : account->profiles()) { - auto meta = MMC->metacache()->resolveEntry("skins", profile.name() + ".png"); + auto meta = MMC->metacache()->resolveEntry("skins", profile.name + ".png"); auto action = CacheDownload::make( - QUrl("http://skins.minecraft.net/MinecraftSkins/" + profile.name() + ".png"), + QUrl("http://skins.minecraft.net/MinecraftSkins/" + profile.name + ".png"), meta); job->addNetAction(action); meta->stale = true; @@ -310,9 +306,9 @@ void MainWindow::repopulateAccountsMenu() section->setEnabled(false); accountMenu->addAction(section); - for (AccountProfile profile : account->profiles()) + for (auto profile : account->profiles()) { - QAction *action = new QAction(profile.name(), this); + QAction *action = new QAction(profile.name, this); action->setData(account->username()); action->setCheckable(true); if(active_username == account->username()) @@ -320,7 +316,7 @@ void MainWindow::repopulateAccountsMenu() action->setChecked(true); } - action->setIcon(SkinUtils::getFaceFromCache(profile.name())); + action->setIcon(SkinUtils::getFaceFromCache(profile.name)); accountMenu->addAction(action); connect(action, SIGNAL(triggered(bool)), SLOT(changeActiveAccount())); } @@ -378,7 +374,7 @@ void MainWindow::activeAccountChanged() const AccountProfile *profile = account->currentProfile(); if (profile != nullptr) { - accountMenuButton->setIcon(SkinUtils::getFaceFromCache(profile->name())); + accountMenuButton->setIcon(SkinUtils::getFaceFromCache(profile->name)); return; } } @@ -781,79 +777,58 @@ void MainWindow::doLaunch() accounts->setActiveAccount(account->username()); } - if (account.get() != nullptr) - { - doLaunchInst(m_selectedInstance, account); - } -} - -void MainWindow::doLaunchInst(BaseInstance* instance, MojangAccountPtr account) -{ - // We'll need to validate the access token to make sure the account is still logged in. - ProgressDialog progDialog(this); - RefreshTask refreshtask(account, &progDialog); - progDialog.exec(&refreshtask); + // if no account is selected, we bail + if (!account.get()) + return; - if (refreshtask.successful()) - { - prepareLaunch(m_selectedInstance, account); - } - else + // do the login. if the account has an access token, try to refresh it first. + if(account->accountStatus() != NotVerified) { - YggdrasilTask::Error *error = refreshtask.getError(); + // We'll need to validate the access token to make sure the account is still logged in. + ProgressDialog progDialog(this); + progDialog.setSkipButton(true, tr("Play Offline")); + auto task = account->login(); + progDialog.exec(task.get()); - if (error != nullptr) + auto status = account->accountStatus(); + if(status == Online) // Online mode! Refresh the token. { - if (error->getErrorMessage().contains("invalid token", Qt::CaseInsensitive)) - { - // TODO: Allow the user to enter their password and "refresh" their access token. - if (doRefreshToken(account, tr("Your account's access token is invalid. Please enter your password to log in again."))) - doLaunchInst(instance, account); - } - else - { - CustomMessageBox::selectable( - this, tr("Access Token Validation Error"), - tr("There was an error when trying to validate your access token.\n" - "Details: %s").arg(error->getDisplayMessage()), - QMessageBox::Warning, QMessageBox::Ok)->exec(); - } + updateInstance(m_selectedInstance, account); + return; } - else + else if(status == Verified) // Offline mode with a verified account { - CustomMessageBox::selectable( - this, tr("Access Token Validation Error"), - tr("There was an unknown error when trying to validate your access token." - "The authentication server might be down, or you might not be connected to " - "the Internet."), - QMessageBox::Warning, QMessageBox::Ok)->exec(); + launchInstance(m_selectedInstance, account); + return; } } + if (loginWithPassword(account, tr("Your account is currently not logged in. Please enter your password to log in again."))) + updateInstance(m_selectedInstance, account); } -bool MainWindow::doRefreshToken(MojangAccountPtr account, const QString& errorMsg) +bool MainWindow::loginWithPassword(MojangAccountPtr account, const QString& errorMsg) { EditAccountDialog passDialog(errorMsg, this, EditAccountDialog::PasswordField); if (passDialog.exec() == QDialog::Accepted) { // To refresh the token, we just create an authenticate task with the given account and the user's password. ProgressDialog progDialog(this); - AuthenticateTask authTask(account, passDialog.password(), &progDialog); - progDialog.exec(&authTask); - if (authTask.successful()) + auto task = account->login(passDialog.password()); + progDialog.exec(task.get()); + if(task->successful()) return true; else { // If the authentication task failed, recurse with the task's error message. - return doRefreshToken(account, authTask.failReason()); + return loginWithPassword(account, task->failReason()); } } - else return false; + return false; } -void MainWindow::prepareLaunch(BaseInstance* instance, MojangAccountPtr account) +void MainWindow::updateInstance(BaseInstance* instance, MojangAccountPtr account) { - Task *updateTask = instance->doUpdate(true); + auto updateTask = instance->doUpdate(true); if (!updateTask) { launchInstance(instance, account); @@ -861,10 +836,9 @@ void MainWindow::prepareLaunch(BaseInstance* instance, MojangAccountPtr account) else { ProgressDialog tDialog(this); - connect(updateTask, &Task::succeeded, [this, instance, account] { launchInstance(instance, account); }); - connect(updateTask, SIGNAL(failed(QString)), SLOT(onGameUpdateError(QString))); - tDialog.exec(updateTask); - delete updateTask; + connect(updateTask.get(), &Task::succeeded, [this, instance, account] { launchInstance(instance, account); }); + connect(updateTask.get(), SIGNAL(failed(QString)), SLOT(onGameUpdateError(QString))); + tDialog.exec(updateTask.get()); } } diff --git a/gui/MainWindow.h b/gui/MainWindow.h index 59cfa3c9..62c9797e 100644 --- a/gui/MainWindow.h +++ b/gui/MainWindow.h @@ -110,18 +110,13 @@ slots: * If no default account is selected, prompts the user to pick an account. */ void doLaunch(); - - /*! - * Launches the given instance with the given account. - */ - void doLaunchInst(BaseInstance* instance, MojangAccountPtr account); /*! * Opens an input dialog, allowing the user to input their password and refresh its access token. * This function will execute the proper Yggdrasil task to refresh the access token. * Returns true if successful. False if the user cancelled. */ - bool doRefreshToken(MojangAccountPtr account, const QString& errorMsg=""); + bool loginWithPassword(MojangAccountPtr account, const QString& errorMsg=""); /*! * Launches the given instance with the given account. @@ -132,7 +127,7 @@ slots: /*! * Prepares the given instance for launch with the given account. */ - void prepareLaunch(BaseInstance* instance, MojangAccountPtr account); + void updateInstance(BaseInstance* instance, MojangAccountPtr account); void onGameUpdateError(QString error); diff --git a/gui/dialogs/AccountListDialog.cpp b/gui/dialogs/AccountListDialog.cpp index f5268b61..8dae5f07 100644 --- a/gui/dialogs/AccountListDialog.cpp +++ b/gui/dialogs/AccountListDialog.cpp @@ -20,12 +20,12 @@ #include <logger/QsLog.h> -#include <logic/auth/flows/AuthenticateTask.h> #include <logic/net/NetJob.h> #include <gui/dialogs/EditAccountDialog.h> #include <gui/dialogs/ProgressDialog.h> #include <gui/dialogs/AccountSelectDialog.h> +#include <logic/tasks/Task.h> #include <MultiMC.h> @@ -117,24 +117,24 @@ void AccountListDialog::addAccount(const QString& errMsg) QString username(loginDialog.username()); QString password(loginDialog.password()); - MojangAccountPtr account = MojangAccountPtr(new MojangAccount(username)); - + MojangAccountPtr account = MojangAccount::createFromUsername(username); ProgressDialog progDialog(this); - AuthenticateTask authTask(account, password, &progDialog); - if (progDialog.exec(&authTask)) + auto task = account->login(password); + progDialog.exec(task.get()); + if(task->successful()) { - // Add the authenticated account to the accounts list. - MojangAccountPtr account = authTask.getMojangAccount(); m_accounts->addAccount(account); + if (m_accounts->count() == 1) + m_accounts->setActiveAccount(account->username()); // Grab associated player skins auto job = new NetJob("Player skins: " + account->username()); for(AccountProfile profile : account->profiles()) { - auto meta = MMC->metacache()->resolveEntry("skins", profile.name() + ".png"); + auto meta = MMC->metacache()->resolveEntry("skins", profile.name + ".png"); auto action = CacheDownload::make( - QUrl("http://skins.minecraft.net/MinecraftSkins/" + profile.name() + ".png"), + QUrl("http://skins.minecraft.net/MinecraftSkins/" + profile.name + ".png"), meta); job->addNetAction(action); meta->stale = true; diff --git a/gui/dialogs/AccountSelectDialog.cpp b/gui/dialogs/AccountSelectDialog.cpp index b8fa9e42..ec2f09be 100644 --- a/gui/dialogs/AccountSelectDialog.cpp +++ b/gui/dialogs/AccountSelectDialog.cpp @@ -20,8 +20,6 @@ #include <logger/QsLog.h> -#include <logic/auth/flows/AuthenticateTask.h> - #include <gui/dialogs/ProgressDialog.h> #include <MultiMC.h> diff --git a/gui/dialogs/ProgressDialog.cpp b/gui/dialogs/ProgressDialog.cpp index ca433dab..ba14cca2 100644 --- a/gui/dialogs/ProgressDialog.cpp +++ b/gui/dialogs/ProgressDialog.cpp @@ -25,9 +25,23 @@ ProgressDialog::ProgressDialog(QWidget *parent) : QDialog(parent), ui(new Ui::Pr { MultiMCPlatform::fixWM_CLASS(this); ui->setupUi(this); + this->setWindowFlags(this->windowFlags() & ~Qt::WindowContextHelpButtonHint); + setSkipButton(false); + changeProgress(0, 100); +} + +void ProgressDialog::setSkipButton(bool present, QString label) +{ + ui->skipButton->setEnabled(present); + ui->skipButton->setVisible(present); + ui->skipButton->setText(label); updateSize(); +} - changeProgress(0, 100); +void ProgressDialog::on_skipButton_clicked(bool checked) +{ + Q_UNUSED(checked); + task->abort(); } ProgressDialog::~ProgressDialog() @@ -51,9 +65,13 @@ int ProgressDialog::exec(ProgressProvider *task) connect(task, SIGNAL(status(QString)), SLOT(changeStatus(const QString &))); connect(task, SIGNAL(progress(qint64, qint64)), SLOT(changeProgress(qint64, qint64))); - // this makes sure that the task is started after the dialog is created - QMetaObject::invokeMethod(task, "start", Qt::QueuedConnection); - return QDialog::exec(); + // if this didn't connect to an already running task, invoke start + if(!task->isRunning()) + task->start(); + if(task->isRunning()) + return QDialog::exec(); + else + return 0; } ProgressProvider *ProgressDialog::getTask() diff --git a/gui/dialogs/ProgressDialog.h b/gui/dialogs/ProgressDialog.h index 0029d3ec..fe63a826 100644 --- a/gui/dialogs/ProgressDialog.h +++ b/gui/dialogs/ProgressDialog.h @@ -35,6 +35,7 @@ public: void updateSize(); int exec(ProgressProvider *task); + void setSkipButton(bool present, QString label = QString()); ProgressProvider *getTask(); @@ -47,7 +48,10 @@ slots: void changeStatus(const QString &status); void changeProgress(qint64 current, qint64 total); -signals: + +private +slots: + void on_skipButton_clicked(bool checked); protected: virtual void keyPressEvent(QKeyEvent *e); diff --git a/gui/dialogs/ProgressDialog.ui b/gui/dialogs/ProgressDialog.ui index a56d2a92..04b8fef3 100644 --- a/gui/dialogs/ProgressDialog.ui +++ b/gui/dialogs/ProgressDialog.ui @@ -7,7 +7,7 @@ <x>0</x> <y>0</y> <width>400</width> - <height>68</height> + <height>100</height> </rect> </property> <property name="minimumSize"> @@ -25,8 +25,8 @@ <property name="windowTitle"> <string>Please wait...</string> </property> - <layout class="QVBoxLayout" name="verticalLayout"> - <item> + <layout class="QGridLayout" name="gridLayout"> + <item row="0" column="0"> <widget class="QLabel" name="statusLabel"> <property name="text"> <string>Task Status...</string> @@ -36,7 +36,7 @@ </property> </widget> </item> - <item> + <item row="1" column="0"> <widget class="QProgressBar" name="taskProgressBar"> <property name="value"> <number>24</number> @@ -46,6 +46,19 @@ </property> </widget> </item> + <item row="2" column="0"> + <widget class="QPushButton" name="skipButton"> + <property name="sizePolicy"> + <sizepolicy hsizetype="Expanding" vsizetype="Expanding"> + <horstretch>0</horstretch> + <verstretch>0</verstretch> + </sizepolicy> + </property> + <property name="text"> + <string>Skip</string> + </property> + </widget> + </item> </layout> </widget> <resources/> diff --git a/logic/BaseInstance.h b/logic/BaseInstance.h index 2d7537d6..603f6105 100644 --- a/logic/BaseInstance.h +++ b/logic/BaseInstance.h @@ -150,7 +150,7 @@ public: virtual SettingsObject &settings() const; /// returns a valid update task if update is needed, NULL otherwise - virtual Task *doUpdate(bool prepare_for_launch) = 0; + virtual std::shared_ptr<Task> doUpdate(bool prepare_for_launch) = 0; /// returns a valid minecraft process, ready for launch with the given account. virtual MinecraftProcess *prepareForLaunch(MojangAccountPtr account) = 0; diff --git a/logic/LegacyInstance.cpp b/logic/LegacyInstance.cpp index 72b6c51a..55523048 100644 --- a/logic/LegacyInstance.cpp +++ b/logic/LegacyInstance.cpp @@ -44,12 +44,12 @@ LegacyInstance::LegacyInstance(const QString &rootDir, SettingsObject *settings, settings->registerSetting(new Setting("IntendedJarVersion", "")); } -Task *LegacyInstance::doUpdate(bool prepare_for_launch) +std::shared_ptr<Task> LegacyInstance::doUpdate(bool prepare_for_launch) { // make sure the jar mods list is initialized by asking for it. auto list = jarModList(); // create an update task - return new LegacyUpdate(this, prepare_for_launch , this); + return std::shared_ptr<Task> (new LegacyUpdate(this, prepare_for_launch , this)); } MinecraftProcess *LegacyInstance::prepareForLaunch(MojangAccountPtr account) @@ -105,7 +105,7 @@ MinecraftProcess *LegacyInstance::prepareForLaunch(MojangAccountPtr account) #endif args << "-jar" << LAUNCHER_FILE; - args << account->currentProfile()->name(); + args << account->currentProfile()->name; args << account->sessionId(); args << windowTitle; args << windowSize; diff --git a/logic/LegacyInstance.h b/logic/LegacyInstance.h index a17ef281..948d4be4 100644 --- a/logic/LegacyInstance.h +++ b/logic/LegacyInstance.h @@ -76,7 +76,7 @@ public: virtual bool shouldUpdate() const override; virtual void setShouldUpdate(bool val) override; - virtual Task *doUpdate(bool prepare_for_launch) override; + virtual std::shared_ptr<Task> doUpdate(bool prepare_for_launch) override; virtual MinecraftProcess *prepareForLaunch(MojangAccountPtr account) override; virtual void cleanupAfterRun() override; diff --git a/logic/MinecraftProcess.cpp b/logic/MinecraftProcess.cpp index 5d99bfae..209929b7 100644 --- a/logic/MinecraftProcess.cpp +++ b/logic/MinecraftProcess.cpp @@ -75,20 +75,22 @@ QString MinecraftProcess::censorPrivateInfo(QString in) { if(!m_account) return in; - else + + QString sessionId = m_account->sessionId(); + QString accessToken = m_account->accessToken(); + QString clientToken = m_account->clientToken(); + in.replace(sessionId, "<SESSION ID>"); + in.replace(accessToken, "<ACCESS TOKEN>"); + in.replace(clientToken, "<CLIENT TOKEN>"); + auto profile = m_account->currentProfile(); + if(profile) { - QString sessionId = m_account->sessionId(); - QString accessToken = m_account->accessToken(); - QString clientToken = m_account->clientToken(); - QString profileId = m_account->currentProfile()->id(); - QString profileName = m_account->currentProfile()->name(); - in.replace(sessionId, "<SESSION ID>"); - in.replace(accessToken, "<ACCESS TOKEN>"); - in.replace(clientToken, "<CLIENT TOKEN>"); + QString profileId = profile->id; + QString profileName = profile->name; in.replace(profileId, "<PROFILE ID>"); in.replace(profileName, "<PROFILE NAME>"); - return in; } + return in; } // console window diff --git a/logic/OneSixInstance.cpp b/logic/OneSixInstance.cpp index 08b63bf9..7a1d7dad 100644 --- a/logic/OneSixInstance.cpp +++ b/logic/OneSixInstance.cpp @@ -37,9 +37,9 @@ OneSixInstance::OneSixInstance(const QString &rootDir, SettingsObject *setting_o reloadFullVersion(); } -Task *OneSixInstance::doUpdate(bool prepare_for_launch) +std::shared_ptr<Task> OneSixInstance::doUpdate(bool prepare_for_launch) { - return new OneSixUpdate(this, prepare_for_launch); + return std::shared_ptr<Task> (new OneSixUpdate(this, prepare_for_launch)); } QString replaceTokensIn(QString text, QMap<QString, QString> with) @@ -77,8 +77,8 @@ QStringList OneSixInstance::processMinecraftArgs(MojangAccountPtr account) token_mapping["auth_username"] = account->username(); token_mapping["auth_session"] = account->sessionId(); token_mapping["auth_access_token"] = account->accessToken(); - token_mapping["auth_player_name"] = account->currentProfile()->name(); - token_mapping["auth_uuid"] = account->currentProfile()->id(); + token_mapping["auth_player_name"] = account->currentProfile()->name; + token_mapping["auth_uuid"] = account->currentProfile()->id; // this is for offline?: /* diff --git a/logic/OneSixInstance.h b/logic/OneSixInstance.h index 042c104b..7ea2d08b 100644 --- a/logic/OneSixInstance.h +++ b/logic/OneSixInstance.h @@ -39,7 +39,7 @@ public: QString loaderModsDir() const; virtual QString instanceConfigFolder() const override; - virtual Task *doUpdate(bool prepare_for_launch) override; + virtual std::shared_ptr<Task> doUpdate(bool prepare_for_launch) override; virtual MinecraftProcess *prepareForLaunch(MojangAccountPtr account) override; virtual void cleanupAfterRun() override; diff --git a/logic/OneSixUpdate.h b/logic/OneSixUpdate.h index b86c205f..5fd2c59f 100644 --- a/logic/OneSixUpdate.h +++ b/logic/OneSixUpdate.h @@ -48,6 +48,7 @@ slots: // extract the appropriate libraries void prepareForLaunch(); + private: NetJobPtr specificVersionDownloadJob; NetJobPtr jarlibDownloadJob; diff --git a/logic/auth/MojangAccount.cpp b/logic/auth/MojangAccount.cpp index 4a61cf19..b1acfb25 100644 --- a/logic/auth/MojangAccount.cpp +++ b/logic/auth/MojangAccount.cpp @@ -16,113 +16,16 @@ */ #include "MojangAccount.h" +#include "flows/RefreshTask.h" +#include "flows/AuthenticateTask.h" #include <QUuid> #include <QJsonObject> #include <QJsonArray> +#include <QRegExp> #include <logger/QsLog.h> -MojangAccount::MojangAccount(const QString &username, QObject *parent) : QObject(parent) -{ - // Generate a client token. - m_clientToken = QUuid::createUuid().toString(); - - m_username = username; - - m_currentProfile = -1; -} - -MojangAccount::MojangAccount(const QString &username, const QString &clientToken, - const QString &accessToken, QObject *parent) - : QObject(parent) -{ - m_username = username; - m_clientToken = clientToken; - m_accessToken = accessToken; - - m_currentProfile = -1; -} - -MojangAccount::MojangAccount(const MojangAccount &other, QObject *parent) -{ - m_username = other.username(); - m_clientToken = other.clientToken(); - m_accessToken = other.accessToken(); - - m_profiles = other.m_profiles; - m_currentProfile = other.m_currentProfile; -} - -QString MojangAccount::username() const -{ - return m_username; -} - -QString MojangAccount::clientToken() const -{ - return m_clientToken; -} - -void MojangAccount::setClientToken(const QString &clientToken) -{ - m_clientToken = clientToken; -} - -QString MojangAccount::accessToken() const -{ - return m_accessToken; -} - -void MojangAccount::setAccessToken(const QString &accessToken) -{ - m_accessToken = accessToken; -} - -QString MojangAccount::sessionId() const -{ - return "token:" + m_accessToken + ":" + currentProfile()->id(); -} - -const QList<AccountProfile> MojangAccount::profiles() const -{ - return m_profiles; -} - -const AccountProfile *MojangAccount::currentProfile() const -{ - if (m_currentProfile < 0) - { - if (m_profiles.length() > 0) - return &m_profiles.at(0); - else - return nullptr; - } - else - return &m_profiles.at(m_currentProfile); -} - -bool MojangAccount::setProfile(const QString &profileId) -{ - const QList<AccountProfile> &profiles = this->profiles(); - for (int i = 0; i < profiles.length(); i++) - { - if (profiles.at(i).id() == profileId) - { - m_currentProfile = i; - return true; - } - } - return false; -} - -void MojangAccount::loadProfiles(const ProfileList &profiles) -{ - m_profiles.clear(); - for (auto profile : profiles) - m_profiles.append(profile); -} - MojangAccountPtr MojangAccount::loadFromJson(const QJsonObject &object) { // The JSON object must at least have a username for it to be valid. @@ -143,7 +46,7 @@ MojangAccountPtr MojangAccount::loadFromJson(const QJsonObject &object) return nullptr; } - ProfileList profiles; + QList<AccountProfile> profiles; for (QJsonValue profileVal : profileArray) { QJsonObject profileObject = profileVal.toObject(); @@ -154,67 +57,116 @@ MojangAccountPtr MojangAccount::loadFromJson(const QJsonObject &object) QLOG_WARN() << "Unable to load a profile because it was missing an ID or a name."; continue; } - profiles.append(AccountProfile(id, name)); + profiles.append({id, name}); } - MojangAccountPtr account(new MojangAccount(username, clientToken, accessToken)); - account->loadProfiles(profiles); + MojangAccountPtr account(new MojangAccount()); + account->m_username = username; + account->m_clientToken = clientToken; + account->m_accessToken = accessToken; + account->m_profiles = profiles; // Get the currently selected profile. QString currentProfile = object.value("activeProfile").toString(""); if (!currentProfile.isEmpty()) - account->setProfile(currentProfile); + account->setCurrentProfile(currentProfile); return account; } -QJsonObject MojangAccount::saveToJson() +MojangAccountPtr MojangAccount::createFromUsername(const QString& username) +{ + MojangAccountPtr account(new MojangAccount()); + account->m_clientToken = QUuid::createUuid().toString().remove(QRegExp("[{}-]")); + account->m_username = username; + return account; +} + +QJsonObject MojangAccount::saveToJson() const { QJsonObject json; - json.insert("username", username()); - json.insert("clientToken", clientToken()); - json.insert("accessToken", accessToken()); + json.insert("username", m_username); + json.insert("clientToken", m_clientToken); + json.insert("accessToken", m_accessToken); QJsonArray profileArray; for (AccountProfile profile : m_profiles) { QJsonObject profileObj; - profileObj.insert("id", profile.id()); - profileObj.insert("name", profile.name()); + profileObj.insert("id", profile.id); + profileObj.insert("name", profile.name); profileArray.append(profileObj); } json.insert("profiles", profileArray); - if (currentProfile() != nullptr) - json.insert("activeProfile", currentProfile()->id()); + if (m_currentProfile != -1) + json.insert("activeProfile", currentProfile()->id); return json; } - -AccountProfile::AccountProfile(const QString& id, const QString& name) +bool MojangAccount::setCurrentProfile(const QString &profileId) { - m_id = id; - m_name = name; + for (int i = 0; i < m_profiles.length(); i++) + { + if (m_profiles[i].id == profileId) + { |
