// 【重要】必须使用 const Component 作为组件变量名 // 提车首付款 - 车辆资产管理后台(运维管理-财务管理-提车首付款) const Component = function() { var useState = React.useState; var useCallback = React.useCallback; var useMemo = React.useMemo; // 分页 var pageState = useState(1); var currentPage = pageState[0]; var setCurrentPage = pageState[1]; var pageSizeState = useState(10); var pageSize = pageSizeState[0]; var setPageSize = pageSizeState[1]; // 筛选:表单输入值(用户填写) var contractInputState = useState(''); var contractInput = contractInputState[0]; var setContractInput = contractInputState[1]; var projectInputState = useState(''); var projectInput = projectInputState[0]; var setProjectInput = projectInputState[1]; var customerInputState = useState(''); var customerInput = customerInputState[0]; var setCustomerInput = customerInputState[1]; var statusInputState = useState([]); var statusInput = statusInputState[0]; var setStatusInput = statusInputState[1]; // 可搜索选择器下拉展开:contract | project | customer | null var filterDropdownOpenState = useState(null); var filterDropdownOpen = filterDropdownOpenState[0]; var setFilterDropdownOpen = filterDropdownOpenState[1]; // 付款状态多选下拉展开 var statusDropdownOpenState = useState(false); var statusDropdownOpen = statusDropdownOpenState[0]; var setStatusDropdownOpen = statusDropdownOpenState[1]; // 筛选:已生效条件(点击查询后与列表联动) var appliedFilterState = useState({ contract: '', project: '', customer: '', status: [] }); var appliedFilter = appliedFilterState[0]; var setAppliedFilter = appliedFilterState[1]; // 查看页:当前视图 list | detail var currentViewState = useState('list'); var currentView = currentViewState[0]; var setCurrentView = currentViewState[1]; // 详情模式:view 查看 | payment 付款 var detailModeState = useState('view'); var detailMode = detailModeState[0]; var setDetailMode = detailModeState[1]; // 付款表单(付款模式可编辑) var paymentFormState = useState({ discountAmount: '', discountReason: '', hydrogenPaidAmount: '', vehicleList: [], hydrogenList: [], violationList: [], returnFeeList: [] }); var paymentForm = paymentFormState[0]; var setPaymentForm = paymentFormState[1]; // 服务费明细弹窗 var popoverState = useState({ type: null, data: null }); var popover = popoverState[0]; var setPopover = popoverState[1]; // 照片查看器 var photoViewerState = useState({ visible: false, photos: [], currentIndex: 0 }); var photoViewer = photoViewerState[0]; var setPhotoViewer = photoViewerState[1]; // 当前查看/付款的账单 id var viewingBillIdState = useState(null); var viewingBillId = viewingBillIdState[0]; var setViewingBillId = viewingBillIdState[1]; // 审核状态覆盖(id -> draft|pending|auditing|completed|withdrawn|rejected)待提交|审核中|审核完成|撤回|审核驳回 var approvalStatusMapState = useState({}); var approvalStatusMap = approvalStatusMapState[0]; var setApprovalStatusMap = approvalStatusMapState[1]; // 撤回二次确认:待撤回的 row id var withdrawConfirmIdState = useState(null); var withdrawConfirmId = withdrawConfirmIdState[0]; var setWithdrawConfirmId = withdrawConfirmIdState[1]; // 查看需求明细弹窗 var requirementDetailVisibleState = useState(false); var requirementDetailVisible = requirementDetailVisibleState[0]; var setRequirementDetailVisible = requirementDetailVisibleState[1]; // 需求明细文案(提车首付款) var requirementDetailContent = '提车首付款\n\n1.面包屑:\n1.1.运维管理-财务管理-提车首付款\n\n2.筛选:\n2.1.合同编码:合同编码显示租赁合同编码;选择器,支持从输入框进行内容模糊搜索;\n2.2.项目名称:项目名称显示租赁合同对应项目名称;选择器,支持从输入框输入内容模糊搜索;\n2.3.客户名称:客户名称显示租赁合同对应客户名称,选择器,支持从输入框输入内容模糊搜索;\n2.4.付款状态:显示合同提车首付款付款状态,选择器,支持多选;选项为全部、部分付款、未付款、已付款;\n2.5.右侧为查询和重置按钮,筛选条件以且的模式进行筛选,点击重置清空条件;\n\n3.列表:\n3.1.列表下方为分页器,支持选择单页数据条数;\n3.2.列表字段按照以下排序:付款状态、合同编码、项目名称、客户名称、合同生效日期、首期应付金额、实付金额、减免金额、未付金额、备注、操作;\n3.3.审核状态:分为待提交、审核中、审核完成、审核驳回、撤回;\n 流程流转为:待提交(交车任务生效/完成收费补充保存) → 完成收费补充提交 → 审核中(可撤回,撤回后显示为撤回)→ 审核完成(最终节点审核完成) / 审核驳回(驳回显示为审核驳回);\n a.待提交:交车单交车成功时系统会自动生成提车首付款,状态为「待提交」;业务人员点击收费补充信息点击保存,状态也为「待提交」,同时操作可:查看、收费;\n b.审核中:提车首付款完成收费信息填写,点击提交审核,状态变更为「审核中」,同时操作可:查看、撤回;\n c.审核完成:提车首付款完成审核后,显示为审核完成,同时操作可:查看;\n d.审核驳回:提车首付款在任意审核节点被驳回时,显示为审核驳回,同时操作可:查看、收费;\n e.撤回:提车首付款在审核中时,发起人可进行撤回,撤回后可重新补充收费信息并再次提交;操作可:查看、收费;\n3.4.付款状态:显示付款状态,状态分为:已付款、部分付款、未付款;\n a.已付款:应付金额为0时,显示为已付款;\n b.部分付款:未付金额>0且<应付金额时,显示为部分付款;\n c.未付款:实付金额为0时,显示为未付款;\n3.5.合同编码:显示租赁合同-合同编码;\n3.6.项目名称:显示该项目租赁合同-项目名称;\n3.7.客户名称:显示该项目租赁合同-客户名称;\n3.8.合同生效日期:显示该项目租赁合同-生效日期,格式为YYYY-MM-DD;\n3.9.首期应付金额:显示该笔账单首期应付金额,精确至2位小数,计算方式为:应付款总额=车辆月租金总计+服务费总计+保证金总计+氢气预付款金额;\n3.10.实付金额:显示该笔账单实付金额,精确至2位小数,如未付则显示为0;如已上传付款信息,则显示金额,计算方式为:实付款金额=实付月租金总计+实付服务费总计+实付保证金总计+氢气实付款金额\n3.11.减免金额:显示该笔账单减免金额,精确至2位小数,如无则显示为0;\n3.12.未付金额:显示该笔账单未付金额,精确至2位小数,如无则显示为0;未付款金额=应付款总额-实付金额-减免金额\n3.13.减免原因:显示减免金额添加原因;\n3.14.操作:查看、收费、撤回;\n a.查看:点击查看进入查看页;\n b.收费:点击收费,录入收费信息;\n c.撤回:审核状态为审核中时,点击撤回,进行二次提示,确认后该条数据审核状态显示为撤回,可重新进行收费操作;'; // 模拟数据:合同编码、项目、客户选项(用于选择器展示,可选) var contractOptions = useMemo(function() { return [ { value: 'HT-ZL-2025-001', label: 'HT-ZL-2025-001' }, { value: 'HT-ZL-2025-002', label: 'HT-ZL-2025-002' }, { value: 'HT-ZL-2025-003', label: 'HT-ZL-2025-003' }, { value: 'HT-ZL-2024-088', label: 'HT-ZL-2024-088' }, { value: 'HT-ZL-2024-099', label: 'HT-ZL-2024-099' } ]; }, []); var projectOptions = useMemo(function() { return [ { value: '北京朝阳区租赁项目', label: '北京朝阳区租赁项目' }, { value: '上海浦东车辆租赁', label: '上海浦东车辆租赁' }, { value: '广州天河运营项目', label: '广州天河运营项目' }, { value: '深圳南山首期项目', label: '深圳南山首期项目' } ]; }, []); var customerOptions = useMemo(function() { return [ { value: '某某科技有限公司', label: '某某科技有限公司' }, { value: '某某物流有限公司', label: '某某物流有限公司' }, { value: '某某制造有限公司', label: '某某制造有限公司' }, { value: '某某出行服务公司', label: '某某出行服务公司' } ]; }, []); // 模拟列表数据 var mockList = useMemo(function() { var list = []; var statuses = ['paid', 'partial', 'unpaid']; var approvalStatuses = ['draft', 'pending', 'auditing', 'completed', 'withdrawn', 'rejected']; var contracts = ['HT-ZL-2025-001', 'HT-ZL-2025-002', 'HT-ZL-2025-003', 'HT-ZL-2024-088', 'HT-ZL-2024-099']; var projects = ['北京朝阳区租赁项目', '上海浦东车辆租赁', '广州天河运营项目', '深圳南山首期项目']; var customers = ['某某科技有限公司', '某某物流有限公司', '某某制造有限公司', '某某出行服务公司']; for (var i = 1; i <= 28; i++) { var status = statuses[i % 3]; var approvalStatus = approvalStatuses[i % 6]; var firstPayable = 15000 + i * 800; var paid = 0; var discount = 0; if (status === 'paid') { paid = firstPayable; discount = i % 4 === 0 ? 200 : 0; } else if (status === 'partial') { paid = Math.floor(firstPayable * 0.5); discount = i % 5 === 0 ? 100 : 0; } var unpaid = Math.max(0, firstPayable - paid - discount); var remark = status !== 'unpaid' ? '已上传付款凭证,备注编号' + i : '-'; var discountReason = discount > 0 ? (i % 4 === 0 ? '长期合作客户优惠' : '首期减免') : '-'; list.push({ id: 'FP' + i, paymentStatus: status, approvalStatus: approvalStatus, contractCode: contracts[i % contracts.length], projectName: projects[i % projects.length], customerName: customers[i % customers.length], contractEffectiveDate: '2025-' + (String((i % 12) + 1)).padStart(2, '0') + '-' + (String((i % 28) + 1)).padStart(2, '0'), firstPayableAmount: firstPayable, paidAmount: paid, discountAmount: discount, unpaidAmount: unpaid, discountReason: discountReason, remark: remark }); } return list; }, []); // 查看页 mock 数据(按 查看页面需求说明 结构) var mockBillDetail = useMemo(function() { return { startDate: '2025-01-01', endDate: '2025-01-31', contractCode: 'HT-ZL-2025-001', projectName: '北京朝阳区租赁项目', customerName: '某某科技有限公司', department: '运营部', responsible: '张三', paymentCycle: '先付(付款周期:1个月)', discountTotal: '200.00', discountReason: '长期合作客户优惠,首期账单减免部分金额' }; }, []); var mockVehicleList = useMemo(function() { return [ { brand: '奔驰', model: 'E300L', plateNo: '京A12345', planDelivery: '2024-12-25', planDeliveryEnd: '2024-12-31', actualDelivery: '2024-12-28', billStart: '2025-01-01', billEnd: '2025-01-31', monthlyRent: '8000.00', paidMonthlyRent: '7600.00', serviceFee: '500.00', paidServiceFee: '480.00', deposit: '2000.00', paidDeposit: '2000.00', serviceItems: [{ name: '保养服务', price: '300.00', effectiveDate: '2025-01-01' }, { name: '保险', price: '200.00', effectiveDate: '2025-01-01' }] }, { brand: '宝马', model: '530Li', plateNo: '京B67890', planDelivery: '2024-12-20', planDeliveryEnd: '2024-12-26', actualDelivery: '2024-12-22', billStart: '2025-01-01', billEnd: '2025-01-31', monthlyRent: '7000.00', paidMonthlyRent: '7000.00', serviceFee: '400.00', paidServiceFee: '380.00', deposit: '1500.00', paidDeposit: '1500.00', serviceItems: [{ name: '保养服务', price: '250.00', effectiveDate: '2025-01-01' }] } ]; }, []); // 氢费账单:氢费付款方式、氢气预付款、氢气实付款金额(元,两位小数) var mockHydrogenData = useMemo(function() { return { paymentMethod: '预付', prepaymentAmount: '3580.00', paidAmount: '3200.00' }; }, []); var mockViolationData = useMemo(function() { return { violationCount: 3, totalAmount: '650.00', paidTotalAmount: '600.00', list: [ { violationTime: '2025-01-10 08:30:00', plateNo: '京A12345', violationType: '违停', location: '北京市朝阳区xxx路', fineAmount: '200.00', paidFineAmount: '200.00' }, { violationTime: '2025-01-18 14:20:00', plateNo: '京B67890', violationType: '超速', location: '北京市海淀区xxx大道', fineAmount: '200.00', paidFineAmount: '180.00' }, { violationTime: '2025-01-25 09:15:00', plateNo: '京A12345', violationType: '闯红灯', location: '北京市东城区xxx路口', fineAmount: '250.00', paidFineAmount: '220.00' } ] }; }, []); var mockReturnFeeData = useMemo(function() { return { totalAmount: '2850.00', paidTotalAmount: '2700.00', list: [ { feeName: '车辆外观损伤费', amount: '800.00', paidAmount: '760.00', photos: ['https://picsum.photos/80/80?random=1', 'https://picsum.photos/80/80?random=2'], attachments: [{ name: '外观损伤说明.pdf' }] }, { feeName: '轮胎磨损费', amount: '1200.00', paidAmount: '1150.00', photos: ['https://picsum.photos/80/80?random=3'], attachments: [{ name: '轮胎检测报告.pdf' }, { name: '维修单据.pdf' }] }, { feeName: '内饰清洁费', amount: '450.00', paidAmount: '430.00', photos: ['https://picsum.photos/80/80?random=4', 'https://picsum.photos/80/80?random=5', 'https://picsum.photos/80/80?random=6'], attachments: [] }, { feeName: '油量补充费', amount: '400.00', paidAmount: '360.00', photos: [], attachments: [{ name: '加油凭证.jpg' }] } ] }; }, []); var vehicleBillTotals = useMemo(function() { var list = mockVehicleList || []; var monthlyRentTotal = 0, paidRentTotal = 0, serviceFeeTotal = 0, paidServiceFeeTotal = 0, depositTotal = 0, paidDepositTotal = 0; list.forEach(function(v) { monthlyRentTotal += parseFloat(v.monthlyRent || 0); paidRentTotal += parseFloat(v.paidMonthlyRent || 0); serviceFeeTotal += parseFloat(v.serviceFee || 0); paidServiceFeeTotal += parseFloat(v.paidServiceFee || 0); depositTotal += parseFloat(v.deposit || 0); paidDepositTotal += parseFloat(v.paidDeposit || 0); }); return { monthlyRentTotal: monthlyRentTotal.toFixed(2), paidRentTotal: paidRentTotal.toFixed(2), serviceFeeTotal: serviceFeeTotal.toFixed(2), paidServiceFeeTotal: paidServiceFeeTotal.toFixed(2), depositTotal: depositTotal.toFixed(2), paidDepositTotal: paidDepositTotal.toFixed(2) }; }, [mockVehicleList]); var vehicleTotals = useMemo(function() { var monthlyRentTotal = parseFloat(vehicleBillTotals.monthlyRentTotal || 0); var serviceFeeTotal = parseFloat(vehicleBillTotals.serviceFeeTotal || 0); var depositTotal = parseFloat(vehicleBillTotals.depositTotal || 0); var hydrogenTotal = parseFloat(mockHydrogenData.prepaymentAmount || 0); var violationTotal = parseFloat(mockViolationData.totalAmount || 0); var returnFeeTotal = parseFloat(mockReturnFeeData.totalAmount || 0); var payableTotal = monthlyRentTotal + serviceFeeTotal + depositTotal + hydrogenTotal + violationTotal + returnFeeTotal; var paidTotal = 0; (mockVehicleList || []).forEach(function(v) { paidTotal += parseFloat(v.paidMonthlyRent || 0) + parseFloat(v.paidServiceFee || 0) + parseFloat(v.paidDeposit || 0); }); var discountTotal = parseFloat(mockBillDetail.discountTotal || 0); var unpaidTotal = payableTotal - paidTotal - discountTotal; if (unpaidTotal < 0) unpaidTotal = 0; return { payableTotal: payableTotal.toFixed(2), paidTotal: paidTotal.toFixed(2), unpaidTotal: unpaidTotal.toFixed(2) }; }, [vehicleBillTotals, mockHydrogenData, mockViolationData, mockReturnFeeData, mockVehicleList, mockBillDetail]); // 筛选后的列表(使用已生效条件,点击查询后才与选择器联动) var filteredList = useMemo(function() { var list = mockList; var af = appliedFilter; // 合同编码选择器:与列表 contractCode 精确匹配 if (af.contract && af.contract.trim()) { var cf = af.contract.trim(); list = list.filter(function(item) { return (item.contractCode || '') === cf; }); } // 项目名称选择器:与列表 projectName 精确匹配 if (af.project && af.project.trim()) { var pf = af.project.trim(); list = list.filter(function(item) { return (item.projectName || '') === pf; }); } // 客户名称选择器:与列表 customerName 精确匹配 if (af.customer && af.customer.trim()) { var cuf = af.customer.trim(); list = list.filter(function(item) { return (item.customerName || '') === cuf; }); } if (af.status && af.status.length > 0) { list = list.filter(function(item) { return af.status.indexOf(item.paymentStatus) >= 0; }); } return list; }, [mockList, appliedFilter]); var totalCount = filteredList.length; var totalPages = Math.ceil(totalCount / pageSize) || 1; var paginatedList = useMemo(function() { var start = (currentPage - 1) * pageSize; return filteredList.slice(start, start + pageSize); }, [filteredList, currentPage, pageSize]); var getStatusText = function(status) { if (status === 'paid') return '已付款'; if (status === 'partial') return '部分付款'; return '未付款'; }; var getStatusColor = function(status) { if (status === 'paid') return '#52c41a'; if (status === 'partial') return '#faad14'; return '#ff4d4f'; }; var formatAmount = function(num) { var n = typeof num === 'number' ? num : parseFloat(num); if (isNaN(n)) return '0.00'; return n.toFixed(2); }; var handleQuery = useCallback(function() { setAppliedFilter({ contract: contractInput, project: projectInput, customer: customerInput, status: statusInput }); setCurrentPage(1); }, [contractInput, projectInput, customerInput, statusInput]); var handleReset = useCallback(function() { setContractInput(''); setProjectInput(''); setCustomerInput(''); setStatusInput([]); setAppliedFilter({ contract: '', project: '', customer: '', status: [] }); setCurrentPage(1); }, []); var getApprovalStatus = useCallback(function(row) { return approvalStatusMap[row.id] != null ? approvalStatusMap[row.id] : row.approvalStatus; }, [approvalStatusMap]); var getApprovalStatusText = function(s) { if (s === 'draft') return '待提交'; if (s === 'pending' || s === 'auditing') return '审核中'; if (s === 'completed') return '审核完成'; if (s === 'withdrawn') return '撤回'; if (s === 'rejected') return '审核驳回'; return s || '-'; }; var handleView = useCallback(function(id) { setViewingBillId(id); setDetailMode('view'); setCurrentView('detail'); }, []); var handlePayment = useCallback(function(id) { setViewingBillId(id); setDetailMode('payment'); var vl = mockVehicleList.map(function(v) { return { paidMonthlyRent: v.paidMonthlyRent || '', paidServiceFee: v.paidServiceFee || '', paidDeposit: v.paidDeposit || '' }; }); var hl = []; var viol = mockViolationData.list.map(function(item) { return { paidFineAmount: item.paidFineAmount || '' }; }); var rfl = mockReturnFeeData.list.map(function(item) { return { paidAmount: item.paidAmount || '' }; }); setPaymentForm({ discountAmount: mockBillDetail.discountTotal || '', discountReason: mockBillDetail.discountReason || '', hydrogenPaidAmount: mockHydrogenData.paidAmount || '', vehicleList: vl, hydrogenList: hl, violationList: viol, returnFeeList: rfl }); setCurrentView('detail'); }, []); var handleBackToList = useCallback(function() { setCurrentView('list'); setDetailMode('view'); setViewingBillId(null); }, []); var handleSave = useCallback(function() { if (viewingBillId) { setApprovalStatusMap(function(prev) { var next = {}; for (var k in prev) { if (prev.hasOwnProperty(k)) next[k] = prev[k]; } next[viewingBillId] = 'draft'; return next; }); } alert('保存成功'); handleBackToList(); }, [viewingBillId, handleBackToList]); var handleWithdraw = useCallback(function(rowId) { setWithdrawConfirmId(rowId); }, []); var handleWithdrawConfirm = useCallback(function() { if (withdrawConfirmId) { setApprovalStatusMap(function(prev) { var next = {}; for (var k in prev) { if (prev.hasOwnProperty(k)) next[k] = prev[k]; } next[withdrawConfirmId] = 'draft'; return next; }); setWithdrawConfirmId(null); alert('已撤回,可重新编辑后提交'); } }, [withdrawConfirmId]); var handlePaymentFormChange = useCallback(function(section, index, field, value) { setPaymentForm(function(prev) { var next = { discountAmount: prev.discountAmount, discountReason: prev.discountReason, hydrogenPaidAmount: prev.hydrogenPaidAmount, vehicleList: prev.vehicleList.slice(), hydrogenList: prev.hydrogenList.slice(), violationList: prev.violationList.slice(), returnFeeList: prev.returnFeeList.slice() }; if (section === 'bill') { if (field === 'discountAmount') next.discountAmount = value; if (field === 'discountReason') next.discountReason = value; if (field === 'hydrogenPaidAmount') next.hydrogenPaidAmount = value; } else if (section === 'vehicle' && index >= 0 && index < next.vehicleList.length) { next.vehicleList[index] = Object.assign({}, next.vehicleList[index]); next.vehicleList[index][field] = value; } else if (section === 'hydrogen' && index >= 0 && index < next.hydrogenList.length) { next.hydrogenList[index] = Object.assign({}, next.hydrogenList[index]); next.hydrogenList[index][field] = value; } else if (section === 'violation' && index >= 0 && index < next.violationList.length) { next.violationList[index] = Object.assign({}, next.violationList[index]); next.violationList[index][field] = value; } else if (section === 'returnFee' && index >= 0 && index < next.returnFeeList.length) { next.returnFeeList[index] = Object.assign({}, next.returnFeeList[index]); next.returnFeeList[index][field] = value; } return next; }); }, []); var handleSubmit = useCallback(function() { var errors = []; if (!paymentForm.discountAmount || String(paymentForm.discountAmount).trim() === '') errors.push('减免金额'); if (!paymentForm.discountReason || String(paymentForm.discountReason).trim() === '') errors.push('减免原因'); if (!paymentForm.hydrogenPaidAmount || String(paymentForm.hydrogenPaidAmount).trim() === '') errors.push('氢气实付款金额'); paymentForm.vehicleList.forEach(function(v, i) { if (!v.paidMonthlyRent || String(v.paidMonthlyRent).trim() === '') errors.push('车辆账单-实付月租金(第' + (i + 1) + '行)'); if (!v.paidServiceFee || String(v.paidServiceFee).trim() === '') errors.push('车辆账单-实付服务费(第' + (i + 1) + '行)'); if (!v.paidDeposit || String(v.paidDeposit).trim() === '') errors.push('车辆账单-实付保证金(第' + (i + 1) + '行)'); }); paymentForm.violationList.forEach(function(v, i) { if (!v.paidFineAmount || String(v.paidFineAmount).trim() === '') errors.push('违章费用-实付罚款金额(第' + (i + 1) + '行)'); }); paymentForm.returnFeeList.forEach(function(r, i) { if (!r.paidAmount || String(r.paidAmount).trim() === '') errors.push('还车费用-实付金额(第' + (i + 1) + '行)'); }); if (errors.length > 0) { alert('请填写必填项:' + errors.join('、')); return; } if (viewingBillId) { setApprovalStatusMap(function(prev) { var next = {}; for (var k in prev) { if (prev.hasOwnProperty(k)) next[k] = prev[k]; } next[viewingBillId] = 'pending'; return next; }); } alert('提交成功'); handleBackToList(); }, [paymentForm, handleBackToList, viewingBillId]); // 样式 var styles = { page: { padding: '24px', backgroundColor: '#f5f5f5', minHeight: '100vh', fontFamily: '-apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, "Helvetica Neue", Arial, sans-serif' }, breadcrumb: { marginBottom: '16px', fontSize: '14px', color: '#666' }, breadcrumbSep: { color: '#bfbfbf', margin: '0 8px' }, content: { backgroundColor: '#fff', borderRadius: '8px', padding: '24px', boxShadow: '0 1px 2px rgba(0,0,0,0.03)', overflowX: 'auto' }, filterRow: { display: 'flex', flexWrap: 'nowrap', gap: '16px', marginBottom: '20px', alignItems: 'center', overflowX: 'auto' }, filterItem: { display: 'flex', alignItems: 'center', gap: '8px' }, label: { fontSize: '14px', color: '#333', minWidth: '80px' }, input: { padding: '8px 12px', border: '1px solid #d9d9d9', borderRadius: '4px', fontSize: '14px', width: '200px' }, select: { padding: '8px 12px', border: '1px solid #d9d9d9', borderRadius: '4px', fontSize: '14px', width: '200px' }, filterSelectWrap: { position: 'relative', width: '200px' }, filterDropdown: { position: 'absolute', top: '100%', left: 0, right: 0, marginTop: '2px', maxHeight: '200px', overflowY: 'auto', backgroundColor: '#fff', border: '1px solid #d9d9d9', borderRadius: '4px', boxShadow: '0 2px 8px rgba(0,0,0,0.15)', zIndex: 10 }, filterDropdownItem: { padding: '8px 12px', fontSize: '14px', cursor: 'pointer', borderBottom: '1px solid #f0f0f0' }, selectMultiple: { padding: '8px 12px', border: '1px solid #d9d9d9', borderRadius: '4px', fontSize: '14px', minWidth: '200px', minHeight: '36px' }, statusMultiWrap: { position: 'relative', display: 'inline-block' }, statusMultiDisplay: { padding: '8px 12px', border: '1px solid #d9d9d9', borderRadius: '4px', fontSize: '14px', width: '200px', backgroundColor: '#fff', cursor: 'pointer', minHeight: '36px', boxSizing: 'border-box' }, statusDropdownPanel: { position: 'absolute', left: 0, top: '100%', marginTop: '2px', width: '100%', maxHeight: '220px', overflowY: 'auto', backgroundColor: '#fff', border: '1px solid #d9d9d9', borderRadius: '4px', boxShadow: '0 2px 8px rgba(0,0,0,0.15)', zIndex: 10 }, statusDropdownOption: { padding: '8px 12px', fontSize: '14px', cursor: 'pointer', borderBottom: '1px solid #f0f0f0' }, table: { width: '100%', borderCollapse: 'collapse', fontSize: '14px' }, th: { textAlign: 'left', padding: '12px 16px', backgroundColor: '#fafafa', borderBottom: '1px solid #f0f0f0', fontWeight: 600, color: '#333', whiteSpace: 'nowrap' }, td: { padding: '12px 16px', borderBottom: '1px solid #f0f0f0', color: '#333', whiteSpace: 'nowrap' }, actionColTh: { position: 'sticky', right: 0, backgroundColor: '#fafafa', boxShadow: '-2px 0 4px rgba(0,0,0,0.06)', zIndex: 1 }, actionColTd: { position: 'sticky', right: 0, backgroundColor: '#fff', boxShadow: '-2px 0 4px rgba(0,0,0,0.06)', zIndex: 1 }, actionBtn: { padding: '4px 12px', marginRight: '8px', borderRadius: '4px', border: 'none', cursor: 'pointer', fontSize: '13px' }, viewBtn: { backgroundColor: '#e6f7ff', color: '#1890ff' }, payBtn: { backgroundColor: '#f6ffed', color: '#52c41a' }, withdrawBtn: { backgroundColor: '#fff7e6', color: '#fa8c16' }, pagination: { display: 'flex', justifyContent: 'space-between', alignItems: 'center', marginTop: '20px', flexWrap: 'wrap', gap: '12px' }, pageSizeSelect: { padding: '6px 10px', border: '1px solid #d9d9d9', borderRadius: '4px', fontSize: '13px' }, pageInfo: { fontSize: '14px', color: '#666' }, pageHeader: { display: 'flex', justifyContent: 'space-between', alignItems: 'center', marginBottom: '16px', flexWrap: 'wrap', gap: '12px' }, requirementLink: { color: '#1890ff', cursor: 'pointer', fontSize: '14px', textDecoration: 'none' }, requirementModalBody: { maxHeight: '70vh', overflowY: 'auto', whiteSpace: 'pre-wrap', fontSize: '14px', lineHeight: 1.6, color: '#333', padding: '0 4px' }, queryBtn: { padding: '8px 20px', backgroundColor: '#1890ff', color: '#fff', border: 'none', borderRadius: '4px', cursor: 'pointer', fontSize: '14px' }, resetBtn: { padding: '8px 20px', backgroundColor: '#fff', color: '#666', border: '1px solid #d9d9d9', borderRadius: '4px', cursor: 'pointer', fontSize: '14px' }, // 查看页样式(按 查看页面需求说明) detailPage: { padding: '24px', backgroundColor: '#f5f5f5', minHeight: '100vh', width: '100%', boxSizing: 'border-box' }, backBtn: { marginBottom: '16px', padding: '8px 16px', backgroundColor: '#fff', border: '1px solid #d9d9d9', borderRadius: '4px', cursor: 'pointer', fontSize: '14px' }, detailContent: { display: 'flex', flexDirection: 'column', gap: '24px', width: '100%' }, detailCard: { backgroundColor: '#fff', borderRadius: '8px', padding: '24px', boxShadow: '0 1px 2px rgba(0,0,0,0.03)', width: '100%', boxSizing: 'border-box' }, detailCardTitle: { fontSize: '16px', fontWeight: 600, marginBottom: '16px', paddingBottom: '12px', borderBottom: '1px solid #f0f0f0' }, detailRow: { display: 'grid', gridTemplateColumns: 'repeat(3, 1fr)', gap: '24px', marginBottom: '12px', fontSize: '14px' }, detailItem: {}, detailItemInline: { display: 'flex', alignItems: 'center' }, detailItemInputRight: { display: 'flex', alignItems: 'center', justifyContent: 'space-between' }, detailLabel: { color: '#666', marginRight: '8px' }, amountInputWrap: { display: 'flex', alignItems: 'center', gap: '8px' }, amountInput: { padding: '8px 12px', border: '1px solid #d9d9d9', borderRadius: '4px', fontSize: '14px', width: '120px' }, amountSuffix: { color: '#666', fontSize: '14px' }, detailTextarea: { padding: '8px 12px', border: '1px solid #d9d9d9', borderRadius: '4px', fontSize: '14px', width: '100%', minWidth: '200px', minHeight: '60px', resize: 'vertical' }, vehicleTable: { width: '100%', borderCollapse: 'collapse', fontSize: '14px' }, hydrogenSummary: { display: 'flex', gap: '48px', marginBottom: '16px', fontSize: '14px' }, hydrogenSummaryItem: { color: '#333' }, photoThumb: { width: '40px', height: '40px', objectFit: 'cover', borderRadius: '4px', cursor: 'pointer', marginRight: '4px', verticalAlign: 'middle' }, attachmentLink: { color: '#1890ff', cursor: 'pointer', textDecoration: 'none', marginRight: '8px', fontSize: '14px' }, amountLink: { color: '#1890ff', cursor: 'pointer', textDecoration: 'none' }, photoViewerOverlay: { position: 'fixed', top: 0, left: 0, right: 0, bottom: 0, backgroundColor: 'rgba(0,0,0,0.85)', display: 'flex', alignItems: 'center', justifyContent: 'center', zIndex: 1001 }, photoViewerContent: { position: 'relative', textAlign: 'center' }, photoViewerImg: { maxWidth: '90vw', maxHeight: '85vh', objectFit: 'contain' }, photoViewerBtn: { position: 'absolute', top: '50%', marginTop: '-20px', padding: '10px 16px', backgroundColor: 'rgba(255,255,255,0.9)', border: 'none', borderRadius: '4px', cursor: 'pointer', fontSize: '14px' }, photoViewerPrev: { left: '20px' }, photoViewerNext: { right: '20px' }, photoViewerClose: { position: 'absolute', top: '-40px', right: '0', padding: '8px 16px', backgroundColor: 'rgba(255,255,255,0.9)', border: 'none', borderRadius: '4px', cursor: 'pointer', fontSize: '14px' }, photoViewerCounter: { color: '#fff', marginTop: '16px', fontSize: '14px' }, popover: { position: 'fixed', top: 0, left: 0, right: 0, bottom: 0, backgroundColor: 'rgba(0,0,0,0.45)', display: 'flex', alignItems: 'center', justifyContent: 'center', zIndex: 1000 }, popoverCard: { backgroundColor: '#fff', borderRadius: '8px', padding: '24px', maxWidth: '90%', maxHeight: '80vh', overflow: 'auto' }, popoverHeader: { display: 'flex', justifyContent: 'space-between', alignItems: 'center', marginBottom: '16px', whiteSpace: 'nowrap' }, popoverTitle: { fontSize: '16px', fontWeight: 600, whiteSpace: 'nowrap' }, popoverClose: { padding: '4px 12px', backgroundColor: '#f5f5f5', border: 'none', borderRadius: '4px', cursor: 'pointer' }, popoverTable: { width: '100%', borderCollapse: 'collapse', fontSize: '14px' }, popoverTh: { textAlign: 'left', padding: '12px 16px', backgroundColor: '#fafafa', borderBottom: '1px solid #f0f0f0', fontWeight: 600, color: '#333', whiteSpace: 'nowrap' }, popoverTd: { padding: '12px 16px', borderBottom: '1px solid #f0f0f0', color: '#333', whiteSpace: 'nowrap' }, modalFooter: { marginTop: '24px', textAlign: 'right', display: 'flex', justifyContent: 'center', gap: '12px' } }; // 查看页:按 查看页面需求说明 渲染(租赁账单详情) if (currentView === 'detail') { return ( React.createElement('div', { style: styles.detailPage }, React.createElement('div', { style: Object.assign({}, styles.breadcrumb, { marginBottom: '16px' }) }, React.createElement('span', null, '财务管理'), React.createElement('span', { style: styles.breadcrumbSep }, '>'), React.createElement('span', null, '提车首付款'), React.createElement('span', { style: styles.breadcrumbSep }, '>'), React.createElement('span', null, detailMode === 'payment' ? '收费' : '查看') ), React.createElement('div', { style: styles.detailContent }, React.createElement('div', { style: styles.detailCard }, React.createElement('div', { style: styles.detailCardTitle }, '账单信息'), React.createElement('div', { style: styles.detailRow }, React.createElement('div', { style: styles.detailItem }, React.createElement('span', { style: styles.detailLabel }, '账单开始日期:'), React.createElement('span', null, mockBillDetail.startDate)), React.createElement('div', { style: styles.detailItem }, React.createElement('span', { style: styles.detailLabel }, '账单结束日期:'), React.createElement('span', null, mockBillDetail.endDate)) ), React.createElement('div', { style: styles.detailRow }, React.createElement('div', { style: styles.detailItem }, React.createElement('span', { style: styles.detailLabel }, '合同编码:'), React.createElement('span', null, mockBillDetail.contractCode)), React.createElement('div', { style: styles.detailItem }, React.createElement('span', { style: styles.detailLabel }, '项目名称:'), React.createElement('span', null, mockBillDetail.projectName)), React.createElement('div', { style: styles.detailItem }, React.createElement('span', { style: styles.detailLabel }, '客户名称:'), React.createElement('span', null, mockBillDetail.customerName)) ), React.createElement('div', { style: styles.detailRow }, React.createElement('div', { style: styles.detailItem }, React.createElement('span', { style: styles.detailLabel }, '业务部门:'), React.createElement('span', null, mockBillDetail.department)), React.createElement('div', { style: styles.detailItem }, React.createElement('span', { style: styles.detailLabel }, '业务负责人:'), React.createElement('span', null, mockBillDetail.responsible)), React.createElement('div', { style: styles.detailItem }, React.createElement('span', { style: styles.detailLabel }, '付款周期:'), React.createElement('span', null, mockBillDetail.paymentCycle)) ), React.createElement('div', { style: styles.detailRow }, React.createElement('div', { style: styles.detailItem }, React.createElement('span', { style: styles.detailLabel }, '首期应付金额:'), React.createElement('span', { style: { color: '#1890ff', fontWeight: 600 } }, vehicleTotals.payableTotal + ' 元')), React.createElement('div', { style: styles.detailItem }, React.createElement('span', { style: styles.detailLabel }, '实付款总额:'), React.createElement('span', { style: { color: '#52c41a', fontWeight: 600 } }, vehicleTotals.paidTotal + ' 元')), React.createElement('div', { style: Object.assign({}, styles.detailItem, styles.detailItemInline) }, React.createElement('span', { style: styles.detailLabel }, '减免金额:'), detailMode === 'payment' ? React.createElement('div', { style: styles.amountInputWrap }, React.createElement('input', { type: 'text', style: styles.amountInput, value: paymentForm.discountAmount, onChange: function(e) { handlePaymentFormChange('bill', -1, 'discountAmount', e.target.value); }, placeholder: '0.00' }), React.createElement('span', { style: styles.amountSuffix }, '元')) : React.createElement('span', { style: { fontWeight: 600 } }, mockBillDetail.discountTotal + ' 元')), React.createElement('div', { style: styles.detailItem }, React.createElement('span', { style: styles.detailLabel }, '未付款总额:'), React.createElement('span', { style: { color: '#ff4d4f', fontWeight: 600 } }, vehicleTotals.unpaidTotal + ' 元')) ), React.createElement('div', { style: styles.detailRow }, React.createElement('div', { style: Object.assign({}, styles.detailItem, { gridColumn: '1 / -1' }) }, React.createElement('span', { style: styles.detailLabel }, '减免原因:'), detailMode === 'payment' ? React.createElement('textarea', { style: styles.detailTextarea, value: paymentForm.discountReason, onChange: function(e) { handlePaymentFormChange('bill', -1, 'discountReason', e.target.value); }, placeholder: '请输入减免原因' }) : React.createElement('span', null, mockBillDetail.discountReason || '-')) ) ), React.createElement('div', { style: styles.detailCard }, React.createElement('div', { style: styles.detailCardTitle }, '车辆账单'), React.createElement('table', { style: styles.vehicleTable }, React.createElement('thead', null, React.createElement('tr', null, React.createElement('th', { style: styles.th }, '品牌'), React.createElement('th', { style: styles.th }, '型号'), React.createElement('th', { style: styles.th }, '车牌号'), React.createElement('th', { style: styles.th }, '计划交车日期'), React.createElement('th', { style: styles.th }, '实际交车日期'), React.createElement('th', { style: styles.th }, '账单开始日期'), React.createElement('th', { style: styles.th }, '计费结束日期'), React.createElement('th', { style: styles.th }, '车辆月租金'), React.createElement('th', { style: styles.th }, '实付月租金'), React.createElement('th', { style: styles.th }, '服务费'), React.createElement('th', { style: styles.th }, '实付服务费'), React.createElement('th', { style: styles.th }, '保证金'), React.createElement('th', { style: styles.th }, '实付保证金') )), React.createElement('tbody', null, mockVehicleList.map(function(v, idx) { var pf = paymentForm.vehicleList[idx] || {}; return React.createElement('tr', { key: v.plateNo }, React.createElement('td', { style: styles.td }, v.brand), React.createElement('td', { style: styles.td }, v.model), React.createElement('td', { style: styles.td }, v.plateNo), React.createElement('td', { style: styles.td }, (v.planDelivery && v.planDeliveryEnd) ? (v.planDelivery + '至' + v.planDeliveryEnd) : (v.planDelivery || '未设置')), React.createElement('td', { style: styles.td }, v.actualDelivery || '未交车'), React.createElement('td', { style: styles.td }, v.billStart || '未设置'), React.createElement('td', { style: styles.td }, v.billEnd || '未设置'), React.createElement('td', { style: styles.td }, v.monthlyRent), React.createElement('td', { style: styles.td }, detailMode === 'payment' ? React.createElement('div', { style: styles.amountInputWrap }, React.createElement('input', { type: 'text', style: styles.amountInput, value: pf.paidMonthlyRent || '', onChange: function(e) { handlePaymentFormChange('vehicle', idx, 'paidMonthlyRent', e.target.value); }, placeholder: '0.00' }), React.createElement('span', { style: styles.amountSuffix }, '元')) : (parseFloat(v.paidMonthlyRent || 0)).toFixed(2)), React.createElement('td', { style: styles.td }, detailMode === 'payment' ? v.serviceFee : React.createElement('span', { style: styles.amountLink, onClick: function() { setPopover({ type: 'service', data: v.serviceItems }); } }, v.serviceFee)), React.createElement('td', { style: styles.td }, detailMode === 'payment' ? React.createElement('div', { style: styles.amountInputWrap }, React.createElement('input', { type: 'text', style: styles.amountInput, value: pf.paidServiceFee || '', onChange: function(e) { handlePaymentFormChange('vehicle', idx, 'paidServiceFee', e.target.value); }, placeholder: '0.00' }), React.createElement('span', { style: styles.amountSuffix }, '元')) : (parseFloat(v.paidServiceFee || 0)).toFixed(2)), React.createElement('td', { style: styles.td }, v.deposit), React.createElement('td', { style: styles.td }, detailMode === 'payment' ? React.createElement('div', { style: styles.amountInputWrap }, React.createElement('input', { type: 'text', style: styles.amountInput, value: pf.paidDeposit || '', onChange: function(e) { handlePaymentFormChange('vehicle', idx, 'paidDeposit', e.target.value); }, placeholder: '0.00' }), React.createElement('span', { style: styles.amountSuffix }, '元')) : (parseFloat(v.paidDeposit || 0)).toFixed(2)) ); })), React.createElement('tfoot', null, React.createElement('tr', { style: { backgroundColor: '#fafafa', fontWeight: 600 } }, React.createElement('td', { style: styles.td, colSpan: 7 }, '总计'), React.createElement('td', { style: styles.td }, vehicleBillTotals.monthlyRentTotal), React.createElement('td', { style: styles.td }, vehicleBillTotals.paidRentTotal), React.createElement('td', { style: styles.td }, vehicleBillTotals.serviceFeeTotal), React.createElement('td', { style: styles.td }, vehicleBillTotals.paidServiceFeeTotal), React.createElement('td', { style: styles.td }, vehicleBillTotals.depositTotal), React.createElement('td', { style: styles.td }, vehicleBillTotals.paidDepositTotal))) ) ), React.createElement('div', { style: styles.detailCard }, React.createElement('div', { style: styles.detailCardTitle }, '氢费账单'), React.createElement('div', { style: styles.detailRow }, React.createElement('div', { style: styles.detailItem }, React.createElement('span', { style: styles.detailLabel }, '氢费付款方式:'), React.createElement('span', null, mockHydrogenData.paymentMethod || '-')), React.createElement('div', { style: styles.detailItem }, React.createElement('span', { style: styles.detailLabel }, '氢气预付款:'), React.createElement('span', null, (parseFloat(mockHydrogenData.prepaymentAmount || 0)).toFixed(2) + ' 元')), React.createElement('div', { style: Object.assign({}, styles.detailItem, styles.detailItemInline) }, React.createElement('span', { style: styles.detailLabel }, '氢气实付款金额:'), detailMode === 'payment' ? React.createElement('div', { style: styles.amountInputWrap }, React.createElement('input', { type: 'text', style: styles.amountInput, value: paymentForm.hydrogenPaidAmount, onChange: function(e) { handlePaymentFormChange('bill', -1, 'hydrogenPaidAmount', e.target.value); }, placeholder: '0.00' }), React.createElement('span', { style: styles.amountSuffix }, '元')) : React.createElement('span', null, (parseFloat(mockHydrogenData.paidAmount || 0)).toFixed(2) + ' 元')) ) ) ), React.createElement('div', { style: { marginTop: '24px', textAlign: 'center', display: 'flex', justifyContent: 'center', gap: '16px' } }, detailMode === 'payment' && React.createElement('button', { type: 'button', style: Object.assign({}, styles.backBtn, { backgroundColor: '#1890ff', color: '#fff', border: 'none' }), onClick: handleSubmit }, '提交审核'), detailMode === 'payment' && React.createElement('button', { type: 'button', style: styles.backBtn, onClick: handleSave }, '保存'), React.createElement('button', { type: 'button', style: styles.backBtn, onClick: handleBackToList }, '取消') ), photoViewer.visible && photoViewer.photos.length > 0 && React.createElement('div', { style: styles.photoViewerOverlay, onClick: function() { setPhotoViewer({ visible: false, photos: [], currentIndex: 0 }); } }, React.createElement('div', { style: styles.photoViewerContent, onClick: function(e) { e.stopPropagation(); } }, React.createElement('button', { style: Object.assign({}, styles.photoViewerBtn, styles.photoViewerClose), onClick: function() { setPhotoViewer({ visible: false, photos: [], currentIndex: 0 }); } }, '关闭'), photoViewer.currentIndex > 0 ? React.createElement('button', { style: Object.assign({}, styles.photoViewerBtn, styles.photoViewerPrev), onClick: function() { setPhotoViewer({ visible: true, photos: photoViewer.photos, currentIndex: photoViewer.currentIndex - 1 }); } }, '上一张') : null, React.createElement('img', { style: styles.photoViewerImg, src: photoViewer.photos[photoViewer.currentIndex].replace('80/80', '600/600'), alt: '' }), photoViewer.currentIndex < photoViewer.photos.length - 1 ? React.createElement('button', { style: Object.assign({}, styles.photoViewerBtn, styles.photoViewerNext), onClick: function() { setPhotoViewer({ visible: true, photos: photoViewer.photos, currentIndex: photoViewer.currentIndex + 1 }); } }, '下一张') : null, React.createElement('div', { style: styles.photoViewerCounter }, (photoViewer.currentIndex + 1) + ' / ' + photoViewer.photos.length) ) ), (popover.type === 'service' && React.createElement('div', { style: styles.popover, onClick: function() { setPopover({ type: null, data: null }); } }, React.createElement('div', { style: styles.popoverCard, onClick: function(e) { e.stopPropagation(); } }, React.createElement('div', { style: styles.popoverHeader }, React.createElement('span', { style: styles.popoverTitle }, '服务费明细'), React.createElement('button', { style: styles.popoverClose, onClick: function() { setPopover({ type: null, data: null }); } }, '关闭')), React.createElement('table', { style: styles.table }, React.createElement('thead', null, React.createElement('tr', null, React.createElement('th', { style: styles.th }, '服务项'), React.createElement('th', { style: styles.th }, '价格'), React.createElement('th', { style: styles.th }, '服务生效日期'))), React.createElement('tbody', null, popover.data ? popover.data.map(function(s, i) { return React.createElement('tr', { key: i }, React.createElement('td', { style: styles.td }, s.name), React.createElement('td', { style: styles.td }, s.price), React.createElement('td', { style: styles.td }, s.effectiveDate)); }) : null)) ) )) ) ); } return ( React.createElement('div', { style: styles.page }, React.createElement('div', { style: styles.pageHeader }, React.createElement('div', { style: styles.breadcrumb }, React.createElement('span', null, '财务管理'), React.createElement('span', { style: styles.breadcrumbSep }, '>'), React.createElement('span', null, '提车首付款') ), React.createElement('a', { style: styles.requirementLink, onClick: function() { setRequirementDetailVisible(true); }, role: 'button', tabIndex: 0, onKeyDown: function(e) { if (e.key === 'Enter' || e.key === ' ') { e.preventDefault(); setRequirementDetailVisible(true); } } }, '查看需求明细') ), React.createElement('div', { style: styles.content }, // 筛选:合同编码、项目名称、客户名称(选择器+输入搜索)、付款状态(多选);右侧 查询、重置 React.createElement('div', { style: styles.filterRow }, React.createElement('div', { style: styles.filterItem }, React.createElement('span', { style: styles.label }, '合同编码:'), React.createElement('div', { style: styles.filterSelectWrap }, React.createElement('input', { style: styles.input, placeholder: '请输入合同编码', value: contractInput, onChange: function(e) { setContractInput(e.target.value); }, onFocus: function() { setFilterDropdownOpen('contract'); }, onBlur: function() { setTimeout(function() { setFilterDropdownOpen(null); }, 200); } }), filterDropdownOpen === 'contract' && React.createElement('div', { style: styles.filterDropdown }, contractOptions.filter(function(opt) { var kw = (contractInput || '').toLowerCase(); if (!kw) return true; return (opt.label || '').toLowerCase().indexOf(kw) >= 0 || (opt.value || '').toLowerCase().indexOf(kw) >= 0; }).map(function(opt) { return React.createElement('div', { key: opt.value, style: styles.filterDropdownItem, onMouseDown: function(e) { e.preventDefault(); setContractInput(opt.value); setFilterDropdownOpen(null); } }, opt.label); }) ) ) ), React.createElement('div', { style: styles.filterItem }, React.createElement('span', { style: styles.label }, '项目名称:'), React.createElement('div', { style: styles.filterSelectWrap }, React.createElement('input', { style: styles.input, placeholder: '请输入项目名称', value: projectInput, onChange: function(e) { setProjectInput(e.target.value); }, onFocus: function() { setFilterDropdownOpen('project'); }, onBlur: function() { setTimeout(function() { setFilterDropdownOpen(null); }, 200); } }), filterDropdownOpen === 'project' && React.createElement('div', { style: styles.filterDropdown }, projectOptions.filter(function(opt) { var kw = (projectInput || '').toLowerCase(); if (!kw) return true; return (opt.label || '').toLowerCase().indexOf(kw) >= 0 || (opt.value || '').toLowerCase().indexOf(kw) >= 0; }).map(function(opt) { return React.createElement('div', { key: opt.value, style: styles.filterDropdownItem, onMouseDown: function(e) { e.preventDefault(); setProjectInput(opt.value); setFilterDropdownOpen(null); } }, opt.label); }) ) ) ), React.createElement('div', { style: styles.filterItem }, React.createElement('span', { style: styles.label }, '客户名称:'), React.createElement('div', { style: styles.filterSelectWrap }, React.createElement('input', { style: styles.input, placeholder: '请输入客户名称', value: customerInput, onChange: function(e) { setCustomerInput(e.target.value); }, onFocus: function() { setFilterDropdownOpen('customer'); }, onBlur: function() { setTimeout(function() { setFilterDropdownOpen(null); }, 200); } }), filterDropdownOpen === 'customer' && React.createElement('div', { style: styles.filterDropdown }, customerOptions.filter(function(opt) { var kw = (customerInput || '').toLowerCase(); if (!kw) return true; return (opt.label || '').toLowerCase().indexOf(kw) >= 0 || (opt.value || '').toLowerCase().indexOf(kw) >= 0; }).map(function(opt) { return React.createElement('div', { key: opt.value, style: styles.filterDropdownItem, onMouseDown: function(e) { e.preventDefault(); setCustomerInput(opt.value); setFilterDropdownOpen(null); } }, opt.label); }) ) ) ), React.createElement('div', { style: styles.filterItem }, React.createElement('span', { style: styles.label }, '付款状态:'), React.createElement('div', { style: styles.statusMultiWrap, tabIndex: 0, onBlur: function() { setTimeout(function() { setStatusDropdownOpen(false); }, 200); } }, React.createElement('div', { style: styles.statusMultiDisplay, onClick: function() { setStatusDropdownOpen(!statusDropdownOpen); } }, statusInput.length === 0 ? '全部' : statusInput.map(function(s) { return getStatusText(s); }).join('、')), statusDropdownOpen ? React.createElement('div', { style: styles.statusDropdownPanel }, ['partial', 'unpaid', 'paid'].map(function(s) { var checked = statusInput.indexOf(s) >= 0; return React.createElement('div', { key: s, style: styles.statusDropdownOption, onMouseDown: function(e) { e.preventDefault(); var idx = statusInput.indexOf(s); var next = statusInput.slice(); if (idx >= 0) next.splice(idx, 1); else next.push(s); setStatusInput(next); } }, React.createElement('label', { style: { cursor: 'pointer', display: 'flex', alignItems: 'center', gap: '6px' } }, React.createElement('input', { type: 'checkbox', checked: checked, readOnly: true }), getStatusText(s) )); }) ) : null ) ), React.createElement('div', { style: { display: 'flex', gap: '8px', marginLeft: 'auto' } }, React.createElement('button', { type: 'button', style: styles.queryBtn, onClick: handleQuery }, '查询'), React.createElement('button', { type: 'button', style: styles.resetBtn, onClick: handleReset }, '重置') ) ), // 列表:审核状态、付款状态、合同编码、项目名称、客户名称、合同生效日期、首期应付金额、实付款总额、减免金额、未付款总额、减免原因、操作(固定右侧) React.createElement('table', { style: styles.table }, React.createElement('thead', null, React.createElement('tr', null, React.createElement('th', { style: styles.th }, '审核状态'), React.createElement('th', { style: styles.th }, '付款状态'), React.createElement('th', { style: styles.th }, '合同编码'), React.createElement('th', { style: styles.th }, '项目名称'), React.createElement('th', { style: styles.th }, '客户名称'), React.createElement('th', { style: styles.th }, '合同生效日期'), React.createElement('th', { style: styles.th }, '首期应付金额'), React.createElement('th', { style: styles.th }, '实付款总额'), React.createElement('th', { style: styles.th }, '减免金额'), React.createElement('th', { style: styles.th }, '未付款总额'), React.createElement('th', { style: styles.th }, '减免原因'), React.createElement('th', { style: Object.assign({}, styles.th, styles.actionColTh) }, '操作') ) ), React.createElement('tbody', null, paginatedList.map(function(row) { var approvalStatus = getApprovalStatus(row); var showPay = approvalStatus === 'draft' || approvalStatus === 'withdrawn' || approvalStatus === 'rejected'; var showWithdraw = approvalStatus === 'auditing' || approvalStatus === 'pending'; return React.createElement('tr', { key: row.id }, React.createElement('td', { style: styles.td }, getApprovalStatusText(approvalStatus)), React.createElement('td', { style: styles.td }, React.createElement('span', { style: { color: getStatusColor(row.paymentStatus) } }, getStatusText(row.paymentStatus)) ), React.createElement('td', { style: styles.td }, row.contractCode), React.createElement('td', { style: styles.td }, row.projectName), React.createElement('td', { style: styles.td }, row.customerName), React.createElement('td', { style: styles.td }, row.contractEffectiveDate), React.createElement('td', { style: styles.td }, formatAmount(row.firstPayableAmount)), React.createElement('td', { style: styles.td }, formatAmount(row.paidAmount)), React.createElement('td', { style: styles.td }, formatAmount(row.discountAmount)), React.createElement('td', { style: styles.td }, formatAmount(row.unpaidAmount)), React.createElement('td', { style: styles.td }, row.discountReason || '-'), React.createElement('td', { style: Object.assign({}, styles.td, styles.actionColTd) }, React.createElement('button', { type: 'button', style: Object.assign({}, styles.actionBtn, styles.viewBtn), onClick: function() { handleView(row.id); } }, '查看'), showPay && React.createElement('button', { type: 'button', style: Object.assign({}, styles.actionBtn, styles.payBtn), onClick: function() { handlePayment(row.id); } }, '收费'), showWithdraw && React.createElement('button', { type: 'button', style: Object.assign({}, styles.actionBtn, styles.withdrawBtn), onClick: function() { handleWithdraw(row.id); } }, '撤回') ) ); }) ) ), // 分页:支持选择单页数据条数 React.createElement('div', { style: styles.pagination }, React.createElement('div', { style: { display: 'flex', alignItems: 'center', gap: '8px' } }, React.createElement('span', { style: styles.pageInfo }, '共 ' + totalCount + ' 条'), React.createElement('select', { style: styles.pageSizeSelect, value: pageSize, onChange: function(e) { setPageSize(Number(e.target.value)); setCurrentPage(1); } }, React.createElement('option', { value: 10 }, '10 条/页'), React.createElement('option', { value: 20 }, '20 条/页'), React.createElement('option', { value: 50 }, '50 条/页') ) ), React.createElement('div', { style: { display: 'flex', gap: '8px', alignItems: 'center' } }, React.createElement('button', { type: 'button', style: Object.assign({}, styles.actionBtn, { padding: '6px 12px' }), disabled: currentPage <= 1, onClick: function() { setCurrentPage(currentPage - 1); } }, '上一页'), React.createElement('span', { style: styles.pageInfo }, currentPage + ' / ' + totalPages), React.createElement('button', { type: 'button', style: Object.assign({}, styles.actionBtn, { padding: '6px 12px' }), disabled: currentPage >= totalPages, onClick: function() { setCurrentPage(currentPage + 1); } }, '下一页') ) ), withdrawConfirmId && React.createElement('div', { style: styles.popover, onClick: function() { setWithdrawConfirmId(null); } }, React.createElement('div', { style: styles.popoverCard, onClick: function(e) { e.stopPropagation(); } }, React.createElement('div', { style: styles.popoverTitle }, '确认撤回?'), React.createElement('p', { style: { margin: '16px 0', fontSize: '14px', color: '#666' } }, '确认后将撤回该数据,审核状态变为撤回。'), React.createElement('div', { style: styles.modalFooter }, React.createElement('button', { type: 'button', style: styles.backBtn, onClick: function() { setWithdrawConfirmId(null); } }, '取消'), React.createElement('button', { type: 'button', style: Object.assign({}, styles.backBtn, { backgroundColor: '#fa8c16', color: '#fff', border: 'none' }), onClick: handleWithdrawConfirm }, '确认') ) ) ), requirementDetailVisible && React.createElement('div', { style: styles.popover, onClick: function() { setRequirementDetailVisible(false); } }, React.createElement('div', { style: Object.assign({}, styles.popoverCard, { maxWidth: '720px', width: '90%' }), onClick: function(e) { e.stopPropagation(); } }, React.createElement('div', { style: styles.popoverHeader }, React.createElement('span', { style: styles.popoverTitle }, '需求明细'), React.createElement('button', { style: styles.popoverClose, onClick: function() { setRequirementDetailVisible(false); } }, '关闭') ), React.createElement('div', { style: styles.requirementModalBody }, requirementDetailContent) ) ) ) ) ); }; if (typeof window !== 'undefined') { window.Component = Component; if (document.readyState === 'loading') { document.addEventListener('DOMContentLoaded', function() { var rootEl = document.getElementById('root'); if (rootEl && window.ReactDOM && window.React) { var root = ReactDOM.createRoot(rootEl); root.render(React.createElement(Component)); } }); } else { var rootEl = document.getElementById('root'); if (rootEl && window.ReactDOM && window.React) { var root = ReactDOM.createRoot(rootEl); root.render(React.createElement(Component)); } } }