Example usage for android.view.accessibility AccessibilityEvent getEventType

List of usage examples for android.view.accessibility AccessibilityEvent getEventType

Introduction

In this page you can find the example usage for android.view.accessibility AccessibilityEvent getEventType.

Prototype

public @EventType int getEventType() 

Source Link

Document

Gets the event type.

Usage

From source file:com.redinput.datetimepickercompat.time.RadialPickerLayout.java

private void installAccessibilityDelegate() {
    // The accessibility delegate enables customizing accessibility behavior
    // via composition as opposed as inheritance. The main benefit is that
    // one can write a backwards compatible application by setting the delegate
    // only if the API level is high enough i.e. the delegate is part of the APIs.
    // The easiest way to achieve that is by using the support library which
    // takes the burden of checking API version and knowing which API version
    // introduced the delegate off the developer.
    ViewCompat.setAccessibilityDelegate(this, new AccessibilityDelegateCompat() {

        @Override//from www .  j  a  v a2s  .c o  m
        public void onInitializeAccessibilityNodeInfo(View host, AccessibilityNodeInfoCompat info) {
            super.onInitializeAccessibilityNodeInfo(host, info);
            // Note that View.onInitializeAccessibilityNodeInfo was introduced in
            // ICS and we would like to tweak a bit the text that is reported to
            // accessibility services via the AccessibilityNodeInfo.
            info.addAction(AccessibilityNodeInfoCompat.ACTION_SCROLL_FORWARD);
            info.addAction(AccessibilityNodeInfoCompat.ACTION_SCROLL_BACKWARD);
        }

        @Override
        public boolean dispatchPopulateAccessibilityEvent(View host, AccessibilityEvent event) {
            if (event.getEventType() == AccessibilityEvent.TYPE_WINDOW_STATE_CHANGED) {
                // Clear the event's current text so that only the current time will be spoken.
                event.getText().clear();
                Time time = new Time();
                time.hour = getHours();
                time.minute = getMinutes();
                long millis = time.normalize(true);
                int flags = DateUtils.FORMAT_SHOW_TIME;
                if (mIs24HourMode) {
                    flags |= DateUtils.FORMAT_24HOUR;
                }
                String timeString = DateUtils.formatDateTime(getContext(), millis, flags);
                event.getText().add(timeString);
                return true;
            }

            return super.dispatchPopulateAccessibilityEvent(host, event);
        }

        @Override
        public boolean performAccessibilityAction(View host, int action, Bundle args) {
            if (super.performAccessibilityAction(host, action, args)) {
                return true;
            }

            int changeMultiplier = 0;
            if (action == AccessibilityNodeInfoCompat.ACTION_SCROLL_FORWARD) {
                changeMultiplier = 1;
            } else if (action == AccessibilityNodeInfoCompat.ACTION_SCROLL_BACKWARD) {
                changeMultiplier = -1;
            }
            if (changeMultiplier != 0) {
                int value = getCurrentlyShowingValue();
                int stepSize = 0;
                int currentItemShowing = getCurrentItemShowing();
                if (currentItemShowing == HOUR_INDEX) {
                    stepSize = HOUR_VALUE_TO_DEGREES_STEP_SIZE;
                    value %= 12;
                } else if (currentItemShowing == MINUTE_INDEX) {
                    stepSize = MINUTE_VALUE_TO_DEGREES_STEP_SIZE;
                }

                int degrees = value * stepSize;
                degrees = snapOnly30s(degrees, changeMultiplier);
                value = degrees / stepSize;
                int maxValue = 0;
                int minValue = 0;
                if (currentItemShowing == HOUR_INDEX) {
                    if (mIs24HourMode) {
                        maxValue = 23;
                    } else {
                        maxValue = 12;
                        minValue = 1;
                    }
                } else {
                    maxValue = 55;
                }
                if (value > maxValue) {
                    // If we scrolled forward past the highest number, wrap around to the
                    // lowest.
                    value = minValue;
                } else if (value < minValue) {
                    // If we scrolled backward past the lowest number, wrap around to the
                    // highest.
                    value = maxValue;
                }
                setItem(currentItemShowing, value);
                mListener.onValueSelected(currentItemShowing, value, false);
                return true;
            }

            return false;
        }
    });
}

From source file:com.android.screenspeak.eventprocessor.AccessibilityEventProcessor.java

