From 4d824d08af409fc0abc7f6a4937633d39fa3028e Mon Sep 17 00:00:00 2001 From: Weiyou Wang Date: Sun, 1 Sep 2024 19:27:26 +1000 Subject: [PATCH] =?UTF-8?q?feat:=20=E5=8A=A0=E5=85=A5hold=E6=A8=A1?= =?UTF-8?q?=E5=BC=8F?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../Task/Reclamation/ReclamationConfig.h | 5 +- .../ReclamationCraftTaskPlugin.cpp | 108 ++++++++++++++---- .../Reclamation/ReclamationCraftTaskPlugin.h | 12 +- 3 files changed, 96 insertions(+), 29 deletions(-) diff --git a/src/MaaCore/Task/Reclamation/ReclamationConfig.h b/src/MaaCore/Task/Reclamation/ReclamationConfig.h index fdbcaffc94..1f370e2868 100644 --- a/src/MaaCore/Task/Reclamation/ReclamationConfig.h +++ b/src/MaaCore/Task/Reclamation/ReclamationConfig.h @@ -59,7 +59,8 @@ private: // 以下注释列出了插件专用参数, 以便于快速检阅。这些参数的具体声明与使用请参考各插件。 // ———————— ReclamationCraftTaskPlugin 专用参数 ——————————————————————————————————————— - // std::string m_tool_to_craft = "荧光棒"; // 要组装的支援道具 - // int m_num_craft_batches = 16; // 支援道具组装批次数, 每批组装 99 个 + // std::string m_tool_to_craft = "荧光棒"; // 要组装的支援道具 + // int m_num_craft_batches = 16; // 支援道具组装批次数, 每批组装 99 个 + // IncrementMode m_increment_mode = IncrementMode::Click; // 点击加号按钮增加组装数量的方式 }; } // namespace asst diff --git a/src/MaaCore/Task/Reclamation/ReclamationCraftTaskPlugin.cpp b/src/MaaCore/Task/Reclamation/ReclamationCraftTaskPlugin.cpp index ad6f80272c..4267ce7b0e 100644 --- a/src/MaaCore/Task/Reclamation/ReclamationCraftTaskPlugin.cpp +++ b/src/MaaCore/Task/Reclamation/ReclamationCraftTaskPlugin.cpp @@ -4,27 +4,33 @@ #include "Controller/Controller.h" #include "Task/ProcessTask.h" #include "Utils/Logger.hpp" -#include "Vision/OCRer.h" +#include "Vision/Matcher.h" +#include "Vision/RegionOCRer.h" -using namespace asst; - -bool ReclamationCraftTaskPlugin::load_params(const json::value& params) +bool asst::ReclamationCraftTaskPlugin::load_params(const json::value& params) { LogTraceFunction; - const ReclamationMode& mode = m_config->get_mode(); - if (mode != ReclamationMode::ProsperityInSave) { + if (const ReclamationMode& mode = m_config->get_mode(); mode != ReclamationMode::ProsperityInSave) { return false; } // 根据 params 设置插件专用参数 m_tool_to_craft = params.get("tool_to_craft", "荧光棒"); - m_num_craft_batches = params.get("num_craft_batches", 16); // 默认值 16 以组装 <荧光棒> 消耗至少 3000 木头为准计算得出 + m_num_craft_batches = + params.get("num_craft_batches", 16); // 默认值 16 以组装 <荧光棒> 消耗至少 3000 木头为准计算得出 + const int increment_mode_int = params.get("increment_mode", static_cast(IncrementMode::Click)); + const auto increment_mode = static_cast(increment_mode_int); + if (increment_mode != IncrementMode::Click && increment_mode != IncrementMode::Hold) { + Log.error(__FUNCTION__, "| unknown increment mode: ", increment_mode_int); + return false; + } + m_increment_mode = increment_mode; return true; } -bool ReclamationCraftTaskPlugin::verify(const AsstMsg msg, const json::value& details) const +bool asst::ReclamationCraftTaskPlugin::verify(const AsstMsg msg, const json::value& details) const { if (msg != AsstMsg::SubTaskStart || details.get("subtask", std::string()) != "ProcessTask") { return false; @@ -38,7 +44,7 @@ bool ReclamationCraftTaskPlugin::verify(const AsstMsg msg, const json::value& de return false; } -bool ReclamationCraftTaskPlugin::_run() +bool asst::ReclamationCraftTaskPlugin::_run() { LogTraceFunction; @@ -51,15 +57,13 @@ bool ReclamationCraftTaskPlugin::_run() for (int batch = 0; !need_exit() && !insufficient_materials && batch < m_num_craft_batches; ++batch) { // Step 1: 选择要组装的道具, 若没有找到则在组装台界面向下滑动屏幕后再次检测, 直到识别到要组装的道具后点击 ProcessTask(*this, { theme + "@RA@PIS-SelectTool" }).run(); - sleep(100); + sleep(500); int craft_amount = 0; - while (!need_exit() && !insufficient_materials && craft_amount < 99 ) { + while (!need_exit() && !insufficient_materials && craft_amount < 99) { // Step 2: 识别加号按钮后点击 99 次增加组装数量 - for (int i = craft_amount; i < 99; ++i) { - ProcessTask(*this, { theme + "@RA@IncreaseCraftAmount" }).run(); - } - sleep(100); + increase_craft_amount(99 - craft_amount); + sleep(500); // Step 3: 识别组装数量 if (!calc_craft_amount(craft_amount)) { @@ -70,7 +74,7 @@ bool ReclamationCraftTaskPlugin::_run() // 再次点击一次加号按钮, 确认组装数量已为最大 int old_craft_amount = craft_amount; ProcessTask(*this, { theme + "@RA@IncreaseCraftAmount" }).run(); - sleep(100); + sleep(500); if (!calc_craft_amount(craft_amount) || craft_amount <= old_craft_amount) { insufficient_materials = true; } @@ -81,32 +85,86 @@ bool ReclamationCraftTaskPlugin::_run() } // Step 4: 开始组装或取消组装 - if (craft_amount == 0) { + if (craft_amount <= 0) { // 点击空白处取消组装 ProcessTask(*this, { theme + "@RA@CancelCraft" }).run(); - } else { + } + else { // 点击开始组装图标, 获得物资, 点击 <点击空白处继续> 文字位置 ProcessTask(*this, { theme + "@RA@PIS-Craft" }).run(); } - sleep(100); + sleep(500); } return true; } -bool ReclamationCraftTaskPlugin::calc_craft_amount(int& value) +void asst::ReclamationCraftTaskPlugin::increase_craft_amount(const int& amount) { + LogTraceFunction; + const std::string& theme = m_config->get_theme(); - OCRer craft_amount_analyzer(ctrler()->get_image()); + // InputEvent touch_down_event; + // touch_down_event.type = InputEvent::Type::TOUCH_DOWN; + // InputEvent touch_up_event; + // touch_up_event.type = InputEvent::Type::TOUCH_UP; + Matcher add_button_analyzer; + add_button_analyzer.set_task_info(theme + "@RA@IncreaseCraftAmount"); + Rect add_button_rect; + + switch (m_increment_mode) { + case IncrementMode::Click: + for (int i = 0; i < amount; ++i) { + ProcessTask(*this, { theme + "@RA@IncreaseCraftAmount" }).run(); + } + break; + // case IncrementMode::FastClick: + // for (int i = 0; i < amount; ++i) { + // add_button_analyzer.set_image(ctrler()->get_image()); + // if (add_button_analyzer.analyze()) { + // const Rect add_button_rect = add_button_analyzer.get_result().rect; + // touch_down_event.point.x = add_button_rect.x + add_button_rect.width / 2; + // touch_down_event.point.y = add_button_rect.y + add_button_rect.height / 2; + // Log.info(touch_down_event.point.x, touch_down_event.point.y); + // ctrler()->inject_input_event(touch_down_event); + // ctrler()->inject_input_event(touch_up_event); + // sleep(500); + // } + // } + // break; + case IncrementMode::Hold: + add_button_analyzer.set_image(ctrler()->get_image()); + if (!add_button_analyzer.analyze()) { + Log.error(__FUNCTION__, "| cannot recongnise the add button"); + return; + } + add_button_rect = add_button_analyzer.get_result().rect; + ctrler()->swipe(add_button_rect, add_button_rect, 12 * 1000 * amount / 100 + 1000); + break; + default: + Log.error(__FUNCTION__, "| unknown increment mode: ", static_cast(m_increment_mode)); + break; + } +} + +bool asst::ReclamationCraftTaskPlugin::calc_craft_amount(int& value) +{ + LogTraceFunction; + + const std::string& theme = m_config->get_theme(); + + RegionOCRer craft_amount_analyzer(ctrler()->get_image()); + craft_amount_analyzer.set_bin_threshold(200, 255); craft_amount_analyzer.set_task_info(theme + "@RA@PIS-CraftAmountOcr"); - if (!craft_amount_analyzer.analyze()) { - Log.error(__FUNCTION__, "| unable to detect the craft amount"); - return false; + std::string value_str; + if (craft_amount_analyzer.analyze()) { + value_str = craft_amount_analyzer.get_result().text; + } else { // 此时组装数量显示为灰色的 1 + value_str = "0"; } - const std::string value_str = craft_amount_analyzer.get_result().front().text; if (!utils::chars_to_number(value_str, value)) { Log.error(__FUNCTION__, "| unable to convert OCR result " + value_str + " to integer"); return false; diff --git a/src/MaaCore/Task/Reclamation/ReclamationCraftTaskPlugin.h b/src/MaaCore/Task/Reclamation/ReclamationCraftTaskPlugin.h index ee85438983..865077008d 100644 --- a/src/MaaCore/Task/Reclamation/ReclamationCraftTaskPlugin.h +++ b/src/MaaCore/Task/Reclamation/ReclamationCraftTaskPlugin.h @@ -16,10 +16,18 @@ protected: virtual bool _run() override; private: + void increase_craft_amount(const int& amount = 99); bool calc_craft_amount(int& value); // ———————— constants and variables ——————————————————————————————————————————————— - std::string m_tool_to_craft; // 要组装的支援道具 - int m_num_craft_batches = 0; // 支援道具组装批次数, 每批组装 99 个 + enum class IncrementMode // 点击加号按钮增加组装数量的方式 + { + Click = 0, + Hold = 1 + }; + + std::string m_tool_to_craft = "荧光棒"; // 要组装的支援道具 + int m_num_craft_batches = 16; // 支援道具组装批次数, 每批组装 99 个 + IncrementMode m_increment_mode = IncrementMode::Click; // 点击加号按钮增加组装数量的方式 }; } // namespace asst