AccessibilityInteractionControllerpublic final class AccessibilityInteractionController extends Object Class for managing accessibility interactions initiated from the system
and targeting the view hierarchy. A *ClientThread method is to be
called from the interaction connection ViewAncestor gives the system to
talk to it and a corresponding *UiThread method that is executed on the
UI thread. |
Fields Summary |
---|
private static final boolean | ENFORCE_NODE_TREE_CONSISTENT | private final ArrayList | mTempAccessibilityNodeInfoList | private final android.os.Handler | mHandler | private final ViewRootImpl | mViewRootImpl | private final AccessibilityNodePrefetcher | mPrefetcher | private final long | mMyLooperThreadId | private final int | mMyProcessId | private final ArrayList | mTempArrayList | private final android.graphics.Point | mTempPoint | private final android.graphics.Rect | mTempRect | private final android.graphics.Rect | mTempRect1 | private final android.graphics.Rect | mTempRect2 | private AddNodeInfosForViewId | mAddNodeInfosForViewId |
Constructors Summary |
---|
public AccessibilityInteractionController(ViewRootImpl viewRootImpl)
Looper looper = viewRootImpl.mHandler.getLooper();
mMyLooperThreadId = looper.getThread().getId();
mMyProcessId = Process.myPid();
mHandler = new PrivateHandler(looper);
mViewRootImpl = viewRootImpl;
mPrefetcher = new AccessibilityNodePrefetcher();
|
Methods Summary |
---|
private void | adjustIsVisibleToUserIfNeeded(java.util.List infos, android.graphics.Region interactiveRegion)
if (interactiveRegion == null || infos == null) {
return;
}
final int infoCount = infos.size();
for (int i = 0; i < infoCount; i++) {
AccessibilityNodeInfo info = infos.get(i);
adjustIsVisibleToUserIfNeeded(info, interactiveRegion);
}
| private void | adjustIsVisibleToUserIfNeeded(android.view.accessibility.AccessibilityNodeInfo info, android.graphics.Region interactiveRegion)
if (interactiveRegion == null || info == null) {
return;
}
Rect boundsInScreen = mTempRect;
info.getBoundsInScreen(boundsInScreen);
if (interactiveRegion.quickReject(boundsInScreen)) {
info.setVisibleToUser(false);
}
| private void | applyAppScaleAndMagnificationSpecIfNeeded(java.util.List infos, MagnificationSpec spec)
if (infos == null) {
return;
}
final float applicationScale = mViewRootImpl.mAttachInfo.mApplicationScale;
if (shouldApplyAppScaleAndMagnificationSpec(applicationScale, spec)) {
final int infoCount = infos.size();
for (int i = 0; i < infoCount; i++) {
AccessibilityNodeInfo info = infos.get(i);
applyAppScaleAndMagnificationSpecIfNeeded(info, spec);
}
}
| private void | applyAppScaleAndMagnificationSpecIfNeeded(android.graphics.Point point, MagnificationSpec spec)
final float applicationScale = mViewRootImpl.mAttachInfo.mApplicationScale;
if (!shouldApplyAppScaleAndMagnificationSpec(applicationScale, spec)) {
return;
}
if (applicationScale != 1.0f) {
point.x *= applicationScale;
point.y *= applicationScale;
}
if (spec != null) {
point.x *= spec.scale;
point.y *= spec.scale;
point.x += (int) spec.offsetX;
point.y += (int) spec.offsetY;
}
| private void | applyAppScaleAndMagnificationSpecIfNeeded(android.view.accessibility.AccessibilityNodeInfo info, MagnificationSpec spec)
if (info == null) {
return;
}
final float applicationScale = mViewRootImpl.mAttachInfo.mApplicationScale;
if (!shouldApplyAppScaleAndMagnificationSpec(applicationScale, spec)) {
return;
}
Rect boundsInParent = mTempRect;
Rect boundsInScreen = mTempRect1;
info.getBoundsInParent(boundsInParent);
info.getBoundsInScreen(boundsInScreen);
if (applicationScale != 1.0f) {
boundsInParent.scale(applicationScale);
boundsInScreen.scale(applicationScale);
}
if (spec != null) {
boundsInParent.scale(spec.scale);
// boundsInParent must not be offset.
boundsInScreen.scale(spec.scale);
boundsInScreen.offset((int) spec.offsetX, (int) spec.offsetY);
}
info.setBoundsInParent(boundsInParent);
info.setBoundsInScreen(boundsInScreen);
if (spec != null) {
AttachInfo attachInfo = mViewRootImpl.mAttachInfo;
if (attachInfo.mDisplay == null) {
return;
}
final float scale = attachInfo.mApplicationScale * spec.scale;
Rect visibleWinFrame = mTempRect1;
visibleWinFrame.left = (int) (attachInfo.mWindowLeft * scale + spec.offsetX);
visibleWinFrame.top = (int) (attachInfo.mWindowTop * scale + spec.offsetY);
visibleWinFrame.right = (int) (visibleWinFrame.left + mViewRootImpl.mWidth * scale);
visibleWinFrame.bottom = (int) (visibleWinFrame.top + mViewRootImpl.mHeight * scale);
attachInfo.mDisplay.getRealSize(mTempPoint);
final int displayWidth = mTempPoint.x;
final int displayHeight = mTempPoint.y;
Rect visibleDisplayFrame = mTempRect2;
visibleDisplayFrame.set(0, 0, displayWidth, displayHeight);
visibleWinFrame.intersect(visibleDisplayFrame);
if (!visibleWinFrame.intersects(boundsInScreen.left, boundsInScreen.top,
boundsInScreen.right, boundsInScreen.bottom)) {
info.setVisibleToUser(false);
}
}
| public void | findAccessibilityNodeInfoByAccessibilityIdClientThread(long accessibilityNodeId, android.graphics.Region interactiveRegion, int interactionId, android.view.accessibility.IAccessibilityInteractionConnectionCallback callback, int flags, int interrogatingPid, long interrogatingTid, MagnificationSpec spec)
Message message = mHandler.obtainMessage();
message.what = PrivateHandler.MSG_FIND_ACCESSIBILITY_NODE_INFO_BY_ACCESSIBILITY_ID;
message.arg1 = flags;
SomeArgs args = SomeArgs.obtain();
args.argi1 = AccessibilityNodeInfo.getAccessibilityViewId(accessibilityNodeId);
args.argi2 = AccessibilityNodeInfo.getVirtualDescendantId(accessibilityNodeId);
args.argi3 = interactionId;
args.arg1 = callback;
args.arg2 = spec;
args.arg3 = interactiveRegion;
message.obj = args;
// If the interrogation is performed by the same thread as the main UI
// thread in this process, set the message as a static reference so
// after this call completes the same thread but in the interrogating
// client can handle the message to generate the result.
if (interrogatingPid == mMyProcessId && interrogatingTid == mMyLooperThreadId) {
AccessibilityInteractionClient.getInstanceForThread(
interrogatingTid).setSameThreadMessage(message);
} else {
mHandler.sendMessage(message);
}
| private void | findAccessibilityNodeInfoByAccessibilityIdUiThread(android.os.Message message)
final int flags = message.arg1;
SomeArgs args = (SomeArgs) message.obj;
final int accessibilityViewId = args.argi1;
final int virtualDescendantId = args.argi2;
final int interactionId = args.argi3;
final IAccessibilityInteractionConnectionCallback callback =
(IAccessibilityInteractionConnectionCallback) args.arg1;
final MagnificationSpec spec = (MagnificationSpec) args.arg2;
final Region interactiveRegion = (Region) args.arg3;
args.recycle();
List<AccessibilityNodeInfo> infos = mTempAccessibilityNodeInfoList;
infos.clear();
try {
if (mViewRootImpl.mView == null || mViewRootImpl.mAttachInfo == null) {
return;
}
mViewRootImpl.mAttachInfo.mAccessibilityFetchFlags = flags;
View root = null;
if (accessibilityViewId == AccessibilityNodeInfo.UNDEFINED_ITEM_ID) {
root = mViewRootImpl.mView;
} else {
root = findViewByAccessibilityId(accessibilityViewId);
}
if (root != null && isShown(root)) {
mPrefetcher.prefetchAccessibilityNodeInfos(root, virtualDescendantId, flags, infos);
}
} finally {
try {
mViewRootImpl.mAttachInfo.mAccessibilityFetchFlags = 0;
applyAppScaleAndMagnificationSpecIfNeeded(infos, spec);
if (spec != null) {
spec.recycle();
}
adjustIsVisibleToUserIfNeeded(infos, interactiveRegion);
callback.setFindAccessibilityNodeInfosResult(infos, interactionId);
infos.clear();
} catch (RemoteException re) {
/* ignore - the other side will time out */
}
}
| public void | findAccessibilityNodeInfosByTextClientThread(long accessibilityNodeId, java.lang.String text, android.graphics.Region interactiveRegion, int interactionId, android.view.accessibility.IAccessibilityInteractionConnectionCallback callback, int flags, int interrogatingPid, long interrogatingTid, MagnificationSpec spec)
Message message = mHandler.obtainMessage();
message.what = PrivateHandler.MSG_FIND_ACCESSIBILITY_NODE_INFO_BY_TEXT;
message.arg1 = flags;
SomeArgs args = SomeArgs.obtain();
args.arg1 = text;
args.arg2 = callback;
args.arg3 = spec;
args.argi1 = AccessibilityNodeInfo.getAccessibilityViewId(accessibilityNodeId);
args.argi2 = AccessibilityNodeInfo.getVirtualDescendantId(accessibilityNodeId);
args.argi3 = interactionId;
args.arg4 = interactiveRegion;
message.obj = args;
// If the interrogation is performed by the same thread as the main UI
// thread in this process, set the message as a static reference so
// after this call completes the same thread but in the interrogating
// client can handle the message to generate the result.
if (interrogatingPid == mMyProcessId && interrogatingTid == mMyLooperThreadId) {
AccessibilityInteractionClient.getInstanceForThread(
interrogatingTid).setSameThreadMessage(message);
} else {
mHandler.sendMessage(message);
}
| private void | findAccessibilityNodeInfosByTextUiThread(android.os.Message message)
final int flags = message.arg1;
SomeArgs args = (SomeArgs) message.obj;
final String text = (String) args.arg1;
final IAccessibilityInteractionConnectionCallback callback =
(IAccessibilityInteractionConnectionCallback) args.arg2;
final MagnificationSpec spec = (MagnificationSpec) args.arg3;
final int accessibilityViewId = args.argi1;
final int virtualDescendantId = args.argi2;
final int interactionId = args.argi3;
final Region interactiveRegion = (Region) args.arg4;
args.recycle();
List<AccessibilityNodeInfo> infos = null;
try {
if (mViewRootImpl.mView == null || mViewRootImpl.mAttachInfo == null) {
return;
}
mViewRootImpl.mAttachInfo.mAccessibilityFetchFlags = flags;
View root = null;
if (accessibilityViewId != AccessibilityNodeInfo.UNDEFINED_ITEM_ID) {
root = findViewByAccessibilityId(accessibilityViewId);
} else {
root = mViewRootImpl.mView;
}
if (root != null && isShown(root)) {
AccessibilityNodeProvider provider = root.getAccessibilityNodeProvider();
if (provider != null) {
if (virtualDescendantId != AccessibilityNodeInfo.UNDEFINED_ITEM_ID) {
infos = provider.findAccessibilityNodeInfosByText(text,
virtualDescendantId);
} else {
infos = provider.findAccessibilityNodeInfosByText(text,
AccessibilityNodeProvider.HOST_VIEW_ID);
}
} else if (virtualDescendantId == AccessibilityNodeInfo.UNDEFINED_ITEM_ID) {
ArrayList<View> foundViews = mTempArrayList;
foundViews.clear();
root.findViewsWithText(foundViews, text, View.FIND_VIEWS_WITH_TEXT
| View.FIND_VIEWS_WITH_CONTENT_DESCRIPTION
| View.FIND_VIEWS_WITH_ACCESSIBILITY_NODE_PROVIDERS);
if (!foundViews.isEmpty()) {
infos = mTempAccessibilityNodeInfoList;
infos.clear();
final int viewCount = foundViews.size();
for (int i = 0; i < viewCount; i++) {
View foundView = foundViews.get(i);
if (isShown(foundView)) {
provider = foundView.getAccessibilityNodeProvider();
if (provider != null) {
List<AccessibilityNodeInfo> infosFromProvider =
provider.findAccessibilityNodeInfosByText(text,
AccessibilityNodeProvider.HOST_VIEW_ID);
if (infosFromProvider != null) {
infos.addAll(infosFromProvider);
}
} else {
infos.add(foundView.createAccessibilityNodeInfo());
}
}
}
}
}
}
} finally {
try {
mViewRootImpl.mAttachInfo.mAccessibilityFetchFlags = 0;
applyAppScaleAndMagnificationSpecIfNeeded(infos, spec);
if (spec != null) {
spec.recycle();
}
adjustIsVisibleToUserIfNeeded(infos, interactiveRegion);
callback.setFindAccessibilityNodeInfosResult(infos, interactionId);
} catch (RemoteException re) {
/* ignore - the other side will time out */
}
}
| public void | findAccessibilityNodeInfosByViewIdClientThread(long accessibilityNodeId, java.lang.String viewId, android.graphics.Region interactiveRegion, int interactionId, android.view.accessibility.IAccessibilityInteractionConnectionCallback callback, int flags, int interrogatingPid, long interrogatingTid, MagnificationSpec spec)
Message message = mHandler.obtainMessage();
message.what = PrivateHandler.MSG_FIND_ACCESSIBILITY_NODE_INFOS_BY_VIEW_ID;
message.arg1 = flags;
message.arg2 = AccessibilityNodeInfo.getAccessibilityViewId(accessibilityNodeId);
SomeArgs args = SomeArgs.obtain();
args.argi1 = interactionId;
args.arg1 = callback;
args.arg2 = spec;
args.arg3 = viewId;
args.arg4 = interactiveRegion;
message.obj = args;
// If the interrogation is performed by the same thread as the main UI
// thread in this process, set the message as a static reference so
// after this call completes the same thread but in the interrogating
// client can handle the message to generate the result.
if (interrogatingPid == mMyProcessId && interrogatingTid == mMyLooperThreadId) {
AccessibilityInteractionClient.getInstanceForThread(
interrogatingTid).setSameThreadMessage(message);
} else {
mHandler.sendMessage(message);
}
| private void | findAccessibilityNodeInfosByViewIdUiThread(android.os.Message message)
final int flags = message.arg1;
final int accessibilityViewId = message.arg2;
SomeArgs args = (SomeArgs) message.obj;
final int interactionId = args.argi1;
final IAccessibilityInteractionConnectionCallback callback =
(IAccessibilityInteractionConnectionCallback) args.arg1;
final MagnificationSpec spec = (MagnificationSpec) args.arg2;
final String viewId = (String) args.arg3;
final Region interactiveRegion = (Region) args.arg4;
args.recycle();
final List<AccessibilityNodeInfo> infos = mTempAccessibilityNodeInfoList;
infos.clear();
try {
if (mViewRootImpl.mView == null || mViewRootImpl.mAttachInfo == null) {
return;
}
mViewRootImpl.mAttachInfo.mAccessibilityFetchFlags = flags;
View root = null;
if (accessibilityViewId != AccessibilityNodeInfo.UNDEFINED_ITEM_ID) {
root = findViewByAccessibilityId(accessibilityViewId);
} else {
root = mViewRootImpl.mView;
}
if (root != null) {
final int resolvedViewId = root.getContext().getResources()
.getIdentifier(viewId, null, null);
if (resolvedViewId <= 0) {
return;
}
if (mAddNodeInfosForViewId == null) {
mAddNodeInfosForViewId = new AddNodeInfosForViewId();
}
mAddNodeInfosForViewId.init(resolvedViewId, infos);
root.findViewByPredicate(mAddNodeInfosForViewId);
mAddNodeInfosForViewId.reset();
}
} finally {
try {
mViewRootImpl.mAttachInfo.mAccessibilityFetchFlags = 0;
applyAppScaleAndMagnificationSpecIfNeeded(infos, spec);
if (spec != null) {
spec.recycle();
}
adjustIsVisibleToUserIfNeeded(infos, interactiveRegion);
callback.setFindAccessibilityNodeInfosResult(infos, interactionId);
} catch (RemoteException re) {
/* ignore - the other side will time out */
}
}
| public void | findFocusClientThread(long accessibilityNodeId, int focusType, android.graphics.Region interactiveRegion, int interactionId, android.view.accessibility.IAccessibilityInteractionConnectionCallback callback, int flags, int interogatingPid, long interrogatingTid, MagnificationSpec spec)
Message message = mHandler.obtainMessage();
message.what = PrivateHandler.MSG_FIND_FOCUS;
message.arg1 = flags;
message.arg2 = focusType;
SomeArgs args = SomeArgs.obtain();
args.argi1 = interactionId;
args.argi2 = AccessibilityNodeInfo.getAccessibilityViewId(accessibilityNodeId);
args.argi3 = AccessibilityNodeInfo.getVirtualDescendantId(accessibilityNodeId);
args.arg1 = callback;
args.arg2 = spec;
args.arg3 = interactiveRegion;
message.obj = args;
// If the interrogation is performed by the same thread as the main UI
// thread in this process, set the message as a static reference so
// after this call completes the same thread but in the interrogating
// client can handle the message to generate the result.
if (interogatingPid == mMyProcessId && interrogatingTid == mMyLooperThreadId) {
AccessibilityInteractionClient.getInstanceForThread(
interrogatingTid).setSameThreadMessage(message);
} else {
mHandler.sendMessage(message);
}
| private void | findFocusUiThread(android.os.Message message)
final int flags = message.arg1;
final int focusType = message.arg2;
SomeArgs args = (SomeArgs) message.obj;
final int interactionId = args.argi1;
final int accessibilityViewId = args.argi2;
final int virtualDescendantId = args.argi3;
final IAccessibilityInteractionConnectionCallback callback =
(IAccessibilityInteractionConnectionCallback) args.arg1;
final MagnificationSpec spec = (MagnificationSpec) args.arg2;
final Region interactiveRegion = (Region) args.arg3;
args.recycle();
AccessibilityNodeInfo focused = null;
try {
if (mViewRootImpl.mView == null || mViewRootImpl.mAttachInfo == null) {
return;
}
mViewRootImpl.mAttachInfo.mAccessibilityFetchFlags = flags;
View root = null;
if (accessibilityViewId != AccessibilityNodeInfo.UNDEFINED_ITEM_ID) {
root = findViewByAccessibilityId(accessibilityViewId);
} else {
root = mViewRootImpl.mView;
}
if (root != null && isShown(root)) {
switch (focusType) {
case AccessibilityNodeInfo.FOCUS_ACCESSIBILITY: {
View host = mViewRootImpl.mAccessibilityFocusedHost;
// If there is no accessibility focus host or it is not a descendant
// of the root from which to start the search, then the search failed.
if (host == null || !ViewRootImpl.isViewDescendantOf(host, root)) {
break;
}
// The focused view not shown, we failed.
if (!isShown(host)) {
break;
}
// If the host has a provider ask this provider to search for the
// focus instead fetching all provider nodes to do the search here.
AccessibilityNodeProvider provider = host.getAccessibilityNodeProvider();
if (provider != null) {
if (mViewRootImpl.mAccessibilityFocusedVirtualView != null) {
focused = AccessibilityNodeInfo.obtain(
mViewRootImpl.mAccessibilityFocusedVirtualView);
}
} else if (virtualDescendantId == AccessibilityNodeInfo.UNDEFINED_ITEM_ID) {
focused = host.createAccessibilityNodeInfo();
}
} break;
case AccessibilityNodeInfo.FOCUS_INPUT: {
View target = root.findFocus();
if (target == null || !isShown(target)) {
break;
}
AccessibilityNodeProvider provider = target.getAccessibilityNodeProvider();
if (provider != null) {
focused = provider.findFocus(focusType);
}
if (focused == null) {
focused = target.createAccessibilityNodeInfo();
}
} break;
default:
throw new IllegalArgumentException("Unknown focus type: " + focusType);
}
}
} finally {
try {
mViewRootImpl.mAttachInfo.mAccessibilityFetchFlags = 0;
applyAppScaleAndMagnificationSpecIfNeeded(focused, spec);
if (spec != null) {
spec.recycle();
}
adjustIsVisibleToUserIfNeeded(focused, interactiveRegion);
callback.setFindAccessibilityNodeInfoResult(focused, interactionId);
} catch (RemoteException re) {
/* ignore - the other side will time out */
}
}
| private View | findViewByAccessibilityId(int accessibilityId)
View root = mViewRootImpl.mView;
if (root == null) {
return null;
}
View foundView = root.findViewByAccessibilityId(accessibilityId);
if (foundView != null && !isShown(foundView)) {
return null;
}
return foundView;
| public void | focusSearchClientThread(long accessibilityNodeId, int direction, android.graphics.Region interactiveRegion, int interactionId, android.view.accessibility.IAccessibilityInteractionConnectionCallback callback, int flags, int interogatingPid, long interrogatingTid, MagnificationSpec spec)
Message message = mHandler.obtainMessage();
message.what = PrivateHandler.MSG_FOCUS_SEARCH;
message.arg1 = flags;
message.arg2 = AccessibilityNodeInfo.getAccessibilityViewId(accessibilityNodeId);
SomeArgs args = SomeArgs.obtain();
args.argi2 = direction;
args.argi3 = interactionId;
args.arg1 = callback;
args.arg2 = spec;
args.arg3 = interactiveRegion;
message.obj = args;
// If the interrogation is performed by the same thread as the main UI
// thread in this process, set the message as a static reference so
// after this call completes the same thread but in the interrogating
// client can handle the message to generate the result.
if (interogatingPid == mMyProcessId && interrogatingTid == mMyLooperThreadId) {
AccessibilityInteractionClient.getInstanceForThread(
interrogatingTid).setSameThreadMessage(message);
} else {
mHandler.sendMessage(message);
}
| private void | focusSearchUiThread(android.os.Message message)
final int flags = message.arg1;
final int accessibilityViewId = message.arg2;
SomeArgs args = (SomeArgs) message.obj;
final int direction = args.argi2;
final int interactionId = args.argi3;
final IAccessibilityInteractionConnectionCallback callback =
(IAccessibilityInteractionConnectionCallback) args.arg1;
final MagnificationSpec spec = (MagnificationSpec) args.arg2;
final Region interactiveRegion = (Region) args.arg3;
args.recycle();
AccessibilityNodeInfo next = null;
try {
if (mViewRootImpl.mView == null || mViewRootImpl.mAttachInfo == null) {
return;
}
mViewRootImpl.mAttachInfo.mAccessibilityFetchFlags = flags;
View root = null;
if (accessibilityViewId != AccessibilityNodeInfo.UNDEFINED_ITEM_ID) {
root = findViewByAccessibilityId(accessibilityViewId);
} else {
root = mViewRootImpl.mView;
}
if (root != null && isShown(root)) {
View nextView = root.focusSearch(direction);
if (nextView != null) {
next = nextView.createAccessibilityNodeInfo();
}
}
} finally {
try {
mViewRootImpl.mAttachInfo.mAccessibilityFetchFlags = 0;
applyAppScaleAndMagnificationSpecIfNeeded(next, spec);
if (spec != null) {
spec.recycle();
}
adjustIsVisibleToUserIfNeeded(next, interactiveRegion);
callback.setFindAccessibilityNodeInfoResult(next, interactionId);
} catch (RemoteException re) {
/* ignore - the other side will time out */
}
}
| private boolean | isShown(View view)
// The first two checks are made also made by isShown() which
// however traverses the tree up to the parent to catch that.
// Therefore, we do some fail fast check to minimize the up
// tree traversal.
return (view.mAttachInfo != null
&& view.mAttachInfo.mWindowVisibility == View.VISIBLE
&& view.isShown());
| public void | performAccessibilityActionClientThread(long accessibilityNodeId, int action, android.os.Bundle arguments, int interactionId, android.view.accessibility.IAccessibilityInteractionConnectionCallback callback, int flags, int interogatingPid, long interrogatingTid)
Message message = mHandler.obtainMessage();
message.what = PrivateHandler.MSG_PERFORM_ACCESSIBILITY_ACTION;
message.arg1 = flags;
message.arg2 = AccessibilityNodeInfo.getAccessibilityViewId(accessibilityNodeId);
SomeArgs args = SomeArgs.obtain();
args.argi1 = AccessibilityNodeInfo.getVirtualDescendantId(accessibilityNodeId);
args.argi2 = action;
args.argi3 = interactionId;
args.arg1 = callback;
args.arg2 = arguments;
message.obj = args;
// If the interrogation is performed by the same thread as the main UI
// thread in this process, set the message as a static reference so
// after this call completes the same thread but in the interrogating
// client can handle the message to generate the result.
if (interogatingPid == mMyProcessId && interrogatingTid == mMyLooperThreadId) {
AccessibilityInteractionClient.getInstanceForThread(
interrogatingTid).setSameThreadMessage(message);
} else {
mHandler.sendMessage(message);
}
| private void | perfromAccessibilityActionUiThread(android.os.Message message)
final int flags = message.arg1;
final int accessibilityViewId = message.arg2;
SomeArgs args = (SomeArgs) message.obj;
final int virtualDescendantId = args.argi1;
final int action = args.argi2;
final int interactionId = args.argi3;
final IAccessibilityInteractionConnectionCallback callback =
(IAccessibilityInteractionConnectionCallback) args.arg1;
Bundle arguments = (Bundle) args.arg2;
args.recycle();
boolean succeeded = false;
try {
if (mViewRootImpl.mView == null || mViewRootImpl.mAttachInfo == null) {
return;
}
mViewRootImpl.mAttachInfo.mAccessibilityFetchFlags = flags;
View target = null;
if (accessibilityViewId != AccessibilityNodeInfo.UNDEFINED_ITEM_ID) {
target = findViewByAccessibilityId(accessibilityViewId);
} else {
target = mViewRootImpl.mView;
}
if (target != null && isShown(target)) {
AccessibilityNodeProvider provider = target.getAccessibilityNodeProvider();
if (provider != null) {
if (virtualDescendantId != AccessibilityNodeInfo.UNDEFINED_ITEM_ID) {
succeeded = provider.performAction(virtualDescendantId, action,
arguments);
} else {
succeeded = provider.performAction(AccessibilityNodeProvider.HOST_VIEW_ID,
action, arguments);
}
} else if (virtualDescendantId == AccessibilityNodeInfo.UNDEFINED_ITEM_ID) {
succeeded = target.performAccessibilityAction(action, arguments);
}
}
} finally {
try {
mViewRootImpl.mAttachInfo.mAccessibilityFetchFlags = 0;
callback.setPerformAccessibilityActionResult(succeeded, interactionId);
} catch (RemoteException re) {
/* ignore - the other side will time out */
}
}
| private boolean | shouldApplyAppScaleAndMagnificationSpec(float appScale, MagnificationSpec spec)
return (appScale != 1.0f || (spec != null && !spec.isNop()));
|
|