import { CameraView } from '@/add-log/camera/CameraView'; import { FoodLogEditor } from '@/add-log/food-log-editor/FoodLogEditor'; import { Text } from '@/aesthetics/Text'; import { TextInput } from '@/aesthetics/TextInput'; import { colors, font, radius, spacing, useColors } from '@/aesthetics/styles'; import { useStrings } from '@/common/hooks/useStrings'; import { Camera as CameraIcon, Check, Crop, ImageIcon, SendHorizontal, X, } from 'lucide-react-native'; import { Keyboard, Pressable, StyleSheet, View } from 'react-native'; import { useKeyboardHandler } from 'react-native-keyboard-controller'; import Animated, { useAnimatedStyle, useSharedValue } from 'react-native-reanimated'; import { StagedFoodLogList } from './StagedFoodLogList'; import { SuggestionList } from './SuggestionList'; import { useLogScreen } from './useLogScreen'; export function LogScreenContent() { const c = useColors(); const strings = useStrings(); const { camera, logs, editor, suggestions, input, layout, haptics } = useLogScreen(); const keyboardHeight = useSharedValue(0); useKeyboardHandler( { onStart: () => { 'worklet'; }, onMove: e => { 'worklet'; keyboardHeight.value = e.height; }, onEnd: () => { 'worklet'; }, onInteractive: e => { 'worklet'; keyboardHeight.value = e.height; }, }, [] ); const animatedContainerStyle = useAnimatedStyle(() => { return { paddingBottom: keyboardHeight.value }; }); const { isCropMode, cropAreaCenterY, cropBoxHeight } = camera; const insetsTop = layout.insets.top; const stagedLogsStyle = useAnimatedStyle(() => { const top = isCropMode ? cropAreaCenterY + cropBoxHeight.value / 2 : insetsTop; return { paddingTop: top }; }, [isCropMode, cropAreaCenterY, insetsTop]); return ( camera.setReady(true)} gesture={camera.gesture} showCropOverlay={camera.showCropOverlay} cropGestures={camera.cropGestures} cropBoxWidth={camera.cropBoxWidth} cropBoxHeight={camera.cropBoxHeight} cropAreaCenterY={camera.cropAreaCenterY} onEnableCamera={() => { Keyboard.dismiss(); haptics.impact(); camera.setMode('fullscreen'); }} focusPoint={camera.focusPoint} /> { haptics.impact(); camera.setMode(prev => { if (prev === 'off') return 'fullscreen'; if (prev === 'fullscreen') return 'cropped'; return 'off'; }); }} > {camera.mode === 'off' && } {camera.mode === 'fullscreen' && ( )} {camera.mode === 'cropped' && } {input.text.trim() ? ( ) : ( )} [styles.sideButton, pressed && styles.pressed]} onPress={() => layout.router.back()} hitSlop={12} > {logs.staged.length > 0 ? ( [styles.logButton, pressed && styles.pressed]} onPress={logs.logAll} > {logs.staged.length} ) : ( )} editor.setLog(null)} editFoodName={editor.foodName} onChangeFoodName={editor.setFoodName} editIngredients={editor.ingredients} newIngredient={editor.newIngredient} onChangeNewIngredient={editor.setNewIngredient} onAddIngredient={editor.addIngredient} onRemoveIngredient={editor.removeIngredient} onSave={editor.save} /> ); } const INPUT_PILL_HEIGHT = 52; const styles = StyleSheet.create({ container: { flex: 1, backgroundColor: colors.camera.background }, contentOverlay: { ...StyleSheet.absoluteFillObject }, keyboardArea: { flex: 1, justifyContent: 'flex-end' }, stagedLogsContainer: { flex: 1, marginHorizontal: 16 }, inputArea: { paddingHorizontal: spacing.lg }, inputPill: { flexDirection: 'row', alignItems: 'center', height: INPUT_PILL_HEIGHT, borderRadius: INPUT_PILL_HEIGHT / 2, paddingHorizontal: spacing.sm, backgroundColor: colors.camera.inputBg, borderWidth: 1, borderColor: colors.camera.inputBorder, gap: spacing.sm, }, cameraToggle: { width: 40, height: 40, borderRadius: 20, alignItems: 'center', justifyContent: 'center', }, cameraToggleActive: { backgroundColor: colors.camera.buttonBgActive }, cameraToggleOff: { backgroundColor: colors.camera.text }, textInput: { flex: 1, height: INPUT_PILL_HEIGHT, fontSize: font.md, color: colors.camera.text, paddingVertical: 0, }, inputAction: { width: 40, height: 40, borderRadius: 20, alignItems: 'center', justifyContent: 'center', }, shutterArea: { paddingHorizontal: spacing.xl }, shutterRow: { flexDirection: 'row', alignItems: 'center', justifyContent: 'center', paddingVertical: spacing.lg, gap: spacing.xxl, }, sideButton: { width: 48, height: 48, borderRadius: radius.xl, alignItems: 'center', justifyContent: 'center', backgroundColor: colors.camera.buttonBg, }, shutterButton: { width: 76, height: 76, borderRadius: 38, backgroundColor: colors.camera.shutterBg, alignItems: 'center', justifyContent: 'center', borderWidth: 3, borderColor: colors.camera.shutterBorder, }, shutterDisabled: { opacity: 0.4 }, shutterInner: { width: 60, height: 60, borderRadius: 30, backgroundColor: colors.camera.shutterInner, }, shutterInnerDisabled: { backgroundColor: colors.camera.shutterInnerDisabled }, logButton: { flexDirection: 'row', alignItems: 'center', justifyContent: 'center', height: 48, paddingHorizontal: spacing.lg, borderRadius: radius.xl, backgroundColor: colors.camera.successBg, gap: spacing.sm, }, logButtonText: { color: colors.camera.text, fontSize: font.lg, fontWeight: '600' }, pressed: { opacity: 0.7 }, });