@momo-kits/carousel 0.161.2-beta.7 → 0.161.2-beta.8

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.
Files changed (2) hide show
  1. package/index.tsx +55 -94
  2. package/package.json +1 -1
package/index.tsx CHANGED
@@ -8,6 +8,7 @@ import React, {
8
8
  useState,
9
9
  } from 'react';
10
10
  import {
11
+ Animated,
11
12
  Dimensions,
12
13
  FlatList,
13
14
  GestureResponderEvent,
@@ -16,79 +17,14 @@ import {
16
17
  NativeSyntheticEvent,
17
18
  Platform,
18
19
  StyleSheet,
19
- View,
20
+ View
20
21
  } from 'react-native';
21
- import Animated, {
22
- Extrapolation,
23
- interpolate,
24
- runOnJS,
25
- useAnimatedScrollHandler,
26
- useAnimatedStyle,
27
- useSharedValue,
28
- type SharedValue,
29
- } from 'react-native-reanimated';
30
22
  import { CarouselProps, CarouselRef } from './types';
31
23
 
32
24
  const { width: viewportWidth } = Dimensions.get('window');
33
25
 
34
26
  const AnimatedFlatList = Animated.createAnimatedComponent(FlatList);
35
27
 
36
- type CarouselItemProps = {
37
- index: number;
38
- itemWidth: number;
39
- scrollX: SharedValue<number>;
40
- inactiveSlideOpacity: number;
41
- inactiveSlideScale: number;
42
- slideStyle: any;
43
- children: React.ReactNode;
44
- };
45
-
46
- const CarouselItem: React.FC<CarouselItemProps> = ({
47
- index,
48
- itemWidth,
49
- scrollX,
50
- inactiveSlideOpacity,
51
- inactiveSlideScale,
52
- slideStyle,
53
- children,
54
- }) => {
55
- const animatedStyle = useAnimatedStyle(() => {
56
- const inputRange = [
57
- (index - 1) * itemWidth,
58
- index * itemWidth,
59
- (index + 1) * itemWidth,
60
- ];
61
- const opacity =
62
- inactiveSlideOpacity < 1
63
- ? interpolate(
64
- scrollX.value,
65
- inputRange,
66
- [inactiveSlideOpacity, 1, inactiveSlideOpacity],
67
- Extrapolation.CLAMP,
68
- )
69
- : 1;
70
- const scale =
71
- inactiveSlideScale < 1
72
- ? interpolate(
73
- scrollX.value,
74
- inputRange,
75
- [inactiveSlideScale, 1, inactiveSlideScale],
76
- Extrapolation.CLAMP,
77
- )
78
- : 1;
79
- return {
80
- opacity,
81
- transform: [{ scale }],
82
- };
83
- });
84
-
85
- return (
86
- <Animated.View style={[{ width: itemWidth }, slideStyle, animatedStyle]}>
87
- {children}
88
- </Animated.View>
89
- );
90
- };
91
-
92
28
  const Carousel = forwardRef<CarouselRef, CarouselProps>((props, ref) => {
93
29
  const {
94
30
  data,
@@ -126,7 +62,7 @@ const Carousel = forwardRef<CarouselRef, CarouselProps>((props, ref) => {
126
62
 
127
63
  const flatListRef = useRef<FlatList>(null);
128
64
  const autoplayTimerRef = useRef<ReturnType<typeof setInterval> | null>(null);
129
- const scrollX = useSharedValue(0);
65
+ const scrollXRef = useRef(new Animated.Value(0)).current;
130
66
  const containerWidthRef = useRef(viewportWidth);
131
67
  const isAutoplayPausedRef = useRef(false);
132
68
  const currentIndexRef = useRef(firstItem);
@@ -310,14 +246,15 @@ const Carousel = forwardRef<CarouselRef, CarouselProps>((props, ref) => {
310
246
  );
311
247
 
312
248
  const handleScroll = useCallback(
313
- (offsetX: number) => {
249
+ (event: NativeSyntheticEvent<NativeScrollEvent>) => {
250
+ const offsetX = event.nativeEvent.contentOffset.x;
314
251
  const index = Math.round(offsetX / itemWidth);
315
252
  const realIndex = getRealIndex(index);
316
253
 
317
254
  if (realIndex !== currentIndexRef.current) {
318
255
  currentIndexRef.current = realIndex;
319
256
  setCurrentIndex(realIndex);
320
-
257
+
321
258
  if (onScrollIndexChanged) {
322
259
  onScrollIndexChanged(realIndex);
323
260
  }
@@ -414,17 +351,41 @@ const Carousel = forwardRef<CarouselRef, CarouselProps>((props, ref) => {
414
351
  );
415
352
  }
416
353
 
354
+ const inputRange = [
355
+ (index - 1) * itemWidth,
356
+ index * itemWidth,
357
+ (index + 1) * itemWidth,
358
+ ];
359
+
360
+ const opacity = hasOpacityAnimation
361
+ ? scrollXRef.interpolate({
362
+ inputRange,
363
+ outputRange: [inactiveSlideOpacity, 1, inactiveSlideOpacity],
364
+ extrapolate: 'clamp',
365
+ })
366
+ : 1;
367
+
368
+ const scale = hasScaleAnimation
369
+ ? scrollXRef.interpolate({
370
+ inputRange,
371
+ outputRange: [inactiveSlideScale, 1, inactiveSlideScale],
372
+ extrapolate: 'clamp',
373
+ })
374
+ : 1;
375
+
417
376
  return (
418
- <CarouselItem
419
- index={index}
420
- itemWidth={itemWidth}
421
- scrollX={scrollX}
422
- inactiveSlideOpacity={inactiveSlideOpacity}
423
- inactiveSlideScale={inactiveSlideScale}
424
- slideStyle={slideStyle}
377
+ <Animated.View
378
+ style={[
379
+ { width: itemWidth },
380
+ slideStyle,
381
+ {
382
+ opacity,
383
+ transform: [{ scale }],
384
+ },
385
+ ]}
425
386
  >
426
387
  {renderItem({ item, index: realIndex })}
427
- </CarouselItem>
388
+ </Animated.View>
428
389
  );
429
390
  },
430
391
  [
@@ -434,7 +395,7 @@ const Carousel = forwardRef<CarouselRef, CarouselProps>((props, ref) => {
434
395
  itemWidth,
435
396
  slideStyle,
436
397
  renderItem,
437
- scrollX,
398
+ scrollXRef,
438
399
  ]
439
400
  );
440
401
 
@@ -448,24 +409,24 @@ const Carousel = forwardRef<CarouselRef, CarouselProps>((props, ref) => {
448
409
  [keyExtractor]
449
410
  );
450
411
 
451
- const emitScrollProp = useCallback(
452
- (offsetX: number) => {
453
- if (onScrollProp) {
454
- onScrollProp({
455
- nativeEvent: { contentOffset: { x: offsetX, y: 0 } },
456
- } as NativeSyntheticEvent<NativeScrollEvent>);
412
+ const onScrollEvent = useMemo(() => {
413
+ const scrollHandler = Animated.event(
414
+ [{ nativeEvent: { contentOffset: { x: scrollXRef } } }],
415
+ {
416
+ useNativeDriver: true,
417
+ listener: handleScroll,
457
418
  }
458
- },
459
- [onScrollProp],
460
- );
419
+ );
461
420
 
462
- const onScrollEvent = useAnimatedScrollHandler({
463
- onScroll: (event) => {
464
- scrollX.value = event.contentOffset.x;
465
- runOnJS(handleScroll)(event.contentOffset.x);
466
- runOnJS(emitScrollProp)(event.contentOffset.x);
467
- },
468
- });
421
+ if (onScrollProp) {
422
+ return (event: NativeSyntheticEvent<NativeScrollEvent>) => {
423
+ scrollHandler(event);
424
+ onScrollProp(event);
425
+ };
426
+ }
427
+
428
+ return scrollHandler;
429
+ }, [scrollXRef, handleScroll, onScrollProp]);
469
430
 
470
431
  useEffect(() => {
471
432
  if (isLayoutReady && firstItem > 0 && firstItem < data.length) {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@momo-kits/carousel",
3
- "version": "0.161.2-beta.7",
3
+ "version": "0.161.2-beta.8",
4
4
  "private": false,
5
5
  "main": "index.tsx",
6
6
  "peerDependencies": {