/**
 * Returns whether the device should drop this event. Caches notifications
 * if necessary.//from  w  ww  .  j a v  a 2s.c  o m
 *
 * @param event The current event.
 * @return {@code true} if the event should be dropped.
 */
private boolean shouldDropEvent(AccessibilityEvent event) {
    // Always drop null events.
    if (event == null) {
        return true;
    }

    // Always drop events if the service is suspended.
    if (!ScreenSpeakService.isServiceActive()) {
        return true;
    }

    // If touch exploration is enabled, drop automatically generated events
    // that are sent immediately after a window state change... unless we
    // decide to keep the event.
    if (AccessibilityManagerCompat.isTouchExplorationEnabled(mAccessibilityManager)
            && ((event.getEventType() & AUTOMATIC_AFTER_STATE_CHANGE) != 0)
            && ((event.getEventTime() - mLastWindowStateChanged) < DELAY_AUTO_AFTER_STATE)
            && !shouldKeepAutomaticEvent(event)) {
        if (LogUtils.LOG_LEVEL <= Log.VERBOSE) {
            Log.v(LOGTAG, "Drop event after window state change");
        }
        return true;
    }

    // Real notification events always have parcelable data.
    final boolean isNotification = (event.getEventType() == AccessibilityEvent.TYPE_NOTIFICATION_STATE_CHANGED)
            && (event.getParcelableData() != null);

    final boolean isPhoneActive = (mCallStateMonitor != null)
            && (mCallStateMonitor.getCurrentCallState() != TelephonyManager.CALL_STATE_IDLE);
    final boolean shouldSpeakCallerId = (mSpeakCallerId && (mCallStateMonitor != null)
            && (mCallStateMonitor.getCurrentCallState() == TelephonyManager.CALL_STATE_RINGING));

    if (mRingerModeAndScreenMonitor != null && !mRingerModeAndScreenMonitor.isScreenOn()
            && !shouldSpeakCallerId) {
        if (!mSpeakWhenScreenOff) {
            // If the user doesn't allow speech when the screen is
            // off, drop the event immediately.
            if (LogUtils.LOG_LEVEL <= Log.VERBOSE) {
                Log.v(LOGTAG, "Drop event due to screen state and user pref");
            }
            return true;
        } else if (!isNotification) {
            // If the user allows speech when the screen is off, drop
            // all non-notification events.
            if (LogUtils.LOG_LEVEL <= Log.VERBOSE) {
                Log.v(LOGTAG, "Drop non-notification event due to screen state");
            }
            return true;
        }
    }

    final boolean canInterruptRadialMenu = AccessibilityEventUtils.eventMatchesAnyType(event,
            MASK_EVENT_TYPES_INTERRUPT_RADIAL_MENU);
    final boolean silencedByRadialMenu = (mService.getMenuManager().isMenuShowing() && !canInterruptRadialMenu);

    // Don't speak events that cannot interrupt the radial menu, if showing
    if (silencedByRadialMenu) {
        if (LogUtils.LOG_LEVEL <= Log.VERBOSE) {
            Log.v(LOGTAG, "Drop event due to radial menu state");
        }
        return true;
    }

    // Don't speak notification events if the user is touch exploring or a phone call is active.
    if (isNotification && (mIsUserTouchExploring || isPhoneActive)) {
        if (LogUtils.LOG_LEVEL <= Log.VERBOSE) {
            Log.v(LOGTAG, "Drop notification due to touch or phone state");
        }
        return true;
    }

    final int touchscreenState = mService.getResources().getConfiguration().touchscreen;
    final boolean isTouchInteractionStateChange = AccessibilityEventUtils.eventMatchesAnyType(event,
            MASK_EVENT_TYPES_TOUCH_STATE_CHANGES);

    // Drop all events related to touch interaction state on devices that don't support touch.
    return (touchscreenState == Configuration.TOUCHSCREEN_NOTOUCH) && isTouchInteractionStateChange;
}

From source file:com.borax12.materialdaterangepicker.single.time.RadialPickerLayout.java

/**
 * Announce the currently-selected time when launched.
 *//*  w  w w .j a v a 2  s  . c  o m*/
