Skip to content

Commit 669cafb

Browse files
authored
Adds experimental event component responder surfaces (#15228)
* Adds Press and Hover event modules + more features to the Event Responder System
1 parent d8cb10f commit 669cafb

File tree

15 files changed

+1040
-161
lines changed

15 files changed

+1040
-161
lines changed

packages/events/EventPluginUtils.js

+1-1
Original file line numberDiff line numberDiff line change
@@ -63,7 +63,7 @@ if (__DEV__) {
6363
* @param {function} listener Application-level callback
6464
* @param {*} inst Internal component instance
6565
*/
66-
function executeDispatch(event, listener, inst) {
66+
export function executeDispatch(event, listener, inst) {
6767
const type = event.type || 'unknown-event';
6868
event.currentTarget = getNodeFromInstance(inst);
6969
invokeGuardedCallbackAndCatchFirstError(type, listener, undefined, event);

packages/events/EventTypes.js

+37
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
/**
2+
* Copyright (c) Facebook, Inc. and its affiliates.
3+
*
4+
* This source code is licensed under the MIT license found in the
5+
* LICENSE file in the root directory of this source tree.
6+
*
7+
* @flow
8+
*/
9+
10+
import SyntheticEvent from 'events/SyntheticEvent';
11+
import type {AnyNativeEvent} from 'events/PluginModuleType';
12+
13+
export type EventResponderContext = {
14+
event: AnyNativeEvent,
15+
eventTarget: EventTarget,
16+
eventType: string,
17+
isPassive: () => boolean,
18+
isPassiveSupported: () => boolean,
19+
dispatchEvent: (
20+
name: string,
21+
listener: (e: SyntheticEvent) => void | null,
22+
pressTarget: EventTarget | null,
23+
discrete: boolean,
24+
extraProperties?: Object,
25+
) => void,
26+
isTargetWithinElement: (
27+
childTarget: EventTarget,
28+
parentTarget: EventTarget,
29+
) => boolean,
30+
isTargetOwned: EventTarget => boolean,
31+
isTargetWithinEventComponent: EventTarget => boolean,
32+
isPositionWithinTouchHitTarget: (x: number, y: number) => boolean,
33+
addRootEventTypes: (rootEventTypes: Array<string>) => void,
34+
removeRootEventTypes: (rootEventTypes: Array<string>) => void,
35+
requestOwnership: (target: EventTarget | null) => boolean,
36+
releaseOwnership: (target: EventTarget | null) => boolean,
37+
};

packages/react-dom/src/client/ReactDOMComponent.js

+6-7
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@ import {registrationNameModules} from 'events/EventPluginRegistry';
1313
import warning from 'shared/warning';
1414
import {canUseDOM} from 'shared/ExecutionEnvironment';
1515
import warningWithoutStack from 'shared/warningWithoutStack';
16-
import type {ReactEventResponder} from 'shared/ReactTypes';
16+
import type {ReactEventResponderEventType} from 'shared/ReactTypes';
1717
import type {DOMTopLevelEventType} from 'events/TopLevelEventTypes';
1818

1919
import {
@@ -1277,19 +1277,18 @@ export function restoreControlledState(
12771277
}
12781278
}
12791279

1280-
export function listenToEventResponderEvents(
1281-
eventResponder: ReactEventResponder,
1280+
export function listenToEventResponderEventTypes(
1281+
eventTypes: Array<ReactEventResponderEventType>,
12821282
element: Element | Document,
12831283
): void {
12841284
if (enableEventAPI) {
1285-
const {targetEventTypes} = eventResponder;
12861285
// Get the listening Set for this element. We use this to track
12871286
// what events we're listening to.
12881287
const listeningSet = getListeningSetForElement(element);
12891288

12901289
// Go through each target event type of the event responder
1291-
for (let i = 0, length = targetEventTypes.length; i < length; ++i) {
1292-
const targetEventType = targetEventTypes[i];
1290+
for (let i = 0, length = eventTypes.length; i < length; ++i) {
1291+
const targetEventType = eventTypes[i];
12931292
let topLevelType;
12941293
let capture = false;
12951294
let passive = true;
@@ -1323,7 +1322,7 @@ export function listenToEventResponderEvents(
13231322
// Create a unique name for this event, plus its properties. We'll
13241323
// use this to ensure we don't listen to the same event with the same
13251324
// properties again.
1326-
const passiveKey = passive ? '_passive' : '';
1325+
const passiveKey = passive ? '_passive' : '_active';
13271326
const captureKey = capture ? '_capture' : '';
13281327
const listeningName = `${topLevelType}${passiveKey}${captureKey}`;
13291328
if (!listeningSet.has(listeningName)) {

packages/react-dom/src/client/ReactDOMHostConfig.js

+5-2
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@ import {
2424
warnForDeletedHydratableText,
2525
warnForInsertedHydratedElement,
2626
warnForInsertedHydratedText,
27-
listenToEventResponderEvents,
27+
listenToEventResponderEventTypes,
2828
} from './ReactDOMComponent';
2929
import {getSelectionInformation, restoreSelection} from './ReactInputSelection';
3030
import setTextContent from './setTextContent';
@@ -864,7 +864,10 @@ export function handleEventComponent(
864864
): void {
865865
if (enableEventAPI) {
866866
const rootElement = rootContainerInstance.ownerDocument;
867-
listenToEventResponderEvents(eventResponder, rootElement);
867+
listenToEventResponderEventTypes(
868+
eventResponder.targetEventTypes,
869+
rootElement,
870+
);
868871
}
869872
}
870873

0 commit comments

Comments
 (0)