summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--core/java/android/text/style/AccessibilityClickableSpan.java43
-rw-r--r--core/java/android/text/style/AccessibilityURLSpan.java4
-rw-r--r--core/java/android/view/accessibility/AccessibilityNodeInfo.java25
3 files changed, 43 insertions, 29 deletions
diff --git a/core/java/android/text/style/AccessibilityClickableSpan.java b/core/java/android/text/style/AccessibilityClickableSpan.java
index 9c305ff0f6ae..7f39cc14718a 100644
--- a/core/java/android/text/style/AccessibilityClickableSpan.java
+++ b/core/java/android/text/style/AccessibilityClickableSpan.java
@@ -16,6 +16,9 @@
package android.text.style;
import static android.view.accessibility.AccessibilityNodeInfo.ACTION_ARGUMENT_ACCESSIBLE_CLICKABLE_SPAN;
+import static android.view.accessibility.AccessibilityNodeInfo.UNDEFINED_CONNECTION_ID;
+import static android.view.accessibility.AccessibilityNodeInfo.UNDEFINED_NODE_ID;
+import static android.view.accessibility.AccessibilityWindowInfo.UNDEFINED_WINDOW_ID;
import android.os.Bundle;
import android.os.Parcel;
@@ -24,13 +27,11 @@ import android.text.ParcelableSpan;
import android.text.Spanned;
import android.text.TextUtils;
import android.view.View;
+import android.view.accessibility.AccessibilityInteractionClient;
import android.view.accessibility.AccessibilityNodeInfo;
import com.android.internal.R;
-import java.lang.ref.WeakReference;
-
-
/**
* {@link ClickableSpan} cannot be parceled, but accessibility services need to be able to cause
* their callback handlers to be called. This class serves as a parcelable placeholder for the
@@ -47,10 +48,9 @@ public class AccessibilityClickableSpan extends ClickableSpan
// The id of the span this one replaces
private final int mOriginalClickableSpanId;
- // Only retain a weak reference to the node to avoid referencing cycles that could create memory
- // leaks.
- private WeakReference<AccessibilityNodeInfo> mAccessibilityNodeInfoRef;
-
+ private int mWindowId = UNDEFINED_WINDOW_ID;
+ private long mSourceNodeId = UNDEFINED_NODE_ID;
+ private int mConnectionId = UNDEFINED_CONNECTION_ID;
/**
* @param originalClickableSpanId The id of the span this one replaces
@@ -110,13 +110,15 @@ public class AccessibilityClickableSpan extends ClickableSpan
}
/**
- * Set the accessibilityNodeInfo that this placeholder belongs to. This node is not
- * included in the parceling logic, and must be set to allow the onClick handler to function.
+ * Configure this object to perform clicks on the view that contains the original span.
*
- * @param accessibilityNodeInfo The info this span is part of
+ * @param accessibilityNodeInfo The info corresponding to the view containing the original
+ * span.
*/
- public void setAccessibilityNodeInfo(AccessibilityNodeInfo accessibilityNodeInfo) {
- mAccessibilityNodeInfoRef = new WeakReference<>(accessibilityNodeInfo);
+ public void copyConnectionDataFrom(AccessibilityNodeInfo accessibilityNodeInfo) {
+ mConnectionId = accessibilityNodeInfo.getConnectionId();
+ mWindowId = accessibilityNodeInfo.getWindowId();
+ mSourceNodeId = accessibilityNodeInfo.getSourceNodeId();
}
/**
@@ -128,17 +130,18 @@ public class AccessibilityClickableSpan extends ClickableSpan
*/
@Override
public void onClick(View unused) {
- if (mAccessibilityNodeInfoRef == null) {
- return;
- }
- AccessibilityNodeInfo info = mAccessibilityNodeInfoRef.get();
- if (info == null) {
- return;
- }
Bundle arguments = new Bundle();
arguments.putParcelable(ACTION_ARGUMENT_ACCESSIBLE_CLICKABLE_SPAN, this);
- info.performAction(R.id.accessibilityActionClickOnClickableSpan, arguments);
+ if ((mWindowId == UNDEFINED_WINDOW_ID) || (mSourceNodeId == UNDEFINED_NODE_ID)
+ || (mConnectionId == UNDEFINED_CONNECTION_ID)) {
+ throw new RuntimeException(
+ "ClickableSpan for accessibility service not properly initialized");
+ }
+
+ AccessibilityInteractionClient client = AccessibilityInteractionClient.getInstance();
+ client.performAccessibilityAction(mConnectionId, mWindowId, mSourceNodeId,
+ R.id.accessibilityActionClickOnClickableSpan, arguments);
}
public static final Parcelable.Creator<AccessibilityClickableSpan> CREATOR =
diff --git a/core/java/android/text/style/AccessibilityURLSpan.java b/core/java/android/text/style/AccessibilityURLSpan.java
index 014700945c57..bd816234a652 100644
--- a/core/java/android/text/style/AccessibilityURLSpan.java
+++ b/core/java/android/text/style/AccessibilityURLSpan.java
@@ -73,7 +73,7 @@ public class AccessibilityURLSpan extends URLSpan implements Parcelable {
* Delegated to AccessibilityClickableSpan
* @param accessibilityNodeInfo
*/
- public void setAccessibilityNodeInfo(AccessibilityNodeInfo accessibilityNodeInfo) {
- mAccessibilityClickableSpan.setAccessibilityNodeInfo(accessibilityNodeInfo);
+ public void copyConnectionDataFrom(AccessibilityNodeInfo accessibilityNodeInfo) {
+ mAccessibilityClickableSpan.copyConnectionDataFrom(accessibilityNodeInfo);
}
}
diff --git a/core/java/android/view/accessibility/AccessibilityNodeInfo.java b/core/java/android/view/accessibility/AccessibilityNodeInfo.java
index 255574f8cee7..94a4547fca64 100644
--- a/core/java/android/view/accessibility/AccessibilityNodeInfo.java
+++ b/core/java/android/view/accessibility/AccessibilityNodeInfo.java
@@ -695,7 +695,7 @@ public class AccessibilityNodeInfo implements Parcelable {
private boolean mSealed;
// Data.
- private int mWindowId = UNDEFINED_ITEM_ID;
+ private int mWindowId = AccessibilityWindowInfo.UNDEFINED_WINDOW_ID;
private long mSourceNodeId = UNDEFINED_NODE_ID;
private long mParentNodeId = UNDEFINED_NODE_ID;
private long mLabelForId = UNDEFINED_NODE_ID;
@@ -2417,12 +2417,12 @@ public class AccessibilityNodeInfo implements Parcelable {
AccessibilityClickableSpan[] clickableSpans =
spanned.getSpans(0, mText.length(), AccessibilityClickableSpan.class);
for (int i = 0; i < clickableSpans.length; i++) {
- clickableSpans[i].setAccessibilityNodeInfo(this);
+ clickableSpans[i].copyConnectionDataFrom(this);
}
AccessibilityURLSpan[] urlSpans =
spanned.getSpans(0, mText.length(), AccessibilityURLSpan.class);
for (int i = 0; i < urlSpans.length; i++) {
- urlSpans[i].setAccessibilityNodeInfo(this);
+ urlSpans[i].copyConnectionDataFrom(this);
}
}
return mText;
@@ -2841,6 +2841,17 @@ public class AccessibilityNodeInfo implements Parcelable {
}
/**
+ * Get the connection ID.
+ *
+ * @return The connection id
+ *
+ * @hide
+ */
+ public int getConnectionId() {
+ return mConnectionId;
+ }
+
+ /**
* {@inheritDoc}
*/
@Override
@@ -3354,7 +3365,7 @@ public class AccessibilityNodeInfo implements Parcelable {
mLabeledById = UNDEFINED_NODE_ID;
mTraversalBefore = UNDEFINED_NODE_ID;
mTraversalAfter = UNDEFINED_NODE_ID;
- mWindowId = UNDEFINED_ITEM_ID;
+ mWindowId = AccessibilityWindowInfo.UNDEFINED_WINDOW_ID;
mConnectionId = UNDEFINED_CONNECTION_ID;
mMaxTextLength = -1;
mMovementGranularities = 0;
@@ -3517,9 +3528,9 @@ public class AccessibilityNodeInfo implements Parcelable {
}
private boolean canPerformRequestOverConnection(long accessibilityNodeId) {
- return (mWindowId != UNDEFINED_ITEM_ID
- && getAccessibilityViewId(accessibilityNodeId) != UNDEFINED_ITEM_ID
- && mConnectionId != UNDEFINED_CONNECTION_ID);
+ return ((mWindowId != AccessibilityWindowInfo.UNDEFINED_WINDOW_ID)
+ && (getAccessibilityViewId(accessibilityNodeId) != UNDEFINED_ITEM_ID)
+ && (mConnectionId != UNDEFINED_CONNECTION_ID));
}
@Override