Да, это возможно После двухдневного расследования я нашел решение.
Требование: Откройте приложение системной камеры и нажмите на картинку.
Шаг 1:
Добавьте разрешение камеры в файл манифеста:
<uses-permission android:name="android.permission.CAMERA"/>
<uses-feature
android:name="android.hardware.camera"
android:required="false" />
<uses-feature
android:name="android.hardware.camera.front"
android:required="false" />
Шаг 2. Создайте одну службу, которая расширяет AccessibilityService.
<service
android:name=".AccessTest"
android:enabled="true"
android:permission="android.permission.BIND_ACCESSIBILITY_SERVICE"
android:exported="true">
<intent-filter>
<action android:name="android.accessibilityservice.AccessibilityService" />
</intent-filter>
<meta-data
android:name="android.accessibilityservice"
android:resource="@xml/accessibility_service_config"/>
</service>
Шаг 3. Запустите службу, когда вам это потребуется.
Intent mailAccessabilityIntent = new Intent(getApplicationContext(), AccessTest.class);
startService(mailAccessabilityIntent);
Шаг 4. Добавьте файл специальных возможностей.
<?xml version="1.0" encoding="utf-8"?>
<accessibility-service xmlns:android="http://schemas.android.com/apk/res/android"
android:accessibilityEventTypes="typeAllMask"
android:accessibilityFeedbackType="feedbackAllMask"
android:accessibilityFlags="flagEnableAccessibilityVolume"
android:canRetrieveWindowContent="true"
android:notificationTimeout="100"
android:packageNames="com.google.android.GoogleCamera"
android:settingsActivity="com.mobiliya.cameraautoclick.MainActivity" />
Шаг 5. Напишите класс обслуживания, в котором вы хотите обрабатывать прослушиватель, связанный с камерой.
public class AccessTest extends AccessibilityService {
private final static String TAG = "Yogesh";
@Override
public void onCreate() {
super.onCreate();
Log.d("Yogesh","I am started");
}
@Override
protected void onServiceConnected() {
super.onServiceConnected();
Log.d(TAG, "onServiceConnected");
}
@Override
public void onAccessibilityEvent(AccessibilityEvent event) {
Log.d(TAG, "ACC::onAccessibilityEvent: " + event.getEventType());
//TYPE_WINDOW_STATE_CHANGED == 32
if (AccessibilityEvent.TYPE_WINDOW_STATE_CHANGED == event
.getEventType()) {
AccessibilityNodeInfo nodeInfo = event.getSource();
if (nodeInfo == null) {
return;
}
Intent takePictureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
String x = takePictureIntent.resolveActivity(getPackageManager()).getPackageName();
Log.d("Yogesh","Package name " + x);
List<AccessibilityNodeInfo> list1 = nodeInfo.findAccessibilityNodeInfosByText("Switch to front camera");
for (AccessibilityNodeInfo node : list1) {
Log.i(TAG, "ACC::onAccessibilityEvent: click " + node);
node.performAction(AccessibilityNodeInfo.ACTION_CLICK);
}
final List<AccessibilityNodeInfo> list = nodeInfo.findAccessibilityNodeInfosByText("Take photo");
final android.os.Handler handler = new android.os.Handler();
handler.postDelayed(new Runnable() {
@Override
public void run() {
for (AccessibilityNodeInfo node : list) {
Log.i(TAG, "ACC::onAccessibilityEvent: click " + node);
node.performAction(AccessibilityNodeInfo.ACTION_CLICK);
}
handler.postDelayed(this,5000);
}
},10000);
for (AccessibilityNodeInfo node : list) {
Log.i(TAG, "ACC::onAccessibilityEvent: click " + node);
node.performAction(AccessibilityNodeInfo.ACTION_CLICK);
}
Log.d(TAG,"Access " + getAllChildNodeText(nodeInfo).toString());
}
}
private List<CharSequence> getAllChildNodeText(AccessibilityNodeInfo infoCompat) {
List<CharSequence> contents = new ArrayList<>();
if (infoCompat == null)
return contents;
if (infoCompat.getContentDescription() != null) {
contents.add(infoCompat.getContentDescription().toString().isEmpty() ? "unlabelled" : infoCompat.getContentDescription());
} else if (infoCompat.getText() != null) {
contents.add(infoCompat.getText().toString().isEmpty() ? "unlabelled" : infoCompat.getText());
} else {
getTextInChildren(infoCompat, contents);
}
if (infoCompat.isClickable()) {
if (infoCompat.getClassName().toString().contains(Button.class.getSimpleName())) {
if (contents.size() == 0) {
contents.add("Unlabelled button");
} else {
contents.add("button");
}
}
contents.add("Double tap to activate");
}
return contents;
}
private void getTextInChildren(AccessibilityNodeInfo nodeInfoCompat, List<CharSequence> contents) {
if (nodeInfoCompat == null)
return;
if (!nodeInfoCompat.isScrollable()) {
if (nodeInfoCompat.getContentDescription() != null) {
contents.add(nodeInfoCompat.getContentDescription());
} else if (nodeInfoCompat.getText() != null) {
contents.add(nodeInfoCompat.getText());
}
if (nodeInfoCompat.getChildCount() > 0) {
for (int i = 0; i < nodeInfoCompat.getChildCount(); i++) {
if (nodeInfoCompat.getChild(i) != null) {
getTextInChildren(nodeInfoCompat.getChild(i), contents);
}
}
}
}
}
@Override
public void onInterrupt() {
}
}
Здесь getAllChildNodeText() возвращает всю текстовую кнопку, на которую можно нажать, приложение Google по умолчанию имеет Take Photo
текст, поэтому для этого представления вы можете выполнить действие.
Добавлен обработчик для захвата изображения каждые 10 секунд для большей ясности.
Если вы хотите отслеживать приложение с несколькими камерами, удалите строку ниже и используйте код Java для более подробной информации о пакете. noreferrer">Служба специальных возможностей
android:packageNames="com.google.android.GoogleCamera"
Я загрузил рабочий пример -> https://github.com/ycrathi/cameraautoclick а>
Примечание. В приведенном выше репозитории GitHub есть несколько нежелательных кодов, которые я пробовал.
Это решение не является глобальным для всех приложений. Вы можете найти какое-нибудь известное приложение, такое как google camera, найти текст, а затем выполнить действие с пакетом кликов.
person
Yogesh Rathi
schedule
27.11.2018