Skip to content

Commit 0e0664f

Browse files
committed
Trigger non-touch events on box-none targets
Currently, this library disables _all_ events for a target with `pointerEvents="box-none"`. This behavior is counter to how React Native itself functions. This change continues to disable touch events, e.g. `press`, for targets set to "box-none", but allows triggering non-touch events, e.g. `layout`, `touchStart`.
1 parent a010ffd commit 0e0664f

File tree

2 files changed

+39
-3
lines changed

2 files changed

+39
-3
lines changed

src/__tests__/fireEvent.test.js

+30
Original file line numberDiff line numberDiff line change
@@ -317,6 +317,36 @@ test('should not fire on box-only pointerEvents View with nested elements', () =
317317
expect(handlePress).not.toHaveBeenCalled();
318318
});
319319

320+
test('should fire non-terminal touch events on box-none pointerEvents View', () => {
321+
const handleTouchStart = jest.fn();
322+
323+
const screen = render(
324+
<View pointerEvents="box-none" onTouchStart={handleTouchStart}>
325+
<Pressable onPress={() => {}}>
326+
<Text>Trigger</Text>
327+
</Pressable>
328+
</View>
329+
);
330+
331+
fireEvent(screen.getByText('Trigger'), 'touchStart');
332+
expect(handleTouchStart).toHaveBeenCalled();
333+
});
334+
335+
test('should fire non-touch events on box-none pointerEvents View', () => {
336+
const handleLayout = jest.fn();
337+
338+
const screen = render(
339+
<View pointerEvents="box-none" onLayout={handleLayout}>
340+
<Pressable onPress={() => {}}>
341+
<Text>Trigger</Text>
342+
</Pressable>
343+
</View>
344+
);
345+
346+
fireEvent(screen.getByText('Trigger'), 'layout');
347+
expect(handleLayout).toHaveBeenCalled();
348+
});
349+
320350
test('should pass event up on disabled TouchableOpacity', () => {
321351
const handleInnerPress = jest.fn();
322352
const handleOuterPress = jest.fn();

src/fireEvent.js

+9-3
Original file line numberDiff line numberDiff line change
@@ -33,12 +33,17 @@ const isPointerEventEnabled = (
3333
return isPointerEventEnabled(element.parent, true);
3434
};
3535

36+
const isTouchEvent = (eventName?: string) => {
37+
return eventName === 'press';
38+
};
39+
3640
const isEventEnabled = (
3741
element?: ReactTestInstance,
38-
touchResponder?: ReactTestInstance
42+
touchResponder?: ReactTestInstance,
43+
eventName?: string
3944
) => {
4045
if (isTextInput(element)) return element?.props.editable !== false;
41-
if (!isPointerEventEnabled(element)) return false;
46+
if (!isPointerEventEnabled(element) && isTouchEvent(eventName)) return false;
4247

4348
const touchStart = touchResponder?.props.onStartShouldSetResponder?.();
4449
const touchMove = touchResponder?.props.onMoveShouldSetResponder?.();
@@ -59,7 +64,8 @@ const findEventHandler = (
5964
: nearestTouchResponder;
6065

6166
const handler = getEventHandler(element, eventName);
62-
if (handler && isEventEnabled(element, touchResponder)) return handler;
67+
if (handler && isEventEnabled(element, touchResponder, eventName))
68+
return handler;
6369

6470
if (element.parent === null || element.parent.parent === null) {
6571
return null;

0 commit comments

Comments
 (0)