diff --git a/src/MaaCore/Task/Interface/StartUpTask.cpp b/src/MaaCore/Task/Interface/StartUpTask.cpp index 1e6e571440..e704c7c2cd 100644 --- a/src/MaaCore/Task/Interface/StartUpTask.cpp +++ b/src/MaaCore/Task/Interface/StartUpTask.cpp @@ -23,10 +23,63 @@ asst::StartUpTask::StartUpTask(const AsstCallback& callback, Assistant* inst) : .set_times_limit("StartButton1", 0) .set_task_delay(Config.get_options().task_delay * 2) .set_retry_times(50); + m_start_game_task_ptr->set_retry_times(0); m_account_switch_task_ptr->set_retry_times(0); - m_subtasks.emplace_back(m_start_game_task_ptr)->set_ignore_error(true).set_retry_times(0); - m_subtasks.emplace_back(m_account_switch_task_ptr); - m_subtasks.emplace_back(m_start_up_task_ptr); +} + +bool asst::StartUpTask::run() +{ + LogTraceFunction; + + if (!m_enable) { + Log.info("task disabled, pass", basic_info().to_string()); + return true; + } + + if (!m_start_game_task_ptr->run()) { + return false; + } + + if (need_exit()) { + return false; + } + + if (!m_account_switch_task_ptr->run()) { + return false; + } + + if (m_start_up_task_ptr->run()) { + return true; + } + + if (!m_start_game) { + LogInfo << __FUNCTION__ + << "| StartUpTask failed, start_game is not enabled, don't restart game and just fail"; + return false; + } + + Log.warn(__FUNCTION__, "| Login failed, entering game-restart loop"); + for (int attempts = 0; attempts < MaxRestartAttempts && !need_exit(); ++attempts) { + Log.info(__FUNCTION__, "| Restarting game client (attempt", attempts + 1, "/", MaxRestartAttempts, ")"); + if (!m_start_game_task_ptr->restart_game()) { + Log.warn(__FUNCTION__, "| restart_game failed, retrying"); + sleep(3000); + continue; + } + + if (!m_account_switch_task_ptr->run()) { + Log.warn(__FUNCTION__, "| Account switch failed after restart, retrying game restart"); + continue; + } + + Log.info(__FUNCTION__, "| Game restarted, retrying login navigation"); + if (m_start_up_task_ptr->run()) { + return true; + } + Log.warn(__FUNCTION__, "| Login navigation failed again, restarting game"); + } + + return false; } bool asst::StartUpTask::set_params(const json::value& params) @@ -39,7 +92,9 @@ bool asst::StartUpTask::set_params(const json::value& params) if (!Config.get_package_name(client_type)) { return false; } - m_start_game_task_ptr->set_client_type(client_type).set_enable(params.get("start_game_enabled", false)); + + m_start_game = params.get("start_game_enabled", false); + m_start_game_task_ptr->set_client_type(client_type).set_enable(m_start_game); m_account_switch_task_ptr->set_enable(!account_name.empty()); m_account_switch_task_ptr->set_account(std::move(account_name)); m_account_switch_task_ptr->set_client_type(std::move(client_type)); diff --git a/src/MaaCore/Task/Interface/StartUpTask.h b/src/MaaCore/Task/Interface/StartUpTask.h index a309b41025..8222d55b04 100644 --- a/src/MaaCore/Task/Interface/StartUpTask.h +++ b/src/MaaCore/Task/Interface/StartUpTask.h @@ -15,11 +15,15 @@ public: StartUpTask(const AsstCallback& callback, Assistant* inst); virtual ~StartUpTask() override = default; + virtual bool run() override; bool set_params(const json::value& params) override; private: std::shared_ptr m_start_game_task_ptr = nullptr; std::shared_ptr m_start_up_task_ptr = nullptr; std::shared_ptr m_account_switch_task_ptr = nullptr; + + bool m_start_game = false; + static constexpr int MaxRestartAttempts = 5; }; } diff --git a/src/MaaCore/Task/Miscellaneous/StartGameTaskPlugin.cpp b/src/MaaCore/Task/Miscellaneous/StartGameTaskPlugin.cpp index a859061994..d52cbbac03 100644 --- a/src/MaaCore/Task/Miscellaneous/StartGameTaskPlugin.cpp +++ b/src/MaaCore/Task/Miscellaneous/StartGameTaskPlugin.cpp @@ -1,6 +1,7 @@ #include "StartGameTaskPlugin.h" #include "Controller/Controller.h" +#include "Utils/Logger.hpp" using namespace asst; @@ -54,3 +55,20 @@ StartGameTaskPlugin& StartGameTaskPlugin::set_client_type(std::string client_typ m_client_type = std::move(client_type); return *this; } + +bool StartGameTaskPlugin::restart_game() +{ + if (m_client_type.empty()) { + Log.error(__FUNCTION__, "| client_type is empty, cannot restart game"); + return false; + } + if (!ctrler()) { + Log.error(__FUNCTION__, "| controller is not initialized, cannot restart game"); + return false; + } + Log.info(__FUNCTION__, "| stopping game client"); + ctrler()->stop_game(m_client_type); + sleep(3000); + Log.info(__FUNCTION__, "| starting game client"); + return _run(); +} diff --git a/src/MaaCore/Task/Miscellaneous/StartGameTaskPlugin.h b/src/MaaCore/Task/Miscellaneous/StartGameTaskPlugin.h index 047a44cd22..5ffbc26370 100644 --- a/src/MaaCore/Task/Miscellaneous/StartGameTaskPlugin.h +++ b/src/MaaCore/Task/Miscellaneous/StartGameTaskPlugin.h @@ -21,6 +21,7 @@ public: } StartGameTaskPlugin& set_client_type(std::string client_type) noexcept; + bool restart_game(); protected: bool _run() override;