@@ -24,6 +24,7 @@ import {registrationNameDependencies} from 'legacy-events/EventPluginRegistry';
2424import { batchedEventUpdates } from 'legacy-events/ReactGenericBatching' ;
2525import { executeDispatchesInOrder } from 'legacy-events/EventPluginUtils' ;
2626import { plugins } from 'legacy-events/EventPluginRegistry' ;
27+ import { LEGACY_FB_SUPPORT , IS_REPLAYED } from 'legacy-events/EventSystemFlags' ;
2728
2829import { HostRoot , HostPortal } from 'shared/ReactWorkTags' ;
2930
@@ -66,6 +67,7 @@ import {
6667 TOP_RATE_CHANGE ,
6768 TOP_PROGRESS ,
6869 TOP_PLAYING ,
70+ TOP_CLICK ,
6971} from './DOMTopLevelEventTypes' ;
7072import {
7173 getClosestInstanceFromNode ,
@@ -78,7 +80,7 @@ import {
7880 ELEMENT_NODE ,
7981} from '../shared/HTMLNodeType' ;
8082
81- import { enableLegacyFBPrimerSupport } from 'shared/ReactFeatureFlags' ;
83+ import { enableLegacyFBSupport } from 'shared/ReactFeatureFlags' ;
8284
8385const capturePhaseEvents = new Set ( [
8486 TOP_FOCUS ,
@@ -197,7 +199,6 @@ export function listenToTopLevelEvent(
197199 topLevelType ,
198200 isCapturePhase ,
199201 ( ( listenerEntry : any ) : ElementListenerMapEntry ) . listener ,
200- ( ( listenerEntry : any ) : ElementListenerMapEntry ) . passive ,
201202 ) ;
202203 }
203204 const listener = addTrappedEventListener (
@@ -225,42 +226,24 @@ export function listenToEvent(
225226 }
226227}
227228
228- const validFBLegacyPrimerRels = new Set ( [
229- 'dialog' ,
230- 'dialog-post' ,
231- 'async' ,
232- 'async-post' ,
233- 'theater' ,
234- 'toggle' ,
235- ] ) ;
236-
237- function willDeferLaterForFBLegacyPrimer ( nativeEvent : any ) : boolean {
238- let node = nativeEvent . target ;
239- const type = nativeEvent . type ;
240- if ( type !== 'click' ) {
229+ function willDeferLaterForLegacyFBSupport (
230+ topLevelType : DOMTopLevelEventType ,
231+ targetContainer : EventTarget ,
232+ ) : boolean {
233+ if ( topLevelType !== TOP_CLICK ) {
241234 return false ;
242235 }
243- while ( node !== null ) {
244- // Primer works by intercepting a click event on an <a> element
245- // that has a "rel" attribute that matches one of the valid ones
246- // in the Set above. If we intercept this before Primer does, we
247- // will need to defer the current event till later and discontinue
248- // execution of the current event. To do this we can add a document
249- // event listener and continue again later after propagation.
250- if ( node . tagName === 'A' && validFBLegacyPrimerRels . has ( node . rel ) ) {
251- const legacyFBSupport = true ;
252- const isCapture = nativeEvent . eventPhase === 1 ;
253- addTrappedEventListener (
254- null ,
255- ( ( type : any ) : DOMTopLevelEventType ) ,
256- isCapture ,
257- legacyFBSupport ,
258- ) ;
259- return true ;
260- }
261- node = node . parentNode ;
262- }
263- return false ;
236+ // We defer all click events with legacy FB support mode on.
237+ // This means we add a one time event listener to trigger
238+ // after the FB delegated listeners fire.
239+ const isDeferredListenerForLegacyFBSupport = true ;
240+ addTrappedEventListener (
241+ targetContainer ,
242+ topLevelType ,
243+ false ,
244+ isDeferredListenerForLegacyFBSupport ,
245+ ) ;
246+ return true ;
264247}
265248
266249function isMatchingRootContainer (
@@ -303,12 +286,19 @@ export function dispatchEventForPluginEventSystem(
303286 // TODO: useEvent for document and window
304287 return ;
305288 }
306- // If we detect the FB legacy primer system , we
289+ // If we are using the legacy FB support flag , we
307290 // defer the event to the null with a one
308291 // time event listener so we can defer the event.
309292 if (
310- enableLegacyFBPrimerSupport &&
311- willDeferLaterForFBLegacyPrimer ( nativeEvent )
293+ enableLegacyFBSupport &&
294+ // We do not want to defer if the event system has already been
295+ // set to LEGACY_FB_SUPPORT. LEGACY_FB_SUPPORT only gets set when
296+ // we call willDeferLaterForLegacyFBSupport, thus not bailing out
297+ // will result in endless cycles like an infinite loop.
298+ ( eventSystemFlags & LEGACY_FB_SUPPORT ) === 0 &&
299+ // We also don't want to defer during event replaying.
300+ ( eventSystemFlags & IS_REPLAYED ) === 0 &&
301+ willDeferLaterForLegacyFBSupport ( topLevelType , targetContainer )
312302 ) {
313303 return ;
314304 }
0 commit comments