diff --git a/src/components/modals/MealRegistrationModal.tsx b/src/components/modals/MealRegistrationModal.tsx index fde8b0c..3457c34 100644 --- a/src/components/modals/MealRegistrationModal.tsx +++ b/src/components/modals/MealRegistrationModal.tsx @@ -1,24 +1,101 @@ -import type { ExamClient } from '../../data/mockData'; -import { EXAM_CLIENTS } from '../../data/mockData'; +import { useEffect, useState } from 'react'; + +import type { PoPhysicalExamDiningLog } from '../../api'; +import { getPhysicalExamDiningList, registerPhysicalExamDining } from '../../api'; import { InfoCard } from '../ui'; interface MealRegistrationModalProps { onClose: () => void; - totalExamCount: number; - mealCount: number; - notMealCount: number; - mealDoneIds: string[]; - onMealDone: (id: string) => void; } -export const MealRegistrationModal = ({ - onClose, - totalExamCount, - mealCount, - notMealCount, - mealDoneIds, - onMealDone, -}: MealRegistrationModalProps) => { +export const MealRegistrationModal = ({ onClose }: MealRegistrationModalProps) => { + const [diningType, setDiningType] = useState(1); // 1-全部 2-已用餐 3-未用餐 + const [loading, setLoading] = useState(false); + const [error, setError] = useState(null); + const [diningData, setDiningData] = useState<{ + today_exam_count: number; + dined_count: number; + not_dined_count: number; + DiningList: PoPhysicalExamDiningLog[]; + } | null>(null); + const [registeringIds, setRegisteringIds] = useState>(new Set()); + + // 获取用餐列表 + useEffect(() => { + const fetchDiningList = async () => { + setLoading(true); + setError(null); + try { + const res = await getPhysicalExamDiningList({ dining_type: diningType }); + if (res.Status === 200 && res.Data) { + setDiningData({ + today_exam_count: res.Data.today_exam_count || 0, + dined_count: res.Data.dined_count || 0, + not_dined_count: res.Data.not_dined_count || 0, + DiningList: res.Data.DiningList || [], + }); + } else { + setError(res.Message || '获取用餐列表失败'); + } + } catch (err) { + console.error('获取用餐列表失败', err); + setError('获取用餐列表失败,请稍后重试'); + } finally { + setLoading(false); + } + }; + + fetchDiningList(); + }, [diningType]); + + // 处理用餐登记 + const handleMealToggle = async (item: PoPhysicalExamDiningLog) => { + if (!item.physical_exam_id || !item.exam_no || !item.customer_name) { + return; + } + + const examId = item.physical_exam_id; + const isCurrentlyDined = item.is_dining === 1; + + // 如果已经用餐,则不处理(取消用餐可能需要其他接口) + if (isCurrentlyDined) { + return; + } + + setRegisteringIds((prev) => new Set(prev).add(examId)); + try { + const res = await registerPhysicalExamDining({ + physical_exam_id: examId, + exam_no: item.exam_no, + customer_name: item.customer_name, + }); + + if (res.Status === 200) { + // 刷新列表 + const refreshRes = await getPhysicalExamDiningList({ dining_type: diningType }); + if (refreshRes.Status === 200 && refreshRes.Data) { + setDiningData({ + today_exam_count: refreshRes.Data.today_exam_count || 0, + dined_count: refreshRes.Data.dined_count || 0, + not_dined_count: refreshRes.Data.not_dined_count || 0, + DiningList: refreshRes.Data.DiningList || [], + }); + } + } else { + setError(res.Message || '用餐登记失败'); + } + } catch (err) { + console.error('用餐登记失败', err); + setError('用餐登记失败,请稍后重试'); + } finally { + setRegisteringIds((prev) => { + const next = new Set(prev); + next.delete(examId); + return next; + }); + } + }; + return (
@@ -30,30 +107,83 @@ export const MealRegistrationModal = ({
-
- - - + {/* 筛选按钮 */} +
+ + + +
+ + {/* 统计信息 */} + {diningData && ( +
+ + + +
+ )} + + {/* 错误提示 */} + {error &&
{error}
} + + {/* 客户列表 */} +
+ {diningType === 1 && '选择已用餐客户进行登记:'} + {diningType === 2 && '已用餐客户列表:'} + {diningType === 3 && '选择未用餐客户进行登记:'}
-
选择已用餐客户进行登记:
- {EXAM_CLIENTS.map((c: ExamClient) => { - const checked = mealDoneIds.includes(c.id); - return ( - - ); - })} + {loading ? ( +
加载中...
+ ) : diningData && diningData.DiningList.length > 0 ? ( + diningData.DiningList.map((item) => { + const isDined = item.is_dining === 1; + const isRegistering = item.physical_exam_id ? registeringIds.has(item.physical_exam_id) : false; + const canToggle = !isDined && !isRegistering; + + return ( + + ); + }) + ) : ( +
暂无数据
+ )}
diff --git a/src/components/modals/QuickActionModal.tsx b/src/components/modals/QuickActionModal.tsx index 85143cd..afc4131 100644 --- a/src/components/modals/QuickActionModal.tsx +++ b/src/components/modals/QuickActionModal.tsx @@ -8,11 +8,6 @@ interface QuickActionModalProps { noteText: string; onNoteChange: (v: string) => void; onClose: () => void; - totalExamCount: number; - mealCount: number; - notMealCount: number; - mealDoneIds: string[]; - onMealDone: (id: string) => void; } export const QuickActionModal = ({ @@ -20,27 +15,13 @@ export const QuickActionModal = ({ noteText, onNoteChange, onClose, - totalExamCount, - mealCount, - notMealCount, - mealDoneIds, - onMealDone, }: QuickActionModalProps) => { if (action === 'none') { return null; } if (action === 'meal') { - return ( - - ); + return ; } if (action === 'note') { diff --git a/src/layouts/MainLayout.tsx b/src/layouts/MainLayout.tsx index 7b1c24e..cd6c2bc 100644 --- a/src/layouts/MainLayout.tsx +++ b/src/layouts/MainLayout.tsx @@ -2,7 +2,6 @@ import { Outlet, useLocation, useNavigate } from 'react-router-dom'; import { useEffect, useMemo, useState } from 'react'; import type { QuickActionType } from '../data/mockData'; -import { EXAM_CLIENTS } from '../data/mockData'; import { QuickActionModal } from '../components/modals/QuickActionModal'; import { LoginModal } from '../components/modals/LoginModal'; import { Sidebar, type SectionKey } from '../components/layout/Sidebar'; @@ -34,13 +33,6 @@ export const MainLayout = () => { const [noteText, setNoteText] = useState(''); const [loginModalOpen, setLoginModalOpen] = useState(false); const [operatorName, setOperatorName] = useState(''); - const [mealDoneIds, setMealDoneIds] = useState( - EXAM_CLIENTS.filter((c) => c.status === '用餐').map((c) => c.id), - ); - - const totalExamCount = EXAM_CLIENTS.length; - const mealCount = mealDoneIds.length; - const notMealCount = totalExamCount - mealCount; const navigate = useNavigate(); const location = useLocation(); @@ -54,10 +46,6 @@ export const MainLayout = () => { navigate(sectionToRoute[section]); }; - const handleMealDone = (id: string) => { - setMealDoneIds((prev) => (prev.includes(id) ? prev : prev.concat(id))); - }; - const handleLoginSuccess = (phone: string) => { // 实际项目中应该从后端获取用户信息 // 这里暂时使用手机号后4位作为操作员名称 @@ -106,11 +94,6 @@ export const MainLayout = () => { noteText={noteText} onNoteChange={setNoteText} onClose={() => setQuickAction('none')} - totalExamCount={totalExamCount} - mealCount={mealCount} - notMealCount={notMealCount} - mealDoneIds={mealDoneIds} - onMealDone={handleMealDone} /> )}