Files
fitaiProto/apps/mobile/src/components/QuickActionGrid.tsx
T
2026-03-11 06:07:16 +01:00

146 lines
3.3 KiB
TypeScript

import React from "react";
import {
View,
Text,
StyleSheet,
TouchableOpacity,
Dimensions,
} from "react-native";
import { LinearGradient } from "expo-linear-gradient";
import { Ionicons } from "@expo/vector-icons";
import { theme } from "../styles/theme";
const { width } = Dimensions.get("window");
const ITEM_WIDTH = (width - 40 - 16) / 2; // (Screen width - padding - gap) / 2
interface QuickActionProps {
icon: keyof typeof Ionicons.glyphMap;
label: string;
gradient: readonly [string, string, ...string[]];
onPress?: () => void;
}
function QuickActionItem({ icon, label, gradient, onPress }: QuickActionProps) {
return (
<TouchableOpacity
onPress={onPress}
activeOpacity={0.8}
style={styles.itemContainer}
>
<LinearGradient
colors={["rgba(255, 255, 255, 0.8)", "rgba(255, 255, 255, 0.6)"]}
style={[styles.item, theme.shadows.subtle]}
>
<LinearGradient
colors={gradient}
style={styles.iconContainer}
start={{ x: 0, y: 0 }}
end={{ x: 1, y: 1 }}
>
<Ionicons name={icon} size={24} color="#fff" />
</LinearGradient>
<Text style={styles.label}>{label}</Text>
<Ionicons
name="chevron-forward"
size={16}
color={theme.colors.gray400}
style={styles.arrow}
/>
</LinearGradient>
</TouchableOpacity>
);
}
interface QuickActionGridProps {
onTrackMealPress?: () => void;
onAddWaterPress?: () => void;
onScanFoodPress?: () => void;
onLogWorkoutPress?: () => void;
}
export function QuickActionGrid({
onTrackMealPress,
onAddWaterPress,
onScanFoodPress,
onLogWorkoutPress,
}: QuickActionGridProps) {
return (
<View style={styles.container}>
<Text style={styles.sectionTitle}>Quick Actions</Text>
<View style={styles.grid}>
<QuickActionItem
icon="barbell"
label="Log Workout"
gradient={theme.gradients.primary}
onPress={onLogWorkoutPress}
/>
<QuickActionItem
icon="restaurant"
label="Track Meal"
gradient={theme.gradients.success}
onPress={onTrackMealPress}
/>
<QuickActionItem
icon="water"
label="Add Water"
gradient={theme.gradients.ocean}
onPress={onAddWaterPress}
/>
<QuickActionItem
icon="scan"
label="Scan Food"
gradient={theme.gradients.purple}
onPress={onScanFoodPress}
/>
</View>
</View>
);
}
const styles = StyleSheet.create({
container: {
paddingHorizontal: 20,
marginBottom: 24,
},
sectionTitle: {
fontSize: 18,
fontWeight: "700",
color: theme.colors.gray900,
marginBottom: 16,
},
grid: {
flexDirection: "row",
flexWrap: "wrap",
gap: 16,
},
itemContainer: {
width: ITEM_WIDTH,
},
item: {
flexDirection: "row",
alignItems: "center",
padding: 16,
borderRadius: 20,
backgroundColor: "#fff",
borderWidth: 1,
borderColor: "rgba(255, 255, 255, 0.6)",
},
iconContainer: {
width: 40,
height: 40,
borderRadius: 14,
justifyContent: "center",
alignItems: "center",
marginRight: 12,
},
label: {
fontSize: 14,
fontWeight: "600",
color: theme.colors.gray800,
flex: 1,
},
arrow: {
opacity: 0.5,
},
});