@Override
public boolean dispatchPopulateAccessibilityEvent(AccessibilityEvent event) {
    if (event.getEventType() == AccessibilityEvent.TYPE_WINDOW_STATE_CHANGED) {
        // Clear the event's current text so that only the current time will be spoken.
        event.getText().clear();
        Calendar time = Calendar.getInstance();
        time.set(Calendar.HOUR, getHours());
        time.set(Calendar.MINUTE, getMinutes());
        time.set(Calendar.SECOND, getSeconds());
        long millis = time.getTimeInMillis();
        int flags = DateUtils.FORMAT_SHOW_TIME;
        if (mIs24HourMode) {
            flags |= DateUtils.FORMAT_24HOUR;
        }
        String timeString = DateUtils.formatDateTime(getContext(), millis, flags);
        event.getText().add(timeString);
        return true;
    }
    return super.dispatchPopulateAccessibilityEvent(event);
}

From source file:com.mojtaba.materialdatetimepicker.time.RadialPickerLayout.java

/**
 * Announce the currently-selected time when launched.
 *//* w  ww. j a v a  2 s  .  c  om*/
@Override
public boolean dispatchPopulateAccessibilityEvent(AccessibilityEvent event) {
    if (event.getEventType() == AccessibilityEvent.TYPE_WINDOW_STATE_CHANGED) {
        // Clear the event's current text so that only the current time will be spoken.
        event.getText().clear();
        Calendar time = Calendar.getInstance();
        time.set(Calendar.HOUR, getHours());
        time.set(Calendar.MINUTE, getMinutes());
        time.set(Calendar.SECOND, getSeconds());
        long millis = time.getTimeInMillis();
        int flags = DateUtils.FORMAT_SHOW_TIME;
        if (mIs24HourMode) {
            flags |= DateUtils.FORMAT_24HOUR;
        }
        String timeString = LanguageUtils
                .getPersianNumbers(DateUtils.formatDateTime(getContext(), millis, flags)); //TODO: Changed Here.
        event.getText().add(timeString);
        return true;
    }
    return super.dispatchPopulateAccessibilityEvent(event);
}

From source file:com.android.talkback.eventprocessor.ProcessorFocusAndSingleTap.java

public boolean isFromRefocusAction(AccessibilityEvent event) {
    long eventTime = event.getEventTime();
    int eventType = event.getEventType();
    if (eventType != AccessibilityEvent.TYPE_VIEW_ACCESSIBILITY_FOCUSED
            && eventType != AccessibilityEvent.TYPE_VIEW_ACCESSIBILITY_FOCUS_CLEARED) {
        return false;
    }/*from  w  w w . j a  v  a  2s .com*/
    AccessibilityNodeInfo source = event.getSource();
    try {
        return mLastRefocusStartTime < eventTime
                && (mLastRefocusEndTime > eventTime || mLastRefocusEndTime < mLastRefocusStartTime)
                && mLastRefocusedNode != null && mLastRefocusedNode.getInfo().equals(source);
    } finally {
        if (source != null) {
            source.recycle();
        }
    }
}

From source file:com.google.android.marvin.mytalkback.ProcessorFocusAndSingleTap.java

@Override
public void onAccessibilityEvent(AccessibilityEvent event) {
    if (!mAccessibilityManager.isTouchExplorationEnabled()) {
        // Don't manage focus when touch exploration is disabled.
        return;/*from   w ww. j  a va2s.  c o  m*/
    }

    final AccessibilityRecordCompat record = new AccessibilityRecordCompat(event);

    switch (event.getEventType()) {
    case AccessibilityEvent.TYPE_VIEW_CLICKED:
        // Prevent conflicts between lift-to-type and single tap. This
        // is only necessary when a CLICKED event occurs during a touch
        // interaction sequence (e.g. before an INTERACTION_END event),
        // but it isn't harmful to call more often.
        cancelSingleTap();
        break;
    case AccessibilityEvent.TYPE_VIEW_FOCUSED:
        setFocusFromViewFocused(event, record);
        break;
    case AccessibilityEvent.TYPE_VIEW_SELECTED:
        setFocusFromViewSelected(event, record);
        break;
    case AccessibilityEvent.TYPE_VIEW_HOVER_ENTER:
        setFocusFromViewHoverEnter(record);
        break;
    case AccessibilityEvent.TYPE_WINDOW_STATE_CHANGED:
        handleWindowStateChange(event);
        break;
    case AccessibilityEvent.TYPE_WINDOW_CONTENT_CHANGED:
        handleWindowContentChanged(record);
        break;
    case AccessibilityEvent.TYPE_VIEW_SCROLLED:
        handleViewScrolled(event, record);
        break;
    case AccessibilityEventCompat.TYPE_TOUCH_INTERACTION_START:
        // This event type only exists on API 17+ (JB MR1).
        handleTouchInteractionStart(event);
        break;
    case AccessibilityEventCompat.TYPE_TOUCH_INTERACTION_END:
        // This event type only exists on API 17+ (JB MR1).
        handleTouchInteractionEnd(event);
        break;
    }
}

