114 lines
2.7 KiB
TypeScript
114 lines
2.7 KiB
TypeScript
import React from 'react';
|
|
import { View, Text, StyleSheet, Image } from 'react-native';
|
|
import COLORS from "@/constants/colors";
|
|
import { CartItem as CartItemType } from '@/constants/types';
|
|
import QuantityControl from '@/components/QuantityControl';
|
|
import Animated, {
|
|
useAnimatedStyle,
|
|
withTiming,
|
|
useSharedValue
|
|
} from 'react-native-reanimated';
|
|
|
|
interface CartItemProps {
|
|
item: CartItemType;
|
|
onUpdateQuantity: (id: string, quantity: number) => void;
|
|
}
|
|
|
|
const CartItem: React.FC<CartItemProps> = ({ item, onUpdateQuantity }) => {
|
|
const opacity = useSharedValue(1);
|
|
const scale = useSharedValue(1);
|
|
|
|
const animatedStyle = useAnimatedStyle(() => ({
|
|
opacity: opacity.value,
|
|
transform: [{ scale: scale.value }],
|
|
}));
|
|
|
|
const handleIncrease = () => {
|
|
scale.value = withTiming(1.02, { duration: 100 }, () => {
|
|
scale.value = withTiming(1, { duration: 100 });
|
|
});
|
|
onUpdateQuantity(item.id, item.quantity + 1);
|
|
};
|
|
|
|
const handleDecrease = () => {
|
|
if (item.quantity > 0) {
|
|
scale.value = withTiming(0.98, { duration: 100 }, () => {
|
|
scale.value = withTiming(1, { duration: 100 });
|
|
});
|
|
onUpdateQuantity(item.id, item.quantity - 1);
|
|
}
|
|
};
|
|
|
|
return (
|
|
<Animated.View style={[styles.container, animatedStyle]}>
|
|
<View style={styles.imageContainer}>
|
|
<Image source={{ uri: item.image }} style={styles.image} />
|
|
</View>
|
|
|
|
<View style={styles.contentContainer}>
|
|
<Text style={styles.name}>{item.name}</Text>
|
|
|
|
<View style={styles.controlRow}>
|
|
<QuantityControl
|
|
quantity={item.quantity}
|
|
onIncrease={handleIncrease}
|
|
onDecrease={handleDecrease}
|
|
/>
|
|
|
|
<Text style={styles.price}>{item.price}TND/Kg</Text>
|
|
</View>
|
|
</View>
|
|
</Animated.View>
|
|
);
|
|
};
|
|
|
|
const styles = StyleSheet.create({
|
|
container: {
|
|
flexDirection: 'row',
|
|
backgroundColor: COLORS.secondary,
|
|
borderRadius: 12,
|
|
marginBottom: 16,
|
|
padding: 16,
|
|
shadowColor: '#000',
|
|
shadowOffset: {
|
|
width: 0,
|
|
height: 2,
|
|
},
|
|
shadowOpacity: 0.2,
|
|
shadowRadius: 4,
|
|
elevation: 5,
|
|
},
|
|
imageContainer: {
|
|
width: 80,
|
|
height: 80,
|
|
borderRadius: 8,
|
|
overflow: 'hidden',
|
|
marginRight: 16,
|
|
},
|
|
image: {
|
|
width: '100%',
|
|
height: '100%',
|
|
},
|
|
contentContainer: {
|
|
flex: 1,
|
|
justifyContent: 'center',
|
|
},
|
|
name: {
|
|
fontSize: 16,
|
|
fontWeight: 700,
|
|
color: '#000',
|
|
marginBottom: 8,
|
|
},
|
|
controlRow: {
|
|
flexDirection: 'row',
|
|
alignItems: 'center',
|
|
justifyContent: 'space-between',
|
|
},
|
|
price: {
|
|
fontSize: 14,
|
|
color: COLORS.primary,
|
|
},
|
|
});
|
|
|
|
export default CartItem;
|