diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml
deleted file mode 100644
index f851bf6..0000000
--- a/.github/workflows/release.yml
+++ /dev/null
@@ -1,26 +0,0 @@
-name: release
-
-on:
- push:
- tags:
- - "v*"
-
- workflow_dispatch:
-
-jobs:
- meta:
- uses: ./.github/workflows/meta.yml
-
- release:
- if: ${{ needs.meta.outputs.is_release == 'true' }}
- needs: meta
- runs-on: ubuntu-latest
-
- steps:
- - name: Checkout
- uses: actions/checkout@v4
-
- - name: Release
- uses: softprops/action-gh-release@v2
- with:
- tag_name: ${{ needs.meta.outputs.tag }}
\ No newline at end of file
diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml
index 797e604..57d39a7 100644
--- a/.github/workflows/test.yml
+++ b/.github/workflows/test.yml
@@ -2,6 +2,8 @@ name: test
on:
push:
+ tags:
+ - "v*"
branches:
- "**"
@@ -9,7 +11,12 @@ on:
branches:
- "**"
+ workflow_dispatch:
+
jobs:
+ meta:
+ uses: ./.github/workflows/meta.yml
+
windows:
runs-on: windows-latest
strategy:
@@ -173,4 +180,15 @@ jobs:
if: always()
with:
name: MAA-macos-${{ matrix.arch }}-full_log
- path: "test/debug"
\ No newline at end of file
+ path: "test/debug"
+
+ release:
+ if: ${{ needs.meta.outputs.is_release == 'true' }}
+ needs: [meta, windows, ubuntu, macos]
+ runs-on: ubuntu-latest
+
+ steps:
+ - name: Release
+ uses: softprops/action-gh-release@v2
+ with:
+ tag_name: ${{ needs.meta.outputs.tag }}
\ No newline at end of file
diff --git a/.gitignore b/.gitignore
index e4d45a8..665b08e 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1,2 +1,3 @@
/.idea
-/test/debug
\ No newline at end of file
+/test/debug
+/test/config
\ No newline at end of file
diff --git a/README.md b/README.md
index 2bc0e95..93f8503 100644
--- a/README.md
+++ b/README.md
@@ -12,8 +12,8 @@
-
-
+
+
@@ -97,7 +97,7 @@ Replace `[path to maafw include directory]` with the actual path to the MaaFrame
## Examples
- [Quirk Start](#quirk-start)
-- [Custom Recognizer](#custom-recognizer)
+- [Custom Recognition](#custom-recognition)
- [Custom Action](#custom-action)
- [PI CLI](#pi-cli)
@@ -140,7 +140,7 @@ func main() {
defer res.Destroy()
res.PostPath("./resource").Wait()
tasker.BindResource(res)
- if tasker.Inited() {
+ if tasker.Initialized() {
fmt.Println("Failed to init MAA.")
os.Exit(1)
}
@@ -151,11 +151,11 @@ func main() {
```
-### Custom Recognizer
+### Custom Recognition
-See [custom-recognizer](examples/custom-recognizer) for details.
+See [custom-recognition](examples/custom-recognition) for details.
-Here is a basic example to implement your custom recognizer:
+Here is a basic example to implement your custom recognition:
```go
package main
@@ -190,12 +190,12 @@ func main() {
defer res.Destroy()
res.PostPath("./resource").Wait()
tasker.BindResource(res)
- if tasker.Inited() {
+ if tasker.Initialized() {
fmt.Println("Failed to init MAA.")
os.Exit(1)
}
- res.RegisterCustomRecognizer("MyRec", &MyRec{})
+ res.RegisterCustomRecognition("MyRec", &MyRec{})
detail := tasker.PostPipeline("Startup").Wait().GetDetail()
fmt.Println(detail)
@@ -203,7 +203,7 @@ func main() {
type MyRec struct{}
-func (r *MyRec) Run(ctx *maa.Context, arg *maa.CustomRecognizerArg) (maa.CustomRecognizerResult, bool) {
+func (r *MyRec) Run(ctx *maa.Context, arg *maa.CustomRecognitionArg) (maa.CustomRecognitionResult, bool) {
ctx.RunRecognition("MyCustomOCR", arg.Img, maa.J{
"MyCustomOCR": maa.J{
"roi": []int{100, 100, 200, 300},
@@ -229,7 +229,7 @@ func (r *MyRec) Run(ctx *maa.Context, arg *maa.CustomRecognizerArg) (maa.CustomR
ctx.OverrideNext(arg.CurrentTaskName, []string{"TaskA", "TaskB"})
- return maa.CustomRecognizerResult{
+ return maa.CustomRecognitionResult{
Box: maa.Rect{0, 0, 100, 100},
Detail: "Hello World!",
}, true
@@ -276,7 +276,7 @@ func main() {
defer res.Destroy()
res.PostPath("./resource").Wait()
tasker.BindResource(res)
- if tasker.Inited() {
+ if tasker.Initialized() {
fmt.Println("Failed to init MAA.")
os.Exit(1)
}
@@ -289,7 +289,7 @@ func main() {
type MyAct struct{}
-func (a *MyAct) Run(_ *maa.Context, arg *maa.CustomActionArg) bool {
+func (a *MyAct) Run(_ *maa.Context, _ *maa.CustomActionArg) bool {
return true
}
diff --git a/README_zh.md b/README_zh.md
index cdc4cf7..e4450ea 100644
--- a/README_zh.md
+++ b/README_zh.md
@@ -11,8 +11,8 @@
-
-
+
+
@@ -139,7 +139,7 @@ func main() {
defer res.Destroy()
res.PostPath("./resource").Wait()
tasker.BindResource(res)
- if tasker.Inited() {
+ if tasker.Initialized() {
fmt.Println("Failed to init MAA.")
os.Exit(1)
}
@@ -152,7 +152,7 @@ func main() {
### 自定义识别器
-有关详细信息,请参阅 [custom-recognizer](examples/custom-recognizer)。
+有关详细信息,请参阅 [custom-recognition](examples/custom-recognition)。
以下是一个实现自定义识别器的基本示例:
@@ -189,12 +189,12 @@ func main() {
defer res.Destroy()
res.PostPath("./resource").Wait()
tasker.BindResource(res)
- if tasker.Inited() {
+ if tasker.Initialized() {
fmt.Println("Failed to init MAA.")
os.Exit(1)
}
- res.RegisterCustomRecognizer("MyRec", &MyRec{})
+ res.RegisterCustomRecognition("MyRec", &MyRec{})
detail := tasker.PostPipeline("Startup").Wait().GetDetail()
fmt.Println(detail)
@@ -202,7 +202,7 @@ func main() {
type MyRec struct{}
-func (r *MyRec) Run(ctx *maa.Context, arg *maa.CustomRecognizerArg) (maa.CustomRecognizerResult, bool) {
+func (r *MyRec) Run(ctx *maa.Context, arg *maa.CustomRecognitionArg) (maa.CustomRecognitionResult, bool) {
ctx.RunRecognition("MyCustomOCR", arg.Img, maa.J{
"MyCustomOCR": maa.J{
"roi": []int{100, 100, 200, 300},
@@ -228,7 +228,7 @@ func (r *MyRec) Run(ctx *maa.Context, arg *maa.CustomRecognizerArg) (maa.CustomR
ctx.OverrideNext(arg.CurrentTaskName, []string{"TaskA", "TaskB"})
- return maa.CustomRecognizerResult{
+ return maa.CustomRecognitionResult{
Box: maa.Rect{0, 0, 100, 100},
Detail: "Hello World!",
}, true
@@ -275,7 +275,7 @@ func main() {
defer res.Destroy()
res.PostPath("./resource").Wait()
tasker.BindResource(res)
- if tasker.Inited() {
+ if tasker.Initialized() {
fmt.Println("Failed to init MAA.")
os.Exit(1)
}
@@ -288,7 +288,7 @@ func main() {
type MyAct struct{}
-func (a *MyAct) Run(_ *maa.Context, arg *maa.CustomActionArg) bool {
+func (a *MyAct) Run(_ *maa.Context, _ *maa.CustomActionArg) bool {
return true
}
diff --git a/context.go b/context.go
index 8a123b4..97007b5 100644
--- a/context.go
+++ b/context.go
@@ -54,7 +54,7 @@ func (ctx *Context) runRecognition(entry, override string, img image.Image) *Rec
cOverride := C.CString(override)
defer C.free(unsafe.Pointer(cOverride))
imgBuf := buffer.NewImageBuffer()
- imgBuf.SetRawData(img)
+ imgBuf.Set(img)
defer imgBuf.Destroy()
recId := int64(C.MaaContextRunRecognition(ctx.handle, cEntry, cOverride, (*C.MaaImageBuffer)(imgBuf.Handle())))
diff --git a/context_test.go b/context_test.go
index aa97f94..2664b85 100644
--- a/context_test.go
+++ b/context_test.go
@@ -21,15 +21,15 @@ func (t *testContextRunPipelineAct) Run(ctx *Context, _ *CustomActionArg) bool {
}
func TestContext_RunPipeline(t *testing.T) {
- ctrl := createDbgController(t)
+ ctrl := createDbgController(t, nil)
defer ctrl.Destroy()
isConnected := ctrl.PostConnect().Wait().Success()
require.True(t, isConnected)
- res := createResource(t)
+ res := createResource(t, nil)
defer res.Destroy()
- tasker := createTasker(t)
+ tasker := createTasker(t, nil)
defer tasker.Destroy()
taskerBind(t, tasker, ctrl, res)
@@ -63,15 +63,15 @@ func (t *testContextRunRecognitionAct) Run(ctx *Context, _ *CustomActionArg) boo
}
func TestContext_RunRecognition(t *testing.T) {
- ctrl := createDbgController(t)
+ ctrl := createDbgController(t, nil)
defer ctrl.Destroy()
isConnected := ctrl.PostConnect().Wait().Success()
require.True(t, isConnected)
- res := createResource(t)
+ res := createResource(t, nil)
defer res.Destroy()
- tasker := createTasker(t)
+ tasker := createTasker(t, nil)
defer tasker.Destroy()
taskerBind(t, tasker, ctrl, res)
@@ -103,15 +103,15 @@ func (a testContextRunActionAct) Run(ctx *Context, arg *CustomActionArg) bool {
}
func TestContext_RunAction(t *testing.T) {
- ctrl := createDbgController(t)
+ ctrl := createDbgController(t, nil)
defer ctrl.Destroy()
isConnected := ctrl.PostConnect().Wait().Success()
require.True(t, isConnected)
- res := createResource(t)
+ res := createResource(t, nil)
defer res.Destroy()
- tasker := createTasker(t)
+ tasker := createTasker(t, nil)
defer tasker.Destroy()
taskerBind(t, tasker, ctrl, res)
@@ -153,15 +153,15 @@ func (t *testContextOverriderPipelineAct) Run(ctx *Context, _ *CustomActionArg)
}
func TestContext_OverridePipeline(t *testing.T) {
- ctrl := createDbgController(t)
+ ctrl := createDbgController(t, nil)
defer ctrl.Destroy()
isConnected := ctrl.PostConnect().Wait().Success()
require.True(t, isConnected)
- res := createResource(t)
+ res := createResource(t, nil)
defer res.Destroy()
- tasker := createTasker(t)
+ tasker := createTasker(t, nil)
defer tasker.Destroy()
taskerBind(t, tasker, ctrl, res)
@@ -200,15 +200,15 @@ func (t *testContextOverrideNextAct) Run(ctx *Context, _ *CustomActionArg) bool
}
func TestContext_OverrideNext(t *testing.T) {
- ctrl := createDbgController(t)
+ ctrl := createDbgController(t, nil)
defer ctrl.Destroy()
isConnected := ctrl.PostConnect().Wait().Success()
require.True(t, isConnected)
- res := createResource(t)
+ res := createResource(t, nil)
defer res.Destroy()
- tasker := createTasker(t)
+ tasker := createTasker(t, nil)
defer tasker.Destroy()
taskerBind(t, tasker, ctrl, res)
@@ -235,15 +235,15 @@ func (t *testContextGetTaskJobAct) Run(ctx *Context, _ *CustomActionArg) bool {
}
func TestContext_GetTaskJob(t *testing.T) {
- ctrl := createDbgController(t)
+ ctrl := createDbgController(t, nil)
defer ctrl.Destroy()
isConnected := ctrl.PostConnect().Wait().Success()
require.True(t, isConnected)
- res := createResource(t)
+ res := createResource(t, nil)
defer res.Destroy()
- tasker := createTasker(t)
+ tasker := createTasker(t, nil)
defer tasker.Destroy()
taskerBind(t, tasker, ctrl, res)
@@ -270,15 +270,15 @@ func (t testContextGetTaskerAct) Run(ctx *Context, _ *CustomActionArg) bool {
}
func TestContext_GetTasker(t *testing.T) {
- ctrl := createDbgController(t)
+ ctrl := createDbgController(t, nil)
defer ctrl.Destroy()
isConnected := ctrl.PostConnect().Wait().Success()
require.True(t, isConnected)
- res := createResource(t)
+ res := createResource(t, nil)
defer res.Destroy()
- tasker := createTasker(t)
+ tasker := createTasker(t, nil)
defer tasker.Destroy()
taskerBind(t, tasker, ctrl, res)
@@ -303,15 +303,15 @@ func (t testContextCloneAct) Run(ctx *Context, _ *CustomActionArg) bool {
}
func TestContext_Clone(t *testing.T) {
- ctrl := createDbgController(t)
+ ctrl := createDbgController(t, nil)
defer ctrl.Destroy()
isConnected := ctrl.PostConnect().Wait().Success()
require.True(t, isConnected)
- res := createResource(t)
+ res := createResource(t, nil)
defer res.Destroy()
- tasker := createTasker(t)
+ tasker := createTasker(t, nil)
defer tasker.Destroy()
taskerBind(t, tasker, ctrl, res)
diff --git a/controller.go b/controller.go
index 7e4752d..c1a3cfe 100644
--- a/controller.go
+++ b/controller.go
@@ -9,9 +9,9 @@ extern void _MaaNotificationCallbackAgent(const char* message, const char* detai
import "C"
import (
"github.com/MaaXYZ/maa-framework-go/internal/buffer"
- "github.com/MaaXYZ/maa-framework-go/internal/notification"
"github.com/MaaXYZ/maa-framework-go/internal/store"
"image"
+ "time"
"unsafe"
)
@@ -26,7 +26,7 @@ type Controller interface {
PostConnect() *Job
PostClick(x, y int32) *Job
- PostSwipe(x1, y1, x2, y2, duration int32) *Job
+ PostSwipe(x1, y1, x2, y2 int32, duration time.Duration) *Job
PostPressKey(keycode int32) *Job
PostInputText(text string) *Job
PostStartApp(intent string) *Job
@@ -99,7 +99,7 @@ func NewAdbController(
screencapMethod AdbScreencapMethod,
inputMethod AdbInputMethod,
config, agentPath string,
- callback func(msg, detailsJson string),
+ notify Notification,
) Controller {
cAdbPath := C.CString(adbPath)
cAddress := C.CString(address)
@@ -112,7 +112,7 @@ func NewAdbController(
C.free(unsafe.Pointer(cAgentPath))
}()
- id := notification.RegisterCallback(callback)
+ id := registerNotificationCallback(notify)
handle := C.MaaAdbControllerCreate(
cAdbPath,
cAddress,
@@ -164,9 +164,9 @@ func NewWin32Controller(
hWnd unsafe.Pointer,
screencapMethod Win32ScreencapMethod,
inputMethod Win32InputMethod,
- callback func(msg, detailsJson string),
+ notify Notification,
) Controller {
- id := notification.RegisterCallback(callback)
+ id := registerNotificationCallback(notify)
handle := C.MaaWin32ControllerCreate(
hWnd,
C.uint64_t(screencapMethod),
@@ -202,7 +202,7 @@ func NewDbgController(
readPath, writePath string,
dbgCtrlType DbgControllerType,
config string,
- callback func(msg, detailsJson string),
+ notify Notification,
) Controller {
cReadPath := C.CString(readPath)
cWritePath := C.CString(writePath)
@@ -213,7 +213,7 @@ func NewDbgController(
C.free(unsafe.Pointer(cConfig))
}()
- id := notification.RegisterCallback(callback)
+ id := registerNotificationCallback(notify)
handle := C.MaaDbgControllerCreate(
cReadPath,
cWritePath,
@@ -236,10 +236,10 @@ func NewDbgController(
// NewCustomController creates a custom controller instance.
func NewCustomController(
ctrl CustomController,
- callback func(msg, detailsJson string),
+ notify Notification,
) Controller {
ctrlID := registerCustomControllerCallbacks(ctrl)
- cbID := notification.RegisterCallback(callback)
+ notifyID := registerNotificationCallback(notify)
handle := C.MaaCustomControllerCreate(
(*C.MaaCustomControllerCallbacks)(ctrl.Handle()),
// Here, we are simply passing the uint64 value as a pointer
@@ -248,13 +248,13 @@ func NewCustomController(
C.MaaNotificationCallback(C._MaaNotificationCallbackAgent),
// Here, we are simply passing the uint64 value as a pointer
// and will not actually dereference this pointer.
- unsafe.Pointer(uintptr(cbID)),
+ unsafe.Pointer(uintptr(notifyID)),
)
if handle == nil {
return nil
}
controllerStore.Set(unsafe.Pointer(handle), controllerStoreValue{
- NotificationCallbackID: cbID,
+ NotificationCallbackID: notifyID,
CustomControllerCallbacksID: ctrlID,
})
return &controller{handle: handle}
@@ -263,7 +263,7 @@ func NewCustomController(
// Destroy frees the controller instance.
func (c *controller) Destroy() {
value := controllerStore.Get(c.Handle())
- notification.UnregisterCallback(value.NotificationCallbackID)
+ unregisterNotificationCallback(value.NotificationCallbackID)
unregisterCustomControllerCallbacks(value.CustomControllerCallbacksID)
controllerStore.Del(c.Handle())
C.MaaControllerDestroy(c.handle)
@@ -353,8 +353,15 @@ func (c *controller) PostClick(x, y int32) *Job {
}
// PostSwipe posts a swipe.
-func (c *controller) PostSwipe(x1, y1, x2, y2, duration int32) *Job {
- id := int64(C.MaaControllerPostSwipe(c.handle, C.int32_t(x1), C.int32_t(y1), C.int32_t(x2), C.int32_t(y2), C.int32_t(duration)))
+func (c *controller) PostSwipe(x1, y1, x2, y2 int32, duration time.Duration) *Job {
+ id := int64(C.MaaControllerPostSwipe(
+ c.handle,
+ C.int32_t(x1),
+ C.int32_t(y1),
+ C.int32_t(x2),
+ C.int32_t(y2),
+ C.int32_t(duration.Milliseconds()),
+ ))
return NewJob(id, c.status, c.wait)
}
@@ -439,7 +446,7 @@ func (c *controller) CacheImage() image.Image {
return nil
}
- img := imgBuffer.GetByRawData()
+ img := imgBuffer.Get()
return img
}
diff --git a/controller_test.go b/controller_test.go
index 49de9db..44d05ca 100644
--- a/controller_test.go
+++ b/controller_test.go
@@ -3,13 +3,180 @@ package maa
import (
"github.com/stretchr/testify/require"
"testing"
+ "time"
)
-func createDbgController(t *testing.T) Controller {
+func createDbgController(t *testing.T, notify Notification) Controller {
testingPath := "./test/data_set/PipelineSmoking/Screenshot"
resultPath := "./test/data_set/debug"
- ctrl := NewDbgController(testingPath, resultPath, DbgControllerTypeCarouselImage, "{}", nil)
+ ctrl := NewDbgController(testingPath, resultPath, DbgControllerTypeCarouselImage, "{}", notify)
require.NotNil(t, ctrl)
return ctrl
}
+
+func TestNewDbgController(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ ctrl.Destroy()
+}
+
+func TestController_Handle(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ handle := ctrl.Handle()
+ require.NotNil(t, handle)
+}
+
+func TestController_SetScreenshotTargetLongSide(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ got := ctrl.SetScreenshotTargetLongSide(1280)
+ require.True(t, got)
+}
+
+func TestController_SetScreenshotTargetShortSide(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ got := ctrl.SetScreenshotTargetShortSide(720)
+ require.True(t, got)
+}
+
+func TestController_SetRecording(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ got := ctrl.SetRecording(true)
+ require.True(t, got)
+}
+
+func TestController_PostConnect(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+}
+
+func TestController_Connected(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+ connected := ctrl.Connected()
+ require.True(t, connected)
+}
+
+func TestController_PostClick(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+ clicked := ctrl.PostClick(100, 200).Wait().Success()
+ require.True(t, clicked)
+}
+
+func TestController_PostSwipe(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+ swiped := ctrl.PostSwipe(100, 200, 400, 300, 2*time.Second).Wait().Success()
+ require.True(t, swiped)
+}
+
+func TestController_PostPressKey(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+ pressed := ctrl.PostPressKey(4).Wait().Success()
+ require.True(t, pressed)
+}
+
+func TestController_PostInputText(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+ inputted := ctrl.PostInputText("Hello World").Wait().Success()
+ require.True(t, inputted)
+}
+
+func TestController_PostStartApp(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+ started := ctrl.PostStartApp("com.android.settings").Wait().Success()
+ require.True(t, started)
+}
+
+func TestController_PostStopApp(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+ stopped := ctrl.PostStopApp("com.android.settings").Wait().Success()
+ require.True(t, stopped)
+}
+
+func TestController_PostTouchDown(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+ downed := ctrl.PostTouchDown(0, 100, 200, 1000).Wait().Success()
+ require.True(t, downed)
+}
+
+func TestController_PostTouchMove(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+ downed := ctrl.PostTouchDown(0, 100, 200, 1000).Wait().Success()
+ require.True(t, downed)
+ moved := ctrl.PostTouchMove(0, 200, 300, 1000).Wait().Success()
+ require.True(t, moved)
+}
+
+func TestController_PostTouchUp(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+ downed := ctrl.PostTouchDown(0, 100, 200, 1000).Wait().Success()
+ require.True(t, downed)
+ moved := ctrl.PostTouchMove(0, 200, 300, 1000).Wait().Success()
+ require.True(t, moved)
+ upped := ctrl.PostTouchUp(0).Wait().Success()
+ require.True(t, upped)
+}
+
+func TestController_PostScreencap(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+ screencaped := ctrl.PostScreencap().Wait().Success()
+ require.True(t, screencaped)
+}
+
+func TestController_CacheImage(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+ screencaped := ctrl.PostScreencap().Wait().Success()
+ require.True(t, screencaped)
+ img := ctrl.CacheImage()
+ require.NotNil(t, img)
+}
+
+func TestController_GetUUID(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+ uuid, oK := ctrl.GetUUID()
+ require.True(t, oK)
+ require.NotEmpty(t, uuid)
+}
diff --git a/custom_controller.go b/custom_controller.go
index 56bc030..e162614 100644
--- a/custom_controller.go
+++ b/custom_controller.go
@@ -176,7 +176,7 @@ func _ScreencapAgent(handleArg unsafe.Pointer, imgBuffer *C.MaaImageBuffer) C.ui
img, captured := ctrl.Screencap()
if captured {
imgImgBuffer := buffer.NewImageBufferByHandle(unsafe.Pointer(imgBuffer))
- if ok := imgImgBuffer.SetRawData(img); ok {
+ if ok := imgImgBuffer.Set(img); ok {
return C.uint8_t(1)
}
}
diff --git a/custom_recognizer.go b/custom_recognition.go
similarity index 70%
rename from custom_recognizer.go
rename to custom_recognition.go
index 24a3b55..710a22e 100644
--- a/custom_recognizer.go
+++ b/custom_recognition.go
@@ -5,7 +5,7 @@ package maa
#include
#include "def.h"
-extern uint8_t _MaaCustomRecognizerCallbackAgent(
+extern uint8_t _MaaCustomRecognitionCallbackAgent(
MaaContext* ctx,
int64_t task_id,
const char* current_task_name,
@@ -26,25 +26,25 @@ import (
)
var (
- customRecognizerCallbackID uint64
- customRecognizerCallbackAgents = make(map[uint64]CustomRecognizer)
+ customRecognitionCallbackID uint64
+ customRecognitionCallbackAgents = make(map[uint64]CustomRecognition)
)
-func registerCustomRecognizer(recognizer CustomRecognizer) uint64 {
- id := atomic.AddUint64(&customRecognizerCallbackID, 1)
- customRecognizerCallbackAgents[id] = recognizer
+func registerCustomRecognition(recognizer CustomRecognition) uint64 {
+ id := atomic.AddUint64(&customRecognitionCallbackID, 1)
+ customRecognitionCallbackAgents[id] = recognizer
return id
}
-func unregisterCustomRecognizer(id uint64) bool {
- if _, ok := customRecognizerCallbackAgents[id]; !ok {
+func unregisterCustomRecognition(id uint64) bool {
+ if _, ok := customRecognitionCallbackAgents[id]; !ok {
return false
}
- delete(customRecognizerCallbackAgents, id)
+ delete(customRecognitionCallbackAgents, id)
return true
}
-type CustomRecognizerArg struct {
+type CustomRecognitionArg struct {
TaskDetail *TaskDetail
CurrentTaskName string
CustomRecognizerName string
@@ -53,17 +53,17 @@ type CustomRecognizerArg struct {
Roi Rect
}
-type CustomRecognizer interface {
- Run(ctx *Context, arg *CustomRecognizerArg) (CustomRecognizerResult, bool)
+type CustomRecognition interface {
+ Run(ctx *Context, arg *CustomRecognitionArg) (CustomRecognitionResult, bool)
}
-type CustomRecognizerResult struct {
+type CustomRecognitionResult struct {
Box Rect
Detail string
}
-//export _MaaCustomRecognizerCallbackAgent
-func _MaaCustomRecognizerCallbackAgent(
+//export _MaaCustomRecognitionCallbackAgent
+func _MaaCustomRecognitionCallbackAgent(
ctx *C.MaaContext,
taskId C.int64_t,
currentTaskName, customRecognizerName, customRecognitionParam C.StringView,
@@ -76,16 +76,16 @@ func _MaaCustomRecognizerCallbackAgent(
// Here, we are simply passing the uint64 value as a pointer
// and will not actually dereference this pointer.
id := uint64(uintptr(recognizerArg))
- recognizer := customRecognizerCallbackAgents[id]
+ recognizer := customRecognitionCallbackAgents[id]
context := Context{handle: ctx}
tasker := context.GetTasker()
taskDetail := tasker.getTaskDetail(int64(taskId))
imgBuffer := buffer.NewImageBufferByHandle(unsafe.Pointer(img))
- imgImg := imgBuffer.GetByRawData()
+ imgImg := imgBuffer.Get()
ret, ok := recognizer.Run(
&Context{handle: ctx},
- &CustomRecognizerArg{
+ &CustomRecognitionArg{
TaskDetail: taskDetail,
CurrentTaskName: C.GoString(currentTaskName),
CustomRecognizerName: C.GoString(customRecognizerName),
diff --git a/examples/custom-action/main.go b/examples/custom-action/main.go
index 301eabb..ebfec11 100644
--- a/examples/custom-action/main.go
+++ b/examples/custom-action/main.go
@@ -30,7 +30,7 @@ func main() {
defer res.Destroy()
res.PostPath("./resource").Wait()
tasker.BindResource(res)
- if tasker.Inited() {
+ if tasker.Initialized() {
fmt.Println("Failed to init MAA.")
os.Exit(1)
}
@@ -43,6 +43,6 @@ func main() {
type MyAct struct{}
-func (a *MyAct) Run(_ *maa.Context, arg *maa.CustomActionArg) bool {
+func (a *MyAct) Run(_ *maa.Context, _ *maa.CustomActionArg) bool {
return true
}
diff --git a/examples/custom-recognizer/main.go b/examples/custom-recognition/main.go
similarity index 86%
rename from examples/custom-recognizer/main.go
rename to examples/custom-recognition/main.go
index e6989dd..637763a 100644
--- a/examples/custom-recognizer/main.go
+++ b/examples/custom-recognition/main.go
@@ -30,12 +30,12 @@ func main() {
defer res.Destroy()
res.PostPath("./resource").Wait()
tasker.BindResource(res)
- if tasker.Inited() {
+ if tasker.Initialized() {
fmt.Println("Failed to init MAA.")
os.Exit(1)
}
- res.RegisterCustomRecognizer("MyRec", &MyRec{})
+ res.RegisterCustomRecognition("MyRec", &MyRec{})
detail := tasker.PostPipeline("Startup").Wait().GetDetail()
fmt.Println(detail)
@@ -43,7 +43,7 @@ func main() {
type MyRec struct{}
-func (r *MyRec) Run(ctx *maa.Context, arg *maa.CustomRecognizerArg) (maa.CustomRecognizerResult, bool) {
+func (r *MyRec) Run(ctx *maa.Context, arg *maa.CustomRecognitionArg) (maa.CustomRecognitionResult, bool) {
ctx.RunRecognition("MyCustomOCR", arg.Img, maa.J{
"MyCustomOCR": maa.J{
"roi": []int{100, 100, 200, 300},
@@ -69,7 +69,7 @@ func (r *MyRec) Run(ctx *maa.Context, arg *maa.CustomRecognizerArg) (maa.CustomR
ctx.OverrideNext(arg.CurrentTaskName, []string{"TaskA", "TaskB"})
- return maa.CustomRecognizerResult{
+ return maa.CustomRecognitionResult{
Box: maa.Rect{0, 0, 100, 100},
Detail: "Hello World!",
}, true
diff --git a/examples/custom-recognizer/resource/image/.gitkeep b/examples/custom-recognition/resource/image/.gitkeep
similarity index 100%
rename from examples/custom-recognizer/resource/image/.gitkeep
rename to examples/custom-recognition/resource/image/.gitkeep
diff --git a/examples/custom-recognizer/resource/model/ocr/.gitkeep b/examples/custom-recognition/resource/model/ocr/.gitkeep
similarity index 100%
rename from examples/custom-recognizer/resource/model/ocr/.gitkeep
rename to examples/custom-recognition/resource/model/ocr/.gitkeep
diff --git a/examples/custom-recognizer/resource/pipeline/pipeline.json b/examples/custom-recognition/resource/pipeline/pipeline.json
similarity index 100%
rename from examples/custom-recognizer/resource/pipeline/pipeline.json
rename to examples/custom-recognition/resource/pipeline/pipeline.json
diff --git a/examples/quick-start/main.go b/examples/quick-start/main.go
index 11d751d..4296bff 100644
--- a/examples/quick-start/main.go
+++ b/examples/quick-start/main.go
@@ -30,7 +30,7 @@ func main() {
defer res.Destroy()
res.PostPath("./resource").Wait()
tasker.BindResource(res)
- if tasker.Inited() {
+ if tasker.Initialized() {
fmt.Println("Failed to init MAA.")
os.Exit(1)
}
diff --git a/internal/buffer/image_buffer.go b/internal/buffer/image_buffer.go
index fd382f2..7ed6917 100644
--- a/internal/buffer/image_buffer.go
+++ b/internal/buffer/image_buffer.go
@@ -6,12 +6,9 @@ package buffer
*/
import "C"
import (
- "bytes"
- "errors"
"image"
"image/color"
"image/draw"
- "image/png"
"unsafe"
)
@@ -21,6 +18,9 @@ type ImageBuffer struct {
func NewImageBuffer() *ImageBuffer {
handle := C.MaaImageBufferCreate()
+ if handle == nil {
+ return nil
+ }
return &ImageBuffer{
handle: handle,
}
@@ -48,8 +48,8 @@ func (i *ImageBuffer) Clear() bool {
return C.MaaImageBufferClear(i.handle) != 0
}
-// GetByRawData retrieves the image from raw data stored in the buffer.
-func (i *ImageBuffer) GetByRawData() image.Image {
+// Get retrieves the image from raw data stored in the buffer.
+func (i *ImageBuffer) Get() image.Image {
rawData := i.getRawData()
if rawData == nil {
return nil
@@ -71,8 +71,8 @@ func (i *ImageBuffer) GetByRawData() image.Image {
return img
}
-// SetRawData converts an image.Image to raw data and sets it in the buffer.
-func (i *ImageBuffer) SetRawData(img image.Image) bool {
+// Set converts an image.Image to raw data and sets it in the buffer.
+func (i *ImageBuffer) Set(img image.Image) bool {
width := img.Bounds().Dx()
height := img.Bounds().Dy()
imageType := int32(16) // CV_8UC3
@@ -139,64 +139,3 @@ func (i *ImageBuffer) setRawData(data unsafe.Pointer, width, height, imageType i
C.int32_t(imageType),
) != 0
}
-
-// GetByEncoded retrieves the decoded image from the buffer.
-// It returns the decoded image and an error if the operation was unsuccessful.
-func (i *ImageBuffer) GetByEncoded() (image.Image, error) {
- encodedData := i.getEncoded()
- if encodedData == nil {
- return nil, errors.New("failed to get encoded image data")
- }
- dataSize := i.getEncodedSize()
- if dataSize == 0 {
- return nil, errors.New("encoded image size is zero")
- }
-
- data := C.GoBytes(encodedData, C.int32_t(dataSize))
- img, err := png.Decode(bytes.NewReader(data))
- if err != nil {
- return nil, err
- }
- return img, nil
-}
-
-// SetEncoded encodes the given image and sets it in the buffer.
-// It takes an image.Image as input and returns an error if the operation was unsuccessful.
-func (i *ImageBuffer) SetEncoded(img image.Image) error {
- var buf bytes.Buffer
- if err := png.Encode(&buf, img); err != nil {
- return err
- }
-
- data := buf.Bytes()
- cData := C.CBytes(data)
- defer C.free(cData)
-
- if !i.setEncoded(cData, uint64(len(data))) {
- return errors.New("failed to set encoded image data")
- }
- return nil
-}
-
-// getEncoded retrieves the encoded image data from the buffer.
-// It returns a pointer to the encoded image data.
-func (i *ImageBuffer) getEncoded() unsafe.Pointer {
- return unsafe.Pointer(C.MaaImageBufferGetEncoded(i.handle))
-}
-
-// getEncodedSize retrieves the size of the encoded image data in the buffer.
-// It returns the size of the encoded image data as an integer.
-func (i *ImageBuffer) getEncodedSize() int32 {
- return int32(C.MaaImageBufferGetEncodedSize(i.handle))
-}
-
-// setEncoded sets the encoded image data in the buffer.
-// It takes a pointer to the encoded image data and the size of the data.
-// It returns true if the operation was successful, otherwise false.
-func (i *ImageBuffer) setEncoded(data unsafe.Pointer, size uint64) bool {
- return C.MaaImageBufferSetEncoded(
- i.handle,
- C.MaaImageEncodedData(data),
- C.uint64_t(size),
- ) != 0
-}
diff --git a/internal/buffer/image_buffer_test.go b/internal/buffer/image_buffer_test.go
new file mode 100644
index 0000000..b758def
--- /dev/null
+++ b/internal/buffer/image_buffer_test.go
@@ -0,0 +1,59 @@
+package buffer
+
+import (
+ "github.com/stretchr/testify/require"
+ "image"
+ "image/color"
+ "testing"
+)
+
+func createImageBuffer(t *testing.T) *ImageBuffer {
+ imageBuffer := NewImageBuffer()
+ require.NotNil(t, imageBuffer)
+ return imageBuffer
+}
+
+func TestNewImageBuffer(t *testing.T) {
+ imageBuffer := createImageBuffer(t)
+ imageBuffer.Destroy()
+}
+
+func TestImageBuffer_Handle(t *testing.T) {
+ imageBuffer := createImageBuffer(t)
+ defer imageBuffer.Destroy()
+ handle := imageBuffer.Handle()
+ require.NotNil(t, handle)
+}
+
+func TestImageBuffer_IsEmpty(t *testing.T) {
+ imageBuffer := createImageBuffer(t)
+ defer imageBuffer.Destroy()
+ got := imageBuffer.IsEmpty()
+ require.True(t, got)
+}
+
+func TestImageBuffer_Clear(t *testing.T) {
+ imageBuffer := createImageBuffer(t)
+ defer imageBuffer.Destroy()
+ got := imageBuffer.Clear()
+ require.True(t, got)
+}
+
+func TestImageBuffer_Set(t *testing.T) {
+ imageBuffer := createImageBuffer(t)
+ defer imageBuffer.Destroy()
+
+ width, height := 2, 2
+ img1 := image.NewNRGBA(image.Rect(0, 0, width, height))
+ img1.SetNRGBA(0, 0, color.NRGBA{R: 255, G: 0, B: 0, A: 255})
+ img1.SetNRGBA(1, 0, color.NRGBA{R: 0, G: 255, B: 0, A: 255})
+ img1.SetNRGBA(0, 1, color.NRGBA{R: 0, G: 0, B: 255, A: 255})
+ img1.SetNRGBA(1, 1, color.NRGBA{R: 255, G: 255, B: 255, A: 255})
+
+ got := imageBuffer.Set(img1)
+ require.True(t, got)
+
+ img2 := imageBuffer.Get()
+ require.NotNil(t, img2)
+ require.Equal(t, img1, img2)
+}
diff --git a/internal/buffer/image_list_buffer.go b/internal/buffer/image_list_buffer.go
index 4eb2a62..95c6fea 100644
--- a/internal/buffer/image_list_buffer.go
+++ b/internal/buffer/image_list_buffer.go
@@ -16,6 +16,9 @@ type ImageListBuffer struct {
func NewImageListBuffer() *ImageListBuffer {
handle := C.MaaImageListBufferCreate()
+ if handle == nil {
+ return nil
+ }
return &ImageListBuffer{
handle: handle,
}
@@ -52,7 +55,7 @@ func (il *ImageListBuffer) Get(index uint64) image.Image {
img := &ImageBuffer{
handle: handle,
}
- return img.GetByRawData()
+ return img.Get()
}
func (il *ImageListBuffer) GetAll() []image.Image {
@@ -65,7 +68,7 @@ func (il *ImageListBuffer) GetAll() []image.Image {
return images
}
-func (il *ImageListBuffer) Append(value ImageBuffer) bool {
+func (il *ImageListBuffer) Append(value *ImageBuffer) bool {
return C.MaaImageListBufferAppend(
il.handle,
(*C.MaaImageBuffer)(value.Handle()),
diff --git a/internal/buffer/image_list_buffer_test.go b/internal/buffer/image_list_buffer_test.go
new file mode 100644
index 0000000..580ab8a
--- /dev/null
+++ b/internal/buffer/image_list_buffer_test.go
@@ -0,0 +1,143 @@
+package buffer
+
+import (
+ "github.com/stretchr/testify/require"
+ "image"
+ "image/color"
+ "testing"
+)
+
+func createImageListBuffer(t *testing.T) *ImageListBuffer {
+ imageListBuffer := NewImageListBuffer()
+ require.NotNil(t, imageListBuffer)
+ return imageListBuffer
+}
+
+func TestNewImageListBuffer(t *testing.T) {
+ imageListBuffer := createImageListBuffer(t)
+ imageListBuffer.Destroy()
+}
+
+func TestImageListBuffer_Handle(t *testing.T) {
+ imageListBuffer := createImageListBuffer(t)
+ defer imageListBuffer.Destroy()
+ handle := imageListBuffer.Handle()
+ require.NotNil(t, handle)
+}
+
+func TestImageListBuffer_IsEmpty(t *testing.T) {
+ imageListBuffer := createImageListBuffer(t)
+ defer imageListBuffer.Destroy()
+ got := imageListBuffer.IsEmpty()
+ require.True(t, got)
+}
+
+func TestImageListBuffer_Clear(t *testing.T) {
+ imageListBuffer := createImageListBuffer(t)
+ defer imageListBuffer.Destroy()
+ got := imageListBuffer.Clear()
+ require.True(t, got)
+}
+
+func TestImageListBuffer_Append(t *testing.T) {
+ imageListBuffer := createImageListBuffer(t)
+ defer imageListBuffer.Destroy()
+
+ imageBuffer := createImageBuffer(t)
+ defer imageBuffer.Destroy()
+
+ width, height := 2, 2
+ img1 := image.NewNRGBA(image.Rect(0, 0, width, height))
+ img1.SetNRGBA(0, 0, color.NRGBA{R: 255, G: 0, B: 0, A: 255})
+ img1.SetNRGBA(1, 0, color.NRGBA{R: 0, G: 255, B: 0, A: 255})
+ img1.SetNRGBA(0, 1, color.NRGBA{R: 0, G: 0, B: 255, A: 255})
+ img1.SetNRGBA(1, 1, color.NRGBA{R: 255, G: 255, B: 255, A: 255})
+
+ got := imageBuffer.Set(img1)
+ require.True(t, got)
+
+ appended := imageListBuffer.Append(imageBuffer)
+ require.True(t, appended)
+
+ got2 := imageListBuffer.IsEmpty()
+ require.False(t, got2)
+
+ img2 := imageListBuffer.Get(0)
+ require.NotNil(t, img2)
+ require.Equal(t, img1, img2)
+}
+
+func TestImageListBuffer_Remove(t *testing.T) {
+ imageListBuffer := createImageListBuffer(t)
+ defer imageListBuffer.Destroy()
+
+ imageBuffer := createImageBuffer(t)
+ defer imageBuffer.Destroy()
+
+ width, height := 2, 2
+ img := image.NewNRGBA(image.Rect(0, 0, width, height))
+ img.SetNRGBA(0, 0, color.NRGBA{R: 255, G: 0, B: 0, A: 255})
+ img.SetNRGBA(1, 0, color.NRGBA{R: 0, G: 255, B: 0, A: 255})
+ img.SetNRGBA(0, 1, color.NRGBA{R: 0, G: 0, B: 255, A: 255})
+ img.SetNRGBA(1, 1, color.NRGBA{R: 255, G: 255, B: 255, A: 255})
+
+ got := imageBuffer.Set(img)
+ require.True(t, got)
+
+ appended := imageListBuffer.Append(imageBuffer)
+ require.True(t, appended)
+
+ removed := imageListBuffer.Remove(0)
+ require.True(t, removed)
+
+ got2 := imageListBuffer.IsEmpty()
+ require.True(t, got2)
+}
+
+func TestImageListBuffer_Size(t *testing.T) {
+ imageListBuffer := createImageListBuffer(t)
+ defer imageListBuffer.Destroy()
+
+ imageBuffer := createImageBuffer(t)
+ defer imageBuffer.Destroy()
+
+ width, height := 2, 2
+ img1 := image.NewNRGBA(image.Rect(0, 0, width, height))
+ img1.SetNRGBA(0, 0, color.NRGBA{R: 255, G: 0, B: 0, A: 255})
+ img1.SetNRGBA(1, 0, color.NRGBA{R: 0, G: 255, B: 0, A: 255})
+ img1.SetNRGBA(0, 1, color.NRGBA{R: 0, G: 0, B: 255, A: 255})
+ img1.SetNRGBA(1, 1, color.NRGBA{R: 255, G: 255, B: 255, A: 255})
+
+ got := imageBuffer.Set(img1)
+ require.True(t, got)
+
+ appended := imageListBuffer.Append(imageBuffer)
+ require.True(t, appended)
+
+ size := imageListBuffer.Size()
+ require.Equal(t, uint64(1), size)
+}
+
+func TestImageListBuffer_GetAll(t *testing.T) {
+ imageListBuffer := createImageListBuffer(t)
+ defer imageListBuffer.Destroy()
+
+ imageBuffer := createImageBuffer(t)
+ defer imageBuffer.Destroy()
+
+ width, height := 2, 2
+ img1 := image.NewNRGBA(image.Rect(0, 0, width, height))
+ img1.SetNRGBA(0, 0, color.NRGBA{R: 255, G: 0, B: 0, A: 255})
+ img1.SetNRGBA(1, 0, color.NRGBA{R: 0, G: 255, B: 0, A: 255})
+ img1.SetNRGBA(0, 1, color.NRGBA{R: 0, G: 0, B: 255, A: 255})
+ img1.SetNRGBA(1, 1, color.NRGBA{R: 255, G: 255, B: 255, A: 255})
+
+ got := imageBuffer.Set(img1)
+ require.True(t, got)
+
+ appended := imageListBuffer.Append(imageBuffer)
+ require.True(t, appended)
+
+ list := imageListBuffer.GetAll()
+ require.Len(t, list, 1)
+}
diff --git a/internal/buffer/rect_buffer.go b/internal/buffer/rect_buffer.go
index aee8fe6..27a71f9 100644
--- a/internal/buffer/rect_buffer.go
+++ b/internal/buffer/rect_buffer.go
@@ -13,12 +13,19 @@ type Rect struct {
X, Y, W, H int32
}
+func (r Rect) ToInts() [4]int32 {
+ return [4]int32{r.X, r.Y, r.W, r.H}
+}
+
type RectBuffer struct {
handle *C.MaaRect
}
func NewRectBuffer() *RectBuffer {
handle := C.MaaRectCreate()
+ if handle == nil {
+ return nil
+ }
return &RectBuffer{
handle: handle,
}
diff --git a/internal/buffer/rect_buffer_test.go b/internal/buffer/rect_buffer_test.go
new file mode 100644
index 0000000..0b17a64
--- /dev/null
+++ b/internal/buffer/rect_buffer_test.go
@@ -0,0 +1,44 @@
+package buffer
+
+import (
+ "github.com/stretchr/testify/require"
+ "testing"
+)
+
+func createRectBuffer(t *testing.T) *RectBuffer {
+ rectBuffer := NewRectBuffer()
+ require.NotNil(t, rectBuffer)
+ return rectBuffer
+}
+
+func TestNewRectBuffer(t *testing.T) {
+ rectBuffer := createRectBuffer(t)
+ rectBuffer.Destroy()
+}
+
+func TestRectBuffer_Handle(t *testing.T) {
+ rectBuffer := createRectBuffer(t)
+ defer rectBuffer.Destroy()
+ handle := rectBuffer.Handle()
+ require.NotNil(t, handle)
+}
+
+func TestRectBuffer_Set(t *testing.T) {
+ rectBuffer := createRectBuffer(t)
+ defer rectBuffer.Destroy()
+
+ rect1 := Rect{100, 200, 300, 400}
+ got := rectBuffer.Set(rect1)
+ require.True(t, got)
+
+ x := rectBuffer.GetX()
+ require.Equal(t, rect1.X, x)
+ y := rectBuffer.GetY()
+ require.Equal(t, rect1.Y, y)
+ w := rectBuffer.GetW()
+ require.Equal(t, rect1.W, w)
+ h := rectBuffer.GetH()
+ require.Equal(t, rect1.H, h)
+ rect2 := rectBuffer.Get()
+ require.Equal(t, rect1, rect2)
+}
diff --git a/internal/buffer/string_buffer.go b/internal/buffer/string_buffer.go
index 12bb159..0493624 100644
--- a/internal/buffer/string_buffer.go
+++ b/internal/buffer/string_buffer.go
@@ -13,6 +13,9 @@ type StringBuffer struct {
func NewStringBuffer() *StringBuffer {
handle := C.MaaStringBufferCreate()
+ if handle == nil {
+ return nil
+ }
return &StringBuffer{
handle: handle,
}
diff --git a/internal/buffer/string_buffer_test.go b/internal/buffer/string_buffer_test.go
new file mode 100644
index 0000000..d8850dc
--- /dev/null
+++ b/internal/buffer/string_buffer_test.go
@@ -0,0 +1,71 @@
+package buffer
+
+import (
+ "github.com/stretchr/testify/require"
+ "testing"
+)
+
+func createStringBuffer(t *testing.T) *StringBuffer {
+ stringBuffer := NewStringBuffer()
+ require.NotNil(t, stringBuffer)
+ return stringBuffer
+}
+
+func TestNewStringBuffer(t *testing.T) {
+ stringBuffer := createStringBuffer(t)
+ stringBuffer.Destroy()
+}
+
+func TestStringBuffer_Handle(t *testing.T) {
+ stringBuffer := createStringBuffer(t)
+ defer stringBuffer.Destroy()
+ handle := stringBuffer.Handle()
+ require.NotNil(t, handle)
+}
+
+func TestStringBuffer_IsEmpty(t *testing.T) {
+ stringBuffer := createStringBuffer(t)
+ defer stringBuffer.Destroy()
+ got := stringBuffer.IsEmpty()
+ require.True(t, got)
+}
+
+func TestStringBuffer_Clear(t *testing.T) {
+ stringBuffer := createStringBuffer(t)
+ defer stringBuffer.Destroy()
+ got := stringBuffer.Clear()
+ require.True(t, got)
+}
+
+func TestStringBuffer_Set(t *testing.T) {
+ stringBuffer := createStringBuffer(t)
+ defer stringBuffer.Destroy()
+ str1 := "test"
+ got := stringBuffer.Set(str1)
+ require.True(t, got)
+
+ str2 := stringBuffer.Get()
+ require.Equal(t, str1, str2)
+}
+
+func TestStringBuffer_Size(t *testing.T) {
+ stringBuffer := createStringBuffer(t)
+ defer stringBuffer.Destroy()
+ str := "test"
+ got := stringBuffer.Set(str)
+ require.True(t, got)
+
+ size := stringBuffer.Size()
+ require.Equal(t, uint64(len(str)), size)
+}
+
+func TestStringBuffer_SetWithSize(t *testing.T) {
+ stringBuffer := createStringBuffer(t)
+ defer stringBuffer.Destroy()
+ str1 := "test"
+ got := stringBuffer.SetWithSize(str1, uint64(len(str1)))
+ require.True(t, got)
+
+ str2 := stringBuffer.Get()
+ require.Equal(t, str1, str2)
+}
diff --git a/internal/buffer/string_list_buffer.go b/internal/buffer/string_list_buffer.go
index 2aa3386..649482f 100644
--- a/internal/buffer/string_list_buffer.go
+++ b/internal/buffer/string_list_buffer.go
@@ -13,6 +13,9 @@ type StringListBuffer struct {
func NewStringListBuffer() *StringListBuffer {
handle := C.MaaStringListBufferCreate()
+ if handle == nil {
+ return nil
+ }
return &StringListBuffer{
handle: handle,
}
diff --git a/internal/buffer/string_list_buffer_test.go b/internal/buffer/string_list_buffer_test.go
new file mode 100644
index 0000000..840f19b
--- /dev/null
+++ b/internal/buffer/string_list_buffer_test.go
@@ -0,0 +1,114 @@
+package buffer
+
+import (
+ "github.com/stretchr/testify/require"
+ "testing"
+)
+
+func createStringListBuffer(t *testing.T) *StringListBuffer {
+ stringListBuffer := NewStringListBuffer()
+ require.NotNil(t, stringListBuffer)
+ return stringListBuffer
+}
+
+func TestNewStringListBuffer(t *testing.T) {
+ stringListBuffer := createStringListBuffer(t)
+ stringListBuffer.Destroy()
+}
+
+func TestStringListBuffer_Handle(t *testing.T) {
+ stringListBuffer := createStringListBuffer(t)
+ defer stringListBuffer.Destroy()
+ handle := stringListBuffer.Handle()
+ require.NotNil(t, handle)
+}
+
+func TestStringListBuffer_IsEmpty(t *testing.T) {
+ stringListBuffer := createStringListBuffer(t)
+ defer stringListBuffer.Destroy()
+ got := stringListBuffer.IsEmpty()
+ require.True(t, got)
+}
+
+func TestStringListBuffer_Clear(t *testing.T) {
+ stringListBuffer := createStringListBuffer(t)
+ defer stringListBuffer.Destroy()
+ got := stringListBuffer.Clear()
+ require.True(t, got)
+}
+
+func TestStringListBuffer_Append(t *testing.T) {
+ stringListBuffer := createStringListBuffer(t)
+ defer stringListBuffer.Destroy()
+
+ stringBuffer := createStringBuffer(t)
+ str1 := "test"
+ got1 := stringBuffer.Set(str1)
+ require.True(t, got1)
+
+ got2 := stringListBuffer.Append(stringBuffer)
+ require.True(t, got2)
+
+ got3 := stringListBuffer.IsEmpty()
+ require.False(t, got3)
+
+ str2 := stringListBuffer.Get(0)
+ require.Equal(t, str1, str2)
+}
+
+func TestStringListBuffer_Remove(t *testing.T) {
+ stringListBuffer := createStringListBuffer(t)
+ defer stringListBuffer.Destroy()
+
+ stringBuffer := createStringBuffer(t)
+ str1 := "test"
+ got1 := stringBuffer.Set(str1)
+ require.True(t, got1)
+
+ got2 := stringListBuffer.Append(stringBuffer)
+ require.True(t, got2)
+
+ removed := stringListBuffer.Remove(0)
+ require.True(t, removed)
+
+ got3 := stringListBuffer.IsEmpty()
+ require.True(t, got3)
+}
+
+func TestStringListBuffer_Size(t *testing.T) {
+ stringListBuffer := createStringListBuffer(t)
+ defer stringListBuffer.Destroy()
+
+ stringBuffer := createStringBuffer(t)
+ str1 := "test"
+ got1 := stringBuffer.Set(str1)
+ require.True(t, got1)
+
+ got2 := stringListBuffer.Append(stringBuffer)
+ require.True(t, got2)
+
+ got3 := stringListBuffer.IsEmpty()
+ require.False(t, got3)
+
+ size := stringListBuffer.Size()
+ require.Equal(t, uint64(1), size)
+}
+
+func TestStringListBuffer_GetAll(t *testing.T) {
+ stringListBuffer := createStringListBuffer(t)
+ defer stringListBuffer.Destroy()
+
+ stringBuffer := createStringBuffer(t)
+ str1 := "test"
+ got1 := stringBuffer.Set(str1)
+ require.True(t, got1)
+
+ got2 := stringListBuffer.Append(stringBuffer)
+ require.True(t, got2)
+
+ got3 := stringListBuffer.IsEmpty()
+ require.False(t, got3)
+
+ list := stringListBuffer.GetAll()
+ require.Len(t, list, 1)
+}
diff --git a/internal/notification/cgo.go b/internal/notification/cgo.go
deleted file mode 100644
index c520cf6..0000000
--- a/internal/notification/cgo.go
+++ /dev/null
@@ -1,10 +0,0 @@
-//go:build !customenv
-
-package notification
-
-/*
-#cgo !windows pkg-config: maa
-#cgo windows CFLAGS: -IC:/maa/include
-#cgo windows LDFLAGS: -LC:/maa/bin -lMaaFramework
-*/
-import "C"
diff --git a/internal/notification/notification.go b/internal/notification/notification.go
deleted file mode 100644
index 56e2411..0000000
--- a/internal/notification/notification.go
+++ /dev/null
@@ -1,41 +0,0 @@
-package notification
-
-/*
-#include
-
-typedef const char* StringView;
-
-extern void _MaaNotificationCallbackAgent(const char* message, const char* details_json, void* callback_arg);
-*/
-import "C"
-import (
- "sync/atomic"
- "unsafe"
-)
-
-var (
- notificationCallbackID uint64
- notificationCallbackAgents = make(map[uint64]func(msg, detailsJson string))
-)
-
-func RegisterCallback(callback func(msg, detailsJson string)) uint64 {
- id := atomic.AddUint64(¬ificationCallbackID, 1)
- notificationCallbackAgents[id] = callback
- return id
-}
-
-func UnregisterCallback(id uint64) {
- delete(notificationCallbackAgents, id)
-}
-
-//export _MaaNotificationCallbackAgent
-func _MaaNotificationCallbackAgent(msg, detailsJson C.StringView, callbackArg unsafe.Pointer) {
- // Here, we are simply passing the uint64 value as a pointer
- // and will not actually dereference this pointer.
- id := uint64(uintptr(callbackArg))
- callback := notificationCallbackAgents[id]
- if callback == nil {
- return
- }
- callback(C.GoString(msg), C.GoString(detailsJson))
-}
diff --git a/json.go b/json.go
index 3cee1e0..2a5a54d 100644
--- a/json.go
+++ b/json.go
@@ -13,3 +13,11 @@ func toJSON(v any) (string, error) {
}
return string(data), nil
}
+
+func formJSON(data []byte, v any) error {
+ err := json.Unmarshal(data, v)
+ if err != nil {
+ return err
+ }
+ return nil
+}
diff --git a/notification.go b/notification.go
new file mode 100644
index 0000000..959835b
--- /dev/null
+++ b/notification.go
@@ -0,0 +1,185 @@
+package maa
+
+/*
+#include
+
+typedef const char* StringView;
+
+extern void _MaaNotificationCallbackAgent(const char* message, const char* details_json, void* notify_arg);
+*/
+import "C"
+import (
+ "strings"
+ "sync/atomic"
+ "unsafe"
+)
+
+var (
+ notificationCallbackID uint64
+ notificationCallbackAgents = make(map[uint64]Notification)
+)
+
+func registerNotificationCallback(notify Notification) uint64 {
+ id := atomic.AddUint64(¬ificationCallbackID, 1)
+ notificationCallbackAgents[id] = notify
+ return id
+}
+
+func unregisterNotificationCallback(id uint64) {
+ delete(notificationCallbackAgents, id)
+}
+
+type NotificationType int
+
+// NotificationType
+const (
+ NotificationTypeUnknown NotificationType = iota
+ NotificationTypeStarting
+ NotificationTypeSucceeded
+ NotificationTypeFailed
+)
+
+type ResourceLoadingDetail struct {
+ ResID uint64 `json:"res_id"`
+ Hash string `json:"hash"`
+ Path string `json:"path"`
+}
+
+type ControllerActionDetail struct {
+ CtrlID uint64 `json:"ctrl_id"`
+ UUID string `json:"uuid"`
+ Action string `json:"action"`
+}
+
+type TaskerTaskDetail struct {
+ TaskID uint64 `json:"task_id"`
+ Entry string `json:"entry"`
+ UUID string `json:"uuid"`
+ Hash string `json:"hash"`
+}
+
+type TaskNextListDetail struct {
+ TaskID uint64 `json:"task_id"`
+ Name string `json:"name"`
+ NextList []string `json:"next_list"`
+}
+
+type TaskRecognitionDetail struct {
+ TaskID uint64 `json:"task_id"`
+ RecID uint64 `json:"reco_id"`
+ Name string `json:"name"`
+}
+
+type TaskActionDetail struct {
+ TaskID uint64 `json:"task_id"`
+ NodeID uint64 `json:"node_id"`
+ Name string `json:"name"`
+}
+
+type Notification interface {
+ OnResourceLoading(notifyType NotificationType, detail ResourceLoadingDetail)
+ OnControllerAction(notifyType NotificationType, detail ControllerActionDetail)
+ OnTaskerTask(notifyType NotificationType, detail TaskerTaskDetail)
+ OnTaskNextList(notifyType NotificationType, detail TaskNextListDetail)
+ OnTaskRecognition(notifyType NotificationType, detail TaskRecognitionDetail)
+ OnTaskAction(notifyType NotificationType, detail TaskActionDetail)
+ OnRawNotification(msg, detailsJSON string)
+ OnUnknownNotification(msg, detailsJSON string)
+}
+
+type NotificationHandler struct{}
+
+func _NewNotificationHandler() Notification {
+ return &NotificationHandler{}
+}
+
+func (n *NotificationHandler) OnResourceLoading(_ NotificationType, _ ResourceLoadingDetail) {
+ // DO NOTHING
+}
+
+func (n *NotificationHandler) OnControllerAction(_ NotificationType, _ ControllerActionDetail) {
+ // DO NOTHING
+}
+
+func (n *NotificationHandler) OnTaskerTask(_ NotificationType, _ TaskerTaskDetail) {
+ // DO NOTHING
+}
+
+func (n *NotificationHandler) OnTaskNextList(_ NotificationType, _ TaskNextListDetail) {
+ // DO NOTHING
+}
+
+func (n *NotificationHandler) OnTaskRecognition(_ NotificationType, _ TaskRecognitionDetail) {
+ // DO NOTHING
+}
+
+func (n *NotificationHandler) OnTaskAction(_ NotificationType, _ TaskActionDetail) {
+ // DO NOTHING
+}
+
+func (n *NotificationHandler) OnRawNotification(msg, detailsJSON string) {
+ notifyType := n.notificationType(msg)
+ switch {
+ case strings.HasPrefix(msg, "Resource.Loading"):
+ var detail ResourceLoadingDetail
+ _ = formJSON([]byte(msg), &detail)
+ n.OnResourceLoading(notifyType, detail)
+ return
+ case strings.HasPrefix(msg, "Controller.Action"):
+ var detail ControllerActionDetail
+ _ = formJSON([]byte(msg), &detail)
+ n.OnControllerAction(notifyType, detail)
+ return
+ case strings.HasPrefix(msg, "Tasker.Task"):
+ var detail TaskerTaskDetail
+ _ = formJSON([]byte(msg), &detail)
+ n.OnTaskerTask(notifyType, detail)
+ return
+ case strings.HasPrefix(msg, "Task.NextList"):
+ var detail TaskNextListDetail
+ _ = formJSON([]byte(msg), &detail)
+ n.OnTaskNextList(notifyType, detail)
+ return
+ case strings.HasPrefix(msg, "Task.Recognition"):
+ var detail TaskRecognitionDetail
+ _ = formJSON([]byte(msg), &detail)
+ n.OnTaskRecognition(notifyType, detail)
+ return
+ case strings.HasPrefix(msg, "Task.Action"):
+ var detail TaskActionDetail
+ _ = formJSON([]byte(msg), &detail)
+ n.OnTaskAction(notifyType, detail)
+ return
+ default:
+ n.OnUnknownNotification(msg, detailsJSON)
+ }
+}
+
+func (n *NotificationHandler) OnUnknownNotification(_, _ string) {
+ // DO NOTHING
+}
+
+func (n *NotificationHandler) notificationType(msg string) NotificationType {
+ switch {
+ case strings.HasSuffix(msg, ".Starting"):
+ return NotificationTypeStarting
+ case strings.HasSuffix(msg, "Succeeded"):
+ return NotificationTypeSucceeded
+ case strings.HasSuffix(msg, "Failed"):
+ return NotificationTypeFailed
+ default:
+ return NotificationTypeUnknown
+ }
+}
+
+//export _MaaNotificationCallbackAgent
+func _MaaNotificationCallbackAgent(msg, detailsJson C.StringView, notifyArg unsafe.Pointer) {
+ // Here, we are simply passing the uint64 value as a pointer
+ // and will not actually dereference this pointer.
+ id := uint64(uintptr(notifyArg))
+ notify := notificationCallbackAgents[id]
+ if notify == nil {
+ return
+ }
+ notify.OnRawNotification(C.GoString(msg), C.GoString(detailsJson))
+}
diff --git a/notification_test.go b/notification_test.go
new file mode 100644
index 0000000..49b2afc
--- /dev/null
+++ b/notification_test.go
@@ -0,0 +1,38 @@
+package maa
+
+import (
+ "fmt"
+ "github.com/stretchr/testify/require"
+ "testing"
+)
+
+type testNotificationHandlerOnRawNotification struct {
+ *NotificationHandler
+}
+
+func (t *testNotificationHandlerOnRawNotification) OnRawNotification(msg, detailsJson string) {
+ fmt.Printf("TestNotificationHandler_OnRawNotification, msg: %s, detailsJson: %s\n", msg, detailsJson)
+ t.NotificationHandler.OnRawNotification(msg, detailsJson)
+}
+
+func TestNotificationHandler_OnRawNotification(t *testing.T) {
+ ctrl := createDbgController(t, &testNotificationHandlerOnRawNotification{})
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+
+ res := createResource(t, &testNotificationHandlerOnRawNotification{})
+ defer res.Destroy()
+
+ tasker := createTasker(t, &testNotificationHandlerOnRawNotification{})
+ defer tasker.Destroy()
+ taskerBind(t, tasker, ctrl, res)
+
+ got := tasker.PostPipeline("TestNotificationHandler_OnRawNotification", J{
+ "TestNotificationHandler_OnRawNotification": J{
+ "action": "Click",
+ "target": []int{100, 200, 100, 100},
+ },
+ }).Wait().Success()
+ require.True(t, got)
+}
diff --git a/option.go b/option.go
index c380991..6d019be 100644
--- a/option.go
+++ b/option.go
@@ -40,14 +40,17 @@ const (
// value: bool, eg: true; val_size: sizeof(bool)
GlobalOptionShowHitDraw
- // GlobalOptionDebugMessage Whether to callback debug message
+ // GlobalOptionDebugMode Whether to debug
//
// value: bool, eg: true; val_size: sizeof(bool)
- GlobalOptionDebugMessage
+ GlobalOptionDebugMode
)
// SetLogDir sets the log directory.
func SetLogDir(path string) bool {
+ if path == "" {
+ return false
+ }
cPath := C.CString(path)
defer C.free(unsafe.Pointer(cPath))
return C.MaaSetGlobalOption(C.int32_t(GlobalOptionLogDir), C.MaaOptionValue(cPath), C.uint64_t(len(path))) != 0
@@ -99,11 +102,11 @@ func SetShowHitDraw(enabled bool) bool {
return C.MaaSetGlobalOption(C.int32_t(GlobalOptionShowHitDraw), C.MaaOptionValue(unsafe.Pointer(&cEnabled)), C.uint64_t(unsafe.Sizeof(cEnabled))) != 0
}
-// SetDebugMessage sets whether to callback debug message.
-func SetDebugMessage(enabled bool) bool {
+// SetDebugMode sets whether to enable debug mode.
+func SetDebugMode(enabled bool) bool {
var cEnabled uint8
if enabled {
cEnabled = 1
}
- return C.MaaSetGlobalOption(C.int32_t(GlobalOptionDebugMessage), C.MaaOptionValue(unsafe.Pointer(&cEnabled)), C.uint64_t(unsafe.Sizeof(cEnabled))) != 0
+ return C.MaaSetGlobalOption(C.int32_t(GlobalOptionDebugMode), C.MaaOptionValue(unsafe.Pointer(&cEnabled)), C.uint64_t(unsafe.Sizeof(cEnabled))) != 0
}
diff --git a/option_test.go b/option_test.go
new file mode 100644
index 0000000..4452a5f
--- /dev/null
+++ b/option_test.go
@@ -0,0 +1,192 @@
+package maa
+
+import (
+ "github.com/stretchr/testify/require"
+ "testing"
+)
+
+func TestSetLogDir(t *testing.T) {
+ testCases := []struct {
+ name string
+ path string
+ expected bool
+ }{
+ {
+ name: "ValidPath",
+ path: "./test/debug",
+ expected: true,
+ },
+ {
+ name: "EmptyPath",
+ path: "",
+ expected: false,
+ },
+ }
+
+ for _, tc := range testCases {
+ t.Run(tc.name, func(t *testing.T) {
+ result := SetLogDir(tc.path)
+ require.Equal(t, tc.expected, result)
+ })
+ }
+}
+
+func TestSetSaveDraw(t *testing.T) {
+ testCases := []struct {
+ name string
+ enabled bool
+ expected bool
+ }{
+ {
+ name: "EnableSaveDraw",
+ enabled: true,
+ expected: true,
+ },
+ {
+ name: "DisableSaveDraw",
+ enabled: false,
+ expected: true,
+ },
+ }
+
+ for _, tc := range testCases {
+ t.Run(tc.name, func(t *testing.T) {
+ result := SetSaveDraw(tc.enabled)
+ require.Equal(t, tc.expected, result)
+ })
+ }
+}
+
+func TestSetRecording(t *testing.T) {
+ testCases := []struct {
+ name string
+ enabled bool
+ expected bool
+ }{
+ {
+ name: "EnableRecording",
+ enabled: true,
+ expected: true,
+ },
+ {
+ name: "DisableRecording",
+ enabled: false,
+ expected: true,
+ },
+ }
+
+ for _, tc := range testCases {
+ t.Run(tc.name, func(t *testing.T) {
+ result := SetRecording(tc.enabled)
+ require.Equal(t, tc.expected, result)
+ })
+ }
+}
+
+func TestSetStdoutLevel(t *testing.T) {
+ testCases := []struct {
+ name string
+ level LoggingLevel
+ expected bool
+ }{
+ {
+ name: "SetLevelOff",
+ level: LoggingLevelOff,
+ expected: true,
+ },
+ {
+ name: "SetLevelFatal",
+ level: LoggingLevelFatal,
+ expected: true,
+ },
+ {
+ name: "SetLevelError",
+ level: LoggingLevelError,
+ expected: true,
+ },
+ {
+ name: "SetLevelWarn",
+ level: LoggingLevelWarn,
+ expected: true,
+ },
+ {
+ name: "SetLevelInfo",
+ level: LoggingLevelInfo,
+ expected: true,
+ },
+ {
+ name: "SetLevelDebug",
+ level: LoggingLevelDebug,
+ expected: true,
+ },
+ {
+ name: "SetLevelTrace",
+ level: LoggingLevelTrace,
+ expected: true,
+ },
+ {
+ name: "SetLevelAll",
+ level: LoggingLevelAll,
+ expected: true,
+ },
+ }
+
+ for _, tc := range testCases {
+ t.Run(tc.name, func(t *testing.T) {
+ result := SetStdoutLevel(tc.level)
+ require.Equal(t, tc.expected, result)
+ })
+ }
+}
+
+func TestSetShowHitDraw(t *testing.T) {
+ testCases := []struct {
+ name string
+ enabled bool
+ expected bool
+ }{
+ {
+ name: "EnableShowHitDraw",
+ enabled: true,
+ expected: true,
+ },
+ {
+ name: "DisableShowHitDraw",
+ enabled: false,
+ expected: true,
+ },
+ }
+
+ for _, tc := range testCases {
+ t.Run(tc.name, func(t *testing.T) {
+ result := SetShowHitDraw(tc.enabled)
+ require.Equal(t, tc.expected, result)
+ })
+ }
+}
+
+func TestSetDebugMode(t *testing.T) {
+ testCases := []struct {
+ name string
+ enabled bool
+ expected bool
+ }{
+ {
+ name: "EnableDebugMode",
+ enabled: true,
+ expected: true,
+ },
+ {
+ name: "DisableDebugMode",
+ enabled: false,
+ expected: true,
+ },
+ }
+
+ for _, tc := range testCases {
+ t.Run(tc.name, func(t *testing.T) {
+ result := SetDebugMode(tc.enabled)
+ require.Equal(t, tc.expected, result)
+ })
+ }
+}
diff --git a/resource.go b/resource.go
index ca62080..c75b358 100644
--- a/resource.go
+++ b/resource.go
@@ -6,7 +6,7 @@ package maa
extern void _MaaNotificationCallbackAgent(const char* message, const char* details_json, void* callback_arg);
-extern uint8_t _MaaCustomRecognizerCallbackAgent(
+extern uint8_t _MaaCustomRecognitionCallbackAgent(
MaaContext* ctx,
int64_t task_id,
const char* current_task_name,
@@ -31,7 +31,6 @@ extern uint8_t _MaaCustomActionCallbackAgent(
import "C"
import (
"github.com/MaaXYZ/maa-framework-go/internal/buffer"
- "github.com/MaaXYZ/maa-framework-go/internal/notification"
"github.com/MaaXYZ/maa-framework-go/internal/store"
"unsafe"
)
@@ -49,8 +48,8 @@ type Resource struct {
}
// NewResource creates a new resource.
-func NewResource(callback func(msg, detailsJson string)) *Resource {
- id := notification.RegisterCallback(callback)
+func NewResource(notify Notification) *Resource {
+ id := registerNotificationCallback(notify)
handle := C.MaaResourceCreate(
C.MaaNotificationCallback(C._MaaNotificationCallbackAgent),
// Here, we are simply passing the uint64 value as a pointer
@@ -73,7 +72,7 @@ func NewResource(callback func(msg, detailsJson string)) *Resource {
// Destroy frees the resource.
func (r *Resource) Destroy() {
value := resourceStore.Get(r.Handle())
- notification.UnregisterCallback(value.NotificationCallbackID)
+ unregisterNotificationCallback(value.NotificationCallbackID)
resourceStore.Del(r.Handle())
C.MaaResourceDestroy(r.handle)
}
@@ -82,12 +81,12 @@ func (r *Resource) Handle() unsafe.Pointer {
return unsafe.Pointer(r.handle)
}
-// RegisterCustomRecognizer registers a custom recognizer to the resource.
-func (r *Resource) RegisterCustomRecognizer(name string, recognizer CustomRecognizer) bool {
- id := registerCustomRecognizer(recognizer)
+// RegisterCustomRecognition registers a custom recognition to the resource.
+func (r *Resource) RegisterCustomRecognition(name string, recognition CustomRecognition) bool {
+ id := registerCustomRecognition(recognition)
value := resourceStore.Get(r.Handle())
if oldID, ok := value.CustomRecognizersCallbackID[name]; ok {
- unregisterCustomRecognizer(oldID)
+ unregisterCustomRecognition(oldID)
}
value.CustomRecognizersCallbackID[name] = id
resourceStore.Set(r.Handle(), value)
@@ -95,10 +94,10 @@ func (r *Resource) RegisterCustomRecognizer(name string, recognizer CustomRecogn
cName := C.CString(name)
defer C.free(unsafe.Pointer(cName))
- got := C.MaaResourceRegisterCustomRecognizer(
+ got := C.MaaResourceRegisterCustomRecognition(
r.handle,
cName,
- C.MaaCustomRecognizerCallback(C._MaaCustomRecognizerCallbackAgent),
+ C.MaaCustomRecognitionCallback(C._MaaCustomRecognitionCallbackAgent),
// Here, we are simply passing the uint64 value as a pointer
// and will not actually dereference this pointer.
unsafe.Pointer(uintptr(id)),
@@ -106,11 +105,11 @@ func (r *Resource) RegisterCustomRecognizer(name string, recognizer CustomRecogn
return got != 0
}
-// UnregisterCustomRecognizer unregisters a custom recognizer from the resource.
-func (r *Resource) UnregisterCustomRecognizer(name string) bool {
+// UnregisterCustomRecognition unregisters a custom recognition from the resource.
+func (r *Resource) UnregisterCustomRecognition(name string) bool {
value := resourceStore.Get(r.Handle())
if id, ok := value.CustomRecognizersCallbackID[name]; ok {
- unregisterCustomRecognizer(id)
+ unregisterCustomRecognition(id)
} else {
return false
}
@@ -118,18 +117,18 @@ func (r *Resource) UnregisterCustomRecognizer(name string) bool {
cName := C.CString(name)
defer C.free(unsafe.Pointer(cName))
- got := C.MaaResourceUnregisterCustomRecognizer(r.handle, cName)
+ got := C.MaaResourceUnregisterCustomRecognition(r.handle, cName)
return got != 0
}
-// ClearCustomRecognizer clears all custom recognizers registered from the resource.
-func (r *Resource) ClearCustomRecognizer() bool {
+// ClearCustomRecognition clears all custom recognitions registered from the resource.
+func (r *Resource) ClearCustomRecognition() bool {
value := resourceStore.Get(r.Handle())
for _, id := range value.CustomRecognizersCallbackID {
- unregisterCustomRecognizer(id)
+ unregisterCustomRecognition(id)
}
- got := C.MaaResourceClearCustomRecognizer(r.handle)
+ got := C.MaaResourceClearCustomRecognition(r.handle)
return got != 0
}
diff --git a/resource_test.go b/resource_test.go
index 1d71570..1183220 100644
--- a/resource_test.go
+++ b/resource_test.go
@@ -5,8 +5,308 @@ import (
"testing"
)
-func createResource(t *testing.T) *Resource {
- res := NewResource(nil)
+func createResource(t *testing.T, notify Notification) *Resource {
+ res := NewResource(notify)
require.NotNil(t, res)
return res
}
+
+func TestNewResource(t *testing.T) {
+ res := createResource(t, nil)
+ res.Destroy()
+}
+
+func TestResource_Handle(t *testing.T) {
+ res := createResource(t, nil)
+ defer res.Destroy()
+ handle := res.Handle()
+ require.NotNil(t, handle)
+}
+
+type testResourceTestRec struct{}
+
+func (t *testResourceTestRec) Run(_ *Context, _ *CustomRecognitionArg) (CustomRecognitionResult, bool) {
+ return CustomRecognitionResult{}, true
+}
+
+func TestResource_RegisterCustomRecognition(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+
+ res := createResource(t, nil)
+ defer res.Destroy()
+
+ tasker := createTasker(t, nil)
+ defer tasker.Destroy()
+ taskerBind(t, tasker, ctrl, res)
+
+ got1 := res.RegisterCustomRecognition("TestRec", &testResourceTestRec{})
+ require.True(t, got1)
+
+ got2 := tasker.PostPipeline("TestResource_RegisterCustomRecognition", J{
+ "TestResource_RegisterCustomRecognition": J{
+ "recognition": "custom",
+ "custom_recognition": "TestRec",
+ },
+ }).Wait().Success()
+ require.True(t, got2)
+}
+
+func TestResource_UnregisterCustomRecognition(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+
+ res := createResource(t, nil)
+ defer res.Destroy()
+
+ tasker := createTasker(t, nil)
+ defer tasker.Destroy()
+ taskerBind(t, tasker, ctrl, res)
+
+ got1 := res.RegisterCustomRecognition("TestRec", &testResourceTestRec{})
+ require.True(t, got1)
+
+ got2 := tasker.PostPipeline("TestResource_UnregisterCustomRecognition", J{
+ "TestResource_UnregisterCustomRecognition": J{
+ "recognition": "custom",
+ "custom_recognition": "TestRec",
+ },
+ }).Wait().Success()
+ require.True(t, got2)
+
+ got3 := res.UnregisterCustomRecognition("TestRec")
+ require.True(t, got3)
+
+ got4 := tasker.PostPipeline("TestResource_UnregisterCustomRecognition", J{
+ "TestResource_UnregisterCustomRecognition": J{
+ "recognition": "custom",
+ "custom_recognition": "TestRec",
+ },
+ }).Wait().Failure()
+ require.True(t, got4)
+}
+
+func TestResource_ClearCustomRecognition(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+
+ res := createResource(t, nil)
+ defer res.Destroy()
+
+ tasker := createTasker(t, nil)
+ defer tasker.Destroy()
+ taskerBind(t, tasker, ctrl, res)
+
+ got1 := res.RegisterCustomRecognition("TestRec1", &testResourceTestRec{})
+ require.True(t, got1)
+ got2 := res.RegisterCustomRecognition("TestRec2", &testResourceTestRec{})
+ require.True(t, got2)
+
+ got3 := tasker.PostPipeline("TestResource_ClearCustomRecognition", J{
+ "TestResource_ClearCustomRecognition": J{
+ "recognition": "custom",
+ "custom_recognition": "TestRec1",
+ },
+ }).Wait().Success()
+ require.True(t, got3)
+ got4 := tasker.PostPipeline("TestResource_ClearCustomRecognition", J{
+ "TestResource_ClearCustomRecognition": J{
+ "recognition": "custom",
+ "custom_recognition": "TestRec2",
+ },
+ }).Wait().Success()
+ require.True(t, got4)
+
+ got5 := res.ClearCustomRecognition()
+ require.True(t, got5)
+
+ got6 := tasker.PostPipeline("TestResource_ClearCustomRecognition", J{
+ "TestResource_ClearCustomRecognition": J{
+ "recognition": "custom",
+ "custom_recognition": "TestRec1",
+ },
+ }).Wait().Failure()
+ require.True(t, got6)
+ got7 := tasker.PostPipeline("TestResource_ClearCustomRecognition", J{
+ "TestResource_ClearCustomRecognition": J{
+ "recognition": "custom",
+ "custom_recognition": "TestRec2",
+ },
+ }).Wait().Failure()
+ require.True(t, got7)
+}
+
+type testResourceTestAct struct{}
+
+func (t *testResourceTestAct) Run(_ *Context, _ *CustomActionArg) bool {
+ return true
+}
+
+func TestResource_RegisterCustomAction(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+
+ res := createResource(t, nil)
+ defer res.Destroy()
+
+ tasker := createTasker(t, nil)
+ defer tasker.Destroy()
+ taskerBind(t, tasker, ctrl, res)
+
+ registered := res.RegisterCustomAction("TestAct", &testResourceTestAct{})
+ require.True(t, registered)
+
+ got := tasker.PostPipeline("TestResource_RegisterCustomAction", J{
+ "TestResource_RegisterCustomAction": J{
+ "action": "custom",
+ "custom_action": "TestAct",
+ },
+ }).Wait().Success()
+ require.True(t, got)
+}
+
+func TestResource_UnregisterCustomAction(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+
+ res := createResource(t, nil)
+ defer res.Destroy()
+
+ tasker := createTasker(t, nil)
+ defer tasker.Destroy()
+ taskerBind(t, tasker, ctrl, res)
+
+ registered := res.RegisterCustomAction("TestAct", &testResourceTestAct{})
+ require.True(t, registered)
+
+ got1 := tasker.PostPipeline("TestResource_RegisterCustomAction", J{
+ "TestResource_RegisterCustomAction": J{
+ "action": "custom",
+ "custom_action": "TestAct",
+ },
+ }).Wait().Success()
+ require.True(t, got1)
+
+ unregistered := res.UnregisterCustomAction("TestAct")
+ require.True(t, unregistered)
+
+ got2 := tasker.PostPipeline("TestResource_RegisterCustomAction", J{
+ "TestResource_RegisterCustomAction": J{
+ "action": "custom",
+ "custom_action": "TestAct",
+ },
+ }).Wait().Failure()
+ require.True(t, got2)
+}
+
+func TestResource_ClearCustomAction(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+
+ res := createResource(t, nil)
+ defer res.Destroy()
+
+ tasker := createTasker(t, nil)
+ defer tasker.Destroy()
+ taskerBind(t, tasker, ctrl, res)
+
+ registered1 := res.RegisterCustomAction("TestAct1", &testResourceTestAct{})
+ require.True(t, registered1)
+ registered2 := res.RegisterCustomAction("TestAct2", &testResourceTestAct{})
+ require.True(t, registered2)
+
+ got1 := tasker.PostPipeline("TestResource_RegisterCustomAction", J{
+ "TestResource_RegisterCustomAction": J{
+ "action": "custom",
+ "custom_action": "TestAct1",
+ },
+ }).Wait().Success()
+ require.True(t, got1)
+ got2 := tasker.PostPipeline("TestResource_RegisterCustomAction", J{
+ "TestResource_RegisterCustomAction": J{
+ "action": "custom",
+ "custom_action": "TestAct2",
+ },
+ }).Wait().Success()
+ require.True(t, got2)
+
+ cleared := res.ClearCustomAction()
+ require.True(t, cleared)
+
+ got3 := tasker.PostPipeline("TestResource_RegisterCustomAction", J{
+ "TestResource_RegisterCustomAction": J{
+ "action": "custom",
+ "custom_action": "TestAct1",
+ },
+ }).Wait().Failure()
+ require.True(t, got3)
+ got4 := tasker.PostPipeline("TestResource_RegisterCustomAction", J{
+ "TestResource_RegisterCustomAction": J{
+ "action": "custom",
+ "custom_action": "TestAct2",
+ },
+ }).Wait().Failure()
+ require.True(t, got4)
+}
+
+func TestResource_PostPath(t *testing.T) {
+ res := createResource(t, nil)
+ defer res.Destroy()
+ resDir := "./test/data_set/PipelineSmoking/resource"
+ isPathSet := res.PostPath(resDir).Wait().Success()
+ require.True(t, isPathSet)
+}
+
+func TestResource_Clear(t *testing.T) {
+ res := createResource(t, nil)
+ defer res.Destroy()
+ resDir := "./test/data_set/PipelineSmoking/resource"
+ isPathSet := res.PostPath(resDir).Wait().Success()
+ require.True(t, isPathSet)
+ cleared := res.Clear()
+ require.True(t, cleared)
+}
+
+func TestResource_Loaded(t *testing.T) {
+ res := createResource(t, nil)
+ defer res.Destroy()
+ resDir := "./test/data_set/PipelineSmoking/resource"
+ isPathSet := res.PostPath(resDir).Wait().Success()
+ require.True(t, isPathSet)
+ loaded := res.Loaded()
+ require.True(t, loaded)
+}
+
+func TestResource_GetHash(t *testing.T) {
+ res := createResource(t, nil)
+ defer res.Destroy()
+ resDir := "./test/data_set/PipelineSmoking/resource"
+ isPathSet := res.PostPath(resDir).Wait().Success()
+ require.True(t, isPathSet)
+ hash, ok := res.GetHash()
+ require.True(t, ok)
+ require.NotEqual(t, "0", hash)
+}
+
+func TestResource_GetTaskList(t *testing.T) {
+ res := createResource(t, nil)
+ defer res.Destroy()
+ resDir := "./test/data_set/PipelineSmoking/resource"
+ isPathSet := res.PostPath(resDir).Wait().Success()
+ require.True(t, isPathSet)
+ taskList, ok := res.GetTaskList()
+ require.True(t, ok)
+ require.NotEmpty(t, taskList)
+}
diff --git a/tasker.go b/tasker.go
index 9c28a76..a0ca65d 100644
--- a/tasker.go
+++ b/tasker.go
@@ -9,10 +9,8 @@ extern void _MaaNotificationCallbackAgent(const char* message, const char* detai
import "C"
import (
"github.com/MaaXYZ/maa-framework-go/internal/buffer"
- "github.com/MaaXYZ/maa-framework-go/internal/notification"
"github.com/MaaXYZ/maa-framework-go/internal/store"
"image"
- "time"
"unsafe"
)
@@ -23,8 +21,8 @@ type Tasker struct {
}
// NewTasker creates an new tasker.
-func NewTasker(callback func(msg, detailsJson string)) *Tasker {
- id := notification.RegisterCallback(callback)
+func NewTasker(notify Notification) *Tasker {
+ id := registerNotificationCallback(notify)
handle := C.MaaTaskerCreate(
C.MaaNotificationCallback(C._MaaNotificationCallbackAgent),
// Here, we are simply passing the uint64 value as a pointer
@@ -41,7 +39,7 @@ func NewTasker(callback func(msg, detailsJson string)) *Tasker {
// Destroy free the tasker.
func (t *Tasker) Destroy() {
id := taskerStore.Get(t.Handle())
- notification.UnregisterCallback(id)
+ unregisterNotificationCallback(id)
taskerStore.Del(t.Handle())
C.MaaTaskerDestroy(t.handle)
}
@@ -61,8 +59,8 @@ func (t *Tasker) BindController(ctrl Controller) bool {
return C.MaaTaskerBindController(t.handle, (*C.MaaController)(ctrl.Handle())) != 0
}
-// Inited checks if the tasker is initialized.
-func (t *Tasker) Inited() bool {
+// Initialized checks if the tasker is initialized.
+func (t *Tasker) Initialized() bool {
return C.MaaTaskerInited(t.handle) != 0
}
@@ -108,13 +106,6 @@ func (t *Tasker) wait(id int64) Status {
return Status(C.MaaTaskerWait(t.handle, C.int64_t(id)))
}
-// WaitAll waits for all tasks to complete.
-func (t *Tasker) WaitAll() {
- for t.Running() {
- time.Sleep(time.Millisecond * 10)
- }
-}
-
// Running checks if the instance running.
func (t *Tasker) Running() bool {
return C.MaaTaskerRunning(t.handle) != 0
@@ -182,7 +173,7 @@ func (t *Tasker) getRecognitionDetail(recId int64) *RecognitionDetail {
return nil
}
- rawImg := raw.GetByRawData()
+ rawImg := raw.Get()
DrawImages := draws.GetAll()
return &RecognitionDetail{
@@ -200,7 +191,6 @@ type NodeDetail struct {
ID int64
Name string
Recognition *RecognitionDetail
- Times uint64
RunCompleted bool
}
@@ -209,14 +199,12 @@ func (t *Tasker) getNodeDetail(nodeId int64) *NodeDetail {
name := buffer.NewStringBuffer()
defer name.Destroy()
var recId int64
- var times uint64
var runCompleted uint8
got := C.MaaTaskerGetNodeDetail(
t.handle,
C.int64_t(nodeId),
(*C.MaaStringBuffer)(name.Handle()),
(*C.int64_t)(unsafe.Pointer(&recId)),
- (*C.uint64_t)(unsafe.Pointer(×)),
(*C.uint8_t)(unsafe.Pointer(&runCompleted)),
)
if got == 0 {
@@ -232,7 +220,6 @@ func (t *Tasker) getNodeDetail(nodeId int64) *NodeDetail {
ID: nodeId,
Name: name.Get(),
Recognition: recognitionDetail,
- Times: times,
RunCompleted: runCompleted != 0,
}
}
diff --git a/tasker_test.go b/tasker_test.go
index f57a868..b2919af 100644
--- a/tasker_test.go
+++ b/tasker_test.go
@@ -3,10 +3,11 @@ package maa
import (
"github.com/stretchr/testify/require"
"testing"
+ "time"
)
-func createTasker(t *testing.T) *Tasker {
- tasker := NewTasker(nil)
+func createTasker(t *testing.T, notify Notification) *Tasker {
+ tasker := NewTasker(notify)
require.NotNil(t, tasker)
return tasker
}
@@ -17,3 +18,177 @@ func taskerBind(t *testing.T, tasker *Tasker, ctrl Controller, res *Resource) {
isCtrlBound := tasker.BindController(ctrl)
require.True(t, isCtrlBound)
}
+
+func TestNewTasker(t *testing.T) {
+ tasker := createTasker(t, nil)
+ tasker.Destroy()
+}
+
+func TestTasker_Handle(t *testing.T) {
+ tasker := createTasker(t, nil)
+ defer tasker.Destroy()
+ handle := tasker.Handle()
+ require.NotNil(t, handle)
+}
+
+func TestTasker_BindResource(t *testing.T) {
+ res := createResource(t, nil)
+ defer res.Destroy()
+
+ tasker := createTasker(t, nil)
+ defer tasker.Destroy()
+ bound := tasker.BindResource(res)
+ require.True(t, bound)
+}
+
+func TestTasker_BindController(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+
+ tasker := createTasker(t, nil)
+ defer tasker.Destroy()
+ bound := tasker.BindController(ctrl)
+ require.True(t, bound)
+}
+
+func TestTasker_Initialized(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ connected := ctrl.PostConnect().Wait().Success()
+ require.True(t, connected)
+
+ res := createResource(t, nil)
+ defer res.Destroy()
+
+ tasker := createTasker(t, nil)
+ defer tasker.Destroy()
+ taskerBind(t, tasker, ctrl, res)
+
+ initialized := tasker.Initialized()
+ require.True(t, initialized)
+}
+
+func TestTasker_PostPipeline(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+
+ res := createResource(t, nil)
+ defer res.Destroy()
+
+ tasker := createTasker(t, nil)
+ defer tasker.Destroy()
+ taskerBind(t, tasker, ctrl, res)
+
+ got := tasker.PostPipeline("TestTasker_PostPipeline", J{
+ "TestTasker_PostPipeline": J{
+ "action": "Click",
+ "target": []int{100, 200, 100, 100},
+ },
+ }).Wait().Success()
+ require.True(t, got)
+}
+
+func TestTasker_Running(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+
+ res := createResource(t, nil)
+ defer res.Destroy()
+
+ tasker := createTasker(t, nil)
+ defer tasker.Destroy()
+ taskerBind(t, tasker, ctrl, res)
+
+ got := tasker.Running()
+ require.False(t, got)
+}
+
+func TestTasker_PostStop(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+
+ res := createResource(t, nil)
+ defer res.Destroy()
+
+ tasker := createTasker(t, nil)
+ defer tasker.Destroy()
+ taskerBind(t, tasker, ctrl, res)
+
+ got := tasker.PostStop()
+ require.True(t, got)
+}
+
+func TestTasker_GetResource(t *testing.T) {
+ res1 := createResource(t, nil)
+ defer res1.Destroy()
+
+ tasker := createTasker(t, nil)
+ defer tasker.Destroy()
+ bound := tasker.BindResource(res1)
+ require.True(t, bound)
+
+ res2 := tasker.GetResource()
+ require.NotNil(t, res2)
+ require.Equal(t, res1.Handle(), res2.Handle())
+}
+
+func TestTasker_GetController(t *testing.T) {
+ ctrl1 := createDbgController(t, nil)
+ defer ctrl1.Destroy()
+
+ tasker := createTasker(t, nil)
+ defer tasker.Destroy()
+ bound := tasker.BindController(ctrl1)
+ require.True(t, bound)
+
+ ctrl2 := tasker.GetController()
+ require.NotNil(t, ctrl2)
+ require.Equal(t, ctrl1.Handle(), ctrl2.Handle())
+}
+
+func TestTasker_ClearCache(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+
+ res := createResource(t, nil)
+ defer res.Destroy()
+
+ tasker := createTasker(t, nil)
+ defer tasker.Destroy()
+ taskerBind(t, tasker, ctrl, res)
+
+ got := tasker.ClearCache()
+ require.True(t, got)
+}
+
+func TestTasker_GetLatestNode(t *testing.T) {
+ ctrl := createDbgController(t, nil)
+ defer ctrl.Destroy()
+ isConnected := ctrl.PostConnect().Wait().Success()
+ require.True(t, isConnected)
+
+ res := createResource(t, nil)
+ defer res.Destroy()
+ resDir := "./test/data_set/PipelineSmoking/resource"
+ isPathSet := res.PostPath(resDir).Wait().Success()
+ require.True(t, isPathSet)
+
+ tasker := createTasker(t, nil)
+ defer tasker.Destroy()
+ taskerBind(t, tasker, ctrl, res)
+ job := tasker.PostPipeline("Wilderness")
+ require.NotNil(t, job)
+ time.Sleep(2 * time.Second)
+ detail := tasker.GetLatestNode("Wilderness")
+ t.Log(detail)
+ got := job.Wait().Success()
+ require.True(t, got)
+}
diff --git a/test/pipleline_smoking_test.go b/test/pipleline_smoking_test.go
index 2770cb0..5b13736 100644
--- a/test/pipleline_smoking_test.go
+++ b/test/pipleline_smoking_test.go
@@ -31,7 +31,7 @@ func TestPipelineSmoking(t *testing.T) {
isCtrlBound := tasker.BindController(ctrl)
require.True(t, isCtrlBound)
- isInitialized := tasker.Inited()
+ isInitialized := tasker.Initialized()
require.True(t, isInitialized)
got := tasker.PostPipeline("Wilderness").Wait().Success()
diff --git a/toolkit.go b/toolkit.go
index 693c139..2867cc7 100644
--- a/toolkit.go
+++ b/toolkit.go
@@ -4,7 +4,7 @@ package maa
#include
#include
-extern uint8_t _MaaCustomRecognizerCallbackAgent(
+extern uint8_t _MaaCustomRecognitionCallbackAgent(
MaaContext* ctx,
int64_t task_id,
const char* current_task_name,
@@ -30,7 +30,6 @@ extern void _MaaNotificationCallbackAgent(const char* message, const char* detai
*/
import "C"
import (
- "github.com/MaaXYZ/maa-framework-go/internal/notification"
"unsafe"
)
@@ -138,9 +137,9 @@ type piStoreValue struct {
var piStore = make(map[uint64]piStoreValue)
-// RegisterPICustomRecognizer registers a custom recognizer.
-func (t *Toolkit) RegisterPICustomRecognizer(instId uint64, name string, recognizer CustomRecognizer) {
- id := registerCustomRecognizer(recognizer)
+// RegisterPICustomRecognition registers a custom recognizer.
+func (t *Toolkit) RegisterPICustomRecognition(instId uint64, name string, recognition CustomRecognition) {
+ id := registerCustomRecognition(recognition)
if _, ok := piStore[instId]; !ok {
piStore[instId] = piStoreValue{
CustomRecognizersCallbackID: make(map[string]uint64),
@@ -155,7 +154,7 @@ func (t *Toolkit) RegisterPICustomRecognizer(instId uint64, name string, recogni
C.MaaToolkitProjectInterfaceRegisterCustomRecognition(
C.uint64_t(instId),
cName,
- C.MaaCustomRecognizerCallback(C._MaaCustomRecognizerCallbackAgent),
+ C.MaaCustomRecognitionCallback(C._MaaCustomRecognitionCallbackAgent),
// Here, we are simply passing the uint64 value as a pointer
// and will not actually dereference this pointer.
unsafe.Pointer(uintptr(id)),
@@ -186,11 +185,11 @@ func (t *Toolkit) RegisterPICustomAction(instId uint64, name string, action Cust
)
}
-// ClearPICustom unregisters all custom recognizers and actions for a given instance.
+// ClearPICustom unregisters all custom recognitions and actions for a given instance.
func (t *Toolkit) ClearPICustom(instId uint64) {
value := piStore[instId]
for _, id := range value.CustomRecognizersCallbackID {
- unregisterCustomRecognizer(id)
+ unregisterCustomRecognition(id)
}
for _, id := range value.CustomActionsCallbackID {
unregisterCustomAction(id)
@@ -198,7 +197,7 @@ func (t *Toolkit) ClearPICustom(instId uint64) {
}
// RunCli runs the PI CLI.
-func (t *Toolkit) RunCli(instId uint64, resourcePath, userPath string, directly bool, callback func(msg, detailsJson string)) bool {
+func (t *Toolkit) RunCli(instId uint64, resourcePath, userPath string, directly bool, notify Notification) bool {
cResourcePath := C.CString(resourcePath)
defer C.free(unsafe.Pointer(cResourcePath))
cUserPath := C.CString(userPath)
@@ -207,7 +206,7 @@ func (t *Toolkit) RunCli(instId uint64, resourcePath, userPath string, directly
if directly {
cDirectly = 1
}
- id := notification.RegisterCallback(callback)
+ id := registerNotificationCallback(notify)
got := C.MaaToolkitProjectInterfaceRunCli(
C.uint64_t(instId),
cResourcePath,
diff --git a/toolkit_test.go b/toolkit_test.go
new file mode 100644
index 0000000..6158936
--- /dev/null
+++ b/toolkit_test.go
@@ -0,0 +1,63 @@
+package maa
+
+import (
+ "github.com/stretchr/testify/require"
+ "testing"
+)
+
+func createToolkit(t *testing.T) *Toolkit {
+ toolkit := NewToolkit()
+ require.NotNil(t, toolkit)
+ return toolkit
+}
+
+func TestNewToolkit(t *testing.T) {
+ createToolkit(t)
+}
+
+func TestToolkit_ConfigInitOption(t *testing.T) {
+ toolkit := createToolkit(t)
+ got := toolkit.ConfigInitOption("./test", "{}")
+ require.True(t, got)
+}
+
+func TestToolkit_FindAdbDevices(t *testing.T) {
+ toolkit := createToolkit(t)
+ adbDevices := toolkit.FindAdbDevices()
+ require.NotNil(t, adbDevices)
+}
+
+func TestToolkit_FindDesktopWindows(t *testing.T) {
+ toolkit := createToolkit(t)
+ desktopWindows := toolkit.FindDesktopWindows()
+ require.NotNil(t, desktopWindows)
+}
+
+type testToolKitRec struct{}
+
+func (t *testToolKitRec) Run(_ *Context, _ *CustomRecognitionArg) (CustomRecognitionResult, bool) {
+ return CustomRecognitionResult{}, true
+}
+
+func TestToolkit_RegisterPICustomRecognition(t *testing.T) {
+ toolkit := createToolkit(t)
+ toolkit.RegisterPICustomRecognition(0, "TestRec", &testToolKitRec{})
+}
+
+type testToolkitAct struct{}
+
+func (t testToolkitAct) Run(_ *Context, _ *CustomActionArg) bool {
+ return true
+}
+
+func TestToolkit_RegisterPICustomAction(t *testing.T) {
+ toolkit := createToolkit(t)
+ toolkit.RegisterPICustomAction(0, "TestAct", &testToolkitAct{})
+}
+
+func TestToolkit_ClearPICustom(t *testing.T) {
+ toolkit := createToolkit(t)
+ toolkit.RegisterPICustomRecognition(0, "TestRec", &testToolKitRec{})
+ toolkit.RegisterPICustomAction(0, "TestAct", &testToolkitAct{})
+ toolkit.ClearPICustom(0)
+}