From source file:com.ucmap.dingdinghelper.services.DingDingHelperAccessibilityService.java

/**
 * ???/*from  w  w  w .j  a  v a  2s .c  om*/
 */
@RequiresApi(api = Build.VERSION_CODES.KITKAT)
@Override
public void onAccessibilityEvent(AccessibilityEvent event) {
    tag_callback_time = System.currentTimeMillis();
    int eventType = event.getEventType();

    Log.i("Info",
            " eventType: " + eventType + "   getEventTime:  " + event.getEventTime() + "     getAction"
                    + event.getAction() + "getContentChangeTypes:" + event.getContentChangeTypes()
                    + " getText :" + event.getText().toString() + "getPackageName :" + event.getPackageName()
                    + "getRecordCount : " + event.getRecordCount() + "  getClassName:" + event.getClassName()
                    + "  :" + event.getClass() + "   getParcelableData:" + event.getParcelableData());

    switch (eventType) {
    /*??*/
    case AccessibilityEvent.TYPE_WINDOW_CONTENT_CHANGED:
        windowContentChanged();
        break;
    //???
    case AccessibilityEvent.TYPE_NOTIFICATION_STATE_CHANGED:
        notificationChanged(event);
        break;
    //Activity???
    case AccessibilityEvent.TYPE_WINDOW_STATE_CHANGED:
        windowChanged(event);
        break;
    }
}

From source file:com.google.android.marvin.talkback.ProcessorFocusAndSingleTap.java

@Override
public void onAccessibilityEvent(AccessibilityEvent event) {
    if (!mAccessibilityManager.isTouchExplorationEnabled()) {
        // Don't manage focus when touch exploration is disabled.
        return;/*from  ww  w  . j  a v  a  2s.  c  o  m*/
    }

    final AccessibilityRecordCompat record = new AccessibilityRecordCompat(event);

    switch (event.getEventType()) {
    case AccessibilityEvent.TYPE_VIEW_CLICKED:
        // Prevent conflicts between lift-to-type and single tap. This
        // is only necessary when a CLICKED event occurs during a touch
        // interaction sequence (e.g. before an INTERACTION_END event),
        // but it isn't harmful to call more often.
        cancelSingleTap();
        break;
    case AccessibilityEvent.TYPE_VIEW_FOCUSED:
        setFocusFromViewFocused(event, record);
        break;
    case AccessibilityEvent.TYPE_VIEW_SELECTED:
        setFocusFromViewSelected(event, record);
        break;
    case AccessibilityEvent.TYPE_VIEW_HOVER_ENTER:
        final AccessibilityNodeInfoCompat touchedNode = record.getSource();
        try {
            if ((touchedNode != null) && !setFocusFromViewHoverEnter(touchedNode) && FEATURE_FLAG_EMPTY_SPACE) {
                mHandler.sendEmptyTouchAreaFeedbackDelayed(touchedNode);
            }
        } finally {
            AccessibilityNodeInfoUtils.recycleNodes(touchedNode);
        }

        break;
    case AccessibilityEvent.TYPE_VIEW_ACCESSIBILITY_FOCUSED:
        mHandler.cancelEmptyTouchAreaFeedback();
        break;
    case AccessibilityEvent.TYPE_WINDOW_STATE_CHANGED:
        handleWindowStateChange(event);
        break;
    case AccessibilityEvent.TYPE_WINDOW_CONTENT_CHANGED:
        handleWindowContentChanged(record);
        break;
    case AccessibilityEvent.TYPE_VIEW_SCROLLED:
        handleViewScrolled(event, record);
        break;
    case AccessibilityEventCompat.TYPE_TOUCH_INTERACTION_START:
        // This event type only exists on API 17+ (JB MR1).
        handleTouchInteractionStart(event);
        break;
    case AccessibilityEventCompat.TYPE_TOUCH_INTERACTION_END:
        // This event type only exists on API 17+ (JB MR1).
        handleTouchInteractionEnd(event);
        break;
    }
}

