Skip to content

Commit f3c0439

Browse files
Fix bug updating hooks and add debounced update for resize events
1 parent c0f52cb commit f3c0439

File tree

5 files changed

+82
-32
lines changed

5 files changed

+82
-32
lines changed

.babelrc

+4-1
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,7 @@
11
{
22
"presets": ["@babel/env", "@babel/react"],
3-
"plugins": ["@babel/plugin-proposal-class-properties"]
3+
"plugins": [
4+
"@babel/plugin-proposal-class-properties",
5+
"@babel/plugin-syntax-dynamic-import"
6+
]
47
}

package.json

+1
Original file line numberDiff line numberDiff line change
@@ -45,6 +45,7 @@
4545
"@babel/cli": "7.2.3",
4646
"@babel/core": "7.4.0",
4747
"@babel/plugin-proposal-class-properties": "7.4.0",
48+
"@babel/plugin-syntax-dynamic-import": "7.2.0",
4849
"@babel/polyfill": "7.4.0",
4950
"@babel/preset-env": "7.4.2",
5051
"@babel/preset-react": "7.0.0",

src/TourHooks.js

+49-16
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
1-
import React, { useState, useReducer, useEffect, createRef } from 'react'
1+
import React, { useState, useReducer, useEffect, useRef, memo } from 'react'
22
import cn from 'classnames'
33
import scrollSmooth from 'scroll-smooth'
44
import Scrollparent from 'scrollparent'
5-
5+
import debounce from 'lodash.debounce'
66
import Portal from './Portal'
77
import {
88
SvgMask,
@@ -22,11 +22,9 @@ function Tour({
2222
isOpen,
2323
startAt,
2424
steps,
25-
2625
scrollDuration,
2726
inViewThreshold,
2827
scrollOffset,
29-
3028
disableInteraction,
3129
disableKeyboardNavigation,
3230
className,
@@ -48,20 +46,24 @@ function Tour({
4846
}) {
4947
const [current, setCurrent] = useState(0)
5048
const [state, dispatch] = useReducer(reducer, initialState)
51-
const helper = createRef()
49+
const helper = useRef(null)
5250

5351
useEffect(() => {
52+
const debouncedShowStep = debounce(showStep, 100)
5453
window.addEventListener('keydown', keyHandler, false)
54+
window.addEventListener('resize', debouncedShowStep, false)
5555

5656
return () => {
5757
window.removeEventListener('keydown', keyHandler)
58+
window.removeEventListener('resize', debouncedShowStep)
5859
}
5960
}, [])
6061

62+
useWhyDidYouUpdate('Counter', { current, state, isOpen })
6163
useEffect(() => {
6264
if (isOpen) {
6365
open(startAt)
64-
showStep()
66+
6567
if (helper.current) {
6668
helper.current.focus()
6769
}
@@ -70,7 +72,7 @@ function Tour({
7072

7173
useEffect(() => {
7274
if (isOpen) showStep()
73-
}, [current])
75+
}, [isOpen, current])
7476

7577
function keyHandler(e) {
7678
e.stopPropagation()
@@ -107,7 +109,7 @@ function Tour({
107109
}
108110

109111
function open(startAt) {
110-
const firstStep = startAt || 0
112+
const firstStep = startAt || current
111113
setCurrent(firstStep)
112114

113115
if (onAfterOpen) {
@@ -130,9 +132,9 @@ function Tour({
130132
function showStep() {
131133
const step = steps[current]
132134
const node = step.selector ? document.querySelector(step.selector) : null
135+
const { w, h } = getWindow()
133136
if (node) {
134137
// DOM node exists
135-
const { w, h } = getWindow()
136138
const nodeRect = hx.getNodeRect(node)
137139

138140
// step is outside view
@@ -153,9 +155,6 @@ function Tour({
153155
// No DOM node
154156
dispatch({
155157
type: 'without_node',
156-
// ...nodeRect,
157-
helperWidth,
158-
helperHeight,
159158
helperPosition: step.position,
160159
w,
161160
h,
@@ -349,11 +348,11 @@ function reducer(state, action) {
349348
top: state.h + 10,
350349
right: state.w / 2 + 9,
351350
bottom: state.h / 2 + 9,
352-
left: w / 2 - state.helperWidth / 2,
351+
left: action.w / 2 - state.helperWidth / 2,
353352
width: 0,
354353
height: 0,
355-
w,
356-
h,
354+
w: action.w,
355+
h: action.h,
357356
helperPosition: 'center',
358357
}
359358
default:
@@ -365,4 +364,38 @@ Tour.propTypes = propTypes
365364

366365
Tour.defaultProps = defaultProps
367366

368-
export default Tour
367+
function useWhyDidYouUpdate(name, props) {
368+
// Get a mutable ref object where we can store props ...
369+
// ... for comparison next time this hook runs.
370+
const previousProps = useRef()
371+
372+
useEffect(() => {
373+
if (previousProps.current) {
374+
// Get all keys from previous and current props
375+
const allKeys = Object.keys({ ...previousProps.current, ...props })
376+
// Use this object to keep track of changed props
377+
const changesObj = {}
378+
// Iterate through keys
379+
allKeys.forEach(key => {
380+
// If previous is different from current
381+
if (previousProps.current[key] !== props[key]) {
382+
// Add to changesObj
383+
changesObj[key] = {
384+
from: previousProps.current[key],
385+
to: props[key],
386+
}
387+
}
388+
})
389+
390+
// If changesObj not empty then output to console
391+
if (Object.keys(changesObj).length) {
392+
console.log('[why-did-you-update]', name, changesObj)
393+
}
394+
}
395+
396+
// Finally update previousProps with current props for next hook call
397+
previousProps.current = props
398+
})
399+
}
400+
401+
export default memo(Tour)

src/demo/App.js

+21-15
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
1-
import React, { Component, useState, useEffect } from 'react'
1+
import React, { Component, useState, useEffect, Suspense, lazy } from 'react'
22
import Demo from './Demo'
3-
import Tour, { Arrow } from '../index'
3+
import { Arrow } from '../index'
44
import Text from './Text'
55
import Glitch from './Glitch'
66
import Tooltip from './Tooltip'
@@ -10,6 +10,10 @@ import { disableBodyScroll, enableBodyScroll } from 'body-scroll-lock'
1010

1111
import './styles.css'
1212

13+
const LazyTour = React.lazy(() =>
14+
import(/* webpackChunkName: "reactour" */ '../index')
15+
)
16+
1317
function App() {
1418
const [isTourOpen, setOpen] = useState(false)
1519
const [isShowingMore, setShowingMore] = useState(false)
@@ -41,18 +45,20 @@ function App() {
4145
toggleShowMore={() => setShowingMore(!isShowingMore)}
4246
isShowingMore={isShowingMore}
4347
/>
44-
<Tour
45-
onAfterOpen={disableBody}
46-
onBeforeClose={enableBody}
47-
onRequestClose={() => setOpen(false)}
48-
steps={tourConfig}
49-
isOpen={isTourOpen}
50-
maskClassName="mask"
51-
className="helper"
52-
rounded={5}
53-
accentColor={accentColor}
54-
CustomHelper={customComps ? MyCustomHelper : null}
55-
/>
48+
<Suspense fallback={<React.Fragment />}>
49+
<LazyTour
50+
onAfterOpen={disableBody}
51+
onBeforeClose={enableBody}
52+
onRequestClose={() => setOpen(false)}
53+
steps={tourConfig}
54+
isOpen={isTourOpen}
55+
maskClassName="mask"
56+
className="helper"
57+
rounded={5}
58+
accentColor={accentColor}
59+
CustomHelper={customComps ? MyCustomHelper : null}
60+
/>
61+
</Suspense>
5662
</div>
5763
)
5864
}
@@ -116,7 +122,7 @@ const tourConfig = [
116122
"Ok, let's start with the name of the Tour that is about to begin.",
117123
},
118124
{
119-
selector: '[data-tut="reactour__logo"]',
125+
selector: '[data-tut="reactour__logoooo"]',
120126
content: 'And this is our cool bus...',
121127
},
122128
{

yarn.lock

+7
Original file line numberDiff line numberDiff line change
@@ -345,6 +345,13 @@
345345
dependencies:
346346
"@babel/helper-plugin-utils" "^7.0.0"
347347

348+
349+
version "7.2.0"
350+
resolved "https://registry.yarnpkg.com/@babel/plugin-syntax-dynamic-import/-/plugin-syntax-dynamic-import-7.2.0.tgz#69c159ffaf4998122161ad8ebc5e6d1f55df8612"
351+
integrity sha512-mVxuJ0YroI/h/tbFTPGZR8cv6ai+STMKNBq0f8hFxsxWjl94qqhsb+wXbpNMDPU3cfR1TIsVFzU3nXyZMqyK4w==
352+
dependencies:
353+
"@babel/helper-plugin-utils" "^7.0.0"
354+
348355
"@babel/plugin-syntax-json-strings@^7.2.0":
349356
version "7.2.0"
350357
resolved "https://registry.yarnpkg.com/@babel/plugin-syntax-json-strings/-/plugin-syntax-json-strings-7.2.0.tgz#72bd13f6ffe1d25938129d2a186b11fd62951470"

0 commit comments

Comments
 (0)