diff --git a/resource/tasks.json b/resource/tasks.json index 40a3c12ef4..0f78f216ff 100644 --- a/resource/tasks.json +++ b/resource/tasks.json @@ -5909,6 +5909,10 @@ "baseTask": "BattleStartPre", "action": "DoNothing" }, + "BattleFormationInvalid": { + "action": "DoNothing", + "roi": [200, 650, 400, 70] + }, "BattleFormationOCRNameFlag": { "templThreshold": 0.6, "roi": [88, 264, 873, 354] diff --git a/resource/template/BattleFormationInvalid.png b/resource/template/BattleFormationInvalid.png new file mode 100644 index 0000000000..06645d2a06 Binary files /dev/null and b/resource/template/BattleFormationInvalid.png differ diff --git a/src/MaaCore/Task/Interface/CopilotTask.cpp b/src/MaaCore/Task/Interface/CopilotTask.cpp index 507739c609..ebe2ee24c3 100644 --- a/src/MaaCore/Task/Interface/CopilotTask.cpp +++ b/src/MaaCore/Task/Interface/CopilotTask.cpp @@ -144,8 +144,7 @@ bool asst::CopilotTask::set_params(const json::value& params) m_not_use_prts_task_ptr->set_enable(need_navigate); // 不使用代理指挥 m_medicine_plugin_ptr->set_enable(use_sanity_potion); - // 关卡名含有"TR"的为教学关,不需要编队 - m_formation_task_ptr->set_enable(with_formation && navigate_name.find("TR") == std::string::npos); + m_formation_task_ptr->set_enable(with_formation); m_formation_task_ptr->set_select_formation(select_formation); m_formation_task_ptr->set_add_trust(add_trust); m_formation_task_ptr->set_support_unit_usage(support_unit_usage); diff --git a/src/MaaCore/Task/Miscellaneous/BattleFormationTask.cpp b/src/MaaCore/Task/Miscellaneous/BattleFormationTask.cpp index 57a05085a3..4ee3818967 100644 --- a/src/MaaCore/Task/Miscellaneous/BattleFormationTask.cpp +++ b/src/MaaCore/Task/Miscellaneous/BattleFormationTask.cpp @@ -48,15 +48,20 @@ bool asst::BattleFormationTask::_run() { LogTraceFunction; + const auto& img = ctrler()->get_image(); + if (!is_formation_valid(img)) { + return true; // 编队不可用,直接返回,常见于TR关卡 + } + if (!parse_formation()) { return false; } - if (m_select_formation_index > 0 && !select_formation(m_select_formation_index)) { + if (m_select_formation_index > 0 && !select_formation(m_select_formation_index, img)) { return false; } - if (!enter_selection_page()) { + if (!enter_selection_page(img)) { save_img(utils::path("debug") / utils::path("other")); return false; } @@ -387,9 +392,9 @@ std::vector asst::BattleFormationTask::analyzer_ope return opers_result; } -bool asst::BattleFormationTask::enter_selection_page() +bool asst::BattleFormationTask::enter_selection_page(const cv::Mat& img) { - return ProcessTask(*this, { "BattleQuickFormation" }).set_retry_times(3).run(); + return ProcessTask(*this, { "BattleQuickFormation" }).set_reusable_image(img).set_retry_times(3).run(); } bool asst::BattleFormationTask::select_opers_in_cur_page(std::vector& groups) @@ -534,17 +539,25 @@ bool asst::BattleFormationTask::parse_formation() return true; } -bool asst::BattleFormationTask::select_formation(int select_index) +bool asst::BattleFormationTask::select_formation(int select_index, const cv::Mat& img) { // 编队不会触发改名的区域有两组 // 一组是上面的黑长条 260*9 // 第二组是名字最左边和最右边的一块区域 // 右边比左边窄,暂定为左边 10*58 - static const std::vector select_formation_task = { "BattleSelectFormation1", - "BattleSelectFormation2", - "BattleSelectFormation3", - "BattleSelectFormation4" }; + static const std::array select_formation_task = { "BattleSelectFormation1", + "BattleSelectFormation2", + "BattleSelectFormation3", + "BattleSelectFormation4" }; - return ProcessTask { *this, { select_formation_task[select_index - 1] } }.run(); + return ProcessTask { *this, { select_formation_task[select_index - 1] } }.set_reusable_image(img).run(); +} + +bool asst::BattleFormationTask::is_formation_valid(const cv::Mat& img) const +{ + static const std::string valid_task = "BattleStartPre@BattleQuickFormation"; + ProcessTask task(*this, { "BattleFormationInvalid", valid_task }); + task.set_reusable_image(img); + return task.run() && task.get_last_task_name() == valid_task; } diff --git a/src/MaaCore/Task/Miscellaneous/BattleFormationTask.h b/src/MaaCore/Task/Miscellaneous/BattleFormationTask.h index e2035917fa..46c68c8cdc 100644 --- a/src/MaaCore/Task/Miscellaneous/BattleFormationTask.h +++ b/src/MaaCore/Task/Miscellaneous/BattleFormationTask.h @@ -79,6 +79,10 @@ protected: using OperGroup = std::pair>; virtual bool _run() override; + bool parse_formation(); + bool is_formation_valid(const cv::Mat& img) const; + bool select_formation(int select_index, const cv::Mat& img); + bool enter_selection_page(const cv::Mat& img = cv::Mat()); // 进入快捷编队清空选择后执行,快速选择非干员组的干员 void formation_with_last_opers(); bool add_formation(battle::Role role, std::vector oper_group, std::vector& missing); @@ -86,14 +90,11 @@ protected: bool add_additional(); // 补充刷信赖的干员,从最小的开始 bool add_trust_operators(); - bool enter_selection_page(); bool select_opers_in_cur_page(std::vector& groups); void swipe_page(); void swipe_to_the_left(int times = 2); bool confirm_selection(); bool click_role_table(battle::Role role); - bool parse_formation(); - bool select_formation(int select_index); bool select_random_support_unit(); void report_missing_operators(std::vector& groups);