question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

[Umbrella] React Flare

See original GitHub issue

This issue tracks tasks related to the React DOM implementation of the experimental React Events API (react-events) aka React Flare (our internal code-name for the project). The idea is to extend React’s event system to include high-level events that allow for consistent cross-device and cross-platform behavior.

Note: For now this is completely experimental and won’t affect the open source builds of React.

Core

  • Document specific UX patterns that this enables and fixes. (inc. from my workplace post on styles, Dan & Brian dev tools, apps, etc.)
  • Every user-facing event should have a timeStamp. Should we provide a standard way to derive data that might be common across events and require different logic for different positional information, e.g., point, delta, offset, etc?
  • How to test discrete vs continuous events?
  • Should we polyfill pointer events or not dispatch emulated touch/mouse events in the core, to avoid multiple event components needing to implement the same logic to ignore emulated events?
  • Investigate native pointer capture for retargeting events - https://www.w3.org/TR/pointerevents/#pointer-capture. This could be particularly useful for drag/swipe UX.
  • Limit all event components to have a single host node as child? If not enforced for all components, we might need this for Hover/Focus/Press at least.
  • FYI https://github.com/facebook/react/pull/12919
  • Optimize bundle output.
  • Replace magic object export with React.unstable_createEventComponent(type: Symbol | number, responder: ReactEventResponder, displayName: ?string)
  • Document core API for building responders
  • Stop propagation by default but scope to event module types.
  • Investigate ways to listen to root events without first needing to wait for a target event to be dispatched to the event component.
  • Remove listener from event object passed to callbacks like onPress
  • Ensure discrete events do not unnecessarily force flush previous non-discrete events.
  • Ensure event responder get unmounted correctly and pending events (e.g. long press) properly get removed when doing so. Maybe an unmount lifecycle method needs adding to event responders?
  • Create a new synthetic event and dispatch mechanism that relies on the event being generated in the event responder module, rather than from React. This allows for the event to be better typed and have a much simpler implementation for how React fires the event when dispatched + it means we can avoid pulling in the current SyntheticEvent system and all its dependencies.

Ownership

  • Decide on prop name equivalents to RN onStartShouldSetResponder and onMoveShouldSetResponder.

Focus module

  • Determine the potential use cases for DOM focusin and focusout events.
  • Cross browser and device/modality testing.
  • add focusVisible functionality
  • Add README
  • Write unit tests
    • disabled
    • onBlur
    • onFocus
    • onFocusChange
    • onFocusVisibleChange
  • Determine event object data (might require a global “modality” tracker to help attach this info to focus/blur events)
{
  pointerType: 'mouse' | 'pen' | 'touch' | 'keyboard'
}

Hover module

  • Cross browser and device/modality testing.
  • Determine event object data.
{
  pointerType: 'mouse' | 'pen',
  point: { x: number, y: number }
}
  • Write unit tests (https://github.com/facebook/react/pull/15283)
    • disabled
    • onHoverMove
    • onHoverChange
    • onHoverStart
    • onHoverEnd
    • delayHoverStart
    • delayHoverEnd
    • ensure doesn’t respond to emulated mouse events
  • Add README
  • Add delayHoverStart and delayHoverEnd props.
  • Rename events to onHoverStart, onHoverEnd.

Press module

  • Cross browser and device/modality testing.
  • Behaviour for selecting text within pressable. End press on selection event? Add a new props to configure the behaviour, like onMoveShouldEndPress?
  • Allow contextMenu to display when element is a link and ctrl is held down during press
  • Cancel long press if active press moves (exceeding threshold, IIRC RN uses 10px delta)
  • Reactivate when moving out-of-bounds press back into the responder region.
  • BUG: press start -> move out of target -> release -> tap press. The second press doesn’t cause onPressStart/Change to be called, even thought those events are dispatched to the core responder system. (https://github.com/facebook/react/pull/15507)
  • FYI: touchAction:'none' is needed on currentTarget to prevent browser cancelling after pointermove.
  • Prevent contextMenu appearing during a long press on touch screens.
  • Account for UX involving interactions on links with modifier keys held.
  • Add pressRetentionOffset to control when press is released after moving the pointer away from the press target.
  • Add README
  • Always prevent default on clicks. Maybe have an override to turn off behaviour?
  • Rename events to onPressStart, onPressEnd (https://github.com/facebook/react/pull/15263).
  • Change longPressCancelsPress to onLongPressShouldCancelPress (https://github.com/facebook/react/pull/15263).
  • Change default delayLongPress to 500ms (see note in https://github.com/facebook/react/pull/15290)
  • Add keyboard support for all events.
  • Prevent scroll-down page when pressing Spacebar on keyboard to interact
  • Add delayPressStart and delayPressEnd props.
  • Write unit tests (https://github.com/facebook/react/pull/15290)
    • disabled
    • onLongPress
    • onLongPressChange
    • onLongPressShouldCancelPress
    • onPress
    • onPressChange
    • onPressStart
    • onPressEnd
    • delayLongPress
    • delayPressStart
    • delayPressEnd
    • pressRententionOffset / pressRect
    • emulated mouse events
    • ~fix keyboard press events when metaKey is involved~ (this currently works the same way as native, so will leave it for now)
    • any special case anchor tag-related tests
    • hitslop interactions
  • Determine event object data.
{
  pointerType: 'mouse' | 'pen' | 'touch' | 'keyboard',
  initial: { x: number, y: number },
  point: { x: number, y: number },
  delta:  { x: number, y: number }
}

FocusScope module

Consider adding onFocusIn and onFocusOut (names tbd) to support userland customisation of focus repair. We could return the native elements.

A use case to consider: being able to programmatically move focus to an element without allowing keyboards to focus the element (e.g., the document body, the root of a modal). In this case the element (other than a few special cases) must have tabIndex={-1}.

InputScope module

  • onChange fires when an input element has been changed. This applies to <input>, <textarea>, <select> and elements with contenteditable or when designMode is enabled. onChange provides a callback with the event for the element that changed and a key of the elment that changed (if a key was supplied).
  • onValueChange is similar to onChange, but only provides the value changed. This applies to <input>, <textarea>, <select> and elements with contenteditable or when designMode is enabled. onValueChange provides a value and key of the element that changed (if a key was supplied).
  • onSubmit for when any <form> elements trigger form submit.
  • onKeyPress for when any keyboard keys are pressed.
  • preventKeys accepts an array of key strings that will get prevented from entering input.
  • onSelectionChange for when any any text selection occurs in any child elements.
  • onBeforeChange fires before a change is about to occur. This applies to <input>, <textarea>, <select> and elements with contenteditable or when designMode is enabled. onBeforeChange provides a callback with the event for the element that changed and a key of the elment that changed (if a key was supplied).

Drag module

  • Determine event object data (same as Pan)
  • Cancelling drag.
  • FYI: touchAction:'none' is needed on currentTarget to prevent browser cancelling after pointermove.
  • FYI: Firefox might have problems when combining mousemove with display:flex.
  • Add README
  • Cross browser and device/modality testing.
  • Write unit tests.

Pan module

  • Write unit tests.
  • Cross browser and device/modality testing.
  • Cancelling pan.
  • Add README
  • FYI: touchAction:'none' is needed on currentTarget to prevent browser cancelling after pointermove.
  • Determine event object data.
{
  pointerType: 'mouse' | 'pen' | 'touch',
  initial: { x: number, y: number },
  point: { x: number, y: number },
  velocity: { x: number, y: number },
  delta:  { x: number, y: number }
}

Scroll module

Swipe module

  • Combine onSwipe{Left,Right,Up,Down} into onSwipe w/ event data.
  • Cancelling swipe.
  • Write comprehensive unit tests.
  • Cross browser and device/modality testing.
  • Add README
  • Determine event object data (same as Pan)
  • FYI: touchAction:'none' is needed on currentTarget to prevent browser cancelling after pointermove.

Touch HitSlop

Consider whether we need this at all. Some browsers have a native hitslop and we could work with vendors on any potential improvements to the native system

  • Figure out how to position parent of hitslop.
  • Measurement without reflows (ResizeObserver?)
  • Add README
  • Figure out solution for SSR w/ non-touch interactions if no client-side JS
  • Add touchHitSlop (https://github.com/facebook/react/pull/15261).
  • Add touchHitSlop SSR support

Dev Tools (https://github.com/facebook/react/issues/15267)

  • Add displayName fields to event components and event targets.
  • Possibly add a description or displayName field to event responders? For example the Press responder module for ReactDOM could have the name ReactDOMPressResponder.
  • Expose some DEV only event triggering exports from event responder modules. i.e. HoverEventResponder.DevToolEvents = [{ name: 'hover', trigger: [{ name: 'pointerup', passive: false }]];
  • Add basic support for rendering event responders and event targets in the tree. @bvaughn

Ancillary work

  • Investigate removing object assign polyfill from individual event modules
  • Add internal interactive documentation / fiddle
  • Investigate press event patterns on input, textarea, select, etc.
  • Implement high-level components like Pressable (inc delays).
  • Nested Pressables should not bubble events.
  • Investigate accounting for element resizes when determining hit bounds, e.g., using resize observer for notifications

Issue Analytics

  • State:closed
  • Created 4 years ago
  • Reactions:310
  • Comments:21 (20 by maintainers)

github_iconTop GitHub Comments

26reactions
necolascommented, Dec 13, 2019

We’re not longer working on this particular approach and will be exploring other ways to work with the DOM event system in the future. We’ve concluded that the “Flare” event system is too high-level an abstraction and we’d like to explore something that is a bit more familiar to developers familiar with the DOM (e.g., addEventListener) and React’s existing tools (e.g., hooks). Our goal is still to make it possible for library authors to work with passive events, capture/bubble phase, custom events, and events occurring on the document from within a React function component…while reducing the amount of event-related code needed in ReactDOM. Ultimately building both intermediate abstractions like the Responder Event system and high-level abstractions like useTap (which we prototyped in Flare) should be possible in user-space.

6reactions
Andaristcommented, Dec 17, 2019

That’s a bummer - this API looked awesome and I had high hopes for it. I guess you have good reasons for not pursuing this, I’m eager to learn with what alternative you will come up with.

Read more comments on GitHub >

github_iconTop Results From Across the Web

Jared Palmer on Twitter: "React Flare looks “The idea is to ...
React Flare looks “The idea is to extend React's event system to include high-level events that allow...
Read more >
Framework Integrations - Flare Docs - Laravel error tracking
Full-stack Laravel error tracking made specifically for your Laravel applications and JavaScript frontends.
Read more >
How To Create File Dropzone Component With React | Ripple ...
May 18, 2019 - In this article you will learn how to write dropzone component using React.
Read more >
Reacting to the LUCKIEST Moments in Fortnite History!
Today I react to the LUCKIEST Moments in Fortnite History but I have to ... ☂️Check out Metal Umbrella ! https://metalumbrella.com Metal ...
Read more >
Solar Urticaria: Symptoms, Treatment, and More - Healthline
Most people with solar urticaria react to UVA or visible light. ... Solar urticaria may flare up only from time to time, or...
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Hashnode Post

No results found