远程控屏场景下Android辅助服务多点触控间隔按压触发onCancelled问题
针对你遇到的多点间隔按压手势触发onCancelled的问题,结合AccessibilityService.dispatchGesture的特性,可从以下几个方向排查解决:
校验笔触的时间参数逻辑
系统对GestureDescription中各笔触的时间戳校验非常严格,若后一个笔触的startTime与前一个笔触的时间线冲突(比如startTime早于前一个笔触的结束时间,或间隔时间设置不合理),会直接判定手势无效并触发取消回调。
正确的时间计算方式应为:后续笔触的startTime = 前一个笔触的startTime + 前一个笔触的duration + 预期间隔时间。确保每个笔触的时间区间完全独立,无重叠。检查笔触路径的合法性
虽然单个笔触可正常执行,但组合时若存在空路径、坐标超出屏幕范围,或路径不符合系统手势的隐性规则(部分安卓版本对多点手势的路径独立性有要求),也会导致手势被取消。需确认每个Path对象都有有效的移动/点击动作,且坐标在当前屏幕的分辨率范围内。调整GestureDescription的构建顺序
部分安卓版本的GestureDescription会优先按添加顺序处理笔触,而非严格按startTime排序。建议将笔触按时间先后顺序添加到Builder中,避免因顺序问题导致时序解析错误。排查系统兼容性与冲突
不同安卓版本对AccessibilityService手势的校验逻辑有差异,尤其是Android 10及以上版本对多点手势的限制更严格。同时需检查是否有其他辅助服务、系统导航手势或第三方悬浮工具正在运行,这类应用可能会中断自定义手势的执行。
示例代码:构建间隔按压的多点手势
// 第一个笔触:在(500,500)位置点击,持续100ms Path firstTapPath = new Path(); firstTapPath.moveTo(500f, 500f); StrokeDescription firstStroke = new StrokeDescription(firstTapPath, 0L, 100L); // 第二个笔触:间隔200ms后,在(1000,1000)位置点击,持续100ms long intervalMs = 200L; long secondStrokeStartTime = firstStroke.getStartTime() + firstStroke.getDuration() + intervalMs; Path secondTapPath = new Path(); secondTapPath.moveTo(1000f, 1000f); StrokeDescription secondStroke = new StrokeDescription(secondTapPath, secondStrokeStartTime, 100L); // 构建并分发手势 GestureDescription intervalGesture = new GestureDescription.Builder() .addStroke(firstStroke) .addStroke(secondStroke) .build(); dispatchGesture(intervalGesture, new GestureResultCallback() { @Override public void onCompleted(GestureDescription gesture) { // 手势执行成功 } @Override public void onCancelled(GestureDescription gesture) { // 排查时间参数或路径合法性 } }, null);
内容的提问来源于stack exchange,提问作者z.houbin

