From 0fb6a96691acdc2ab69ee5bd2267fd2d36cb10c9 Mon Sep 17 00:00:00 2001 From: LmeSzinc <37934724+LmeSzinc@users.noreply.github.com> Date: Sun, 28 Apr 2024 23:27:23 +0800 Subject: [PATCH] Refactor: Make MaaTouch inputs synchronous --- bin/MaaTouch/maatouchsync | Bin 0 -> 15347 bytes module/config/config_manual.py | 4 +- module/device/method/maatouch.py | 117 +++++++++++++++++++++++++----- module/device/method/minitouch.py | 81 ++++++++++++++++++--- 4 files changed, 170 insertions(+), 32 deletions(-) create mode 100644 bin/MaaTouch/maatouchsync diff --git a/bin/MaaTouch/maatouchsync b/bin/MaaTouch/maatouchsync new file mode 100644 index 0000000000000000000000000000000000000000..dc75d231dd64cfaf161211f6cea35b9a6f852ae3 GIT binary patch literal 15347 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 literal 0 HcmV?d00001 diff --git a/module/config/config_manual.py b/module/config/config_manual.py index d4e90c0a4..7eb6ecb09 100644 --- a/module/config/config_manual.py +++ b/module/config/config_manual.py @@ -91,8 +91,8 @@ class ManualConfig: SCRCPY_FILEPATH_LOCAL = './bin/scrcpy/scrcpy-server-v1.20.jar' SCRCPY_FILEPATH_REMOTE = '/data/local/tmp/scrcpy-server-v1.20.jar' - MAATOUCH_FILEPATH_LOCAL = './bin/MaaTouch/maatouch' - MAATOUCH_FILEPATH_REMOTE = '/data/local/tmp/maatouch' + MAATOUCH_FILEPATH_LOCAL = './bin/MaaTouch/maatouchsync' + MAATOUCH_FILEPATH_REMOTE = '/data/local/tmp/maatouchsync' """ module.campaign.gems_farming diff --git a/module/device/method/maatouch.py b/module/device/method/maatouch.py index e9a171322..7745a81f7 100644 --- a/module/device/method/maatouch.py +++ b/module/device/method/maatouch.py @@ -1,5 +1,6 @@ import socket import threading +import time from functools import wraps from adbutils.errors import AdbError @@ -8,7 +9,7 @@ from module.base.decorator import cached_property, del_cached_property, has_cach from module.base.timer import Timer from module.base.utils import * from module.device.connection import Connection -from module.device.method.minitouch import CommandBuilder, insert_swipe +from module.device.method.minitouch import CommandBuilder, insert_swipe, Command from module.device.method.utils import RETRY_TRIES, handle_adb_error, retry_sleep from module.exception import RequestHumanTakeover from module.logger import logger @@ -38,6 +39,15 @@ def retry(func): def init(): self.adb_reconnect() del_cached_property(self, '_maatouch_builder') + # MaaTouchSyncTimeout + # Probably because adb server was killed + except MaaTouchSyncTimeout as e: + logger.error(e) + + def init(): + self.adb_reconnect() + del_cached_property(self, '_maatouch_builder') + self.reset_maatouch() # Emulator closed except ConnectionAbortedError as e: logger.error(e) @@ -79,7 +89,12 @@ def retry(func): class MaatouchBuilder(CommandBuilder): - def __init__(self, device, contact=0, handle_orientation=False): + def __init__( + self, + device, + contact=0, + handle_orientation=False, + ): """ Args: device (MaaTouch): @@ -90,11 +105,21 @@ class MaatouchBuilder(CommandBuilder): def send(self): return self.device.maatouch_send(builder=self) + def send_sync(self, mode=2): + return self.device.maatouch_send_sync(builder=self, mode=mode) + + def end(self): + self.device.sleep(self.DEFAULT_DELAY) + class MaaTouchNotInstalledError(Exception): pass +class MaaTouchSyncTimeout(Exception): + pass + + class MaaTouch(Connection): """ Control method that implements the same as scrcpy and has an interface similar to minitouch. @@ -121,6 +146,8 @@ class MaaTouch(Connection): del self._maatouch_init_thread self._maatouch_init_thread = None + # Return an empty builder + self._maatouch_builder.clear() return self._maatouch_builder def early_maatouch_init(self): @@ -174,7 +201,7 @@ class MaaTouch(Connection): # CLASSPATH=/data/local/tmp/maatouch app_process / com.shxyke.MaaTouch.App stream = self.adb_shell( - ['CLASSPATH=/data/local/tmp/maatouch', 'app_process', '/', 'com.shxyke.MaaTouch.App'], + [f'CLASSPATH={self.config.MAATOUCH_FILEPATH_REMOTE}', 'app_process', '/', 'com.shxyke.MaaTouch.App'], stream=True, recvall=False ) @@ -226,6 +253,8 @@ class MaaTouch(Connection): # _, pid = out.split(" ") # self._maatouch_pid = pid + # Timeout 2s for sync + stream.settimeout(2) logger.info( "MaaTouch stream connected" ) @@ -237,11 +266,56 @@ class MaaTouch(Connection): def maatouch_send(self, builder: MaatouchBuilder): content = builder.to_minitouch() - # logger.info("send operation: {}".format(content.replace("\n", "\\n"))) + logger.info("send operation: {}".format(content.replace("\n", "\\n"))) byte_content = content.encode('utf-8') self._maatouch_stream.sendall(byte_content) self._maatouch_stream.recv(0) - self.sleep(self.maatouch_builder.delay / 1000 + builder.DEFAULT_DELAY) + self.sleep(builder.delay / 1000 + builder.DEFAULT_DELAY) + builder.clear() + + def maatouch_send_sync(self, builder: MaatouchBuilder, mode=2): + # Set inject mode to the last command + for command in builder.commands[::-1]: + if command.operation in ['r', 'd', 'm', 'u']: + command.mode = mode + break + + # add maatouch sync command: 's \n' + timestamp = str(int(time.time() * 1000)) + builder.commands.insert(0, Command( + 's', text=timestamp + )) + + # Send + content = builder.to_maatouch_sync() + logger.info("send operation: {}".format(content.replace("\n", "\\n"))) + byte_content = content.encode('utf-8') + self._maatouch_stream.sendall(byte_content) + self._maatouch_stream.recv(0) + + # Wait until operations finished + start = time.time() + socket_out = self._maatouch_stream.makefile() + max_trial = 3 + for n in range(3): + try: + out = socket_out.readline() + except socket.timeout as e: + raise MaaTouchSyncTimeout(str(e)) + out = out.strip() + logger.info(out) + + if out == timestamp: + break + if out == 'Killed': + raise MaaTouchNotInstalledError('MaaTouch died, probably because version incompatible') + if n == max_trial - 1: + raise MaaTouchSyncTimeout('Too many incorrect sync response') + time.sleep(0.001) + + logger.info(f'Delay: {builder.delay}') + logger.info(f'Waiting control {time.time() - start}') + self.sleep(builder.DEFAULT_DELAY) builder.clear() def maatouch_install(self): @@ -257,30 +331,31 @@ class MaaTouch(Connection): builder = self.maatouch_builder builder.down(x, y).commit() builder.up().commit() - builder.send() + builder.send_sync() @retry def long_click_maatouch(self, x, y, duration=1.0): duration = int(duration * 1000) builder = self.maatouch_builder - builder.down(x, y).commit().wait(duration) + builder.down(x, y).wait(duration).commit() builder.up().commit() - builder.send() + builder.send_sync() @retry def swipe_maatouch(self, p1, p2): points = insert_swipe(p0=p1, p3=p2) builder = self.maatouch_builder - builder.down(*points[0]).commit() - builder.send() + builder.down(*points[0]).wait(10).commit() + builder.send_sync() for point in points[1:]: - builder.move(*point).commit().wait(10) - builder.send() + builder.move(*point).wait(10) + builder.commit() + builder.send_sync() builder.up().commit() - builder.send() + builder.send_sync() @retry def drag_maatouch(self, p1, p2, point_random=(-10, -10, 10, 10)): @@ -289,16 +364,22 @@ class MaaTouch(Connection): points = insert_swipe(p0=p1, p3=p2, speed=20) builder = self.maatouch_builder - builder.down(*points[0]).commit() - builder.send() + builder.down(*points[0]).commit().wait(10) + builder.send_sync() for point in points[1:]: builder.move(*point).commit().wait(10) - builder.send() + builder.send_sync() builder.move(*p2).commit().wait(140) builder.move(*p2).commit().wait(140) - builder.send() + builder.send_sync() builder.up().commit() - builder.send() + builder.send_sync() + + @retry + def reset_maatouch(self): + builder = self.maatouch_builder + builder.reset().commit() + builder.send_sync() diff --git a/module/device/method/minitouch.py b/module/device/method/minitouch.py index 30fdcc88c..98817a3fd 100644 --- a/module/device/method/minitouch.py +++ b/module/device/method/minitouch.py @@ -100,7 +100,9 @@ class Command: x: int = 0, y: int = 0, ms: int = 10, - pressure: int = 100 + pressure: int = 100, + mode: int = 0, + text: str = '' ): """ See https://github.com/openstf/minitouch#writable-to-the-socket @@ -112,6 +114,8 @@ class Command: y: ms: pressure: + mode: + text: """ self.operation = operation self.contact = contact @@ -119,6 +123,8 @@ class Command: self.y = y self.ms = ms self.pressure = pressure + self.mode = mode + self.text = text def to_minitouch(self) -> str: """ @@ -139,6 +145,36 @@ class Command: else: return '' + def to_maatouch_sync(self): + if self.operation == 'c': + return f'{self.operation}\n' + elif self.operation == 'r': + if self.mode: + return f'{self.operation} {self.mode}\n' + else: + return f'{self.operation}\n' + elif self.operation == 'd': + if self.mode: + return f'{self.operation} {self.contact} {self.x} {self.y} {self.pressure} {self.mode}\n' + else: + return f'{self.operation} {self.contact} {self.x} {self.y} {self.pressure}\n' + elif self.operation == 'm': + if self.mode: + return f'{self.operation} {self.contact} {self.x} {self.y} {self.pressure} {self.mode}\n' + else: + return f'{self.operation} {self.contact} {self.x} {self.y} {self.pressure}\n' + elif self.operation == 'u': + if self.mode: + return f'{self.operation} {self.contact} {self.mode}\n' + else: + return f'{self.operation} {self.ms}\n' + elif self.operation == 'w': + return f'{self.operation} {self.ms}\n' + elif self.operation == 's': + return f'{self.operation} {self.text}\n' + else: + return '' + def to_atx_agent(self, max_x=1280, max_y=720) -> str: """ Dict that send to atx-agent, $DEVICE_URL/minitouch @@ -184,7 +220,12 @@ class CommandBuilder: max_x = 1280 max_y = 720 - def __init__(self, device, contact=0, handle_orientation=True): + def __init__( + self, + device, + contact=0, + handle_orientation=True, + ): """ Args: device: @@ -230,45 +271,61 @@ class CommandBuilder: def commit(self): """ add minitouch command: 'c\n' """ - self.commands.append(Command('c')) + self.commands.append(Command( + 'c' + )) return self - def reset(self): + def reset(self, mode=0): """ add minitouch command: 'r\n' """ - self.commands.append(Command('r')) + self.commands.append(Command( + 'r', mode=mode + )) return self def wait(self, ms=10): """ add minitouch command: 'w \n' """ - self.commands.append(Command('w', ms=ms)) + self.commands.append(Command( + 'w', ms=ms + )) self.delay += ms return self - def up(self): + def up(self, mode=0): """ add minitouch command: 'u \n' """ - self.commands.append(Command('u', contact=self.contact)) + self.commands.append(Command( + 'u', contact=self.contact, mode=mode + )) return self - def down(self, x, y, pressure=100): + def down(self, x, y, pressure=100, mode=0): """ add minitouch command: 'd \n' """ x, y = self.convert(x, y) - self.commands.append(Command('d', x=x, y=y, contact=self.contact, pressure=pressure)) + self.commands.append(Command( + 'd', x=x, y=y, contact=self.contact, pressure=pressure, mode=mode + )) return self - def move(self, x, y, pressure=100): + def move(self, x, y, pressure=100, mode=0): """ add minitouch command: 'm \n' """ x, y = self.convert(x, y) - self.commands.append(Command('m', x=x, y=y, contact=self.contact, pressure=pressure)) + self.commands.append(Command( + 'm', x=x, y=y, contact=self.contact, pressure=pressure, mode=mode + )) return self def clear(self): """ clear current commands """ self.commands = [] self.delay = 0 + return self def to_minitouch(self) -> str: return ''.join([command.to_minitouch() for command in self.commands]) + def to_maatouch_sync(self) -> str: + return ''.join([command.to_maatouch_sync() for command in self.commands]) + def to_atx_agent(self) -> List[str]: return [command.to_atx_agent(self.max_x, self.max_y) for command in self.commands]