From dcf4c20f16b9467956a94e54c8d2134134240bfb Mon Sep 17 00:00:00 2001 From: "firedcto@gmail.com" Date: Tue, 24 Sep 2024 23:18:26 +0800 Subject: [PATCH] =?UTF-8?q?=E4=BC=98=E5=8C=96=E8=87=AA=E5=8A=A8=E6=88=98?= =?UTF-8?q?=E6=96=97,=20=E4=BF=AE=E5=A4=8D=E4=BB=8A=E6=B1=90=E4=B8=8D?= =?UTF-8?q?=E5=88=87=E9=97=AE=E9=A2=98?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/char/Baizhi.py | 13 +++---------- src/char/BaseChar.py | 17 +++++++++++------ src/char/Changli.py | 2 +- src/char/Encore.py | 38 +++++++++++++++----------------------- src/char/HavocRover.py | 11 +++++++---- src/char/Healer.py | 16 ++++++++++++++++ src/char/Jinhsi.py | 2 +- src/char/Sanhua.py | 8 ++++---- src/char/Verina.py | 10 ++-------- src/task/BaseCombatTask.py | 30 ++++++++++++++++-------------- src/task/DiagnosisTask.py | 1 + 11 files changed, 77 insertions(+), 71 deletions(-) create mode 100644 src/char/Healer.py diff --git a/src/char/Baizhi.py b/src/char/Baizhi.py index 320b0bd..3cc5016 100644 --- a/src/char/Baizhi.py +++ b/src/char/Baizhi.py @@ -1,13 +1,7 @@ -from src.char.BaseChar import BaseChar +from src.char.Healer import Healer -class Baizhi(BaseChar): - - def count_base_priority(self): - return -1 - - def count_echo_priority(self): - return 0 +class Baizhi(Healer): def do_perform(self): if self.has_intro: @@ -15,6 +9,5 @@ class Baizhi(BaseChar): self.continues_normal_attack(1.2, click_resonance_if_ready_and_return=True) self.click_liberation(con_less_than=1) self.click_resonance() - if self.get_current_con() > 0.65: - self.click_echo() + self.click_echo() self.switch_next_char() diff --git a/src/char/BaseChar.py b/src/char/BaseChar.py index 38e576c..20d25d3 100644 --- a/src/char/BaseChar.py +++ b/src/char/BaseChar.py @@ -231,7 +231,7 @@ class BaseChar: self.logger.info('reset state') self.has_intro = False - def click_liberation(self, wait_end=True, con_less_than=-1, send_click=False): + def click_liberation(self, con_less_than=-1, send_click=False, wait_if_cd_ready=0): if con_less_than > 0: if self.get_current_con() > con_less_than: return False @@ -239,6 +239,11 @@ class BaseChar: start = time.time() last_click = 0 clicked = False + while time.time() - start < wait_if_cd_ready and not self.liberation_available() and not self.has_cd( + 'liberation'): + self.logger.debug(f'click_liberation wait ready {wait_if_cd_ready}') + self.click(interval=0.1) + self.task.next_frame() while self.liberation_available(): # clicked and still in team wait for animation self.logger.debug(f'click_liberation liberation_available click') now = time.time() @@ -299,14 +304,14 @@ class BaseChar: def get_resonance_key(self): return self.task.get_resonance_key() - def get_switch_priority(self, current_char, has_intro): - priority = self.do_get_switch_priority(current_char, has_intro) + def get_switch_priority(self, current_char, has_intro, target_low_con): + priority = self.do_get_switch_priority(current_char, has_intro, target_low_con) if priority < Priority.MAX and time.time() - self.last_switch_time < 0.9: return Priority.SWITCH_CD # switch cd else: return priority - def do_get_switch_priority(self, current_char, has_intro=False): + def do_get_switch_priority(self, current_char, has_intro=False, target_low_con=False): priority = 0 if self.count_liberation_priority() and self.liberation_available(): priority += self.count_liberation_priority() @@ -353,10 +358,10 @@ class BaseChar: return time.time() - self.last_echo > self.echo_cd def is_con_full(self): - return self.task.is_con_full() + return self.task.is_con_full(self.config) def get_current_con(self): - self.current_con = self.task.get_current_con() + self.current_con = self.task.get_current_con(self.config) return self.current_con def is_forte_full(self): diff --git a/src/char/Changli.py b/src/char/Changli.py index f620122..8cca259 100644 --- a/src/char/Changli.py +++ b/src/char/Changli.py @@ -11,7 +11,7 @@ class Changli(BaseChar): def reset_state(self): self.enhanced_normal = False - def do_get_switch_priority(self, current_char: BaseChar, has_intro=False): + def do_get_switch_priority(self, current_char: BaseChar, has_intro=False, target_low_con=False): if self.time_elapsed_accounting_for_freeze(self.last_e) < 4: self.logger.info( f'switch priority MIN because e not finished') diff --git a/src/char/Encore.py b/src/char/Encore.py index 7411940..fe1d3f8 100644 --- a/src/char/Encore.py +++ b/src/char/Encore.py @@ -19,36 +19,28 @@ class Encore(BaseChar): self.last_resonance = 0 def do_perform(self): - target_low_con = False if self.has_intro: self.logger.debug('encore wait intro') - self.continues_normal_attack(1.5) + self.continues_normal_attack(1.4) self.wait_down() - else: - while not self.still_in_liberation() and self.can_resonance_step2(): - if self.click_resonance()[0]: - self.last_resonance = 0 - self.logger.info('try Encore resonance_step2 success') - self.sleep(0.2) - break - else: - self.task.next_frame() if self.still_in_liberation(): - target_low_con = True self.n4() - elif self.click_resonance()[0]: - self.logger.debug('click_resonance') - self.last_resonance = time.time() - elif self.click_liberation(): + return self.switch_next_char() + if self.click_resonance()[0]: + if not self.can_resonance_step2(delay=4): + self.last_resonance = time.time() + return self.switch_next_char() + if self.click_liberation(wait_if_cd_ready=0.4): self.liberation_time = time.time() self.n4() - target_low_con = True - elif self.echo_available(): - self.logger.debug('click_echo') - self.click_echo(duration=1.5) + return self.switch_next_char() else: self.logger.info('Encore nothing is available') - self.switch_next_char(target_low_con=target_low_con) + if self.echo_available(): + self.logger.debug('click_echo') + self.click_echo(duration=1.5) + return self.switch_next_char() + self.switch_next_char() def count_liberation_priority(self): return 40 @@ -62,7 +54,7 @@ class Encore(BaseChar): def can_resonance_step2(self, delay=2): return self.time_elapsed_accounting_for_freeze(self.last_resonance) < delay - def do_get_switch_priority(self, current_char: BaseChar, has_intro=False): + def do_get_switch_priority(self, current_char: BaseChar, has_intro=False, target_low_con=False): if self.time_elapsed_accounting_for_freeze(self.last_heavy) < 4: return Priority.MIN elif self.still_in_liberation() or self.can_resonance_step2(): @@ -73,7 +65,7 @@ class Encore(BaseChar): return super().do_get_switch_priority(current_char, has_intro) def n4(self, duration=2.0): - duration = 2.6 if self.click_resonance()[0] else 2.3 + duration = 2.7 if self.click_resonance()[0] else 2.4 if self.time_elapsed_accounting_for_freeze(self.liberation_time) < 6: self.logger.debug('encore liberation n4') self.continues_normal_attack(duration=duration) diff --git a/src/char/HavocRover.py b/src/char/HavocRover.py index f74f129..753eef4 100644 --- a/src/char/HavocRover.py +++ b/src/char/HavocRover.py @@ -3,12 +3,15 @@ from src.char.BaseChar import BaseChar class HavocRover(BaseChar): def do_perform(self): - if self.is_forte_full() and self.liberation_available(): + self.click_liberation() + if self.click_resonance()[0]: + return self.switch_next_char() + if self.is_forte_full(): self.logger.info(f'forte_full, and liberation_available, heavy attack') self.wait_down() self.heavy_attack() self.sleep(0.4) - self.click_liberation() - if not self.click_resonance()[0]: - self.click_echo() + if self.click_resonance()[0]: + return self.switch_next_char() + self.click_echo() self.switch_next_char() diff --git a/src/char/Healer.py b/src/char/Healer.py new file mode 100644 index 0000000..6280b33 --- /dev/null +++ b/src/char/Healer.py @@ -0,0 +1,16 @@ +from src.char.BaseChar import BaseChar, Priority + + +class Healer(BaseChar): + + def count_base_priority(self): + return -1 + + def count_echo_priority(self): + return 0 + + def do_get_switch_priority(self, current_char, has_intro=False, target_low_con=False): + if has_intro and not target_low_con: + return Priority.MIN + else: + return super().do_get_switch_priority(current_char, has_intro, target_low_con) diff --git a/src/char/Jinhsi.py b/src/char/Jinhsi.py index 3f30a23..85b691a 100644 --- a/src/char/Jinhsi.py +++ b/src/char/Jinhsi.py @@ -33,7 +33,7 @@ class Jinhsi(BaseChar): super().switch_next_char(free_intro=self.has_free_intro, target_low_con=True) self.has_free_intro = False - def do_get_switch_priority(self, current_char: BaseChar, has_intro=False): + def do_get_switch_priority(self, current_char: BaseChar, has_intro=False, target_low_con=False): if has_intro or self.incarnation or self.incarnation_cd: self.logger.info( f'switch priority max because has_intro {has_intro} incarnation {self.incarnation} incarnation_cd {self.incarnation_cd}') diff --git a/src/char/Sanhua.py b/src/char/Sanhua.py index 2e06577..40005da 100644 --- a/src/char/Sanhua.py +++ b/src/char/Sanhua.py @@ -3,14 +3,14 @@ from src.char.BaseChar import BaseChar class Sanhua(BaseChar): def do_perform(self): + if self.has_intro: + self.continues_normal_attack(1.2) self.click_liberation() if self.click_resonance()[0]: return self.switch_next_char() if self.click_echo(): return self.switch_next_char() - self.task.mouse_down() - self.sleep(.7) - self.task.mouse_up() - self.sleep(0.3) + self.heavy_attack(0.75) + self.sleep(0.4) self.switch_next_char() diff --git a/src/char/Verina.py b/src/char/Verina.py index deac050..a58a5ae 100644 --- a/src/char/Verina.py +++ b/src/char/Verina.py @@ -1,7 +1,7 @@ -from src.char.BaseChar import BaseChar +from src.char.Healer import Healer -class Verina(BaseChar): +class Verina(Healer): def do_perform(self): self.click_liberation() @@ -15,9 +15,3 @@ class Verina(BaseChar): self.heavy_attack() # self.normal_attack() self.switch_next_char() - - def count_base_priority(self): - return - 1 - - def count_echo_priority(self): - return 0 diff --git a/src/task/BaseCombatTask.py b/src/task/BaseCombatTask.py index af8bc0a..2c17d46 100644 --- a/src/task/BaseCombatTask.py +++ b/src/task/BaseCombatTask.py @@ -158,7 +158,7 @@ class BaseCombatTask(BaseWWTask, FindFeature, OCR, CombatCheck): if char == current_char: priority = Priority.CURRENT_CHAR else: - priority = char.get_switch_priority(current_char, has_intro) + priority = char.get_switch_priority(current_char, has_intro, target_low_con) logger.info( f'switch_next_char priority: {char} {priority} {char.current_con} target_low_con {target_low_con}') if target_low_con: @@ -217,6 +217,7 @@ class BaseCombatTask(BaseWWTask, FindFeature, OCR, CombatCheck): if post_action: post_action() + self.next_frame() logger.info(f'switch_next_char end {(current_char.last_switch_time - start):.3f}s') def get_liberation_key(self): @@ -376,10 +377,10 @@ class BaseCombatTask(BaseWWTask, FindFeature, OCR, CombatCheck): def get_resonance_percentage(self): return self.calculate_color_percentage(white_color, self.get_box_by_name('box_resonance')) - def is_con_full(self): - return self.get_current_con() == 1 + def is_con_full(self, char_config=None): + return self.get_current_con(char_config) == 1 - def get_current_con(self): + def get_current_con(self, char_config=None): box = self.box_of_screen_scaled(3840, 2160, 1422, 1939, to_x=1566, to_y=2076, name='con_full', hcenter=True) box.confidence = 0 @@ -388,7 +389,9 @@ class BaseCombatTask(BaseWWTask, FindFeature, OCR, CombatCheck): percent = 0 max_is_full = False color_index = -1 - target_index = self.config.get('_ring_color_index', -1) + target_index = -1 + if char_config: + target_index = char_config.get('_ring_color_index', target_index) cropped = box.crop_frame(self.frame) for i in range(len(con_colors)): if target_index != -1 and i != target_index: @@ -403,20 +406,19 @@ class BaseCombatTask(BaseWWTask, FindFeature, OCR, CombatCheck): if area > max_area: max_area = int(area) if max_is_full: + percent = 1 + if max_is_full and char_config: self.logger.info( - f'is_con_full found a full ring {self.config.get("_full_ring_area", 0)} -> {max_area} {color_index}') - self.config['_full_ring_area'] = max_area - self.config['_ring_color_index'] = color_index + f'is_con_full found a full ring {char_config.get("_full_ring_area", 0)} -> {max_area} {color_index}') + char_config['_full_ring_area'] = max_area + char_config['_ring_color_index'] = color_index self.logger.info( - f'is_con_full2 found a full ring {self.config.get("_full_ring_area", 0)} -> {max_area} {color_index}') - if self.config.get('_full_ring_area', 0) > 0: - percent = max_area / self.config['_full_ring_area'] + f'is_con_full2 found a full ring {char_config.get("_full_ring_area", 0)} -> {max_area} {color_index}') + if percent != 1 and char_config and char_config.get('_full_ring_area', 0) > 0: + percent = max_area / char_config['_full_ring_area'] if not max_is_full and percent >= 1: self.logger.warning( f'is_con_full not full but percent greater than 1, set to 0.99, {percent} {max_is_full}') - # self.task.screenshot( - # f'is_con_full not full but percent greater than 1, set to 0.99, {percent} {max_is_full}', - # cropped) percent = 0.99 if percent > 1: self.logger.error(f'is_con_full percent greater than 1, set to 1, {percent} {max_is_full}') diff --git a/src/task/DiagnosisTask.py b/src/task/DiagnosisTask.py index 1341ffa..7123449 100644 --- a/src/task/DiagnosisTask.py +++ b/src/task/DiagnosisTask.py @@ -41,6 +41,7 @@ class DiagnosisTask(BaseCombatTask): self.info['Echo Available'] = char.current_echo() > 0 self.info['Liberation in CD'] = char.has_cd('liberation') self.info['Liberation Available'] = char.current_liberation() > 0 + self.info['Concerto'] = char.get_current_con() self.next_frame() def choose_level(self, start):