Autox.js 中文文档 下载 App

Autox.js 控件选择器基础 text id className desc 四种属性定位

Autox.js 的核心:选择器 API

如果说无障碍服务是 Autox.js 的眼睛,那选择器 API 就是它的大脑。整个自动化体系建立在这套 API 之上——用它们来"找到"屏幕上的控件,然后对找到的控件发送动作。

选择器的四件事

所有选择器调用最后都落到这四件事:

操作函数返回
创建选择器text("登录")一个 Selector 对象
查找一个匹配.findOne(timeout?)第一个匹配的控件或 null
查找全部匹配.find()所有匹配控件的数组
等待出现.until(timeout?)等待匹配控件出现,期间会自动刷新

四种基础属性选择器

1. text() — 按显示文字

text("确定").click();

匹配屏幕上所有显示文字为"确定"的控件。最直观、最容易用,但稳定性一般——App 改版改了文字就失效。

2. id() — 按资源 ID

id("confirm_btn").click();
// 或完整包名
id("com.example:id/confirm_btn").click();

匹配控件的 resource-id。id 是最稳定的选择器——开发者在代码里写死了,除非 App 重构或混淆,一般不会变。但注意:不是所有控件都有 id(自定义 View 可能没有、游戏引擎的控件一定没有)。

3. className() — 按类名

className("Button").click();
className("android.widget.Button").click();  // 完整类名

匹配控件的 Java 类名。Android 标准控件的类名一般是 android.widget.Button、android.widget.EditText 这样。只用短名 "Button" 会匹配所有包下叫 Button 的类。

4. desc() — 按无障碍描述

desc("登录按钮").click();

匹配 contentDescription,这是开发者为残障用户添加的无障碍描述。很多 App 没填这个字段,所以用的人不多,但如果有,稳定性和 id 差不多。

组合选择器

单个条件可能匹配到太多控件,这时可以链式叠加多个条件:

// 既是 Button 类、又显示"确定"文字
className("Button").text("确定").click();

// id 是 btn_confirm 且 desc 是确认
id("btn_confirm").desc("确认").click();

模糊匹配变体

Autox.js 的选择器还提供了模糊匹配版本:

精确模糊作用
text("确定")textContains("确定")包含"确定"文字
textStartsWith("确")以"确"开头
textEndsWith("定")以"定"结尾
textMatches("确.定")正则匹配
id("btn")idContains("btn")id 包含
className("Button")classNameContains("Button")类名包含
desc("登录")descContains("登录")desc 包含

模糊匹配在不知道精确值时很有用,但优先级低于精确匹配——能用精确值时别偷懒。

从父控件查找子控件

// 从 id 为 container 的父容器中找 Button
id("container").findOne().findOne(className("Button")).click();

// 或者直接 descendants 遍历
id("container").findOne().descendants()
    .filter(c => c.className() === "Button")
    .forEach(c => c.click());

这招在"屏幕上有多个同名 Button,但只有某个特定容器里的那个是我要的"时特别有用。

实战代码示例

假设你要在一个登录页面自动填写并提交:

console.show();

// 等待登录页加载(最多 10 秒)
if (!text("登录").findOne(10000)) {
    console.error("登录页加载超时");
    exit();
}

console.log("登录页已就绪");

// 找到账号输入框并填入
let username = className("EditText").id("username_input").findOne();
if (username) {
    username.setText("myaccount");
    console.log("账号填写完成");
}

// 找到密码输入框并填入
let password = className("EditText").id("password_input").findOne();
if (password) {
    password.setText("123456");
    console.log("密码填写完成");
}

// 点击登录
let loginBtn = className("Button").text("登录").findOne();
if (loginBtn) {
    loginBtn.click();
    console.log("登录按钮已点击");
} else {
    console.error("没找到登录按钮");
}

性能提示

选择器查找是昂贵操作(每次查找都要遍历整个控件树),注意: