1- import { useEffect , useState , useRef } from 'react'
1+ import { useEffect , useState , useRef , useLayoutEffect } from 'react'
22import classNames from 'classnames'
33import debounce from 'utils/debounce'
44import { TooltipContent } from 'components/TooltipContent'
@@ -73,6 +73,19 @@ const Tooltip = ({
7373 setAnchorsBySelect ( [ ] )
7474 }
7575 } , [ anchorSelect ] )
76+ const mounted = useRef ( false )
77+
78+ /**
79+ * useLayoutEffect runs before useEffect,
80+ * but should be used carefully because of caveats
81+ * https://beta.reactjs.org/reference/react/useLayoutEffect#caveats
82+ */
83+ useLayoutEffect ( ( ) => {
84+ mounted . current = true
85+ return ( ) => {
86+ mounted . current = false
87+ }
88+ } , [ ] )
7689
7790 useEffect ( ( ) => {
7891 if ( ! show ) {
@@ -91,12 +104,18 @@ const Tooltip = ({
91104 } , [ show ] )
92105
93106 const handleShow = ( value : boolean ) => {
107+ if ( ! mounted . current ) {
108+ return
109+ }
94110 setRendered ( true )
95111 /**
96112 * wait for the component to render and calculate position
97113 * before actually showing
98114 */
99115 setTimeout ( ( ) => {
116+ if ( ! mounted . current ) {
117+ return
118+ }
100119 setIsOpen ?.( value )
101120 if ( isOpen === undefined ) {
102121 setShow ( value )
@@ -375,23 +394,13 @@ const Tooltip = ({
375394 * rendered is also a dependency to ensure anchor observers are re-registered
376395 * since `tooltipRef` becomes stale after removing/adding the tooltip to the DOM
377396 */
378- } , [
379- rendered ,
380- anchorRefs ,
381- activeAnchor ,
382- closeOnEsc ,
383- anchorId ,
384- anchorsBySelect ,
385- events ,
386- delayHide ,
387- delayShow ,
388- ] )
397+ } , [ rendered , anchorRefs , activeAnchor , closeOnEsc , events , delayHide , delayShow ] )
389398
390399 useEffect ( ( ) => {
391400 if ( position ) {
392401 // if `position` is set, override regular and `float` positioning
393402 handleTooltipPosition ( position )
394- return ( ) => null
403+ return
395404 }
396405
397406 if ( float ) {
@@ -406,10 +415,9 @@ const Tooltip = ({
406415 handleTooltipPosition ( lastFloatPosition . current )
407416 }
408417 // if `float` is set, override regular positioning
409- return ( ) => null
418+ return
410419 }
411420
412- let mounted = true
413421 computeTooltipPosition ( {
414422 place,
415423 offset,
@@ -419,7 +427,7 @@ const Tooltip = ({
419427 strategy : positionStrategy ,
420428 middlewares,
421429 } ) . then ( ( computedStylesData ) => {
422- if ( ! mounted ) {
430+ if ( ! mounted . current ) {
423431 // invalidate computed positions after remount
424432 return
425433 }
@@ -430,21 +438,7 @@ const Tooltip = ({
430438 setInlineArrowStyles ( computedStylesData . tooltipArrowStyles )
431439 }
432440 } )
433- return ( ) => {
434- mounted = false
435- }
436- } , [
437- show ,
438- anchorId ,
439- anchorsBySelect ,
440- activeAnchor ,
441- content ,
442- html ,
443- place ,
444- offset ,
445- positionStrategy ,
446- position ,
447- ] )
441+ } , [ show , activeAnchor , content , html , place , offset , positionStrategy , position ] )
448442
449443 useEffect ( ( ) => {
450444 const anchorById = document . querySelector < HTMLElement > ( `[id='${ anchorId } ']` )
0 commit comments