Skip to content

Commit 814edca

Browse files
rozelefacebook-github-bot
authored andcommitted
Fix accessibilityLabelledBy crash on empty array (#57029)
Summary: Fixes a crash in `BaseViewManager.setAccessibilityLabelledBy` when an empty array is passed. The method now guards against accessing index 0 on empty arrays and properly clears the tag when null or empty arrays are provided, instead of leaving stale associations. ## Changelog [Android][Fixed] - Issue when clearing accessibilityLabelledBy Reviewed By: bvanderhoof Differential Revision: D107127388
1 parent 7f396d1 commit 814edca

2 files changed

Lines changed: 33 additions & 2 deletions

File tree

packages/react-native/ReactAndroid/src/main/java/com/facebook/react/uimanager/BaseViewManager.java

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -309,15 +309,17 @@ public void setNativeId(@NonNull T view, @Nullable String nativeId) {
309309

310310
@ReactProp(name = ViewProps.ACCESSIBILITY_LABELLED_BY)
311311
public void setAccessibilityLabelledBy(@NonNull T view, @Nullable Dynamic nativeId) {
312-
if (nativeId.isNull()) {
312+
if (nativeId == null || nativeId.isNull()) {
313+
view.setTag(R.id.labelled_by, null);
313314
return;
314315
}
315316
if (nativeId.getType() == ReadableType.String) {
316317
view.setTag(R.id.labelled_by, nativeId.asString());
317318
} else if (nativeId.getType() == ReadableType.Array) {
318319
// On Android, this takes a single View as labeledBy. If an array is specified, set the first
319320
// element in the tag.
320-
view.setTag(R.id.labelled_by, nativeId.asArray().getString(0));
321+
ReadableArray array = nativeId.asArray();
322+
view.setTag(R.id.labelled_by, array.size() > 0 ? array.getString(0) : null);
321323
}
322324
}
323325

packages/react-native/ReactAndroid/src/test/java/com/facebook/react/uimanager/BaseViewManagerTest.kt

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,8 @@ package com.facebook.react.uimanager
1212
import android.view.View.OnFocusChangeListener
1313
import com.facebook.react.R
1414
import com.facebook.react.bridge.BridgeReactContext
15+
import com.facebook.react.bridge.DynamicFromObject
16+
import com.facebook.react.bridge.JavaOnlyArray
1517
import com.facebook.react.bridge.JavaOnlyMap
1618
import com.facebook.react.internal.featureflags.ReactNativeFeatureFlagsForTests
1719
import com.facebook.react.views.view.ReactViewGroup
@@ -101,4 +103,31 @@ class BaseViewManagerTest {
101103
verify(originalFocusListener, times(2)).onFocusChange(view, true)
102104
Assertions.assertThat(originalFocusListener).isEqualTo(view.onFocusChangeListener)
103105
}
106+
107+
@Test
108+
fun testAccessibilityLabelledByString() {
109+
viewManager.setAccessibilityLabelledBy(view, DynamicFromObject("target_id"))
110+
Assertions.assertThat(view.getTag(R.id.labelled_by)).isEqualTo("target_id")
111+
}
112+
113+
@Test
114+
fun testAccessibilityLabelledByArray() {
115+
val array = JavaOnlyArray.of("first_id", "second_id")
116+
viewManager.setAccessibilityLabelledBy(view, DynamicFromObject(array))
117+
Assertions.assertThat(view.getTag(R.id.labelled_by)).isEqualTo("first_id")
118+
}
119+
120+
@Test
121+
fun testAccessibilityLabelledByNullClearsTag() {
122+
view.setTag(R.id.labelled_by, "stale_id")
123+
viewManager.setAccessibilityLabelledBy(view, DynamicFromObject(null))
124+
Assertions.assertThat(view.getTag(R.id.labelled_by)).isNull()
125+
}
126+
127+
@Test
128+
fun testAccessibilityLabelledByEmptyArrayDoesNotCrash() {
129+
view.setTag(R.id.labelled_by, "stale_id")
130+
viewManager.setAccessibilityLabelledBy(view, DynamicFromObject(JavaOnlyArray()))
131+
Assertions.assertThat(view.getTag(R.id.labelled_by)).isNull()
132+
}
104133
}

0 commit comments

Comments
 (0)