react-spring-carousel 3.0.0-beta010 → 3.0.0-beta015

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/umd/index.js CHANGED
@@ -1,779 +1,2 @@
1
- (function (global, factory) {
2
- typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('react/jsx-runtime'), require('@react-spring/web'), require('react'), require('@use-gesture/react'), require('screenfull')) :
3
- typeof define === 'function' && define.amd ? define(['exports', 'react/jsx-runtime', '@react-spring/web', 'react', '@use-gesture/react', 'screenfull'], factory) :
4
- (global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.ReactSpringCarousel = {}, global.ReactJSXRuntime, global.ReactSpring, global.React, global.UseGestureReact, global.Screenfull));
5
- })(this, (function (exports, jsxRuntime, web, react, react$1, screenfull) { 'use strict';
6
-
7
- const eventLabel = 'RSC::Event';
8
- function useEventsModule() {
9
- const targetEvent = react.useRef(null);
10
- react.useEffect(() => {
11
- targetEvent.current = document.createElement('div');
12
- }, []);
13
- function useListenToCustomEvent(eventHandler) {
14
- react.useEffect(() => {
15
- function handleEvent(event) {
16
- eventHandler(event.detail);
17
- }
18
- if (targetEvent.current) {
19
- // @ts-ignore
20
- targetEvent.current.addEventListener(eventLabel, handleEvent, false);
21
- return () => {
22
- var _a;
23
- // @ts-ignore
24
- (_a = targetEvent.current) === null || _a === void 0 ? void 0 : _a.removeEventListener(eventLabel, handleEvent, false);
25
- };
26
- }
27
- }, []);
28
- }
29
- function emitEvent(event) {
30
- if (targetEvent.current) {
31
- const newEvent = new CustomEvent(eventLabel, {
32
- detail: event,
33
- });
34
- targetEvent.current.dispatchEvent(newEvent);
35
- }
36
- }
37
- return {
38
- useListenToCustomEvent,
39
- emitEvent,
40
- };
41
- }
42
-
43
- function useFullscreenModule({ mainCarouselWrapperRef, emitEvent, handleResize, }) {
44
- const isFullscreen = react.useRef(false);
45
- react.useEffect(() => {
46
- function handleFullscreenChange() {
47
- if (document.fullscreenElement) {
48
- setIsFullscreen(true);
49
- emitEvent({
50
- eventName: 'onFullscreenChange',
51
- isFullscreen: true,
52
- });
53
- handleResize && handleResize();
54
- }
55
- if (!document.fullscreenElement) {
56
- setIsFullscreen(false);
57
- emitEvent({
58
- eventName: 'onFullscreenChange',
59
- isFullscreen: false,
60
- });
61
- handleResize && handleResize();
62
- }
63
- }
64
- if (screenfull.isEnabled) {
65
- screenfull.on('change', handleFullscreenChange);
66
- return () => {
67
- if (screenfull.isEnabled) {
68
- screenfull.off('change', handleFullscreenChange);
69
- }
70
- };
71
- }
72
- }, []);
73
- function setIsFullscreen(_isFullscreen) {
74
- isFullscreen.current = _isFullscreen;
75
- }
76
- function getIsFullscreen() {
77
- return isFullscreen.current;
78
- }
79
- function enterFullscreen(elementRef) {
80
- if (screenfull.isEnabled) {
81
- screenfull.request((elementRef || mainCarouselWrapperRef.current));
82
- }
83
- }
84
- function exitFullscreen() {
85
- screenfull.isEnabled && screenfull.exit();
86
- }
87
- return {
88
- enterFullscreen,
89
- exitFullscreen,
90
- getIsFullscreen,
91
- };
92
- }
93
-
94
- function isInViewport(el) {
95
- const rect = el.getBoundingClientRect();
96
- return (rect.top >= 0 &&
97
- rect.left >= 0 &&
98
- rect.bottom <= (window.innerHeight || document.documentElement.clientHeight) &&
99
- rect.right <= (window.innerWidth || document.documentElement.clientWidth));
100
- }
101
- function useThumbsModule({ thumbsSlideAxis = 'x', withThumbs = false, prepareThumbsData, items, }) {
102
- const wrapperRef = react.useRef(null);
103
- const [spring, setSpring] = web.useSpring(() => ({
104
- val: 0,
105
- }));
106
- function getTotalScrollValue() {
107
- var _a;
108
- return Math.round(Number((_a = wrapperRef.current) === null || _a === void 0 ? void 0 : _a[thumbsSlideAxis === 'x' ? 'scrollWidth' : 'scrollHeight']) -
109
- wrapperRef.current.getBoundingClientRect()[thumbsSlideAxis === 'x' ? 'width' : 'height']);
110
- }
111
- function handleScroll(activeItem) {
112
- var _a, _b;
113
- function getThumbNode() {
114
- if (wrapperRef.current) {
115
- return wrapperRef.current.querySelector(`#thumb-item-${items[activeItem].id}`);
116
- }
117
- return null;
118
- }
119
- const thumbNode = getThumbNode();
120
- if (thumbNode && wrapperRef.current) {
121
- if (!isInViewport(thumbNode)) {
122
- const offset = thumbNode.offsetLeft;
123
- const val = offset > getTotalScrollValue() ? getTotalScrollValue() : offset;
124
- setSpring.start({
125
- from: {
126
- val: (_b = (_a = wrapperRef.current) === null || _a === void 0 ? void 0 : _a[thumbsSlideAxis === 'x' ? 'scrollLeft' : 'scrollTop']) !== null && _b !== void 0 ? _b : 0,
127
- },
128
- to: {
129
- val,
130
- },
131
- onChange: ({ value }) => {
132
- if (wrapperRef.current) {
133
- wrapperRef.current[thumbsSlideAxis === 'x' ? 'scrollLeft' : 'scrollTop'] =
134
- Math.abs(value.val);
135
- }
136
- },
137
- });
138
- }
139
- }
140
- }
141
- function handlePrepareThumbsData() {
142
- function getPreparedItems(_items) {
143
- return _items.map(i => ({
144
- id: i.id,
145
- renderThumb: i.renderThumb,
146
- }));
147
- }
148
- if (prepareThumbsData) {
149
- return prepareThumbsData(getPreparedItems(items));
150
- }
151
- return getPreparedItems(items);
152
- }
153
- const thumbsFragment = withThumbs ? (jsxRuntime.jsx("div", Object.assign({ className: "use-spring-carousel-thumbs-wrapper", ref: wrapperRef, onWheel: () => spring.val.stop(), style: Object.assign({ display: 'flex', flex: '1', position: 'relative', width: '100%', height: '100%', flexDirection: thumbsSlideAxis === 'x' ? 'row' : 'column' }, (thumbsSlideAxis === 'x'
154
- ? { overflowX: 'auto' }
155
- : {
156
- overflowY: 'auto',
157
- maxHeight: '100%',
158
- })) }, { children: handlePrepareThumbsData().map(({ id, renderThumb }) => {
159
- const thumbId = `thumb-item-${id}`;
160
- return (jsxRuntime.jsx("div", Object.assign({ id: thumbId, className: "thumb-item" }, { children: renderThumb }), thumbId));
161
- }) }))) : null;
162
- return {
163
- thumbsFragment,
164
- handleScroll,
165
- };
166
- }
167
-
168
- function useSpringCarousel({ items, init = true, withThumbs, thumbsSlideAxis = 'x', itemsPerSlide = 1, slideType = 'fixed', gutter = 0, withLoop = false, startEndGutter = 0, carouselSlideAxis = 'x', disableGestures = false, draggingSlideTreshold: _draggingSlideTreshold, slideWhenThresholdIsReached = false, freeScroll, enableFreeScrollDrag, initialStartingPosition, prepareThumbsData, initialActiveItem = 0, }) {
169
- const prevWindowWidth = react.useRef(0);
170
- const draggingSlideTreshold = react.useRef(_draggingSlideTreshold !== null && _draggingSlideTreshold !== void 0 ? _draggingSlideTreshold : 0);
171
- const slideActionType = react.useRef('initial');
172
- const slideModeType = react.useRef('initial');
173
- const prevSlidedValue = react.useRef(0);
174
- const [spring, setSpring] = web.useSpring(() => ({
175
- val: 0,
176
- pause: !init,
177
- onChange({ value }) {
178
- if (freeScroll && mainCarouselWrapperRef.current) {
179
- setStartEndItemReachedOnFreeScroll();
180
- if (carouselSlideAxis === 'x') {
181
- mainCarouselWrapperRef.current.scrollLeft = Math.abs(value.val);
182
- }
183
- else {
184
- mainCarouselWrapperRef.current.scrollTop = Math.abs(value.val);
185
- }
186
- }
187
- else if (carouselTrackWrapperRef.current) {
188
- if (carouselSlideAxis === 'x') {
189
- carouselTrackWrapperRef.current.style.transform = `translate3d(${value.val}px, 0px,0px)`;
190
- }
191
- else {
192
- carouselTrackWrapperRef.current.style.transform = `translate3d(0px,${value.val}px,0px)`;
193
- }
194
- }
195
- },
196
- }));
197
- const activeItem = react.useRef(initialActiveItem);
198
- const firstItemReached = react.useRef(initialActiveItem === 0);
199
- const lastItemReached = react.useRef(false);
200
- const mainCarouselWrapperRef = react.useRef(null);
201
- const carouselTrackWrapperRef = react.useRef(null);
202
- const getItems = react.useCallback(() => {
203
- if (withLoop) {
204
- return [
205
- ...items.map(i => (Object.assign(Object.assign({}, i), { id: `prev-repeated-item-${i.id}` }))),
206
- ...items,
207
- ...items.map(i => (Object.assign(Object.assign({}, i), { id: `next-repeated-item-${i.id}` }))),
208
- ];
209
- }
210
- return [...items];
211
- }, [items, withLoop]);
212
- const internalItems = getItems();
213
- const { emitEvent, useListenToCustomEvent } = useEventsModule();
214
- const { thumbsFragment, handleScroll } = useThumbsModule({
215
- withThumbs: !!withThumbs,
216
- thumbsSlideAxis,
217
- prepareThumbsData,
218
- items: items,
219
- });
220
- const { enterFullscreen, exitFullscreen, getIsFullscreen } = useFullscreenModule({
221
- mainCarouselWrapperRef,
222
- emitEvent,
223
- handleResize: () => adjustCarouselWrapperPosition(),
224
- });
225
- function getItemStyles() {
226
- if (slideType === 'fixed' && !freeScroll) {
227
- return {
228
- marginRight: `${gutter}px`,
229
- flex: `1 0 calc(100% / ${itemsPerSlide} - ${(gutter * (itemsPerSlide - 1)) / itemsPerSlide}px)`,
230
- };
231
- }
232
- return Object.assign({ marginRight: `${gutter}px` });
233
- }
234
- function getSlideValue() {
235
- var _a;
236
- const carouselItem = (_a = mainCarouselWrapperRef.current) === null || _a === void 0 ? void 0 : _a.querySelector('.use-spring-carousel-item');
237
- if (!carouselItem) {
238
- throw Error('No carousel items available!');
239
- }
240
- return (carouselItem.getBoundingClientRect()[carouselSlideAxis === 'x' ? 'width' : 'height'] + gutter);
241
- }
242
- function slideToItem({ from, to, nextActiveItem, immediate = false, slideMode, }) {
243
- slideModeType.current = slideMode;
244
- if (typeof nextActiveItem === 'number') {
245
- if (!freeScroll) {
246
- activeItem.current = nextActiveItem;
247
- }
248
- emitEvent({
249
- eventName: 'onSlideStartChange',
250
- slideActionType: slideActionType.current,
251
- slideMode: slideModeType.current,
252
- nextItem: {
253
- startReached: firstItemReached.current,
254
- endReached: lastItemReached.current,
255
- index: freeScroll ? -1 : activeItem.current,
256
- id: freeScroll ? '' : items[activeItem.current].id,
257
- },
258
- });
259
- }
260
- prevSlidedValue.current = to;
261
- setSpring.start({
262
- immediate,
263
- from: {
264
- val: from,
265
- },
266
- to: {
267
- val: to,
268
- },
269
- config: Object.assign(Object.assign({}, web.config.default), { velocity: spring.val.velocity }),
270
- onRest(value) {
271
- if (!immediate && value.finished) {
272
- emitEvent({
273
- eventName: 'onSlideChange',
274
- slideActionType: slideActionType.current,
275
- slideMode: slideModeType.current,
276
- currentItem: {
277
- startReached: firstItemReached.current,
278
- endReached: lastItemReached.current,
279
- index: freeScroll ? -1 : activeItem.current,
280
- id: freeScroll ? '' : items[activeItem.current].id,
281
- },
282
- });
283
- }
284
- },
285
- });
286
- if (withThumbs && !immediate) {
287
- handleScroll(activeItem.current);
288
- }
289
- }
290
- function getTotalScrollValue() {
291
- var _a;
292
- if (withLoop) {
293
- return getSlideValue() * items.length;
294
- }
295
- return Math.round(Number((_a = carouselTrackWrapperRef.current) === null || _a === void 0 ? void 0 : _a[carouselSlideAxis === 'x' ? 'scrollWidth' : 'scrollHeight']) -
296
- carouselTrackWrapperRef.current.getBoundingClientRect()[carouselSlideAxis === 'x' ? 'width' : 'height']);
297
- }
298
- function getAnimatedWrapperStyles() {
299
- const percentValue = `calc(100% - ${startEndGutter * 2}px)`;
300
- return {
301
- width: carouselSlideAxis === 'x' ? percentValue : '100%',
302
- height: carouselSlideAxis === 'y' ? percentValue : '100%',
303
- };
304
- }
305
- function getCarouselItemWidth() {
306
- var _a;
307
- const carouselItem = (_a = carouselTrackWrapperRef.current) === null || _a === void 0 ? void 0 : _a.querySelector('.use-spring-carousel-item');
308
- if (!carouselItem) {
309
- throw Error('No carousel items available!');
310
- }
311
- return (carouselItem.getBoundingClientRect()[carouselSlideAxis === 'x' ? 'width' : 'height'] + gutter);
312
- }
313
- function adjustCarouselWrapperPosition() {
314
- const positionProperty = carouselSlideAxis === 'x' ? 'left' : 'top';
315
- function setPosition(v) {
316
- const ref = carouselTrackWrapperRef.current;
317
- if (!ref)
318
- return;
319
- if (withLoop) {
320
- ref.style.top = '0px';
321
- ref.style.left = '0px';
322
- ref.style[positionProperty] = `-${v - startEndGutter}px`;
323
- }
324
- else {
325
- ref.style.left = '0px';
326
- ref.style.top = '0px';
327
- }
328
- }
329
- const currentFromValue = Math.abs(getFromValue());
330
- if (currentFromValue < getTotalScrollValue() && lastItemReached.current) {
331
- lastItemReached.current = false;
332
- }
333
- if (currentFromValue > getTotalScrollValue()) {
334
- const val = -getTotalScrollValue();
335
- lastItemReached.current = true;
336
- prevSlidedValue.current = val;
337
- setSpring.start({
338
- immediate: true,
339
- val,
340
- });
341
- return;
342
- }
343
- if (initialStartingPosition === 'center') {
344
- setPosition(getCarouselItemWidth() * items.length -
345
- getSlideValue() * Math.round((itemsPerSlide - 1) / 2));
346
- }
347
- else if (initialStartingPosition === 'end') {
348
- setPosition(getCarouselItemWidth() * items.length -
349
- getSlideValue() * Math.round(itemsPerSlide - 1));
350
- }
351
- else {
352
- setPosition(getCarouselItemWidth() * items.length);
353
- }
354
- if (!freeScroll && slideType === 'fixed') {
355
- const val = -(getSlideValue() * activeItem.current);
356
- prevSlidedValue.current = val;
357
- setSpring.start({
358
- immediate: true,
359
- val,
360
- });
361
- }
362
- }
363
- function getFromValue() {
364
- if (freeScroll && mainCarouselWrapperRef.current) {
365
- return mainCarouselWrapperRef.current[carouselSlideAxis === 'x' ? 'scrollLeft' : 'scrollTop'];
366
- }
367
- return spring.val.get();
368
- }
369
- function getToValue(type, index) {
370
- if (freeScroll && type === 'next') {
371
- const next = prevSlidedValue.current + getSlideValue();
372
- if (next > getTotalScrollValue()) {
373
- return getTotalScrollValue();
374
- }
375
- return next;
376
- }
377
- if (freeScroll && type === 'prev') {
378
- const next = prevSlidedValue.current - getSlideValue();
379
- if (next < 0) {
380
- return 0;
381
- }
382
- return next;
383
- }
384
- if (type === 'next') {
385
- if (index) {
386
- return -(index * getSlideValue());
387
- }
388
- return prevSlidedValue.current - getSlideValue();
389
- }
390
- if (index) {
391
- return -(index * getSlideValue());
392
- }
393
- return prevSlidedValue.current + getSlideValue();
394
- }
395
- function slideToPrevItem(type = 'click', index) {
396
- if (!init || (firstItemReached.current && !withLoop))
397
- return;
398
- slideActionType.current = 'prev';
399
- lastItemReached.current = false;
400
- const nextItem = index || activeItem.current - 1;
401
- if (!withLoop) {
402
- const nextItemWillExceed = getToValue('prev', index) + getSlideValue() / 3 > 0;
403
- if (firstItemReached.current)
404
- return;
405
- if (nextItemWillExceed) {
406
- firstItemReached.current = true;
407
- lastItemReached.current = false;
408
- slideToItem({
409
- slideMode: type,
410
- from: getFromValue(),
411
- to: 0,
412
- nextActiveItem: 0,
413
- });
414
- return;
415
- }
416
- }
417
- if (withLoop && firstItemReached.current) {
418
- firstItemReached.current = false;
419
- lastItemReached.current = true;
420
- slideToItem({
421
- slideMode: type,
422
- from: getFromValue() - getSlideValue() * items.length,
423
- to: -(getSlideValue() * items.length) + getSlideValue(),
424
- nextActiveItem: items.length - 1,
425
- });
426
- return;
427
- }
428
- if (nextItem === 0) {
429
- firstItemReached.current = true;
430
- }
431
- if (nextItem === items.length - 1 || nextItem === -1) {
432
- lastItemReached.current = true;
433
- }
434
- slideToItem({
435
- slideMode: type,
436
- from: getFromValue(),
437
- to: getToValue('prev', index),
438
- nextActiveItem: nextItem,
439
- });
440
- }
441
- function slideToNextItem(type = 'click', index) {
442
- if (!init || (lastItemReached.current && !withLoop))
443
- return;
444
- slideActionType.current = 'next';
445
- firstItemReached.current = false;
446
- const nextItem = index || activeItem.current + 1;
447
- if (!withLoop) {
448
- const nextItemWillExceed = Math.abs(getToValue('next', index)) > getTotalScrollValue() - getSlideValue() / 3;
449
- if (lastItemReached.current)
450
- return;
451
- if (nextItemWillExceed) {
452
- firstItemReached.current = false;
453
- lastItemReached.current = true;
454
- slideToItem({
455
- slideMode: type,
456
- from: getFromValue(),
457
- to: -getTotalScrollValue(),
458
- nextActiveItem: nextItem,
459
- });
460
- return;
461
- }
462
- }
463
- if (withLoop && lastItemReached.current) {
464
- lastItemReached.current = false;
465
- firstItemReached.current = true;
466
- slideToItem({
467
- slideMode: type,
468
- from: getFromValue() + getSlideValue() * items.length,
469
- to: 0,
470
- nextActiveItem: 0,
471
- });
472
- return;
473
- }
474
- if (nextItem === 0) {
475
- firstItemReached.current = true;
476
- }
477
- if (nextItem === items.length - 1) {
478
- lastItemReached.current = true;
479
- }
480
- slideToItem({
481
- slideMode: type,
482
- from: getFromValue(),
483
- to: getToValue('next', index),
484
- nextActiveItem: nextItem,
485
- });
486
- }
487
- react.useEffect(() => {
488
- prevWindowWidth.current = window.innerWidth;
489
- }, []);
490
- react.useEffect(() => {
491
- adjustCarouselWrapperPosition();
492
- }, [
493
- initialStartingPosition,
494
- itemsPerSlide,
495
- withLoop,
496
- startEndGutter,
497
- gutter,
498
- freeScroll,
499
- slideType,
500
- init,
501
- ]);
502
- react.useLayoutEffect(() => {
503
- /**
504
- * Set initial track position
505
- */
506
- if (carouselTrackWrapperRef.current) {
507
- adjustCarouselWrapperPosition();
508
- }
509
- // eslint-disable-next-line react-hooks/exhaustive-deps
510
- }, []);
511
- react.useEffect(() => {
512
- if (_draggingSlideTreshold) {
513
- draggingSlideTreshold.current = _draggingSlideTreshold;
514
- }
515
- else {
516
- draggingSlideTreshold.current = Math.floor(getSlideValue() / 2 / 2);
517
- }
518
- }, [_draggingSlideTreshold]);
519
- react.useEffect(() => {
520
- function handleResize() {
521
- if (window.innerWidth === prevWindowWidth.current)
522
- return;
523
- prevWindowWidth.current = window.innerWidth;
524
- adjustCarouselWrapperPosition();
525
- }
526
- window.addEventListener('resize', handleResize);
527
- return () => {
528
- window.removeEventListener('resize', handleResize);
529
- };
530
- }, []);
531
- const bindDrag = react$1.useDrag(state => {
532
- const isDragging = state.dragging;
533
- const movement = state.offset[carouselSlideAxis === 'x' ? 0 : 1];
534
- const currentMovement = state.movement[carouselSlideAxis === 'x' ? 0 : 1];
535
- const direction = state.direction[carouselSlideAxis === 'x' ? 0 : 1];
536
- const prevItemTreshold = currentMovement > draggingSlideTreshold.current;
537
- const nextItemTreshold = currentMovement < -draggingSlideTreshold.current;
538
- if (isDragging) {
539
- if (direction > 0) {
540
- slideActionType.current = 'prev';
541
- }
542
- else {
543
- slideActionType.current = 'next';
544
- }
545
- emitEvent(Object.assign(Object.assign({}, state), { eventName: 'onDrag', slideActionType: slideActionType.current }));
546
- if (freeScroll) {
547
- if (slideActionType.current === 'prev' && movement > 0) {
548
- state.cancel();
549
- setSpring.start({
550
- from: {
551
- val: getFromValue(),
552
- },
553
- to: {
554
- val: 0,
555
- },
556
- config: {
557
- velocity: state.velocity,
558
- friction: 50,
559
- tension: 1000,
560
- },
561
- });
562
- return;
563
- }
564
- setSpring.start({
565
- from: {
566
- val: getFromValue(),
567
- },
568
- to: {
569
- val: -movement,
570
- },
571
- config: {
572
- velocity: state.velocity,
573
- friction: 50,
574
- tension: 1000,
575
- },
576
- });
577
- return;
578
- }
579
- setSpring.start({
580
- val: movement,
581
- config: {
582
- velocity: state.velocity,
583
- friction: 50,
584
- tension: 1000,
585
- },
586
- });
587
- if (slideWhenThresholdIsReached && nextItemTreshold) {
588
- slideToNextItem('drag');
589
- state.cancel();
590
- }
591
- else if (slideWhenThresholdIsReached && prevItemTreshold) {
592
- slideToPrevItem('drag');
593
- state.cancel();
594
- }
595
- return;
596
- }
597
- if (state.last && !state.canceled && freeScroll) {
598
- if (slideActionType.current === 'prev') {
599
- slideToPrevItem('drag');
600
- }
601
- if (slideActionType.current === 'next') {
602
- slideToNextItem('drag');
603
- }
604
- }
605
- if (state.last && !state.canceled && !freeScroll) {
606
- if (nextItemTreshold) {
607
- if (!withLoop && lastItemReached.current) {
608
- setSpring.start({
609
- val: -getTotalScrollValue(),
610
- config: Object.assign(Object.assign({}, web.config.default), { velocity: state.velocity }),
611
- });
612
- }
613
- else {
614
- slideToNextItem('drag');
615
- }
616
- }
617
- else if (prevItemTreshold) {
618
- if (!withLoop && firstItemReached.current) {
619
- setSpring.start({
620
- val: 0,
621
- config: Object.assign(Object.assign({}, web.config.default), { velocity: state.velocity }),
622
- });
623
- }
624
- else {
625
- slideToPrevItem('drag');
626
- }
627
- }
628
- else {
629
- setSpring.start({
630
- val: prevSlidedValue.current,
631
- config: Object.assign(Object.assign({}, web.config.default), { velocity: state.velocity }),
632
- });
633
- }
634
- }
635
- }, {
636
- enabled: (init && !disableGestures && !freeScroll) ||
637
- (!!freeScroll && !!enableFreeScrollDrag),
638
- axis: carouselSlideAxis,
639
- from: () => {
640
- if (freeScroll && mainCarouselWrapperRef.current) {
641
- return [
642
- -mainCarouselWrapperRef.current.scrollLeft,
643
- -mainCarouselWrapperRef.current.scrollTop,
644
- ];
645
- }
646
- if (carouselSlideAxis === 'x') {
647
- return [spring.val.get(), spring.val.get()];
648
- }
649
- return [spring.val.get(), spring.val.get()];
650
- },
651
- });
652
- function getWrapperOverflowStyles() {
653
- if (freeScroll) {
654
- if (carouselSlideAxis === 'x') {
655
- return {
656
- overflowX: 'auto',
657
- };
658
- }
659
- return {
660
- overflowY: 'auto',
661
- };
662
- }
663
- return {};
664
- }
665
- function setStartEndItemReachedOnFreeScroll() {
666
- if (mainCarouselWrapperRef.current) {
667
- prevSlidedValue.current =
668
- mainCarouselWrapperRef.current[carouselSlideAxis === 'x' ? 'scrollLeft' : 'scrollTop'];
669
- if (mainCarouselWrapperRef.current[carouselSlideAxis === 'x' ? 'scrollLeft' : 'scrollTop'] === 0) {
670
- firstItemReached.current = true;
671
- lastItemReached.current = false;
672
- }
673
- if (mainCarouselWrapperRef.current[carouselSlideAxis === 'x' ? 'scrollLeft' : 'scrollTop'] > 0 &&
674
- mainCarouselWrapperRef.current[carouselSlideAxis === 'x' ? 'scrollLeft' : 'scrollTop'] < getTotalScrollValue()) {
675
- firstItemReached.current = false;
676
- lastItemReached.current = false;
677
- }
678
- if (mainCarouselWrapperRef.current[carouselSlideAxis === 'x' ? 'scrollLeft' : 'scrollTop'] === getTotalScrollValue()) {
679
- firstItemReached.current = false;
680
- lastItemReached.current = true;
681
- }
682
- }
683
- }
684
- function getScrollHandlers() {
685
- if (freeScroll) {
686
- return {
687
- onWheel() {
688
- spring.val.stop();
689
- setStartEndItemReachedOnFreeScroll();
690
- },
691
- };
692
- }
693
- return {};
694
- }
695
- function findItemIndex(id) {
696
- return items.findIndex(item => item.id === id);
697
- }
698
- function findItemIndexById(id, error) {
699
- let itemIndex = 0;
700
- if (typeof id === 'string') {
701
- itemIndex = items.findIndex(_item => _item.id === id);
702
- }
703
- else {
704
- itemIndex = id;
705
- }
706
- if (itemIndex < 0 || itemIndex >= items.length) {
707
- throw new Error(error);
708
- }
709
- return itemIndex;
710
- }
711
- function internalSlideToItem(id) {
712
- if (!init)
713
- return;
714
- firstItemReached.current = false;
715
- lastItemReached.current = false;
716
- const itemIndex = findItemIndexById(id, "The item you want to slide to doesn't exist; please check che item id or the index you're passing to.");
717
- if (itemIndex === activeItem.current) {
718
- return;
719
- }
720
- const currentItem = findItemIndex(items[activeItem.current].id);
721
- const newActiveItem = findItemIndex(items[itemIndex].id);
722
- if (newActiveItem > currentItem) {
723
- slideToNextItem('click', newActiveItem);
724
- }
725
- else {
726
- slideToPrevItem('click', newActiveItem);
727
- }
728
- }
729
- function getIsNextItem(id) {
730
- const itemIndex = findItemIndex(id);
731
- const _activeItem = activeItem.current;
732
- if (withLoop && _activeItem === items.length - 1) {
733
- return itemIndex === 0;
734
- }
735
- return itemIndex === _activeItem + 1;
736
- }
737
- function getIsPrevItem(id) {
738
- const itemIndex = findItemIndex(id);
739
- const _activeItem = activeItem.current;
740
- if (withLoop && _activeItem === 0) {
741
- return itemIndex === items.length - 1;
742
- }
743
- return itemIndex === _activeItem - 1;
744
- }
745
- const carouselFragment = (jsxRuntime.jsx("div", Object.assign({ ref: mainCarouselWrapperRef }, getScrollHandlers(), { style: Object.assign({ display: 'flex', position: 'relative', width: '100%', height: '100%' }, getWrapperOverflowStyles()) }, { children: jsxRuntime.jsx("div", Object.assign({ ref: carouselTrackWrapperRef }, bindDrag(), { style: Object.assign({ position: 'relative', display: 'flex', flexDirection: carouselSlideAxis === 'x' ? 'row' : 'column', touchAction: 'none' }, getAnimatedWrapperStyles()) }, { children: internalItems.map((item, index) => {
746
- return (jsxRuntime.jsx("div", Object.assign({ className: "use-spring-carousel-item", "data-testid": "use-spring-carousel-item-wrapper", style: Object.assign({ display: 'flex', position: 'relative', flex: '1' }, getItemStyles()) }, { children: item.renderItem }), `${item.id}-${index}`));
747
- }) })) })));
748
- return {
749
- useListenToCustomEvent,
750
- carouselFragment,
751
- enterFullscreen,
752
- exitFullscreen,
753
- getIsFullscreen,
754
- thumbsFragment,
755
- slideToItem: internalSlideToItem,
756
- getIsNextItem,
757
- getIsPrevItem,
758
- slideToPrevItem: () => slideToPrevItem(),
759
- slideToNextItem: () => slideToNextItem(),
760
- getIsActiveItem: (id) => {
761
- return (findItemIndexById(id, "The item you want to check doesn't exist") ===
762
- activeItem.current);
763
- },
764
- };
765
- }
766
- const Context = react.createContext(undefined);
767
- function useSpringCarouselContext() {
768
- const context = react.useContext(Context);
769
- if (!context) {
770
- throw new Error('useSpringCarouselContext must be used within the carousel.');
771
- }
772
- return context;
773
- }
774
-
775
- exports.useSpringCarousel = useSpringCarousel;
776
- exports.useSpringCarouselContext = useSpringCarouselContext;
777
-
778
- }));
1
+ !function(e,t){"object"==typeof exports&&"undefined"!=typeof module?t(exports,require("react/jsx-runtime"),require("@react-spring/web"),require("react"),require("@use-gesture/react"),require("screenfull")):"function"==typeof define&&define.amd?define(["exports","react/jsx-runtime","@react-spring/web","react","@use-gesture/react","screenfull"],t):t((e="undefined"!=typeof globalThis?globalThis:e||self).ReactSpringCarousel={},e.ReactJSXRuntime,e.ReactSpring,e.React,e.UseGestureReact,e.Screenfull)}(this,(function(e,t,r,n,i,c){"use strict";const u="RSC::Event";function s({thumbsSlideAxis:e="x",withThumbs:i=!1,prepareThumbsData:c,items:u}){const s=n.useRef(null),[o,l]=r.useSpring((()=>({val:0})));function a(){var t;return Math.round(Number(null===(t=s.current)||void 0===t?void 0:t["x"===e?"scrollWidth":"scrollHeight"])-s.current.getBoundingClientRect()["x"===e?"width":"height"])}return{thumbsFragment:i?t.jsx("div",Object.assign({className:"use-spring-carousel-thumbs-wrapper",ref:s,onWheel:()=>o.val.stop(),style:Object.assign({display:"flex",flex:"1",position:"relative",width:"100%",height:"100%",flexDirection:"x"===e?"row":"column"},"x"===e?{overflowX:"auto"}:{overflowY:"auto",maxHeight:"100%"})},{children:function(){function e(e){return e.map((e=>({id:e.id,renderThumb:e.renderThumb})))}return c?c(e(u)):e(u)}().map((({id:e,renderThumb:r})=>{const n=`thumb-item-${e}`;return t.jsx("div",Object.assign({id:n,className:"thumb-item"},{children:r}),n)}))})):null,handleScroll:function(t){var r,n;const i=s.current?s.current.querySelector(`#thumb-item-${u[t].id}`):null;if(i&&s.current&&!function(e){const t=e.getBoundingClientRect();return t.top>=0&&t.left>=0&&t.bottom<=(window.innerHeight||document.documentElement.clientHeight)&&t.right<=(window.innerWidth||document.documentElement.clientWidth)}(i)){const t=i.offsetLeft,c=t>a()?a():t;l.start({from:{val:null!==(n=null===(r=s.current)||void 0===r?void 0:r["x"===e?"scrollLeft":"scrollTop"])&&void 0!==n?n:0},to:{val:c},onChange:({value:t})=>{s.current&&(s.current["x"===e?"scrollLeft":"scrollTop"]=Math.abs(t.val))}})}}}}const o=n.createContext(void 0);e.useSpringCarousel=function({items:e,init:o=!0,withThumbs:l,thumbsSlideAxis:a="x",itemsPerSlide:d=1,slideType:f="fixed",gutter:h=0,withLoop:g=!1,startEndGutter:m=0,carouselSlideAxis:v="x",disableGestures:x=!1,draggingSlideTreshold:p,slideWhenThresholdIsReached:b=!1,freeScroll:w,enableFreeScrollDrag:y,initialStartingPosition:T,prepareThumbsData:E,initialActiveItem:R=0}){const j=d>e.length?e.length:d,S=n.useRef(0),C=n.useRef(null!=p?p:0),I=n.useRef("initial"),F=n.useRef("initial"),O=n.useRef(0),[L,$]=r.useSpring((()=>({val:0,pause:!o,onChange({value:e}){w&&N.current?("x"===v?N.current.scrollLeft=Math.abs(e.val):N.current.scrollTop=Math.abs(e.val),re()):W.current&&(W.current.style.transform="x"===v?`translate3d(${e.val}px, 0px,0px)`:`translate3d(0px,${e.val}px,0px)`)}}))),M=n.useRef(R),A=n.useRef(0===R),k=n.useRef(!1),N=n.useRef(null),W=n.useRef(null),q=n.useCallback((()=>g?[...e.map((e=>Object.assign(Object.assign({},e),{id:`prev-repeated-item-${e.id}`}))),...e,...e.map((e=>Object.assign(Object.assign({},e),{id:`next-repeated-item-${e.id}`})))]:[...e]),[e,g])(),{emitEvent:D,useListenToCustomEvent:P}=function(){const e=n.useRef(null);return n.useEffect((()=>{e.current=document.createElement("div")}),[]),{useListenToCustomEvent:function(t){n.useEffect((()=>{function r(e){t(e.detail)}if(e.current)return e.current.addEventListener(u,r,!1),()=>{var t;null===(t=e.current)||void 0===t||t.removeEventListener(u,r,!1)}}),[])},emitEvent:function(t){if(e.current){const r=new CustomEvent(u,{detail:t});e.current.dispatchEvent(r)}}}}(),{thumbsFragment:B,handleScroll:H}=s({withThumbs:!!l,thumbsSlideAxis:a,prepareThumbsData:E,items:e}),{enterFullscreen:z,exitFullscreen:G,getIsFullscreen:X}=function({mainCarouselWrapperRef:e,onFullScreenChange:t,handleResize:r}){const i=n.useRef(!1);function u(e){i.current=e}return n.useEffect((()=>{function e(){document.fullscreenElement&&(u(!0),t(!0),r&&r()),document.fullscreenElement||(u(!1),t(!1),r&&r())}if(c.isEnabled)return c.on("change",e),()=>{c.isEnabled&&c.off("change",e)}}),[]),{enterFullscreen:function(t){c.isEnabled&&c.request(t||e.current)},exitFullscreen:function(){c.isEnabled&&c.exit()},getIsFullscreen:function(){return i.current}}}({mainCarouselWrapperRef:N,handleResize:()=>Q(),onFullScreenChange:e=>{D({eventName:"onFullscreenChange",isFullscreen:e})}});function Y(){var e;const t=null===(e=N.current)||void 0===e?void 0:e.querySelector(".use-spring-carousel-item");if(!t)throw Error("No carousel items available!");return t.getBoundingClientRect()["x"===v?"width":"height"]+h}function J({from:t,to:n,nextActiveItem:i,immediate:c=!1,slideMode:u}){F.current=u,"number"==typeof i&&(w||(M.current=i),D({eventName:"onSlideStartChange",slideActionType:I.current,slideMode:F.current,nextItem:{startReached:A.current,endReached:k.current,index:w?-1:M.current,id:w?"":e[M.current].id}})),O.current=n,$.start({immediate:c,from:{val:t},to:{val:n},config:Object.assign(Object.assign({},r.config.default),{velocity:L.val.velocity}),onRest(t){!c&&t.finished&&D({eventName:"onSlideChange",slideActionType:I.current,slideMode:F.current,currentItem:{startReached:A.current,endReached:k.current,index:w?-1:M.current,id:w?"":e[M.current].id}})}}),l&&!c&&H(M.current)}function U(){var t;return g?Y()*e.length:Math.round(Number(null===(t=W.current)||void 0===t?void 0:t["x"===v?"scrollWidth":"scrollHeight"])-W.current.getBoundingClientRect()["x"===v?"width":"height"]-2*m)}function K(){var e;const t=null===(e=W.current)||void 0===e?void 0:e.querySelector(".use-spring-carousel-item");if(!t)throw Error("No carousel items available!");return t.getBoundingClientRect()["x"===v?"width":"height"]+h}function Q(){const t="x"===v?"left":"top";function r(e){const r=W.current;r&&(g?(r.style.top="0px",r.style.left="0px",r.style[t]=`-${e-m}px`):(r.style.left="0px",r.style.top="0px"))}const n=Math.abs(V());if(n<U()&&k.current&&(k.current=!1),n>U()){const e=-U();return k.current=!0,O.current=e,void $.start({immediate:!0,val:e})}if(r("center"===T?K()*e.length-Y()*Math.round((j-1)/2):"end"===T?K()*e.length-Y()*Math.round(j-1):K()*e.length),!w&&"fixed"===f){const e=-Y()*M.current;O.current=e,$.start({immediate:!0,val:e})}}function V(){return w&&N.current?N.current["x"===v?"scrollLeft":"scrollTop"]:L.val.get()}function Z(e,t){if(w&&"next"===e){const e=O.current+Y();return e>U()?U():e}if(w&&"prev"===e){const e=O.current-Y();return e<0?0:e}return"next"===e?t?-t*Y():O.current-Y():t?-t*Y():O.current+Y()}function _(t="click",r){if(!o||A.current&&!g)return;I.current="prev",k.current=!1;const n=r||M.current-1;if(!g){const e=w?Z("prev",r)-Y()/3<0:Z("prev",r)+Y()/3>0;if(A.current)return;if(e)return A.current=!0,k.current=!1,void J({slideMode:t,from:V(),to:0,nextActiveItem:0})}if(g&&A.current)return A.current=!1,k.current=!0,void J({slideMode:t,from:V()-Y()*e.length,to:-Y()*e.length+Y(),nextActiveItem:e.length-1});0===n&&(A.current=!0),n!==e.length-1&&-1!==n||(k.current=!0),J({slideMode:t,from:V(),to:Z("prev",r),nextActiveItem:n})}function ee(t="click",r){if(!o||k.current&&!g)return;I.current="next",A.current=!1;const n=r||M.current+1;if(!g){const e=Math.abs(Z("next",r))>U()-Y()/3;if(k.current)return;if(e)return A.current=!1,k.current=!0,void J({slideMode:t,from:V(),to:w?U():-U(),nextActiveItem:n})}if(g&&k.current)return k.current=!1,A.current=!0,void J({slideMode:t,from:V()+Y()*e.length,to:0,nextActiveItem:0});0===n&&(A.current=!0),n===e.length-1&&(k.current=!0),J({slideMode:t,from:V(),to:Z("next",r),nextActiveItem:n})}n.useEffect((()=>{if(o){if(R>e.length-1)throw new Error(`initialActiveItem (${R}) is greater than the total quantity available items (${e.length}).`);j>e.length&&console.warn(`itemsPerSlide (${j}) is greater than the total quantity available items (${e.length}). Fallback to ${e.length})`)}}),[R,e,j,o]),n.useEffect((()=>{S.current=window.innerWidth}),[]),n.useEffect((()=>{Q()}),[T,j,g,m,h,w,f,o]),n.useLayoutEffect((()=>{W.current&&Q()}),[]),n.useEffect((()=>{C.current=p||Math.floor(Y()/2/2)}),[p]),n.useEffect((()=>{function e(){window.innerWidth!==S.current&&(S.current=window.innerWidth,Q())}return window.addEventListener("resize",e),()=>{window.removeEventListener("resize",e)}}),[]);const te=i.useDrag((e=>{const t=e.dragging,n=e.offset["x"===v?0:1],i=e.movement["x"===v?0:1],c=e.direction["x"===v?0:1],u=i>C.current,s=i<-C.current;if(t)return I.current=c>0?"prev":"next",D(Object.assign(Object.assign({},e),{eventName:"onDrag",slideActionType:I.current})),w?"prev"===I.current&&n>0?(e.cancel(),void $.start({from:{val:V()},to:{val:0},config:{velocity:e.velocity,friction:50,tension:1e3}})):void $.start({from:{val:V()},to:{val:-n},config:{velocity:e.velocity,friction:50,tension:1e3}}):($.start({val:n,config:{velocity:e.velocity,friction:50,tension:1e3}}),void(b&&s?(ee("drag"),e.cancel()):b&&u&&(_("drag"),e.cancel())));e.last&&!e.canceled&&w&&("prev"===I.current&&_("drag"),"next"===I.current&&ee("drag")),!e.last||e.canceled||w||(s?!g&&k.current?$.start({val:-U(),config:Object.assign(Object.assign({},r.config.default),{velocity:e.velocity})}):ee("drag"):u?!g&&A.current?$.start({val:0,config:Object.assign(Object.assign({},r.config.default),{velocity:e.velocity})}):_("drag"):$.start({val:O.current,config:Object.assign(Object.assign({},r.config.default),{velocity:e.velocity})}))}),{enabled:o&&!x&&!w||!!w&&!!y,axis:v,from:()=>w&&N.current?[-N.current.scrollLeft,-N.current.scrollTop]:[L.val.get(),L.val.get()]});function re(){N.current&&(O.current=N.current["x"===v?"scrollLeft":"scrollTop"],0===N.current["x"===v?"scrollLeft":"scrollTop"]&&(A.current=!0,k.current=!1),N.current["x"===v?"scrollLeft":"scrollTop"]>0&&N.current["x"===v?"scrollLeft":"scrollTop"]<U()&&(A.current=!1,k.current=!1),N.current["x"===v?"scrollLeft":"scrollTop"]===U()&&(A.current=!1,k.current=!0))}function ne(t,r){let n=0;if(n="string"==typeof t?e.findIndex((e=>e.id===t)):t,n<0||n>=e.length){if(r)throw new Error(r);console.error(`The item doesn't exist; check that the id provided - ${t} - is correct.`),n=-1}return n}const ie=t.jsx("div",Object.assign({ref:N},w?{onWheel(){L.val.stop(),re()}}:{},{style:Object.assign({display:"flex",position:"relative",width:"100%",height:"100%"},w?"x"===v?{overflowX:"auto"}:{overflowY:"auto"}:{})},{children:t.jsxs("div",Object.assign({ref:W},te(),{style:Object.assign({position:"relative",display:"flex",flexDirection:"x"===v?"row":"column",touchAction:"none"},function(){const e=`calc(100% - ${2*m}px)`;return{width:"x"===v?e:"100%",height:"y"===v?e:"100%"}}())},{children:[w&&m?t.jsx("div",{style:{flexShrink:0,width:m}}):null,q.map(((r,n)=>{return t.jsx("div",Object.assign({className:"use-spring-carousel-item","data-testid":"use-spring-carousel-item-wrapper",style:Object.assign({display:"flex",position:"relative",flex:"1"},(i=!!w&&n===e.length-1,"fixed"!==f||w?Object.assign({marginRight:`${i?0:h}px`}):{marginRight:`${i?0:h}px`,flex:`1 0 calc(100% / ${j} - ${h*(j-1)/j}px)`}))},{children:r.renderItem}),`${r.id}-${n}`);var i})),w&&m?t.jsx("div",{style:{flexShrink:0,width:m}}):null]}))}));return w?{useListenToCustomEvent:P,carouselFragment:ie,enterFullscreen:z,exitFullscreen:G,getIsFullscreen:X,thumbsFragment:B,slideToPrevItem:()=>_(),slideToNextItem:()=>ee()}:{useListenToCustomEvent:P,carouselFragment:ie,enterFullscreen:z,exitFullscreen:G,getIsFullscreen:X,thumbsFragment:B,slideToPrevItem:()=>_(),slideToNextItem:()=>ee(),slideToItem:function(t){if(!o)return;A.current=!1,k.current=!1;const r=ne(t,"The item you want to slide to doesn't exist; check the provided id.");if(r===M.current)return;const n=ne(e[M.current].id),i=ne(e[r].id);i>n?ee("click",i):_("click",i)},getIsNextItem:function(t){const r=ne(t,"The item doesn't exist; check the provided id."),n=M.current;return g&&n===e.length-1?0===r:r===n+1},getIsPrevItem:function(t){const r=ne(t,"The item doesn't exist; check the provided id."),n=M.current;return g&&0===n?r===e.length-1:r===n-1},getIsActiveItem:e=>ne(e,"The item you want to check doesn't exist; check the provided id.")===M.current}},e.useSpringCarouselContext=function(){const e=n.useContext(o);if(!e)throw new Error("useSpringCarouselContext must be used within the carousel.");return e}}));
779
2
  //# sourceMappingURL=index.js.map