From source file:com.android.talkback.eventprocessor.AccessibilityEventProcessor.java

/**
 * Returns whether the device should drop this event. Caches notifications
 * if necessary./*ww w  .  j av a2 s  .c o m*/
 *
 * @param event The current event.
 * @return {@code true} if the event should be dropped.
 */
private boolean shouldDropEvent(AccessibilityEvent event) {
    // Always drop null events.
    if (event == null) {
        return true;
    }

    // Always drop events if the service is suspended.
    if (!TalkBackService.isServiceActive()) {
        return true;
    }

    // If touch exploration is enabled, drop automatically generated events
    // that are sent immediately after a window state change... unless we
    // decide to keep the event.
    if (AccessibilityManagerCompat.isTouchExplorationEnabled(mAccessibilityManager)
            && ((event.getEventType() & AUTOMATIC_AFTER_STATE_CHANGE) != 0)
            && ((event.getEventTime() - mLastWindowStateChanged) < DELAY_AUTO_AFTER_STATE)
            && !shouldKeepAutomaticEvent(event)) {
        if (LogUtils.LOG_LEVEL <= Log.VERBOSE) {
            Log.v(LOGTAG, "Drop event after window state change");
        }
        return true;
    }

    // Some view-selected events are spurious if sent immediately after a focused event.
    if (event.getEventType() == AccessibilityEvent.TYPE_VIEW_SELECTED && !shouldKeepViewSelectedEvent(event)) {
        if (LogUtils.LOG_LEVEL <= Log.VERBOSE) {
            Log.v(LOGTAG, "Drop selected event after focused event");
        }
        return true;
    }

    // Real notification events always have parcelable data.
    final boolean isNotification = (event.getEventType() == AccessibilityEvent.TYPE_NOTIFICATION_STATE_CHANGED)
            && (event.getParcelableData() != null);

    final boolean isPhoneActive = (mCallStateMonitor != null)
            && (mCallStateMonitor.getCurrentCallState() != TelephonyManager.CALL_STATE_IDLE);
    final boolean isPhoneRinging = (mCallStateMonitor != null)
            && (mCallStateMonitor.getCurrentCallState() == TelephonyManager.CALL_STATE_RINGING);

    // Sometimes the dialer's window-state-changed event gets sent right before the
    // TelephonyManager transitions to CALL_STATE_RINGING, so we need to check isDialerEvent().
    final boolean shouldSpeakCallerId = isPhoneRinging || isDialerEvent(event);

    if (mRingerModeAndScreenMonitor != null && !mRingerModeAndScreenMonitor.isScreenOn()
            && !shouldSpeakCallerId) {
        if (!mSpeakWhenScreenOff) {
            // If the user doesn't allow speech when the screen is
            // off, drop the event immediately.
            if (LogUtils.LOG_LEVEL <= Log.VERBOSE) {
                Log.v(LOGTAG, "Drop event due to screen state and user pref");
            }
            return true;
        } else if (!isNotification) {
            // If the user allows speech when the screen is off, drop
            // all non-notification events.
            if (LogUtils.LOG_LEVEL <= Log.VERBOSE) {
                Log.v(LOGTAG, "Drop non-notification event due to screen state");
            }
            return true;
        }
    }

    final boolean canInterruptRadialMenu = AccessibilityEventUtils.eventMatchesAnyType(event,
            MASK_EVENT_TYPES_INTERRUPT_RADIAL_MENU);
    final boolean silencedByRadialMenu = (mService.getMenuManager().isMenuShowing() && !canInterruptRadialMenu);

    // Don't speak events that cannot interrupt the radial menu, if showing
    if (silencedByRadialMenu) {
        if (LogUtils.LOG_LEVEL <= Log.VERBOSE) {
            Log.v(LOGTAG, "Drop event due to radial menu state");
        }
        return true;
    }

    // Don't speak notification events if the user is touch exploring or a phone call is active.
    if (isNotification && (mIsUserTouchExploring || isPhoneActive)) {
        if (LogUtils.LOG_LEVEL <= Log.VERBOSE) {
            Log.v(LOGTAG, "Drop notification due to touch or phone state");
        }
        return true;
    }

    final int touchscreenState = mService.getResources().getConfiguration().touchscreen;
    final boolean isTouchInteractionStateChange = AccessibilityEventUtils.eventMatchesAnyType(event,
            MASK_EVENT_TYPES_TOUCH_STATE_CHANGES);

    // Drop all events related to touch interaction state on devices that don't support touch.
    return (touchscreenState == Configuration.TOUCHSCREEN_NOTOUCH) && isTouchInteractionStateChange;
}

