import React, { useState, useEffect } from 'react'; import { View, Text, StyleSheet, ScrollView, TouchableOpacity, ActivityIndicator, Alert, } from 'react-native'; import { SafeAreaView } from 'react-native-safe-area-context'; import { useRouter, useLocalSearchParams } from 'expo-router'; import { Ionicons } from '@expo/vector-icons'; import orderApi, { Order, OrderProgress } from '../services/orderApi'; const STATUS_COLORS: Record = { PENDING: '#FFA726', CONFIRMED: '#42A5F5', SHIPPING: '#AB47BC', DELIVERED: '#66BB6A', CANCELLED: '#EF5350', }; const STATUS_LABELS: Record = { PENDING: 'Chờ xác nhận', CONFIRMED: 'Đã xác nhận', SHIPPING: 'Đang giao hàng', DELIVERED: 'Đã giao hàng', CANCELLED: 'Đã hủy', }; export default function OrderDetailScreen() { const router = useRouter(); const params = useLocalSearchParams(); const orderId = params.orderId as string; const [order, setOrder] = useState(null); const [timeline, setTimeline] = useState([]); const [loading, setLoading] = useState(true); const [cancelling, setCancelling] = useState(false); useEffect(() => { if (orderId) { console.log("Order Success Params:", params); console.log("Order ID:", orderId); loadOrderDetail(); loadOrderProgress(); } }, [orderId]); const loadOrderDetail = async () => { try { const response = await orderApi.getOrderDetail(Number(orderId)); if (response.success && response.data) { setOrder(response.data); } } catch (error: any) { console.error('Load order detail error:', error); Alert.alert('Lỗi', 'Không thể tải thông tin đơn hàng'); } finally { setLoading(false); } }; const loadOrderProgress = async () => { try { const response = await orderApi.getOrderProgress(Number(orderId)); if (response.success && response.data) { setTimeline(response.data.timeline); } } catch (error: any) { console.error('Load order progress error:', error); } }; const handleCancelOrder = () => { Alert.alert( 'Hủy đơn hàng', 'Bạn có chắc chắn muốn hủy đơn hàng này?', [ { text: 'Không', style: 'cancel' }, { text: 'Có', onPress: cancelOrder, style: 'destructive' }, ] ); }; const cancelOrder = async () => { setCancelling(true); try { const response = await orderApi.cancelOrder(Number(orderId)); if (response.success) { Alert.alert('Thành công', 'Đơn hàng đã được hủy'); loadOrderDetail(); loadOrderProgress(); } else { Alert.alert('Lỗi', response.message || 'Không thể hủy đơn hàng'); } } catch (error: any) { Alert.alert('Lỗi', error.message || 'Không thể hủy đơn hàng'); } finally { setCancelling(false); } }; const formatDate = (dateString: string) => { const date = new Date(dateString); return date.toLocaleDateString('vi-VN', { day: '2-digit', month: '2-digit', year: 'numeric', hour: '2-digit', minute: '2-digit', }); }; const formatPrice = (price: number) => { return new Intl.NumberFormat('vi-VN', { style: 'currency', currency: 'VND', }).format(price); }; if (loading) { return ( ); } if (!order) { return ( Không tìm thấy đơn hàng router.back()} > Quay lại ); } return ( {/* Header */} router.push("/orders")}> Chi tiết đơn hàng {/* Order Status */} {STATUS_LABELS[order.orderStatus]} Đơn hàng #{order.orderId} Đặt hàng: {formatDate(order.createdAt)} {/* Timeline */} {order.orderStatus !== 'CANCELLED' && timeline.length > 0 && ( Tiến độ đơn hàng {timeline.map((step, index) => ( {step.completed && ( )} {index < timeline.length - 1 && ( )} {STATUS_LABELS[step.status]} {step.timestamp && ( {formatDate(step.timestamp)} )} ))} )} {/* Shipping Address */} Địa chỉ giao hàng {order.shippingAddress} {/* Order Items */} Sản phẩm {order.orderItems.map((item) => ( {item.productName} x{item.quantity} {formatPrice(item.price)} {formatPrice(item.subtotal)} ))} {/* Payment Summary */} Thanh toán Tạm tính {formatPrice(order.totalPrice)} Phí vận chuyển Miễn phí Tổng cộng {formatPrice(order.totalPrice)} {/* Cancel Button */} {(order.orderStatus === 'PENDING' || order.orderStatus === 'CONFIRMED') && ( {cancelling ? ( ) : ( Hủy đơn hàng )} )} ); } const styles = StyleSheet.create({ container: { flex: 1, backgroundColor: '#f5f5f5', }, header: { flexDirection: 'row', alignItems: 'center', justifyContent: 'space-between', padding: 16, backgroundColor: '#fff', borderBottomWidth: 1, borderBottomColor: '#e0e0e0', }, headerTitle: { fontSize: 20, fontWeight: '700', color: '#333', }, scrollView: { flex: 1, }, statusSection: { backgroundColor: '#fff', padding: 20, alignItems: 'center', marginTop: 12, }, statusBadge: { paddingHorizontal: 20, paddingVertical: 8, borderRadius: 20, marginBottom: 12, }, statusText: { color: '#fff', fontSize: 14, fontWeight: '700', }, orderId: { fontSize: 18, fontWeight: '700', marginBottom: 4, color: '#333', }, orderDate: { fontSize: 14, color: '#666', }, section: { backgroundColor: '#fff', marginTop: 12, padding: 16, }, sectionHeader: { flexDirection: 'row', alignItems: 'center', marginBottom: 12, }, sectionTitle: { fontSize: 16, fontWeight: '700', marginLeft: 8, color: '#333', }, timelineItem: { flexDirection: 'row', marginBottom: 8, }, timelineLeft: { alignItems: 'center', marginRight: 12, }, timelineDot: { width: 24, height: 24, borderRadius: 12, backgroundColor: '#e0e0e0', alignItems: 'center', justifyContent: 'center', }, timelineDotActive: { backgroundColor: '#4CAF50', }, timelineLine: { width: 2, flex: 1, backgroundColor: '#e0e0e0', marginTop: 4, }, timelineLineActive: { backgroundColor: '#4CAF50', }, timelineRight: { flex: 1, paddingBottom: 16, }, timelineStatus: { fontSize: 14, color: '#999', marginBottom: 4, }, timelineStatusActive: { color: '#333', fontWeight: '700', }, timelineDate: { fontSize: 12, color: '#999', }, addressText: { fontSize: 14, color: '#333', lineHeight: 20, }, productItem: { flexDirection: 'row', justifyContent: 'space-between', paddingVertical: 12, borderBottomWidth: 1, borderBottomColor: '#f0f0f0', }, productInfo: { flex: 1, marginRight: 12, }, productName: { fontSize: 15, marginBottom: 4, color: '#333', }, productQuantity: { fontSize: 13, color: '#666', }, productPrices: { alignItems: 'flex-end', }, productPrice: { fontSize: 13, color: '#666', marginBottom: 4, }, productSubtotal: { fontSize: 15, fontWeight: '700', color: '#ff6b6b', }, summaryRow: { flexDirection: 'row', justifyContent: 'space-between', paddingVertical: 10, }, summaryLabel: { fontSize: 15, color: '#666', }, summaryValue: { fontSize: 15, color: '#333', }, totalRow: { borderTopWidth: 1, borderTopColor: '#e0e0e0', marginTop: 8, paddingTop: 16, }, totalLabel: { fontSize: 17, fontWeight: '700', color: '#333', }, totalValue: { fontSize: 20, fontWeight: '700', color: '#ff6b6b', }, footer: { backgroundColor: '#fff', padding: 16, borderTopWidth: 1, borderTopColor: '#e0e0e0', }, cancelButton: { backgroundColor: '#EF5350', padding: 16, borderRadius: 12, alignItems: 'center', }, buttonDisabled: { opacity: 0.6, }, cancelButtonText: { color: '#fff', fontSize: 16, fontWeight: '700', }, loadingContainer: { flex: 1, justifyContent: 'center', alignItems: 'center', }, errorContainer: { flex: 1, justifyContent: 'center', alignItems: 'center', padding: 32, }, errorText: { fontSize: 16, color: '#999', marginTop: 16, marginBottom: 24, }, backButton: { backgroundColor: '#ff6b6b', paddingHorizontal: 32, paddingVertical: 14, borderRadius: 12, }, backButtonText: { color: '#fff', fontSize: 16, fontWeight: '700', }, });