import ButtonConfirm from '@/components/ButtomConfirm'; import { RESPONSE_CODE } from '@/constants/enum'; import { postServiceOrderAfterSalesCompletion, postServiceOrderNoNeedSend, postServiceOrderOrderCancel, postServiceOrderQueryServiceOrder, } from '@/services'; import { orderExport } from '@/services/order'; import { enumValueToLabel, formatDateTime } from '@/utils'; import { getUserInfo } from '@/utils/user'; import { ClockCircleTwoTone, ContainerTwoTone, CopyTwoTone, DownOutlined, EditTwoTone, EllipsisOutlined, QuestionCircleOutlined, } from '@ant-design/icons'; import { PageContainer, ProColumns, ProTable, } from '@ant-design/pro-components'; import { history } from '@umijs/max'; import { Avatar, Button, Checkbox, Divider, Dropdown, Flex, MenuProps, Space, Tag, Tooltip, message, } from 'antd'; import { cloneDeep } from 'lodash'; import { Key, useRef, useState } from 'react'; import OrderPrintModal from '../OrderPrint/OrderPrintModal'; import AfterSalesDrawer from './components/AfterSalesDrawer'; import ApplyForInvoicingModal from './components/ApplyForInvoicingModal'; import AttachmentModal from './components/AttachmentModal'; import CheckModal from './components/CheckModal'; import ConfirmReceiptModal from './components/ConfirmReceiptModal'; import DeliverInfoDrawer from './components/DeliverInfoDrawer'; import DeliverModal from './components/DeliverModal'; import FinancialDrawer from './components/FinancialDrawer'; import HistoryModal from './components/HistoryModal'; import ImportModal from './components/ImportModal'; import OrderDrawer from './components/OrderDrawer'; import OrderNotesEditModal from './components/OrderNotesEditModal'; import ProcureCheckModal from './components/ProcureCheckModal'; import SubOrderComfirmReceiptImagesModal from './components/SubOrderComfirmReceiptImagesModal'; import { AFTER_INVOICING_STATUS, AFTE_SALES_PLAN_OPTIONS, CHECK_TYPE, LOGISTICS_STATUS_OPTIONS, MAIN_ORDER_COLUMNS, ORDER_STATUS_OPTIONS, PAYMENT_CHANNEL_OPTIONS, PAYMENT_METHOD_OPTIONS, PRODUCT_BELONG_DEPARTMENT_OPTIONS, TAGS_COLOR, getInvoicingType, getNeedInvoicing, } from './constant'; import './index.less'; import { OrderListItemType, OrderType } from './type.d'; const OrderPage = () => { const [orderDrawerVisible, setOrderDrawerVisible] = useState<boolean>(false); const [checkVisible, setCheckVisible] = useState<boolean>(false); const [orderPrintVisible, setOrderPrintVisible] = useState<boolean>(false); const [ subOrderConfirmReceiptImagesVisible, setSubOrderConfirmReceiptImagesVisible, ] = useState<boolean>(false); const [notesEditVisible, setNotesEditVisible] = useState<boolean>(false); const [attachmentModalVisible, setAttachmentModalVisible] = useState<boolean>(false); const [financialVisible, setFinancialVisible] = useState<boolean>(false); const [afterSalesDrawerVisible, setAfterSalesDrawerVisible] = useState<boolean>(false); const [historyModalVisible, setHistoryModalVisible] = useState<boolean>(false); const [isRePrintOrder, setIsRePrintOrder] = useState<boolean>(false); const [isSendProduct, setIsSendProduct] = useState<boolean>(false); const [isMainOrder, setIsMainOrder] = useState<boolean>(false); const [importModalVisible, setImportModalVisible] = useState<boolean>(false); const [applyForInvoicingVisible, setApplyForInvoicingVisible] = useState<boolean>(false); const [procureCheckModalVisible, setProcureCheckModalVisible] = useState<boolean>(false); const [confirmReceiptVisible, setConfirmReceiptVisible] = useState<boolean>(false); const [deliverVisible, setDeliverVisible] = useState<boolean>(false); const [deliverInfoDrawerVisible, setDeliverInfoDrawerVisible] = useState<boolean>(false); const [orderOptType, setOrderOptType] = useState<string>(''); const [isFinalcialEdit, setIsFinalcialEdit] = useState<boolean>(false); const [expandedRowKeys, setExpandedRowKeys] = useState<Key[]>([]); const [orderRow, setOrderRow] = useState<Partial<OrderType>>({}); const [mainOrderAllItemKeys, setMainOrderAllItemKeys] = useState([]); const [rolePath, setRolePath] = useState([]); //当前角色权限(新增跟打印按钮) const userInfo = getUserInfo(); // const [tableHeight, setTableHeight] = useState(200); const [selectedRows, setSelectedRows] = useState({}); const [selectedRowObj, setSelectedRowObj] = useState({}); const [selectedItems, setSelectedItems] = useState([]); const [selectedRowKeys, setSelectedRowKeys] = useState([]); const [pageSize, setPageSize] = useState(10); const [currentPage, setCurrentPage] = useState(1); const [orderCheckType, setOrderCheckType] = useState(''); const [onlyShowCancelOrder, setOnlyShowCancelOrder] = useState(false); const mainTableRef = useRef(); let [searchParams, setSearchParam] = useState(Object); //表格的查询条件存储 const [messageApi, contextHolder] = message.useMessage(); // const openCheckNotes = (checkNotes: string) => { // Modal.info({ // title: '驳回备注', // content: ( // <div> // <p>{checkNotes}</p> // </div> // ), // onOk() { }, // }); // }; const exportLoading = () => { messageApi.open({ type: 'loading', content: '正在导出文件...', duration: 0, }); }; const exportLoadingDestory = () => { messageApi.destroy(); }; const refreshTable = () => { mainTableRef.current?.reload(); //刷新表格数据的时候,取消选中行 setSelectedRowObj([]); setSelectedRows([]); setSelectedRowKeys([]); }; function changeCancelOrderShow(e: any) { setOnlyShowCancelOrder(e.target.checked); refreshTable(); } // const resize = () => { // // 计算元素底部到视口顶部的距离 // let bottomDistance = document // .getElementById('mainTable') // ?.getElementsByClassName('ant-table-thead')[0] // .getBoundingClientRect().bottom; // // 获取屏幕高度 // let screenHeight = // window.innerHeight || document.documentElement.clientHeight; // // 计算元素底部到屏幕底部的距离 // let bottomToScreenBottomDistance = screenHeight - bottomDistance; // // //底部分页元素的高度 // // var pH = screenHeight - document.getElementById("main-table").getElementsByClassName('ant-table-body')[0].getBoundingClientRect().bottom; // setTableHeight(bottomToScreenBottomDistance - 88); // }; // useEffect(() => { // resize(); // // 添加事件监听器,当窗口大小改变时调用resize方法 // window.addEventListener('resize', resize); // }); const MyToolTip = ({ title, content }) => { return ( <Tooltip color="#FFFFFF" placement="bottom" title={<div className="px-5 py-4 text-black">{title}</div>} > {content} </Tooltip> ); }; /** * 检查是否可以打印 * @param paths 按钮集合 * @returns */ function checkePrintable(paths: any) { if ( !paths?.includes('printOrder') && !paths?.includes('supplierPrint') && !paths?.includes('procurePrint') && !paths?.includes('rePrintOrder') ) { return false; } return true; } const onCheckboxChange = (record: never) => { let newSelectedItems = []; if (selectedItems.includes(record.id)) { newSelectedItems = selectedItems.filter((key) => key !== record.id); setSelectedRowKeys([]); setSelectedRowObj({ ...setSelectedRowObj, [record.id]: [], }); selectedRowObj[record.id] = []; setSelectedRows([]); } else { newSelectedItems = [...selectedItems, record.id]; //子订单全部自动选中 let subIds = record.subOrderInformationLists?.map((item) => { return item.id; }); setSelectedRowKeys(subIds); setSelectedRowObj({ ...setSelectedRowObj, [record.id]: record.subOrderInformationLists, }); selectedRowObj[record.id] = record.subOrderInformationLists; setSelectedRows(record.subOrderInformationLists); } setSelectedItems(newSelectedItems); }; const handleTableExpand = (mainOrderIds: any) => { setExpandedRowKeys(mainOrderIds); }; //表头渲染 const OrderTableHeader = () => { return ( <Flex className="w-full"> <Flex className="w-[29%] ml-[4%]"> <span className="font-medium">商品信息</span> </Flex> <Flex className="w-[16%]"> <span className="font-medium">交易金额</span> </Flex> <Flex className="w-[10%]"> <span className="font-medium">支付</span> </Flex> <Flex className="w-[14%]"> <span className="font-medium">其他</span> </Flex> <Flex className="w-[10%]"> <span className="font-medium">交易状态</span> </Flex> <Flex className="w-[17%]"> <span className="font-medium">操作</span> </Flex> </Flex> ); }; //子订单内容渲染 const SubOderRander = ({ record, optRecord }) => { /** * 获取订单状态标签 * @param optRecord */ function getOrderStatusTag(optRecord: any): import('react').ReactNode { const orderStatus = optRecord.orderStatus; if (orderStatus === 'AUDIT_FAILED') { return ( <MyToolTip title={optRecord.checkNotes} content={ <> <Tag color={TAGS_COLOR.get(optRecord.orderStatus)} style={{ marginRight: '4px' }} > {enumValueToLabel( optRecord.orderStatus, ORDER_STATUS_OPTIONS, )} </Tag> <QuestionCircleOutlined style={{ color: '#C1C1C1' }} /> </> } /> ); } if ( orderStatus === 'AFTER_SALES_COMPLETION' || orderStatus === 'IN_AFTER_SALES' ) { return ( <MyToolTip title={ enumValueToLabel( optRecord.afterSalesPlan, AFTE_SALES_PLAN_OPTIONS, ) + ' ' + optRecord.afterSalesNotes } content={ <> <Tag color={TAGS_COLOR.get(optRecord.orderStatus)} style={{ marginRight: '4px' }} > {enumValueToLabel( optRecord.orderStatus, ORDER_STATUS_OPTIONS, )} </Tag> <QuestionCircleOutlined style={{ color: '#C1C1C1' }} /> </> } /> ); } if (orderStatus === 'PROCURE_CONVERT_WAREHOUSE_KEEPER') { return ( <MyToolTip title={optRecord.checkNotes} content={ <> <Tag color={TAGS_COLOR.get(optRecord.orderStatus)} style={{ marginRight: '4px' }} > {enumValueToLabel( optRecord.orderStatus, ORDER_STATUS_OPTIONS, )} </Tag> <QuestionCircleOutlined style={{ color: '#C1C1C1' }} /> </> } /> ); } return ( <Tag color={TAGS_COLOR.get(optRecord.orderStatus)}> {enumValueToLabel(optRecord.orderStatus, ORDER_STATUS_OPTIONS)} </Tag> ); } return ( <Flex className="w-full border-b-indigo-500"> <Flex vertical className="w-[31%]" gap="small"> {/* 商品名称 */} <div className="overflow-hidden whitespace-no-wrap overflow-ellipsis" title={optRecord.productName} > <span className="font-medium text-black "> {optRecord.productName} </span> </div> <div className="overflow-hidden whitespace-no-wrap overflow-ellipsis" title={optRecord.parameters} > <span className="text-[#8C8C8C]">参数:{optRecord.parameters}</span> </div> <Flex title={optRecord.notes}> <div className="max-w-[90%] whitespace-no-wrap overflow-hidden overflow-ellipsis"> <span className="text-[#8C8C8C]"> 备注: {optRecord.notes === undefined ? '暂无备注' : optRecord.notes} </span> </div> {/* 编辑备注按钮 */} <EditTwoTone onClick={() => { setNotesEditVisible(true); setOrderRow(optRecord); setIsMainOrder(false); }} /> </Flex> {optRecord.applyInvoicingNotes !== undefined && optRecord.applyInvoicingNotes !== null ? ( <Flex title={optRecord.notes}> <div className="max-w-[90%] whitespace-no-wrap overflow-hidden overflow-ellipsis"> <span className="text-[#8C8C8C]"> 开票备注: {optRecord.applyInvoicingNotes} </span> </div> </Flex> ) : ( '' )} </Flex> <Flex className="w-[16%]" vertical gap="small"> <div className="overflow-hidden whitespace-no-wrap overflow-ellipsis" title={optRecord.productPrice} > <span className="text-[#8C8C8C]">单价:</span> <span className="text-slate-700">¥{optRecord.productPrice}</span> </div> <div className="overflow-hidden whitespace-no-wrap overflow-ellipsis" title={optRecord.quantity} > <span className="text-[#8C8C8C]">数量:</span> <span className="text-slate-700">x{optRecord.quantity}</span> </div> <div className="overflow-hidden whitespace-no-wrap overflow-ellipsis" title={optRecord.subOrderPayment} > <span className="text-[#8C8C8C]">合计:</span> <span className="text-slate-700"> ¥{optRecord.subOrderPayment} </span> </div> </Flex> <Flex className="w-[10%]" vertical gap="small"> {/* 支付方式 */} <div className="overflow-hidden whitespace-no-wrap overflow-ellipsis"> <span className="text-slate-700"> {enumValueToLabel( optRecord.paymentMethod, PAYMENT_METHOD_OPTIONS, )} </span> </div> {/* 支付渠道 */} <div className="overflow-hidden whitespace-no-wrap overflow-ellipsis"> <span className="text-slate-700"> {enumValueToLabel( optRecord.paymentChannel, PAYMENT_CHANNEL_OPTIONS, )} </span> </div> </Flex> <Flex className="w-[15%]" vertical gap="small"> {/* 所属部门 */} <div className="overflow-hidden whitespace-no-wrap overflow-ellipsis" title={enumValueToLabel( optRecord.productBelongBusiness, PRODUCT_BELONG_DEPARTMENT_OPTIONS, )} > <span className="text-slate-700"> {enumValueToLabel( optRecord.productBelongBusiness, PRODUCT_BELONG_DEPARTMENT_OPTIONS, )} </span> </div> {/* 开票类型 */} {getInvoicingType(optRecord) === undefined ? ( <div className="overflow-hidden whitespace-no-wrap overflow-ellipsis"> <span className="text-slate-700"> {getInvoicingType(optRecord)} </span> </div> ) : ( '' )} {/* 开票状态 */} <div className="overflow-hidden whitespace-no-wrap overflow-ellipsis"> <span className="text-slate-700"> {enumValueToLabel( optRecord.afterInvoicingStatus, AFTER_INVOICING_STATUS, )} </span> </div> </Flex> <Flex className="w-[10%]" vertical gap="small"> {/* 开票状态 */} <div className="overflow-hidden whitespace-no-wrap overflow-ellipsis"> <Tag color={ optRecord.invoicingTime === null || optRecord.invoicingTime === undefined ? TAGS_COLOR.get(optRecord.invoicingStatus) : 'success' } > {getNeedInvoicing(optRecord)} </Tag> </div> {/* 订单状态 */} <div className="overflow-hidden whitespace-no-wrap overflow-ellipsis"> {getOrderStatusTag(optRecord)} </div> {/* 物流信息 */} <div className="overflow-hidden whitespace-no-wrap overflow-ellipsis"> {optRecord.orderStatus === 'CONFIRM_RECEIPT' || optRecord.orderStatus === 'AFTER_SALES_COMPLETION' || optRecord.orderStatus === 'IN_AFTER_SALES' || optRecord.orderStatus === 'SHIPPED' ? ( <MyToolTip title={ optRecord.serialNumber === undefined ? '暂无物流信息' : enumValueToLabel( optRecord.logisticsMethod, LOGISTICS_STATUS_OPTIONS, ) + ' ' + optRecord.serialNumber } content={ <Button type="link" size="small" style={{ padding: 0 }}> 物流信息 </Button> } /> ) : ( '' )} </div> </Flex> <Flex className="w-[18%]" wrap="wrap" gap="small"> {optRecord.subPath?.includes('sendProduct') ? ( <Button className="p-0" type="link" onClick={() => { optRecord.mainOrderId = record.id; setSelectedRows([cloneDeep(optRecord)]); //克隆一份数据,避免后续修改污染 setDeliverVisible(true); setIsSendProduct(true); setOrderCheckType(CHECK_TYPE.NORMAL); }} > 仓库发货 </Button> ) : ( '' )} {optRecord.subPath?.includes('supplierSendOrder') ? ( <Button className="p-0" type="link" onClick={() => { optRecord.mainOrderId = record.id; setSelectedRows([cloneDeep(optRecord)]); //克隆一份数据,避免后续修改污染 setDeliverVisible(true); setIsSendProduct(true); setOrderCheckType(CHECK_TYPE.SUPPLIER); }} > 供应商发货 </Button> ) : ( '' )} {optRecord.subPath?.includes('procureSend') ? ( <Button className="p-0" type="link" onClick={() => { optRecord.mainOrderId = record.id; setSelectedRows([cloneDeep(optRecord)]); //克隆一份数据,避免后续修改污染 setDeliverVisible(true); setIsSendProduct(true); setOrderCheckType(CHECK_TYPE.PROCURE); }} > 采购发货 </Button> ) : ( '' )} {optRecord.subPath?.includes('queryAnnex') && optRecord.listAnnex?.length > 0 ? ( <Button className="p-0" type="link" onClick={() => { optRecord.mainOrderId = record.id; setAttachmentModalVisible(true); setOrderRow(optRecord); }} > 附件 </Button> ) : ( '' )} {optRecord.subPath?.includes('modifySendInformation') ? ( <Button className="p-0" type="link" onClick={() => { optRecord.mainOrderId = record.id; setSelectedRows([cloneDeep(optRecord)]); //克隆一份数据,避免后续修改污染 setDeliverVisible(true); setIsSendProduct(false); }} > 修改发货信息 </Button> ) : ( '' )} {optRecord.subPath?.includes('printOrder') ? ( <Button className="p-0" type="link" onClick={async () => { setOrderPrintVisible(true); setSelectedRows([optRecord]); setOrderRow(record); setOrderCheckType(CHECK_TYPE.NORMAL); }} > 仓库打印 </Button> ) : ( '' )} {optRecord.subPath?.includes('supplierPrint') ? ( <Button className="p-0" type="link" onClick={async () => { setOrderPrintVisible(true); setSelectedRows([optRecord]); setOrderRow(record); setOrderCheckType(CHECK_TYPE.SUPPLIER); }} > 供应商打印 </Button> ) : ( '' )} {optRecord.subPath?.includes('procurePrint') ? ( <Button className="p-0" type="link" onClick={async () => { setOrderPrintVisible(true); setSelectedRows([optRecord]); setOrderRow(record); setOrderCheckType(CHECK_TYPE.PROCURE); }} > 采购打印 </Button> ) : ( '' )} {optRecord.subPath?.includes('editOrder') ? ( <Button className="p-0" type="link" onClick={() => { setFinancialVisible(true); setOrderRow(record); setSelectedRows([optRecord]); setIsFinalcialEdit(true); }} > 编辑 </Button> ) : ( '' )} {optRecord.subPath?.includes('invoicing') ? ( <Button className="p-0" type="link" onClick={() => { setFinancialVisible(true); setIsFinalcialEdit(false); setOrderRow(record); setSelectedRows([optRecord]); setIsMainOrder(false); }} > 开票 </Button> ) : ( '' )} {optRecord.subPath?.includes('applyInvoicing') ? ( <Button className="p-0" type="link" onClick={() => { setApplyForInvoicingVisible(true); setSelectedRows([optRecord]); }} > 申请开票 </Button> ) : ( '' )} {optRecord.subPath?.includes('checkOrder') ? ( <Button className="p-0" type="link" onClick={() => { setOrderRow(optRecord); setCheckVisible(true); setSelectedRows([optRecord]); setOrderCheckType(CHECK_TYPE.NORMAL); }} > 审核 </Button> ) : ( '' )} {optRecord.subPath?.includes('financeCheckOrder') ? ( <Button className="p-0" type="link" onClick={() => { setOrderRow(optRecord); setCheckVisible(true); setSelectedRows([optRecord]); setOrderCheckType(CHECK_TYPE.FINALCIAL); }} > 财务审核 </Button> ) : ( '' )} {optRecord.subPath?.includes('procureCheckOrder') ? ( <Button className="p-0" type="link" onClick={() => { setOrderRow(optRecord); setSelectedRows([optRecord]); setOrderCheckType(CHECK_TYPE.PROCURE); setProcureCheckModalVisible(true); }} > 采购审核 </Button> ) : ( '' )} {optRecord.subPath?.includes('rePrintOrder') ? ( <Button className="p-0" type="link" onClick={() => { setOrderPrintVisible(true); setSelectedRows([optRecord]); setOrderRow(record); setIsRePrintOrder(true); }} > 重新打印 </Button> ) : ( '' )} {optRecord.subPath?.includes('confirmReceipt') ? ( <Button className="p-0" type="link" onClick={() => { setConfirmReceiptVisible(true); setOrderRow(optRecord); }} > 确认收货 </Button> ) : ( '' )} {optRecord.subPath?.includes('applyAfterSales') ? ( <Button className="p-0" type="link" onClick={() => { setAfterSalesDrawerVisible(true); setSelectedRows([optRecord]); setOrderRow(record); }} > 申请售后 </Button> ) : ( '' )} {optRecord.subPath?.includes('afterSalesCompletion') ? ( <ButtonConfirm className="p-0" title="是否完成售后?" text="完成售后" onConfirm={async () => { let res = await postServiceOrderAfterSalesCompletion({ data: { ids: [optRecord.id] }, }); if (res.result === RESPONSE_CODE.SUCCESS) { message.success(res.message); refreshTable(); return true; } }} /> ) : ( '' )} {optRecord.subPath?.includes('noNeedSend') ? ( <ButtonConfirm className="p-0" title="此订单是否无需发货?" text="无需发货" onConfirm={async () => { let res = await postServiceOrderNoNeedSend({ data: { ids: [optRecord.id] }, }); if (res.result === RESPONSE_CODE.SUCCESS) { message.success(res.message); refreshTable(); return true; } }} /> ) : ( '' )} {optRecord.subPath?.includes('viewImages') ? ( <Button className="p-0" type="link" onClick={() => { setSubOrderConfirmReceiptImagesVisible(true); setOrderRow(optRecord); }} > 查看收货凭证 </Button> ) : ( '' )} {optRecord.subPath?.includes('orderCancel') ? ( <ButtonConfirm className="p-0" title="确认作废?" text="作废" onConfirm={async () => { let body = { ids: [optRecord.id], checkIsMainOrderId: false }; const data = await postServiceOrderOrderCancel({ data: body, }); if (data.result === RESPONSE_CODE.SUCCESS) { message.success(data.message); refreshTable(); } }} /> ) : ( '' )} </Flex> </Flex> ); }; const expandedRowRender = (record) => { let subOrders = record.subOrderInformationLists; return ( <ProTable id="sub-table" className="w-full " showHeader={false} columns={[ { title: 'ID', dataIndex: 'id', key: 'id', render: (text: any, optRecord: any) => { return <SubOderRander record={record} optRecord={optRecord} />; }, }, ]} rowSelection={{ onChange: (selectedRowKeys: any, selectedRows: any) => { setSelectedRowKeys(selectedRowKeys); setSelectedRowObj({ ...setSelectedRowObj, [record.id]: selectedRows, }); selectedRowObj[record.id] = selectedRows; setSelectedRows(selectedRows); }, selectedRowKeys: selectedRowKeys, // 自定义选择项参考: https://ant.design/components/table-cn/#components-table-demo-row-selection-custom // 注释该行则默认不显示下拉选项 // selections: [Table.SELECTION_ALL, Table.SELECTION_INVERT], // defaultSelectedRowKeys: [], }} rowKey="id" headerTitle={false} search={false} options={false} dataSource={subOrders} pagination={false} tableAlertRender={false} /> ); }; // 主订单内容渲染 const MainOrderColumnRender = ({ record }: { record: OrderListItemType }) => { return ( <Flex vertical={true}> {/* 编号、时间、销售信息 */} <Flex className="px-4 py-4 bg-white rounded-t-lg" justify="space-between" > <Flex wrap="wrap" gap="middle" vertical> <Flex> <Flex> <Checkbox onChange={() => onCheckboxChange(record)} checked={selectedItems.includes(record.id)} > <Space split={<Divider type="vertical" />}> <div> <span className="text-[#8C8C8C]">订单号:</span> <span className="text-slate-700">{record.id}</span> </div> <span>{formatDateTime(record.createTime)}</span> </Space> </Checkbox> <Space split={<Divider type="vertical" />}> <div> <span className="text-[#8C8C8C]">代表:</span> <span className="text-slate-700">{record.salesCode}</span> </div> <div title={record.institution} className="whitespace-no-wrap overflow-hidden overflow-ellipsis max-w-[150px]" > <span className="text-[#8C8C8C]">单位:</span> <span className="text-slate-700">{record.institution}</span> </div> <span> <span className="text-[#8C8C8C]">联系人:</span> <span className="text-slate-700"> {record.institutionContactName + ' '} </span> </span> <span> <span className="text-[#8C8C8C]">收货人:</span> <span className="text-slate-700"> {record.customerName + ' '} <Tooltip className="order-tooltip" title="详情"> <ContainerTwoTone className="hover:curcor-pointer" onClick={() => { setDeliverInfoDrawerVisible(true); setOrderRow(record); }} /> </Tooltip> </span> </span> </Space> </Flex> </Flex> <Flex className="pl-6" align="center"> <div title={record.notes}> <div className="max-w-md overflow-hidden whitespace-no-wrap overflow-ellipsis"> <span className="text-[#8C8C8C]">备注:</span> <span className="ml-2"> {record.notes === undefined ? '暂无备注' : record.notes} </span> </div> </div> <Tooltip title="编辑"> <EditTwoTone className="hover:curcor-pointer" onClick={() => { setNotesEditVisible(true); setOrderRow(record); setIsMainOrder(true); }} /> </Tooltip> </Flex> </Flex> <Flex wrap="wrap" gap="middle" vertical> <Flex justify="flex-end"> <Flex wrap="wrap" gap="middle" align="center"> <div> <span className="text-[#8C8C8C]">总金额:¥</span> <span className="text-lg font-medium"> {record.totalPayment} </span> </div> {rolePath?.includes('addOrder') ? ( <Tooltip title="复制"> <CopyTwoTone className="hover:cursor-pointer" onClick={() => { setOrderOptType('copy'); setOrderDrawerVisible(true); let copy = cloneDeep(record); copy.id = undefined; copy.subOrderInformationLists?.forEach((item) => { item.id = undefined; }); setOrderRow(copy); }} /> </Tooltip> ) : ( '' )} <Tooltip title="历史"> <ClockCircleTwoTone className="hover:cursor-pointer" onClick={() => { setHistoryModalVisible(true); if (selectedRowObj[record.id]?.length) { setSelectedRows(selectedRowObj[record.id]); } else { setSelectedRows(record.subOrderInformationLists); } }} /> </Tooltip> </Flex> </Flex> <Flex justify="flex-end"> <Space.Compact direction="vertical" align="end"> <Space> {record.mainPath?.includes('sendProduct') ? ( <Button className="p-0" type="link" onClick={() => { if (!selectedRowObj[record.id]?.length) { return message.error('请选择选择子订单'); } setSelectedRows(selectedRowObj[record.id]); setDeliverVisible(true); setIsSendProduct(true); setOrderCheckType(CHECK_TYPE.NORMAL); }} > 仓库发货 </Button> ) : ( '' )} {/* 供应商发货 */} {record.mainPath?.includes('supplierSendOrder') ? ( <Button className="p-0" type="link" onClick={() => { if (!selectedRowObj[record.id]?.length) { return message.error('请选择选择子订单'); } setSelectedRows(selectedRowObj[record.id]); setDeliverVisible(true); setIsSendProduct(true); setOrderCheckType(CHECK_TYPE.SUPPLIER); }} > 供应商发货 </Button> ) : ( '' )} {record.mainPath?.includes('procureSend') ? ( <Button className="p-0" type="link" onClick={() => { if (!selectedRowObj[record.id]?.length) { return message.error('请选择选择子订单'); } setSelectedRows(selectedRowObj[record.id]); setDeliverVisible(true); setIsSendProduct(true); setOrderCheckType(CHECK_TYPE.PROCURE); }} > 采购发货 </Button> ) : ( '' )} {record.mainPath?.includes('printOrder') ? ( <Button className="p-0" type="link" onClick={() => { const selectedSubOrders = selectedRowObj[record.id]; if (!selectedSubOrders?.length) { return message.error('请选择选择子订单'); } for (let subOrderRecord of selectedSubOrders) { let subPath = subOrderRecord.subPath; if (!checkePrintable(subPath)) { return message.error('请选择可以打印的子订单'); } } setSelectedRows(selectedSubOrders); setOrderRow(record); setOrderPrintVisible(true); setOrderCheckType(CHECK_TYPE.NORMAL); }} > 仓库打印 </Button> ) : ( '' )} {record.mainPath?.includes('supplierPrint') ? ( <Button className="p-0" type="link" onClick={() => { if (!selectedRowObj[record.id]?.length) { return message.error('请选择选择子订单'); } setSelectedRows(selectedRowObj[record.id]); setOrderRow(record); setOrderPrintVisible(true); setOrderCheckType(CHECK_TYPE.SUPPLIER); }} > 供应商打印 </Button> ) : ( '' )} {record.mainPath?.includes('rePrintOrder') ? ( <Button className="p-0" type="link" onClick={() => { if (!selectedRowObj[record.id]?.length) { return message.error('请选择选择子订单'); } setSelectedRows(selectedRowObj[record.id]); setOrderRow(record); setOrderPrintVisible(true); setIsRePrintOrder(true); }} > 重新打印 </Button> ) : ( '' )} {record.mainPath?.includes('modifySendInformation') ? ( <Button className="p-0" type="link" onClick={() => { if (!selectedRowObj[record.id]?.length) { return message.error( '请选择已经发货或者已经确认收货的子订单', ); } for (let row of selectedRowObj[record.id]) { if ( row.orderStatus !== 'CONFIRM_RECEIPT' && row.orderStatus !== 'SHIPPED' ) { return message.error( '请选择已经发货或者已经确认收货的子订单', ); } } setSelectedRows(selectedRowObj[record.id]); setDeliverVisible(true); setIsSendProduct(false); }} > 修改发货信息 </Button> ) : ( '' )} {record.mainPath?.includes('invoicing') ? ( <Button type="link" className="p-0" onClick={() => { let selectedSubOrders = selectedRowObj[record.id]; setSelectedRows(selectedSubOrders); if (selectedSubOrders === undefined) { setIsMainOrder(true); setSelectedRows(record.subOrderInformationLists); } else { setIsMainOrder(false); } setOrderRow(record); setFinancialVisible(true); setIsFinalcialEdit(false); }} > 开票 </Button> ) : ( '' )} {record.mainPath?.includes('applyInvoicing') ? ( <Button type="link" className="p-0" onClick={() => { let selectedSubOrders = selectedRowObj[record.id]; if (selectedSubOrders === undefined) { selectedSubOrders = record.subOrderInformationLists; } setSelectedRows(selectedSubOrders); for (let i = 0; i < selectedSubOrders.length; i++) { if ( selectedSubOrders[i].invoicingStatus === 'UN_INVOICE' || selectedSubOrders[i].afterInvoicingStatus === 'APPLY_FOR_INVOICING' ) { message.error( '请选择需要开票且未申请开票的子订单进行申请', ); return; } } setApplyForInvoicingVisible(true); }} > 申请开票 </Button> ) : ( '' )} {record.mainPath?.includes('updateOrder') ? ( <Button className="p-0" type="link" onClick={() => { //勾选的子订单:如果有勾选,后面只校验有勾选的 let selectedSubOrders = selectedRowObj[record.id]; if ( selectedSubOrders === undefined || selectedSubOrders.length === 0 ) { selectedSubOrders = record.subOrderInformationLists; } for ( let index = 0; index < selectedSubOrders.length; index++ ) { let orderStatus = selectedSubOrders[index].orderStatus; //是审核通过及之后的订单 if ( orderStatus !== 'UNAUDITED' && orderStatus !== 'AUDIT_FAILED' ) { message.error( '请选择未审核或者审核失败的订单进行编辑', ); return; } } setOrderDrawerVisible(true); setOrderRow(record); setSelectedRows(selectedSubOrders); setOrderOptType('edit'); }} > 编辑 </Button> ) : ( '' )} {record.mainPath?.includes('checkOrder') ? ( <Button className="p-0" type="link" onClick={() => { let selectedSubOrders = selectedRowObj[record.id]; setSelectedRows(selectedSubOrders); if (selectedSubOrders === undefined) { setSelectedRows(record.subOrderInformationLists); } console.log(selectedRows); for (let i = 0; i < selectedRows.length; i++) { if ( selectedRows[i].orderStatus !== 'UNAUDITED' && selectedRows[i].orderStatus !== 'FINANCE_PROCESS' ) { message.error('请选择未审核的子订单进行审核'); return; } } setOrderRow(record); setCheckVisible(true); setOrderCheckType(CHECK_TYPE.NORMAL); }} > 审核 </Button> ) : ( '' )} {record.mainPath?.includes('noNeedSend') ? ( <ButtonConfirm className="p-0" title="此订单是否无需发货?" text="无需发货" onConfirm={async () => { let selectedSubOrders = selectedRowObj[record.id]; if (selectedSubOrders === undefined) { selectedSubOrders = record.subOrderInformationLists; } setSelectedRows(selectedSubOrders); for (let i = 0; i < selectedSubOrders.length; i++) { if ( selectedSubOrders[i].orderStatus !== 'AUDITED' && selectedSubOrders[i].orderStatus !== 'PROCURE_PROCESS' && selectedSubOrders[i].orderStatus !== 'PROCURE_PROCESS_FOR_MINE' && selectedSubOrders[i].orderStatus !== 'PROCURE_WAIT_SHIP' && selectedSubOrders[i].orderStatus !== 'SUPPLIER_WAIT_SHIP' && selectedSubOrders[i].orderStatus !== 'WAIT_SHIP' ) { message.error( '请选择未发货的子订单进行无需发货操作', ); return; } } const data = await postServiceOrderNoNeedSend({ data: { ids: selectedSubOrders.map((item) => { return item.id; }), }, }); if (data.result === RESPONSE_CODE.SUCCESS) { message.success(data.message); refreshTable(); } }} /> ) : ( '' )} {/* 财务审核:主订单暂无 */} {record.mainPath?.includes('financeCheckOrder') ? ( <Button className="p-0" type="link" onClick={() => { let selectedSubOrders = selectedRowObj[record.id]; setSelectedRows(selectedSubOrders); if (selectedSubOrders === undefined) { setSelectedRows(record.subOrderInformationLists); console.log( 'subOrderInformationLists:' + record.subOrderInformationLists, ); } for (let i = 0; i < selectedRows.length; i++) { if ( selectedRows[i].orderStatus !== 'UNAUDITED' && selectedRows[i].orderStatus !== 'FINANCE_PROCESS' ) { message.error('请选择未审核的子订单进行审核'); return; } } setOrderRow(record); setCheckVisible(true); setOrderCheckType(CHECK_TYPE.FINALCIAL); }} > 财务审核 </Button> ) : ( '' )} {/* 采购审核 */} {record.mainPath?.includes('procureCheckOrder') ? ( <Button className="p-0" type="link" onClick={() => { let selectedSubOrders = selectedRowObj[record.id]; setSelectedRows(selectedSubOrders); if (selectedSubOrders === undefined) { setSelectedRows(record.subOrderInformationLists); console.log( 'subOrderInformationLists:' + record.subOrderInformationLists, ); } for (let i = 0; i < selectedRows.length; i++) { if ( selectedRows[i].orderStatus !== 'PROCURE_UN_PROCESS' ) { message.error('请选择未审核的子订单进行审核'); return; } } setOrderRow(record); setProcureCheckModalVisible(true); setOrderCheckType(CHECK_TYPE.PROCURE); }} > 采购审核 </Button> ) : ( '' )} {record.mainPath?.includes('applyAfterSales') ? ( <Button className="p-0" type="link" onClick={() => { let selectedSubOrders = selectedRowObj[record.id]; if (selectedSubOrders === undefined) { selectedSubOrders = record.subOrderInformationLists; } setSelectedRows(selectedSubOrders); for (let i = 0; i < selectedSubOrders.length; i++) { if ( selectedSubOrders[i].orderStatus !== 'CONFIRM_RECEIPT' ) { message.error('请选择确认收货状态的子订单进行售后'); return; } } setAfterSalesDrawerVisible(true); setOrderRow(record); }} > 申请售后 </Button> ) : ( '' )} {record.mainPath?.includes('afterSalesCompletion') ? ( <ButtonConfirm className="p-0" title="售后是否已完成?" text="完成售后" onConfirm={async () => { let selectedSubOrders = selectedRowObj[record.id]; if (selectedSubOrders === undefined) { selectedSubOrders = record.subOrderInformationLists; } for (let i = 0; i < selectedSubOrders.length; i++) { if ( selectedSubOrders[i].orderStatus !== 'IN_AFTER_SALES' ) { message.error( '请选择售后中状态的子订单进行完成售后', ); return false; } } const ids = selectedSubOrders?.map((item) => { return item.id; }); let body = { ids: ids, }; const data = await postServiceOrderAfterSalesCompletion( { data: body, }, ); if (data.result === RESPONSE_CODE.SUCCESS) { message.success(data.message); refreshTable(); } }} /> ) : ( '' )} {record.mainPath?.includes('orderCancel') ? ( <ButtonConfirm className="p-0" title="确认作废?" text="作废" onConfirm={async () => { let body = { ids: [record.id], checkIsMainOrderId: true, }; const data = await postServiceOrderOrderCancel({ data: body, }); if (data.result === RESPONSE_CODE.SUCCESS) { message.success(data.message); refreshTable(); } }} /> ) : ( '' )} {record.mainPath?.includes('procurePrint') ? ( <Button className="p-0" type="link" onClick={() => { if (!selectedRowObj[record.id]?.length) { return message.error('请选择选择子订单'); } setSelectedRows(selectedRowObj[record.id]); setOrderRow(record); setOrderPrintVisible(true); setOrderCheckType(CHECK_TYPE.PROCURE); }} > 采购打印 </Button> ) : ( '' )} </Space> </Space.Compact> </Flex> </Flex> </Flex> <Flex className="p-0 pb-[24px] pt-[4px] pl-[23px] pr-[5px] bg-white rounded-b-lg"> {expandedRowRender(record)} </Flex> </Flex> ); }; // 主订单列表 const mainOrdersColumns: ProColumns<OrderType>[] = MAIN_ORDER_COLUMNS.map( (item) => { if (item.dataIndex === 'name') { return { ...item, title: <OrderTableHeader />, render: (text, record) => { return <MainOrderColumnRender record={record} />; }, }; } return item; }, ); function toolBarRender() { let toolBtns = []; toolBtns.push( <Checkbox onChange={changeCancelOrderShow}>只看作废</Checkbox>, ); //导出按钮配置 const items: MenuProps['items'] = [ { label: '导出查询结果订单', key: '2', onClick: async () => { let body = { flag: 50, ...searchParams }; exportLoading(); orderExport('/api/service/order/export', body, exportLoadingDestory); }, }, { label: '导出已选中订单', key: '1', onClick: async () => { if (selectedItems.length === 0) { message.error('请选择订单'); return; } let body = { flag: 30, ids: selectedItems }; exportLoading(); orderExport('/api/service/order/export', body, exportLoadingDestory); }, }, // { // label: '导出当前页订单', // key: '2', // onClick: async () => { // if (mainOrderAllItemKeys.length === 0) { // message.error('当前没有订单'); // return; // } // let body = { flag: 20, ids: mainOrderAllItemKeys }; // exportLoading(); // orderExport('/api/service/order/export', body, exportLoadingDestory); // }, // }, { label: '导出当天订单', key: '4', onClick: async () => { let body = { flag: 40, ids: [] }; exportLoading(); orderExport('/api/service/order/export', body, exportLoadingDestory); }, }, { label: '导出所有订单', key: '3', onClick: async () => { let body = { flag: 10, ids: [] }; exportLoading(); orderExport('/api/service/order/export', body, exportLoadingDestory); }, }, ]; const menuProps = { items, onClick: () => {}, }; if (rolePath?.includes('addOrder')) { toolBtns.push( <Button type="primary" key="out" onClick={() => { setOrderDrawerVisible(true); setOrderOptType('add'); }} > 新增 </Button>, ); } if (rolePath?.includes('importExcel')) { toolBtns.push( <Button type="primary" key="out" onClick={() => { setImportModalVisible(true); }} > 导入 </Button>, ); } if (rolePath?.includes('export')) { toolBtns.push( <Dropdown menu={menuProps}> <Button> <Space> 导出 <DownOutlined /> </Space> </Button> </Dropdown>, ); } // toolBtns.push( // <Button // key="show" // onClick={() => { // handleAllExpand(); // }} // > // {mainOrderAllItemKeys?.length !== expandedRowKeys.length // ? '一键展开' // : '一键收起'} // </Button>, // ); return toolBtns; } return ( <PageContainer className="order-page-container" header={{ title: '订单管理', extra: [ <Avatar key="0" style={{ verticalAlign: 'middle' }} size="large"> {userInfo?.username} </Avatar>, <Tag key="nickName">{userInfo?.nickName}</Tag>, <Dropdown key="dropdown" trigger={['click']} menu={{ items: [ { label: '退出登录', key: '1', onClick: () => { localStorage.removeItem('token'); history.push('/login'); }, }, // { // label: '修改密码', // key: '2', // }, ], }} > <Button key="4" style={{ padding: '0 8px' }}> <EllipsisOutlined /> </Button> </Dropdown>, ], }} > <div id="resizeDiv"></div> <ProTable id="main-table" // tableStyle={{backgroundColor:'red'}} actionRef={mainTableRef} expandIconColumnIndex={-1} columns={mainOrdersColumns} rowKey="id" pagination={{ showQuickJumper: true, pageSize: pageSize, current: currentPage, showSizeChanger: true, onChange: (page, size) => { setPageSize(size); setCurrentPage(page); }, }} // showHeader={false} expandedRowKeys={expandedRowKeys} // expandable={{ expandedRowRender }} dateFormatter="string" options={false} headerTitle="" search={{ labelWidth: 'auto', // onCollapse: resize, }} request={async ( // 第一个参数 params 查询表单和 params 参数的结合 // 第一个参数中一定会有 pageSize 和 current ,这两个参数是 antd 的规范 params, sorter, filter, ) => { //保存这个搜索条件 //订单id处理 if (params.id !== '') { if (params.id.indexOf(',')) { params.id = params.id.split(','); params.id = params.id.filter((id) => { return id !== ''; }); } } setSearchParam(params); const { data } = await postServiceOrderQueryServiceOrder({ // ...params, // FIXME: remove @ts-ignore // @ts-ignore sorter, filter, data: { ...params, isDeleteQueryOrder: onlyShowCancelOrder }, }); let mainOrderIds = data?.data?.map((d) => d.id); if (mainOrderAllItemKeys === undefined) { setMainOrderAllItemKeys([]); } else { setMainOrderAllItemKeys(mainOrderIds); } setRolePath(data.specialPath); handleTableExpand(mainOrderIds); return { data: data?.data || [], total: data?.total || 0, }; }} toolBarRender={() => { return toolBarRender(); }} /> {orderDrawerVisible && ( <OrderDrawer data={orderRow} subOrders={selectedRows} onClose={(isSuccess: boolean) => { setOrderDrawerVisible(false); setOrderRow({}); if (isSuccess) { refreshTable(); } }} orderOptType={orderOptType} /> )} {checkVisible && ( <CheckModal setCheckVisible={setCheckVisible} data={orderRow} subOrders={selectedRows} orderCheckType={orderCheckType} onClose={() => { setCheckVisible(false); setOrderRow({}); setSelectedRows({}); refreshTable(); }} /> )} {applyForInvoicingVisible && ( <ApplyForInvoicingModal setCheckVisible={setApplyForInvoicingVisible} subOrders={selectedRows} onClose={() => { setApplyForInvoicingVisible(false); setSelectedRows({}); refreshTable(); }} /> )} {notesEditVisible && ( <OrderNotesEditModal setNotesEditVisible={setNotesEditVisible} data={orderRow} isMianOrder={isMainOrder} onClose={() => { setNotesEditVisible(false); setOrderRow({}); refreshTable(); }} /> )} {deliverVisible && ( <DeliverModal data={selectedRows} isSendProduct={isSendProduct} setVisible={(b: boolean) => { setDeliverVisible(b); }} sendType={orderCheckType} onClose={() => { setDeliverVisible(false); setOrderRow({}); setIsSendProduct(false); refreshTable(); }} /> )} {financialVisible && ( <FinancialDrawer isEdit={isFinalcialEdit} mainOrder={orderRow} subOrders={selectedRows} isMainOrder={isMainOrder} cancel={() => { setFinancialVisible(false); setOrderRow({}); setIsMainOrder(false); setIsFinalcialEdit(false); }} onClose={() => { setFinancialVisible(false); setOrderRow({}); refreshTable(); setIsMainOrder(false); setIsFinalcialEdit(false); }} /> )} {orderPrintVisible && ( <OrderPrintModal mainOrder={orderRow} subOrders={selectedRows} isRePrint={isRePrintOrder} setVisible={(b: boolean) => { setOrderPrintVisible(b); }} printOptType={orderCheckType} onClose={() => { setOrderPrintVisible(false); setOrderRow({}); setIsRePrintOrder(false); refreshTable(); }} /> )} {confirmReceiptVisible && ( <ConfirmReceiptModal data={orderRow} onClose={() => { setConfirmReceiptVisible(false); setOrderRow({}); refreshTable(); }} /> )} {subOrderConfirmReceiptImagesVisible && ( <SubOrderComfirmReceiptImagesModal setVisible={setSubOrderConfirmReceiptImagesVisible} onClose={() => { setSubOrderConfirmReceiptImagesVisible(false); }} orderRow={orderRow} /> )} {importModalVisible && ( <ImportModal onClose={() => { setImportModalVisible(false); refreshTable(); }} /> )} {attachmentModalVisible && ( <AttachmentModal data={orderRow} onClose={() => { setAttachmentModalVisible(false); setOrderRow({}); }} /> )} {historyModalVisible && ( <HistoryModal subOrders={selectedRows} isCancelledOrder={onlyShowCancelOrder} onClose={() => { setHistoryModalVisible(false); setSelectedRows({}); }} /> )} {deliverInfoDrawerVisible && ( <DeliverInfoDrawer data={orderRow} onClose={() => { setDeliverInfoDrawerVisible(false); setOrderRow({}); }} /> )} {deliverInfoDrawerVisible && ( <DeliverInfoDrawer data={orderRow} onClose={() => { setDeliverInfoDrawerVisible(false); setOrderRow({}); }} /> )} {procureCheckModalVisible && ( <ProcureCheckModal setCheckVisible={setProcureCheckModalVisible} data={orderRow} subOrders={selectedRows} onClose={() => { setProcureCheckModalVisible(false); setOrderRow({}); setSelectedRows({}); refreshTable(); }} /> )} {afterSalesDrawerVisible && ( <AfterSalesDrawer setVisible={setAfterSalesDrawerVisible} mainOrder={orderRow} subOrders={selectedRows} onClose={() => { setAfterSalesDrawerVisible(false); setSelectedRows({}); setOrderRow({}); refreshTable(); }} /> )} {contextHolder} </PageContainer> ); }; export default OrderPage;