From source file:com.android.screenspeak.eventprocessor.ProcessorFocusAndSingleTap.java

@Override
public void onAccessibilityEvent(AccessibilityEvent event) {
    if (!mAccessibilityManager.isTouchExplorationEnabled()) {
        // Don't manage focus when touch exploration is disabled.
        return;/*ww w .j a v  a 2s.com*/
    }

    final AccessibilityRecordCompat record = AccessibilityEventCompat.asRecord(event);

    switch (event.getEventType()) {
    case AccessibilityEvent.TYPE_VIEW_CLICKED:
        // Prevent conflicts between lift-to-type and single tap. This
        // is only necessary when a CLICKED event occurs during a touch
        // interaction sequence (e.g. before an INTERACTION_END event),
        // but it isn't harmful to call more often.
        cancelSingleTap();
        break;
    case AccessibilityEvent.TYPE_VIEW_FOCUSED:
    case AccessibilityEvent.TYPE_VIEW_SELECTED:
        if (!mFirstWindowFocusManager.shouldProcessFocusEvent(event)) {
            return;
        }
        boolean isViewFocusedEvent = (AccessibilityEvent.TYPE_VIEW_FOCUSED == event.getEventType());
        if (!setFocusOnView(record, isViewFocusedEvent)) {
            // It is possible that the only speakable child of source node is invisible
            // at the moment, but could be made visible when view scrolls, or window state
            // changes. Cache it now. And try to focus on the cached record on:
            // VIEW_SCROLLED, WINDOW_CONTENT_CHANGED, WINDOW_STATE_CHANGED.
            // The above 3 are the events that could affect view visibility.
            if (mCachedPotentiallyFocusableRecordQueue.size() == MAX_CACHED_FOCUSED_RECORD_QUEUE) {
                mCachedPotentiallyFocusableRecordQueue.remove().first.recycle();
            }

            mCachedPotentiallyFocusableRecordQueue
                    .add(new Pair<>(AccessibilityRecordCompat.obtain(record), event.getEventType()));
        } else {
            emptyCachedPotentialFocusQueue();
        }
        break;
    case AccessibilityEvent.TYPE_VIEW_HOVER_ENTER:
        final AccessibilityNodeInfoCompat touchedNode = record.getSource();
        try {
            if ((touchedNode != null) && !setFocusFromViewHoverEnter(touchedNode)) {
                mHandler.sendEmptyTouchAreaFeedbackDelayed(touchedNode);
            }
        } finally {
            AccessibilityNodeInfoUtils.recycleNodes(touchedNode);
        }

        break;
    case AccessibilityEvent.TYPE_VIEW_ACCESSIBILITY_FOCUSED:
        mHandler.cancelEmptyTouchAreaFeedback();
        AccessibilityNodeInfo source = event.getSource();
        if (source != null) {
            AccessibilityNodeInfoCompat compatSource = new AccessibilityNodeInfoCompat(source);
            mLastFocusedItem = AccessibilityNodeInfoCompat.obtain(compatSource);
        }
        break;
    case AccessibilityEvent.TYPE_WINDOW_STATE_CHANGED:
        mFirstWindowFocusManager.registerWindowChange(event);
        handleWindowStateChange(event);
        break;
    case AccessibilityEvent.TYPE_WINDOW_CONTENT_CHANGED:
        handleWindowContentChanged();
        break;
    case AccessibilityEvent.TYPE_VIEW_SCROLLED:
        handleViewScrolled(event, record);
        break;
    case AccessibilityEventCompat.TYPE_TOUCH_INTERACTION_START:
        // This event type only exists on API 17+ (JB MR1).
        handleTouchInteractionStart();
        break;
    case AccessibilityEventCompat.TYPE_TOUCH_INTERACTION_END:
        // This event type only exists on API 17+ (JB MR1).
        handleTouchInteractionEnd();
        break;
    }
}