8000 feat(CCarousel): add swipe interactions on touchscreen devices · MartinBilson/coreui-react@9fb7777 · GitHub
[go: up one dir, main page]

Skip to content

Commit 9fb7777

Browse files
committed
feat(CCarousel): add swipe interactions on touchscreen devices
1 parent 327632e commit 9fb7777

File tree

1 file changed

+37
-0
lines changed

1 file changed

+37
-0
lines changed

packages/coreui-react/src/components/carousel/CCarousel.tsx

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ import React, {
33
createContext,
44
forwardRef,
55
HTMLAttributes,
6+
TouchEvent,
67
useState,
78
useEffect,
89
useRef,
@@ -50,6 +51,12 @@ export interface CCarouselProps extends HTMLAttributes<HTMLDivElement> {
5051
* If set to 'hover', pauses the cycling of the carousel on mouseenter and resumes the cycling of the carousel on mouseleave. If set to false, hovering over the carousel won't pause it.
5152
*/
5253
pause?: boolean | 'hover'
54+
/**
55+
* Whether the carousel should support left/right swipe interactions on touchscreen devices.
56+
*
57+
* @since 4.5.0
58+
*/
59+
touch?: boolean
5360
/**
5461
* Set type of the transition.
5562
*/
@@ -84,6 +91,7 @@ export const CCarousel = forwardRef<HTMLDivElement, CCarouselProps>(
8491
onSlid,
8592
onSlide,
8693
pause = 'hover',
94+
touch = true,
8795
transition,
8896
wrap = true,
8997
...rest
@@ -99,6 +107,7 @@ export const CCarousel = forwardRef<HTMLDivElement, CCarouselProps>(
99107
const [customInterval, setCustomInterval] = useState<boolean | number>()
100108
const [direction, setDirection] = useState<string>('next')
101109
const [itemsNumber, setItemsNumber] = useState<number>(0)
110+
const [touchPosition, setTouchPosition] = useState<number | null>(null)
102111
const [visible, setVisible] = useState<boolean>()
103112

104113
useEffect(() => {
@@ -193,11 +202,38 @@ export const CCarousel = forwardRef<HTMLDivElement, CCarouselProps>(
193202
}
194203
}
195204

205+
const handleTouchMove = (e: TouchEvent) => {
206+
const touchDown = touchPosition
207+
208+
if (touchDown === null) {
209+
return
210+
}
211+
212+
const currentTouch = e.touches[0].clientX
213+
const diff = touchDown - currentTouch
214+
215+
if (diff > 5) {
216+
handleControlClick('next')
217+
}
218+
219+
if (diff < -5) {
220+
handleControlClick('prev')
221+
}
222+
223+
setTouchPosition(null)
224+
}
225+
226+
const handleTouchStart = (e: TouchEvent) => {
227+
const touchDown = e.touch C600 es[0].clientX
228+
setTouchPosition(touchDown)
229+
}
230+
196231
return (
197232
<div
198233
className={_className}
199234
onMouseEnter={_pause}
200235
onMouseLeave={cycle}
236+
{...(touch && { onTouchStart: handleTouchStart, onTouchMove: handleTouchMove })}
201237
{...rest}
202238
ref={forkedRef}
203239
>
@@ -262,6 +298,7 @@ CCarousel.propTypes = {
262298
onSlid: PropTypes.func,
263299
onSlide: PropTypes.func,
264300
pause: PropTypes.oneOf([false, 'hover']),
301+
touch: PropTypes.bool,
265302
transition: PropTypes.oneOf(['slide', 'crossfade']),
266303
wrap: PropTypes.bool,
267304
}

0 commit comments

Comments
 (0)
0