diff --git a/config/forgotten_hall_sample.yml b/config/forgotten_hall_sample.yml index a30e04c3..80705f2e 100644 --- a/config/forgotten_hall_sample.yml +++ b/config/forgotten_hall_sample.yml @@ -1 +1 @@ -team_list: [] \ No newline at end of file +team_module_list: [] \ No newline at end of file diff --git a/config/one_stop_service_sample.yml b/config/one_stop_service_sample.yml index 86182249..00de0c7b 100644 --- a/config/one_stop_service_sample.yml +++ b/config/one_stop_service_sample.yml @@ -8,6 +8,7 @@ app_order: - 'nameless_honor' - 'claim_training' - 'buy_xianzhou_parcel' + - 'forgotten_hall' app_run: - 'world_patrol' - 'echo_of_war' @@ -18,3 +19,4 @@ app_run: - 'nameless_honor' - 'claim_training' - 'buy_xianzhou_parcel' + - 'forgotten_hall' diff --git a/src/gui/settings/settings_forgotten_hall_view.py b/src/gui/settings/settings_forgotten_hall_view.py index 3d77b57c..1ecf53bd 100644 --- a/src/gui/settings/settings_forgotten_hall_view.py +++ b/src/gui/settings/settings_forgotten_hall_view.py @@ -121,7 +121,9 @@ def update_team_member(self, character_id_list: List[str]): :param character_id_list: 角色ID列表 :return: """ - self.team_value.character_id_list = character_id_list + self.team_value.character_id_list.clear() # 注意不能直接等于 因为这样会共用了同一个数组 + for character_id in character_id_list: + self.team_value.character_id_list.append(character_id) self._update_character_dropdown_value() self._on_value_changed() @@ -253,8 +255,10 @@ def _on_item_click_del(self, e): if to_del_idx != -1: self.controls.pop(to_del_idx) + self.update() self._on_list_item_value_changed() + class SettingsForgottenHallView(SrBasicView, ft.Row): def __init__(self, page: ft.Page, ctx: Context): diff --git a/src/sr/app/routine/forgotten_hall_app.py b/src/sr/app/routine/forgotten_hall_app.py index c78ed680..46fbb0d9 100644 --- a/src/sr/app/routine/forgotten_hall_app.py +++ b/src/sr/app/routine/forgotten_hall_app.py @@ -71,11 +71,14 @@ def update_mission_star(self, mission_num: int, star: int): """ stars = self.mission_stars stars[mission_num] = star + if 'mission_stars' not in self.data: + self.update('mission_stars', stars, False) total_star: int = 0 for v in stars.values(): total_star += v if total_star > self.star: self.star = total_star + self.save() _forgotten_hall_record: Optional[ForgottenHallRecord] = None diff --git a/src/sr/image/sceenshot/battle.py b/src/sr/image/sceenshot/battle.py index 7e0aabc0..faa1a0a9 100644 --- a/src/sr/image/sceenshot/battle.py +++ b/src/sr/image/sceenshot/battle.py @@ -147,9 +147,9 @@ def get_battle_result_str(screen: MatLike, ocr: OcrMatcher) -> Optional[str]: for rect in [AFTER_BATTLE_RESULT_RECT_1, AFTER_BATTLE_RESULT_RECT_2]: part, _ = cv2_utils.crop_image(screen, rect) ocr_result = ocr.ocr_for_single_line(part, strict_one_line=True) - if str_utils.find_by_lcs(gt('挑战成功', 'ocr'), ocr_result, percent=0.55): + if str_utils.find_by_lcs(gt('成功', 'ocr'), ocr_result, percent=0.1): return gt('挑战成功', 'ocr') - elif str_utils.find_by_lcs(gt('挑战失败', 'ocr'), ocr_result, percent=0.55): + elif str_utils.find_by_lcs(gt('失败', 'ocr'), ocr_result, percent=0.1): return gt('挑战失败', 'ocr') return None diff --git a/src/sr/operation/__init__.py b/src/sr/operation/__init__.py index ebbdf3fc..710309a4 100644 --- a/src/sr/operation/__init__.py +++ b/src/sr/operation/__init__.py @@ -185,9 +185,9 @@ def _after_operation_done(self, result: OperationResult): :return: """ if result.success: - log.info('指令 %s 执行成功 返回状态 %s', self.display_name, result.status) + log.info('%s 执行成功 返回状态 %s', self.display_name, result.status) else: - log.error('指令 %s 执行失败 返回状态 %s', self.display_name, result.status) + log.error('%s 执行失败 返回状态 %s', self.display_name, result.status) @staticmethod def round_success(status: str = None) -> OperationOneRoundResult: diff --git a/src/sr/operation/unit/enter_auto_fight.py b/src/sr/operation/unit/enter_auto_fight.py index efb39e56..814b2b35 100644 --- a/src/sr/operation/unit/enter_auto_fight.py +++ b/src/sr/operation/unit/enter_auto_fight.py @@ -24,9 +24,10 @@ def __init__(self, ctx: Context): 根据小地图的红圈 判断是否被敌人锁定 进行主动攻击 """ super().__init__(ctx, op_name=gt('进入战斗', 'ui')) - self.last_attack_time = 0 - self.last_alert_time = 0 # 上次警报时间 - self.last_in_battle_time = 0 # 上次在战斗的时间 + self.last_attack_time: float = 0 + self.last_alert_time: float = 0 # 上次警报时间 + self.last_in_battle_time: float = 0 # 上次在战斗的时间 + self.last_check_auto_fight_time: float = 0 # 上次检测自动战斗的时间 self.with_battle: bool = False # 是否有进入战斗 self.attach_direction: int = 0 # 攻击方向 @@ -34,6 +35,7 @@ def _init_before_execute(self): self.last_attack_time = time.time() self.last_alert_time = time.time() # 上次警报时间 self.last_in_battle_time = time.time() # 上次在战斗的时间 + self.last_check_auto_fight_time = time.time() # 上次检测自动战斗的时间 def _execute_one_round(self) -> OperationOneRoundResult: ctrl: GameController = self.ctx.controller @@ -43,8 +45,9 @@ def _execute_one_round(self) -> OperationOneRoundResult: now_time = time.time() screen_status = battle.get_battle_status(screen, self.ctx.im) if screen_status != battle.IN_WORLD: # 在战斗界面 - eaf = EnableAutoFight(self.ctx) - eaf.execute() + if now_time - self.last_check_auto_fight_time > 10: + eaf = EnableAutoFight(self.ctx) + eaf.execute() time.sleep(0.5) # 战斗部分 self.last_in_battle_time = time.time() self.last_alert_time = self.last_in_battle_time diff --git a/src/sr/operation/unit/forgotten_hall/__init__.py b/src/sr/operation/unit/forgotten_hall/__init__.py index f9921b98..b8e15dea 100644 --- a/src/sr/operation/unit/forgotten_hall/__init__.py +++ b/src/sr/operation/unit/forgotten_hall/__init__.py @@ -9,7 +9,7 @@ from basic.img import MatchResult, cv2_utils, MatchResultList from sr.context import Context -CHOOSE_MISSION_RECT = Rect(10, 495, 1900, 850) +CHOOSE_MISSION_RECT = Rect(10, 400, 1900, 850) def get_all_mission_num_pos(ctx: Context, screen: MatLike) -> dict[int, MatchResult]: @@ -24,6 +24,7 @@ def get_all_mission_num_pos(ctx: Context, screen: MatLike) -> dict[int, MatchRes lower_color = np.array([240, 240, 240], dtype=np.uint8) upper_color = np.array([255, 255, 255], dtype=np.uint8) white_part = cv2.inRange(part, lower_color, upper_color) + # cv2_utils.show_image(white_part, win_name='white_part', wait=0) digit_rect_list: List[Rect] = [] # 整张图片进行OCR容易出现匹配不到的情况 因为先切割再匹配 @@ -99,8 +100,8 @@ def get_mission_num_pos(ctx: Context, target_mission_num: int, screen: MatLike, break drag_from = CHOOSE_MISSION_RECT.center - drag_to = drag_from + Point((400 if existed_larger else -400), 0) - ctx.controller.drag_to(drag_to, drag_from) + drag_to = drag_from + Point((600 if existed_larger else -600), 0) + ctx.controller.drag_to(drag_to, drag_from, duration=0.3) time.sleep(0.5) return None diff --git a/src/sr/operation/unit/forgotten_hall/auto_fight_in_forgotten_hall.py b/src/sr/operation/unit/forgotten_hall/auto_fight_in_forgotten_hall.py index c4d1dc56..1dd97a94 100644 --- a/src/sr/operation/unit/forgotten_hall/auto_fight_in_forgotten_hall.py +++ b/src/sr/operation/unit/forgotten_hall/auto_fight_in_forgotten_hall.py @@ -1,5 +1,5 @@ import time -from typing import Optional, ClassVar +from typing import Optional, ClassVar, List from cv2.typing import MatLike @@ -15,8 +15,10 @@ class AutoFightInForgottenHall(Operation): - AFTER_BATTLE_RESULT_RECT_1: ClassVar[Rect] = Rect(820, 300, 1100, 370) # 挑战成功 - AFTER_BATTLE_RESULT_RECT_2: ClassVar[Rect] = Rect(785, 230, 1155, 310) # 战斗失败 + AFTER_BATTLE_RESULT_RECT_1: ClassVar[Rect] = Rect(820, 200, 1100, 270) # 挑战成功 有奖励 + AFTER_BATTLE_RESULT_RECT_2: ClassVar[Rect] = Rect(820, 300, 1100, 370) # 挑战成功 无奖励 + AFTER_BATTLE_SUCCESS_RECT_LIST: ClassVar[List[Rect]] = [AFTER_BATTLE_RESULT_RECT_1, AFTER_BATTLE_RESULT_RECT_2] + AFTER_BATTLE_RESULT_RECT_3: ClassVar[Rect] = Rect(785, 230, 1155, 320) # 战斗失败 BATTLE_SUCCESS_STATUS: ClassVar[str] = 'battle_success' # 成功 最后一个节点成功才会出现 BATTLE_FAIL_STATUS: ClassVar[str] = 'battle_fail' # 失败 任意一个节点失败都会出现 @@ -30,6 +32,7 @@ def __init__(self, ctx: Context, timeout_seconds: float = 600): self.with_battle: bool = False # 是否有进入战斗 self.last_attack_time: float = 0 # 上次攻击的时间 self.last_in_battle_time: float = 0 # 上次在战斗时间 + self.last_check_auto_fight_time: float = 0 # 上次检测自动战斗的时间 def _init_before_execute(self): super()._init_before_execute() @@ -47,9 +50,9 @@ def _execute_one_round(self) -> OperationOneRoundResult: part, _ = cv2_utils.crop_image(screen, WaitNodeStart.EXIT_BTN) match_result_list = self.ctx.im.match_template(part, 'ui_icon_10', only_best=True) if len(match_result_list) == 0: # 在战斗界面 - log.info('战斗中') - eaf = EnableAutoFight(self.ctx) - eaf.execute() + if now_time - self.last_check_auto_fight_time > 10: + eaf = EnableAutoFight(self.ctx) + eaf.execute() time.sleep(0.5) # 战斗部分 self.with_battle = True self.last_in_battle_time = now_time @@ -78,12 +81,13 @@ def _check_battle_result(self, screen: Optional[MatLike] = None) -> Optional[str if screen is None: screen = self.screenshot() - part, _ = cv2_utils.crop_image(screen, AutoFightInForgottenHall.AFTER_BATTLE_RESULT_RECT_1) - ocr_result = self.ctx.ocr.ocr_for_single_line(part, strict_one_line=True) - if str_utils.find_by_lcs(gt('挑战成功', 'ocr'), ocr_result, percent=0.1): - return AutoFightInForgottenHall.BATTLE_SUCCESS_STATUS + for rect in AutoFightInForgottenHall.AFTER_BATTLE_SUCCESS_RECT_LIST: + part, _ = cv2_utils.crop_image(screen, rect) + ocr_result = self.ctx.ocr.ocr_for_single_line(part, strict_one_line=True) + if str_utils.find_by_lcs(gt('挑战成功', 'ocr'), ocr_result, percent=0.1): + return AutoFightInForgottenHall.BATTLE_SUCCESS_STATUS - part, _ = cv2_utils.crop_image(screen, AutoFightInForgottenHall.AFTER_BATTLE_RESULT_RECT_2) + part, _ = cv2_utils.crop_image(screen, AutoFightInForgottenHall.AFTER_BATTLE_RESULT_RECT_3) ocr_result = self.ctx.ocr.ocr_for_single_line(part, strict_one_line=True) if str_utils.find_by_lcs(gt('战斗失败', 'ocr'), ocr_result, percent=0.1): return AutoFightInForgottenHall.BATTLE_FAIL_STATUS diff --git a/src/sr/operation/unit/forgotten_hall/check_forgotten_hall_star.py b/src/sr/operation/unit/forgotten_hall/check_forgotten_hall_star.py index fc28b288..e5eb7781 100644 --- a/src/sr/operation/unit/forgotten_hall/check_forgotten_hall_star.py +++ b/src/sr/operation/unit/forgotten_hall/check_forgotten_hall_star.py @@ -55,6 +55,6 @@ def _get_star_cnt(self, screen: MatLike) -> int: :return: 星数。如果没有获取到就返回-1 """ part, _ = cv2_utils.crop_image(screen, CheckForgottenHallStar._STAR_RECT) - cv2_utils.show_image(part, win_name='_get_star_cnt') + # cv2_utils.show_image(part, win_name='_get_star_cnt') ocr_str = self.ctx.ocr.ocr_for_single_line(part, strict_one_line=True) return str_utils.get_positive_digits(ocr_str, -1) diff --git a/src/sr/operation/unit/forgotten_hall/check_mission_star.py b/src/sr/operation/unit/forgotten_hall/check_mission_star.py index 15831780..698c75e7 100644 --- a/src/sr/operation/unit/forgotten_hall/check_mission_star.py +++ b/src/sr/operation/unit/forgotten_hall/check_mission_star.py @@ -19,7 +19,7 @@ def __init__(self, ctx: Context, mission_num: int, star_callback: Callable = Non :param mission_num: 扫描哪个关卡 1~10 :param star_callback: 获取到星数后的回调 """ - super().__init__(ctx, try_times=5, op_name='%s %d' % (gt('忘却之庭关卡星数', 'ui'), mission_num)) + super().__init__(ctx, try_times=10, op_name='%s %d' % (gt('忘却之庭 获取关卡星数', 'ui'), mission_num)) self.mission_num: int = mission_num self.star_callback: Callable = star_callback diff --git a/src/sr/operation/unit/forgotten_hall/move_to_enemy.py b/src/sr/operation/unit/forgotten_hall/move_to_enemy.py index 78371847..b78ad959 100644 --- a/src/sr/operation/unit/forgotten_hall/move_to_enemy.py +++ b/src/sr/operation/unit/forgotten_hall/move_to_enemy.py @@ -69,12 +69,12 @@ def _find_enemy_pos(self, mm: Optional[MatLike] = None) -> Optional[Point]: to_del = cal_pos.get_radio_to_del(self.ctx.im, angle) mm2 = mini_map.remove_radio(mm, to_del) - cv2_utils.show_image(mm2, win_name='mm2') + # cv2_utils.show_image(mm2, win_name='mm2') lower_color = np.array([0, 0, 150], dtype=np.uint8) upper_color = np.array([60, 60, 255], dtype=np.uint8) red_part = cv2.inRange(mm2, lower_color, upper_color) - cv2_utils.show_image(red_part, win_name='red_part') + # cv2_utils.show_image(red_part, win_name='red_part') # 膨胀一下找连通块 to_check = cv2_utils.dilate(red_part, 5) diff --git a/test/src/sr/operation/unit/forgotten_hall/check_mission_star_test.py b/test/src/sr/operation/unit/forgotten_hall/check_mission_star_test.py index ad9e116e..61ba12c3 100644 --- a/test/src/sr/operation/unit/forgotten_hall/check_mission_star_test.py +++ b/test/src/sr/operation/unit/forgotten_hall/check_mission_star_test.py @@ -5,7 +5,7 @@ def _test_get_all_mission_num_pos(): - screen = get_debug_image('_1701610115616') + screen = get_debug_image('_1701790574790') print(get_all_mission_num_pos(ctx, screen)) diff --git a/version.yml b/version.yml index b966300c..6f3e8f3b 100644 --- a/version.yml +++ b/version.yml @@ -1 +1 @@ -version: "v0.7.6" \ No newline at end of file +version: "v0.7.7" \ No newline at end of file