Click on the Notification programmatically

2019-01-09 14:14发布

问题:

I trying click on the notification after receiving it.

I'm able to drag the notification drawer using the Accessibility service.

For clicking the notification I'm using accessibilityEvent.getSource() and accessibilityNodeInfo.performAction(AccessibilityNodeInfo.ACTION_CLICK);

My code:

public class MyAccessibilityService extends AccessibilityService {

/**
 * On receiving the AccessibilityEvent performs the Actions
 *
 * @param event
 */
@Override
public void onAccessibilityEvent(AccessibilityEvent event) {
    Log.i(TAG, "Get the Accessibility Event");
    if (event.getEventType() == AccessibilityEvent.TYPE_TOUCH_INTERACTION_END) {
        handleTypeTouchInteractionEndEvents(event);
    }
    if (event.getEventType() == AccessibilityEvent.TYPE_WINDOW_STATE_CHANGED) {
        handleTypeWindowStateChangedEvents(event);
    }
}

@Override
public void onServiceConnected() {
    AccessibilityServiceInfo accessibilityServiceInfo = new AccessibilityServiceInfo();
    accessibilityServiceInfo.eventTypes = AccessibilityEvent.TYPE_TOUCH_INTERACTION_END | AccessibilityEvent.TYPE_VIEW_CLICKED |
            AccessibilityEvent.TYPE_VIEW_FOCUSED | AccessibilityEvent.TYPE_WINDOW_CONTENT_CHANGED | AccessibilityEvent.TYPE_WINDOW_STATE_CHANGED;
    accessibilityServiceInfo.feedbackType = AccessibilityServiceInfo.CAPABILITY_CAN_PERFORM_GESTURES;
    accessibilityServiceInfo.flags = AccessibilityServiceInfo.DEFAULT | AccessibilityServiceInfo.FLAG_RETRIEVE_INTERACTIVE_WINDOWS;
    accessibilityServiceInfo.notificationTimeout = NOTIFICATION_TIME_OUT;
    this.setServiceInfo(accessibilityServiceInfo);
}

@Override
public void onInterrupt() {
    //Do Nothing
}

/**
 * Performs the action for TYPE_TOUCH_INTERACTION_END events
 *
 * @param accessibilityEvent
 */
private void handleTypeTouchInteractionEndEvents(AccessibilityEvent accessibilityEvent) {
    switch (accessibilityEvent.getAction()) {
        case EXPAND_NOTIFICATIONS_DRAWER:
            Log.i(TAG, "perfroming expand notification bar");         performGlobalAction(AccessibilityService.GLOBAL_ACTION_NOTIFICATIONS);
            break;
        default:
            Log.i(TAG, "Event type not defined");
    }
}

private void handleTypeWindowStateChangedEvents(AccessibilityEvent accessibilityEvent) {
    switch (accessibilityEvent.getAction()) {
        case ACTION_CLICK:
            Log.i(TAG, "Performing click Action");
            findNotificationIconAndClick("com.my.app:id/notification_icon", accessibilityEvent);
            Log.i(TAG, "Click Action is successfull");
        default:
            Log.i(TAG, "Event type not defined");
    }
}


public void findNotificationIconAndClick(String id, AccessibilityEvent accessibilityEvent) {
    AccessibilityNodeInfo accessibilityNodeInfo = accessibilityEvent.getSource();
    List<AccessibilityNodeInfo> nodeInfoList = accessibilityNodeInfo.findAccessibilityNodeInfosByViewId(id);
    if (nodeInfoList != null && !nodeInfoList.isEmpty()) {
        for (AccessibilityNodeInfo nodeInfo : nodeInfoList) {
            if (nodeInfo != null) {
                performClick(nodeInfo);
                break;
            }
        }
    }
}
}

I'm new to using accessibility service. Can someone tell me if there is any mistake from my side or if it is not possible to click on a notification using accessibility service? Are there any other possibilities without using Accessibility Service to click on the Notification?

回答1:

Not all accessibility events will return a source. In fact, most (or at least the events that occur most frequently) do not. Make sure you're limiting to a reasonable subset of events in your configuration AND/OR doing a null check on event.getSource().



回答2:

If you want to click on the notification, you have to extend the NotificationListenerService, implement what have to be implemented then you can call sbn.getNotification().contentIntent.send(). This way is like if user was clicking on the notification from the notification tray.