Skip to content

Commit

Permalink
feat: 优化并补全 Python 绑定 (#133)
Browse files Browse the repository at this point in the history
  • Loading branch information
MistEO authored Jan 26, 2024
2 parents 2a3c74d + 8bfeee8 commit f04cb8a
Show file tree
Hide file tree
Showing 16 changed files with 975 additions and 116 deletions.
3 changes: 3 additions & 0 deletions .vscode/settings.json
Original file line number Diff line number Diff line change
Expand Up @@ -29,5 +29,8 @@
"-runtime/references",
"-runtime/string",
"-runtime/indentation_namespace"
],
"python.analysis.extraPaths": [
"./source/binding/Python"
]
}
10 changes: 5 additions & 5 deletions sample/python/__main__.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
from typing import Tuple
from typing import List, Tuple, Union
from maa.define import RectType
from maa.library import Library
from maa.resource import Resource
from maa.controller import AdbController
Expand Down Expand Up @@ -30,27 +31,26 @@ async def main():
controller = AdbController(
adb_path=device.adb_path,
address=device.address,
agent_path="share/MaaAgentBinary",
)
await controller.connect()

maa_inst = Instance()
maa_inst.bind(resource, controller)

if not maa_inst.inited():
if not maa_inst.inited:
print("Failed to init MAA.")
exit()

maa_inst.register_recognizer("MyRec", my_rec)
maa_inst.register_action("MyAct", my_act)

await maa_inst.run_task("StartUpAndClickButton", {})
await maa_inst.run_task("StartUpAndClickButton")


class MyRecognizer(CustomRecognizer):
def analyze(
self, context, image, task_name, custom_param
) -> Tuple[bool, Tuple[int, int, int, int], str]:
) -> Tuple[bool, RectType, str]:
return True, (0, 0, 100, 100), "Hello World!"


Expand Down
9 changes: 8 additions & 1 deletion source/binding/Python/maa/__init__.py
Original file line number Diff line number Diff line change
@@ -1 +1,8 @@
__all__ = ["library", "resource", "controller", "instance", "toolkit"]
__all__ = [
"library",
"resource",
"controller",
"instance",
"toolkit",
"custom_controller",
]
28 changes: 20 additions & 8 deletions source/binding/Python/maa/buffer.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,10 @@ class StringBuffer:
_handle: MaaStringBufferHandle
_own: bool

@property
def c_handle(self) -> MaaStringBufferHandle:
return self._handle

def __init__(self, c_handle: Optional[MaaStringBufferHandle] = None):
if not Library.initialized:
raise RuntimeError(
Expand Down Expand Up @@ -42,6 +46,7 @@ def set(self, value: Union[str, bytes]) -> bool:
value = value.encode()
return bool(Library.framework.MaaSetString(self._handle, value))

@property
def empty(self) -> bool:
return bool(Library.framework.MaaIsStringEmpty(self._handle))

Expand Down Expand Up @@ -89,6 +94,10 @@ class ImageBuffer:
_handle: MaaImageBufferHandle
_own: bool

@property
def c_handle(self) -> MaaImageBufferHandle:
return self._handle

def __init__(self, c_handle: Optional[MaaImageBufferHandle] = None):
if not Library.initialized:
raise RuntimeError(
Expand Down Expand Up @@ -137,6 +146,7 @@ def set(self, value: Union[numpy.ndarray, Image.Image]) -> bool:
)
)

@property
def empty(self) -> bool:
return bool(Library.framework.MaaIsImageEmpty(self._handle))

Expand Down Expand Up @@ -189,6 +199,10 @@ class RectBuffer:
_handle: MaaRectHandle
_own: bool

@property
def c_handle(self) -> MaaRectHandle:
return self._handle

def __init__(self, c_handle: Optional[MaaRectHandle] = None):
if not Library.initialized:
raise RuntimeError(
Expand All @@ -211,21 +225,17 @@ def __del__(self):
if self._handle and self._own:
Library.framework.MaaDestroyRectBuffer(self._handle)

def get(self) -> Tuple[int, int, int, int]:
def get(self) -> Rect:
x = Library.framework.MaaGetRectX(self._handle)
y = Library.framework.MaaGetRectY(self._handle)
w = Library.framework.MaaGetRectW(self._handle)
h = Library.framework.MaaGetRectH(self._handle)

return x, y, w, h
return Rect(x, y, w, h)

def set(
self,
value: Union[
numpy.ndarray,
Tuple[int, int, int, int],
List[int],
],
value: RectType,
) -> bool:
if isinstance(value, numpy.ndarray):
if value.ndim != 1:
Expand All @@ -238,8 +248,10 @@ def set(
if len(value) != 4:
raise ValueError("value must have 4 elements")
value = numpy.array(value, dtype=numpy.int32)
elif isinstance(value, Rect):
pass
else:
raise TypeError("value must be a numpy.ndarray, tuple or list")
raise TypeError("value must be a Rect, numpy.ndarray, tuple or list")

return bool(
Library.framework.MaaSetRect(
Expand Down
4 changes: 3 additions & 1 deletion source/binding/Python/maa/callback_agent.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import ctypes
import json
from typing import Callable, Any, Optional, Dict
from typing import Callable, Any, Optional

from .define import MaaApiCallback

Expand All @@ -13,9 +13,11 @@ def __init__(self, callback: Optional[Callback] = None, callback_arg: Any = None
self._callback = callback
self._callback_arg = callback_arg

@property
def c_callback(self) -> MaaApiCallback:
return self._c_callback_agent

@property
def c_callback_arg(self) -> ctypes.c_void_p:
return ctypes.c_void_p.from_buffer(ctypes.py_object(self))

Expand Down
24 changes: 9 additions & 15 deletions source/binding/Python/maa/context.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
import numpy
import json

from typing import Any, Dict, Optional, Tuple
from typing import Dict, Optional, Tuple

from .library import Library
from .define import MaaBool
Expand Down Expand Up @@ -38,16 +38,16 @@ def run_recognizer(
self,
image: numpy.ndarray,
task_name: str,
task_param: Dict,
) -> Optional[Tuple[Tuple[int, int, int, int], str]]:
task_param: Dict = {},
) -> Tuple[bool, Rect, str]:
"""
Sync context run recognizer.
:param image: image
:param task_name: task name
:param task_param: task param
:return: (x, y, width, height), detail
:return: rect, detail
"""

image_buffer = ImageBuffer()
Expand All @@ -58,26 +58,20 @@ def run_recognizer(

ret = Library.framework.MaaSyncContextRunRecognizer(
self._handle,
image_buffer.c_handle(),
image_buffer.c_handle,
task_name.encode("utf-8"),
json.dumps(task_param).encode("utf-8"),
rect_buffer.c_handle(),
detail_buffer.c_handle(),
rect_buffer.c_handle,
detail_buffer.c_handle,
)

if not ret:
return None

return (
rect_buffer.get(),
detail_buffer.get(),
)
return (ret, rect_buffer.get(), detail_buffer.get())

def run_action(
self,
task_name: str,
task_param: Dict,
cur_box: Tuple[int, int, int, int],
cur_box: RectType,
cur_rec_detail: str,
) -> Optional[str]:
"""
Expand Down
Loading

0 comments on commit f04cb8a

Please sign in to comment.