fix web flow
This commit is contained in:
@@ -12,9 +12,9 @@ import {
|
||||
View,
|
||||
useWindowDimensions,
|
||||
} from "react-native";
|
||||
import PersonaCard from "../cards/PersonaCard/PersonaCard";
|
||||
import { ai } from "../../assets";
|
||||
import { getCreationStageStates } from "../../utils/projectStages";
|
||||
import PersonaCard from "../cards/PersonaCard/PersonaCard";
|
||||
|
||||
const STAGE_CARD_CONTENT = [
|
||||
{
|
||||
@@ -43,6 +43,8 @@ const STAGE_CARD_CONTENT = [
|
||||
},
|
||||
];
|
||||
|
||||
const WEB_SCROLL_INACTIVE_DELTA = 0.05;
|
||||
|
||||
const FeatureCarousel = ({
|
||||
style,
|
||||
selectedProject,
|
||||
@@ -63,14 +65,14 @@ const FeatureCarousel = ({
|
||||
...item,
|
||||
isLocked: stageStates[index]?.isLocked ?? true,
|
||||
})),
|
||||
[stageStates],
|
||||
[stageStates]
|
||||
);
|
||||
|
||||
const { height: windowHeight } = useWindowDimensions();
|
||||
const isWeb = Platform.OS === "web";
|
||||
|
||||
const [viewportHeight, setViewportHeight] = useState(() =>
|
||||
Math.max(windowHeight, 1),
|
||||
Math.max(windowHeight, 1)
|
||||
);
|
||||
|
||||
const updateSnapHeight = useCallback((height) => {
|
||||
@@ -95,7 +97,7 @@ const FeatureCarousel = ({
|
||||
const pendingScrollRef = useRef(false);
|
||||
const alignTimeoutRef = useRef(null);
|
||||
const activeIndexRef = useRef(
|
||||
typeof activeIndex === "number" ? activeIndex : 0,
|
||||
typeof activeIndex === "number" ? activeIndex : 0
|
||||
);
|
||||
const onActiveIndexChangeRef = useRef(onActiveIndexChange);
|
||||
|
||||
@@ -122,12 +124,12 @@ const FeatureCarousel = ({
|
||||
}
|
||||
return index;
|
||||
},
|
||||
[carouselItems.length],
|
||||
[carouselItems.length]
|
||||
);
|
||||
|
||||
const clearPendingAlignment = useCallback(() => {
|
||||
if (alignTimeoutRef.current != null) {
|
||||
clearTimeout(alignTimeoutRef.current);
|
||||
globalThis.clearTimeout(alignTimeoutRef.current);
|
||||
alignTimeoutRef.current = null;
|
||||
}
|
||||
}, []);
|
||||
@@ -151,7 +153,7 @@ const FeatureCarousel = ({
|
||||
}
|
||||
updateSnapHeight(height);
|
||||
try {
|
||||
ref.scrollToOffset({ offset: clamped * height, animated: false });
|
||||
ref.scrollToOffset({ offset: clamped * height, animated });
|
||||
} catch (_error) {
|
||||
// Ignore scroll errors when list is not ready yet.
|
||||
}
|
||||
@@ -167,7 +169,7 @@ const FeatureCarousel = ({
|
||||
pendingScrollRef.current = false;
|
||||
}
|
||||
},
|
||||
[clampIndex, isWeb, itemHeight, updateSnapHeight],
|
||||
[clampIndex, isWeb, itemHeight, updateSnapHeight]
|
||||
);
|
||||
|
||||
useEffect(() => {
|
||||
@@ -200,7 +202,23 @@ const FeatureCarousel = ({
|
||||
|
||||
updateSnapHeight(height);
|
||||
|
||||
const nextIndex = clampIndex(Math.round(offset / height));
|
||||
const currentIndex = activeIndexRef.current;
|
||||
const rawIndex = height ? offset / height : currentIndex;
|
||||
|
||||
let nextIndex = currentIndex;
|
||||
if (isWeb) {
|
||||
const delta = rawIndex - currentIndex;
|
||||
if (Math.abs(delta) > WEB_SCROLL_INACTIVE_DELTA) {
|
||||
if (Math.abs(delta) <= 1) {
|
||||
nextIndex = clampIndex(currentIndex + (delta > 0 ? 1 : -1));
|
||||
} else {
|
||||
nextIndex = clampIndex(currentIndex + Math.round(delta));
|
||||
}
|
||||
}
|
||||
} else {
|
||||
nextIndex = clampIndex(Math.round(rawIndex));
|
||||
}
|
||||
|
||||
const hasChanged = nextIndex !== activeIndexRef.current;
|
||||
|
||||
if (hasChanged) {
|
||||
@@ -212,10 +230,11 @@ const FeatureCarousel = ({
|
||||
}
|
||||
|
||||
if (isWeb || hasChanged) {
|
||||
scrollToIndex(nextIndex, !isWeb, height);
|
||||
const shouldAnimate = isWeb ? true : !isWeb;
|
||||
scrollToIndex(nextIndex, shouldAnimate, height);
|
||||
}
|
||||
},
|
||||
[clampIndex, isWeb, itemHeight, scrollToIndex, updateSnapHeight],
|
||||
[clampIndex, isWeb, itemHeight, scrollToIndex, updateSnapHeight]
|
||||
);
|
||||
|
||||
const handleScrollEnd = useCallback(
|
||||
@@ -225,7 +244,7 @@ const FeatureCarousel = ({
|
||||
const layoutHeight = event?.nativeEvent?.layoutMeasurement?.height;
|
||||
alignToOffset(offsetY, layoutHeight);
|
||||
},
|
||||
[alignToOffset, clearPendingAlignment],
|
||||
[alignToOffset, clearPendingAlignment]
|
||||
);
|
||||
|
||||
const handleScroll = useCallback(
|
||||
@@ -236,12 +255,12 @@ const FeatureCarousel = ({
|
||||
const offsetY = event?.nativeEvent?.contentOffset?.y ?? 0;
|
||||
const layoutHeight = event?.nativeEvent?.layoutMeasurement?.height;
|
||||
clearPendingAlignment();
|
||||
alignTimeoutRef.current = setTimeout(() => {
|
||||
alignTimeoutRef.current = globalThis.setTimeout(() => {
|
||||
alignToOffset(offsetY, layoutHeight);
|
||||
alignTimeoutRef.current = null;
|
||||
}, 80);
|
||||
},
|
||||
[alignToOffset, clearPendingAlignment, isWeb],
|
||||
[alignToOffset, clearPendingAlignment, isWeb]
|
||||
);
|
||||
|
||||
const handleLayout = useCallback(
|
||||
@@ -251,7 +270,7 @@ const FeatureCarousel = ({
|
||||
updateSnapHeight(layoutHeight);
|
||||
}
|
||||
},
|
||||
[updateSnapHeight],
|
||||
[updateSnapHeight]
|
||||
);
|
||||
|
||||
const keyExtractor = useCallback((item) => item.key, []);
|
||||
@@ -265,7 +284,7 @@ const FeatureCarousel = ({
|
||||
height={itemHeight}
|
||||
/>
|
||||
),
|
||||
[itemHeight],
|
||||
[itemHeight]
|
||||
);
|
||||
|
||||
const getItemLayout = useCallback(
|
||||
@@ -274,7 +293,7 @@ const FeatureCarousel = ({
|
||||
offset: itemHeight * index,
|
||||
index,
|
||||
}),
|
||||
[itemHeight],
|
||||
[itemHeight]
|
||||
);
|
||||
|
||||
const viewabilityConfig = useRef({ viewAreaCoveragePercentThreshold: 60 });
|
||||
@@ -303,7 +322,7 @@ const FeatureCarousel = ({
|
||||
return undefined;
|
||||
}
|
||||
return carouselItems.map((_, index) => index * itemHeight);
|
||||
}, [carouselItems.length, isWeb, itemHeight]);
|
||||
}, [carouselItems, isWeb, itemHeight]);
|
||||
|
||||
return (
|
||||
<View style={[styles.container, style]} onLayout={handleLayout}>
|
||||
|
||||
Reference in New Issue
Block a user