| src/pages/equipmentManagement/repair/add.vue | ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史 | |
| src/pages/equipmentManagement/repair/maintain.vue | ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史 | |
| src/pages/procurementManagement/receiptPaymentHistory/index.vue | ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史 |
src/pages/equipmentManagement/repair/add.vue
@@ -1,435 +1,489 @@ <template> <view class="repair-add"> <!-- 使用通用页面头部组件 --> <PageHeader :title="operationType === 'edit' ? '编辑报修' : '新增报修'" @back="goBack" /> <!-- 表单内容 --> <u-form @submit="sendForm" ref="formRef" :rules="formRules" :model="form" label-width="110"> <!-- 基本信息 --> <u-cell-group title="基本信息"> <u-form-item label="设备名称" prop="deviceLedgerId" required border-bottom> <u-input v-model="deviceNameText" placeholder="请选择设备名称" @click="showDevicePicker" clearable readonly="" /> <template #right> <u-icon name="scan" @click="startScan" class="scan-icon" /> </template> </u-form-item> <u-form-item label="规格型号" prop="deviceModel" border-bottom> <u-input v-model="form.deviceModel" placeholder="请输入规格型号" clearable /> </u-form-item> <u-form-item label="报修日期" prop="repairTime" required border-bottom> <u-input v-model="form.repairTime" placeholder="请选择报修日期" readonly @click="showDatePicker" clearable /> <template #right> <u-icon name="arrow-right" @click="showDatePicker"></u-icon> </template> </u-form-item> <u-form-item label="报修人" prop="repairName" required border-bottom> <u-input v-model="form.repairName" placeholder="请输入报修人" clearable /> </u-form-item> <u-form-item label="故障现象" prop="remark" required border-bottom> <u-textarea v-model="form.remark" rows="3" placeholder="请输入故障现象" clearable count maxlength="200" /> </u-form-item> </u-cell-group> <!-- 提交按钮 --> <view class="footer-btns"> <u-button class="cancel-btn" @click="goBack">取消</u-button> <u-button class="save-btn" type="primary" @click="sendForm" :loading="loading">保存</u-button> </view> </u-form> <!-- 设备选择器 --> <up-action-sheet :show="showDevice" :actions="deviceActionList" title="选择设备名称" @select="onDeviceSelect" @close="showDevice = false" /> <!-- 日期选择器 --> <up-datetime-picker :show="showDate" v-model="pickerDateValue" @confirm="onDateConfirm" @cancel="showDate = false" mode="date" /> </view> <view class="repair-add"> <!-- 使用通用页面头部组件 --> <PageHeader :title="operationType === 'edit' ? '编辑报修' : '新增报修'" @back="goBack" /> <!-- 表单内容 --> <u-form @submit="sendForm" ref="formRef" :rules="formRules" :model="form" label-width="110"> <!-- 基本信息 --> <u-cell-group title="基本信息"> <u-form-item label="设备名称" prop="deviceLedgerId" required border-bottom> <u-input v-model="deviceNameText" placeholder="请选择设备名称" @click="showDevicePicker" clearable readonly="" /> <template #right> <u-icon name="scan" @click="startScan" class="scan-icon" /> </template> </u-form-item> <u-form-item label="规格型号" prop="deviceModel" border-bottom> <u-input v-model="form.deviceModel" placeholder="请输入规格型号" clearable /> </u-form-item> <u-form-item label="报修日期" prop="repairTime" required border-bottom> <u-input v-model="form.repairTime" placeholder="请选择报修日期" readonly @click="showDatePicker" clearable /> <template #right> <u-icon name="arrow-right" @click="showDatePicker"></u-icon> </template> </u-form-item> <u-form-item label="报修状态" prop="repairTime" required border-bottom> <u-input v-model="repairStatusText" placeholder="请选择报修状态" readonly @click="openRepairStatusPicker" clearable /> <template #right> <u-icon name="arrow-right" @click="openRepairStatusPicker"></u-icon> </template> </u-form-item> <u-form-item label="报修人" prop="repairName" required border-bottom> <u-input v-model="form.repairName" placeholder="请输入报修人" clearable /> </u-form-item> <u-form-item label="故障现象" prop="remark" required border-bottom> <u-textarea v-model="form.remark" rows="3" placeholder="请输入故障现象" clearable count maxlength="200" /> </u-form-item> </u-cell-group> <!-- 提交按钮 --> <view class="footer-btns"> <u-button class="cancel-btn" @click="goBack">取消</u-button> <u-button class="save-btn" type="primary" @click="sendForm" :loading="loading">保存</u-button> </view> </u-form> <!-- 设备选择器 --> <up-action-sheet :show="showDevice" :actions="deviceActionList" title="选择设备名称" @select="onDeviceSelect" @close="showDevice = false" /> <!-- 日期选择器 --> <up-datetime-picker :show="showDate" v-model="pickerDateValue" @confirm="onDateConfirm" @cancel="showDate = false" mode="date" /> </view> </template> <script setup> import { ref, computed, onMounted, onUnmounted } from 'vue'; import { onShow } from '@dcloudio/uni-app'; import PageHeader from '@/components/PageHeader.vue'; import { getDeviceLedger } from '@/api/equipmentManagement/ledger'; import { addRepair, editRepair, getRepairById } from '@/api/equipmentManagement/repair'; import dayjs from "dayjs"; import { formatDateToYMD } from '@/utils/ruoyi'; const showToast = (message) => { uni.showToast({ title: message, icon: 'none' }) } import { ref, computed, onMounted, onUnmounted } from "vue"; import { onShow } from "@dcloudio/uni-app"; import PageHeader from "@/components/PageHeader.vue"; import { getDeviceLedger } from "@/api/equipmentManagement/ledger"; import { addRepair, editRepair, getRepairById, } from "@/api/equipmentManagement/repair"; import dayjs from "dayjs"; import { formatDateToYMD } from "@/utils/ruoyi"; const showToast = message => { uni.showToast({ title: message, icon: "none", }); }; defineOptions({ name: "设备报修表单", }); defineOptions({ name: "设备报修表单", }); // 表单引用 const formRef = ref(null); const operationType = ref('add'); const loading = ref(false); const showDevice = ref(false); const showDate = ref(false); const pickerDateValue = ref(Date.now()); // 表单引用 const formRef = ref(null); const operationType = ref("add"); const loading = ref(false); const showDevice = ref(false); const showDate = ref(false); const pickerDateValue = ref(Date.now()); // 设备选项 const deviceOptions = ref([]); const deviceNameText = ref(''); const deviceActionList = computed(() => { return deviceOptions.value.map(item => ({ name: item.deviceName, value: item.id })); }); // 设备选项 const deviceOptions = ref([]); const deviceNameText = ref(""); const deviceActionList = computed(() => { return deviceOptions.value.map(item => ({ name: item.deviceName, value: item.id, })); }); // 扫码相关状态 const isScanning = ref(false); const scanTimer = ref(null); // 扫码相关状态 const isScanning = ref(false); const scanTimer = ref(null); // 表单验证规则 const formRules = { deviceLedgerId: [{ required: true, trigger: "change", message: "请选择设备名称" }], repairTime: [{ required: true, trigger: "change", message: "请选择报修日期" }], repairName: [{ required: true, trigger: "blur", message: "请输入报修人" }], remark: [{ required: true, trigger: "blur", message: "请输入故障现象" }], }; // 表单验证规则 const formRules = { deviceLedgerId: [ { required: true, trigger: "change", message: "请选择设备名称" }, ], repairTime: [ { required: true, trigger: "change", message: "请选择报修日期" }, ], repairName: [{ required: true, trigger: "blur", message: "请输入报修人" }], remark: [{ required: true, trigger: "blur", message: "请输入故障现象" }], }; // 使用 ref 声明表单数据 const form = ref({ deviceLedgerId: undefined, // 设备ID deviceModel: undefined, // 规格型号 repairTime: dayjs().format("YYYY-MM-DD"), // 报修日期 repairName: undefined, // 报修人 remark: undefined, // 故障现象 }); // 使用 ref 声明表单数据 const form = ref({ deviceLedgerId: undefined, // 设备ID deviceModel: undefined, // 规格型号 repairTime: dayjs().format("YYYY-MM-DD"), // 报修日期 repairName: undefined, // 报修人 remark: undefined, // 故障现象 }); // 加载设备列表 const loadDeviceName = async () => { try { const { data } = await getDeviceLedger(); deviceOptions.value = data || []; } catch (e) { showToast('获取设备列表失败'); } }; // 报修状态选项 const repairStatusOptions = ref([ { name: "待维修", value: "0" }, { name: "完结", value: "1" }, { name: "失败", value: "2" }, ]); const repairStatusText = ref(""); // 设置设备规格型号 const setDeviceModel = (id) => { const option = deviceOptions.value.find((item) => item.id === id); if (option) { form.value.deviceModel = option.deviceModel; deviceNameText.value = option.deviceName; } }; // 打开报修状态选择器 const openRepairStatusPicker = () => { uni.showActionSheet({ itemList: repairStatusOptions.value.map(item => item.name), success: res => { form.value.status = repairStatusOptions.value[res.tapIndex].value; repairStatusText.value = repairStatusOptions.value[res.tapIndex].name; }, }); }; // 加载表单数据(编辑模式) const loadForm = async (id) => { if (id) { operationType.value = 'edit'; try { const { code, data } = await getRepairById(id); if (code == 200) { form.value.deviceLedgerId = data.deviceLedgerId; form.value.deviceModel = data.deviceModel; form.value.repairTime = dayjs(data.repairTime).format("YYYY-MM-DD"); form.value.repairName = data.repairName; form.value.remark = data.remark; // 设置设备名称显示 const device = deviceOptions.value.find(item => item.id === data.deviceLedgerId); if (device) { deviceNameText.value = device.deviceName; } } } catch (e) { showToast('获取详情失败'); } } else { // 新增模式 operationType.value = 'add'; } }; // 加载设备列表 const loadDeviceName = async () => { try { const { data } = await getDeviceLedger(); deviceOptions.value = data || []; } catch (e) { showToast("获取设备列表失败"); } }; // 扫描二维码功能 const startScan = () => { if (isScanning.value) { showToast('正在扫描中,请稍候...'); return; } // 调用uni-app的扫码API uni.scanCode({ scanType: ['qrCode', 'barCode'], success: (res) => { handleScanResult(res.result); }, fail: (err) => { console.error('扫码失败:', err); showToast('扫码失败,请重试'); } }); }; // 设置设备规格型号 const setDeviceModel = id => { const option = deviceOptions.value.find(item => item.id === id); if (option) { form.value.deviceModel = option.deviceModel; deviceNameText.value = option.deviceName; } }; // 处理扫码结果 const handleScanResult = (scanResult) => { if (!scanResult) { showToast('扫码结果为空'); return; } isScanning.value = true; showToast('扫码成功'); // 3秒后处理扫码结果 scanTimer.value = setTimeout(() => { processScanResult(scanResult); isScanning.value = false; }, 100); }; function getDeviceIdByRegExp(url) { // 匹配deviceId=后面的数字 const reg = /deviceId=(\d+)/; const match = url.match(reg); // 如果匹配到结果,返回数字类型,否则返回null return match ? Number(match[1]) : null; } // 加载表单数据(编辑模式) const loadForm = async id => { if (id) { operationType.value = "edit"; try { const { code, data } = await getRepairById(id); if (code == 200) { form.value.deviceLedgerId = data.deviceLedgerId; form.value.deviceModel = data.deviceModel; form.value.repairTime = dayjs(data.repairTime).format("YYYY-MM-DD"); form.value.repairName = data.repairName; form.value.remark = data.remark; repairStatusText.value = repairStatusOptions.value.find(item => item.value == data.status) ?.name || ""; // 设置设备名称显示 const device = deviceOptions.value.find( item => item.id === data.deviceLedgerId ); if (device) { deviceNameText.value = device.deviceName; } } } catch (e) { showToast("获取详情失败"); } } else { // 新增模式 operationType.value = "add"; } }; // 处理扫码结果并匹配设备 const processScanResult = (scanResult) => { const deviceId = getDeviceIdByRegExp(scanResult); const matchedDevice = deviceOptions.value.find(item => item.id == deviceId); if (matchedDevice) { // 找到匹配的设备,自动填充 form.value.deviceLedgerId = matchedDevice.id; deviceNameText.value = matchedDevice.deviceName; form.value.deviceModel = matchedDevice.deviceModel; showToast('设备信息已自动填充'); } else { // 未找到匹配的设备 showToast('未找到匹配的设备,请手动选择'); } }; // 扫描二维码功能 const startScan = () => { if (isScanning.value) { showToast("正在扫描中,请稍候..."); return; } // 显示设备选择器 const showDevicePicker = () => { showDevice.value = true; }; // 调用uni-app的扫码API uni.scanCode({ scanType: ["qrCode", "barCode"], success: res => { handleScanResult(res.result); }, fail: err => { console.error("扫码失败:", err); showToast("扫码失败,请重试"); }, }); }; // 确认设备选择 const onDeviceSelect = (e) => { form.value.deviceLedgerId = e.value; setDeviceModel(e.value); showDevice.value = false; }; // 处理扫码结果 const handleScanResult = scanResult => { if (!scanResult) { showToast("扫码结果为空"); return; } // 显示日期选择器 const showDatePicker = () => { showDate.value = true; }; isScanning.value = true; showToast("扫码成功"); // 确认日期选择 const onDateConfirm = (e) => { form.value.repairTime = formatDateToYMD(e.value); pickerDateValue.value = dayjs(e.value).format("YYYY-MM-DD"); showDate.value = false; }; // 3秒后处理扫码结果 scanTimer.value = setTimeout(() => { processScanResult(scanResult); isScanning.value = false; }, 100); }; function getDeviceIdByRegExp(url) { // 匹配deviceId=后面的数字 const reg = /deviceId=(\d+)/; const match = url.match(reg); // 如果匹配到结果,返回数字类型,否则返回null return match ? Number(match[1]) : null; } onShow(() => { // 页面显示时获取参数 getPageParams(); }); // 处理扫码结果并匹配设备 const processScanResult = scanResult => { const deviceId = getDeviceIdByRegExp(scanResult); const matchedDevice = deviceOptions.value.find(item => item.id == deviceId); onMounted(() => { // 页面加载时获取设备列表和参数 loadDeviceName(); getPageParams(); }); if (matchedDevice) { // 找到匹配的设备,自动填充 form.value.deviceLedgerId = matchedDevice.id; deviceNameText.value = matchedDevice.deviceName; form.value.deviceModel = matchedDevice.deviceModel; showToast("设备信息已自动填充"); } else { // 未找到匹配的设备 showToast("未找到匹配的设备,请手动选择"); } }; // 组件卸载时清理定时器 onUnmounted(() => { if (scanTimer.value) { clearTimeout(scanTimer.value); } }); // 显示设备选择器 const showDevicePicker = () => { showDevice.value = true; }; // 提交表单 const sendForm = async () => { try { // 手动验证表单 let isValid = true; let errorMessage = ''; if (!form.value.deviceLedgerId) { isValid = false; errorMessage = '请选择设备名称'; } else if (!form.value.repairTime || form.value.repairTime.trim() === '') { isValid = false; errorMessage = '请选择报修日期'; } else if (!form.value.repairName || form.value.repairName.trim() === '') { isValid = false; errorMessage = '请输入报修人'; } else if (!form.value.remark || form.value.remark.trim() === '') { isValid = false; errorMessage = '请输入故障现象'; } // 确认设备选择 const onDeviceSelect = e => { form.value.deviceLedgerId = e.value; setDeviceModel(e.value); showDevice.value = false; }; if (!isValid) { showToast(errorMessage); return; } // 显示日期选择器 const showDatePicker = () => { showDate.value = true; }; loading.value = true; const id = getPageId(); // 确认日期选择 const onDateConfirm = e => { form.value.repairTime = formatDateToYMD(e.value); pickerDateValue.value = dayjs(e.value).format("YYYY-MM-DD"); showDate.value = false; }; // 准备提交数据 const submitData = { ...form.value }; onShow(() => { // 页面显示时获取参数 getPageParams(); }); const { code } = id ? await editRepair({ id: id, ...submitData }) : await addRepair(submitData); onMounted(() => { // 页面加载时获取设备列表和参数 loadDeviceName(); getPageParams(); }); if (code == 200) { showToast(`${id ? "编辑" : "新增"}报修成功`); setTimeout(() => { uni.navigateBack(); }, 1500); } else { loading.value = false; } } catch (e) { loading.value = false; showToast('表单验证失败'); } }; // 组件卸载时清理定时器 onUnmounted(() => { if (scanTimer.value) { clearTimeout(scanTimer.value); } }); // 返回上一页 const goBack = () => { uni.removeStorageSync('repairId'); uni.navigateBack(); }; // 提交表单 const sendForm = async () => { try { // 手动验证表单 let isValid = true; let errorMessage = ""; if (!form.value.deviceLedgerId) { isValid = false; errorMessage = "请选择设备名称"; } else if (!form.value.repairTime || form.value.repairTime.trim() === "") { isValid = false; errorMessage = "请选择报修日期"; } else if (!form.value.repairName || form.value.repairName.trim() === "") { isValid = false; errorMessage = "请输入报修人"; } else if (!form.value.remark || form.value.remark.trim() === "") { isValid = false; errorMessage = "请输入故障现象"; } // 获取页面参数 const getPageParams = () => { // 使用uni.getStorageSync获取id const id = uni.getStorageSync('repairId'); // 根据是否有id参数来判断是新增还是编辑 if (id) { // 编辑模式,获取详情 loadForm(id); // 可选:获取后清除存储的id,避免影响后续操作 uni.removeStorageSync('repairId'); } else { // 新增模式 loadForm(); } }; if (!isValid) { showToast(errorMessage); return; } // 获取页面ID const getPageId = () => { // 使用uni.getStorageSync获取id const id = uni.getStorageSync('repairId'); return id; }; loading.value = true; const id = getPageId(); // 准备提交数据 const submitData = { ...form.value }; const { code } = id ? await editRepair({ id: id, ...submitData }) : await addRepair(submitData); if (code == 200) { showToast(`${id ? "编辑" : "新增"}报修成功`); setTimeout(() => { uni.navigateBack(); }, 1500); } else { loading.value = false; } } catch (e) { loading.value = false; showToast("表单验证失败"); } }; // 返回上一页 const goBack = () => { uni.removeStorageSync("repairId"); uni.navigateBack(); }; // 获取页面参数 const getPageParams = () => { // 使用uni.getStorageSync获取id const id = uni.getStorageSync("repairId"); // 根据是否有id参数来判断是新增还是编辑 if (id) { // 编辑模式,获取详情 loadForm(id); // 可选:获取后清除存储的id,避免影响后续操作 uni.removeStorageSync("repairId"); } else { // 新增模式 loadForm(); } }; // 获取页面ID const getPageId = () => { // 使用uni.getStorageSync获取id const id = uni.getStorageSync("repairId"); return id; }; </script> <style scoped lang="scss"> @import '@/static/scss/form-common.scss'; .repair-add { min-height: 100vh; background: #f8f9fa; padding-bottom: 5rem; } @import "@/static/scss/form-common.scss"; .repair-add { min-height: 100vh; background: #f8f9fa; padding-bottom: 5rem; } .footer-btns { position: fixed; left: 0; right: 0; bottom: 0; background: #fff; display: flex; justify-content: space-around; align-items: center; padding: 0.75rem 0; box-shadow: 0 -0.125rem 0.5rem rgba(0,0,0,0.05); z-index: 1000; } .footer-btns { position: fixed; left: 0; right: 0; bottom: 0; background: #fff; display: flex; justify-content: space-around; align-items: center; padding: 0.75rem 0; box-shadow: 0 -0.125rem 0.5rem rgba(0, 0, 0, 0.05); z-index: 1000; } .cancel-btn { font-weight: 400; font-size: 1rem; color: #FFFFFF; width: 6.375rem; background: #C7C9CC; box-shadow: 0 0.25rem 0.625rem 0 rgba(3,88,185,0.2); border-radius: 2.5rem 2.5rem 2.5rem 2.5rem; } .cancel-btn { font-weight: 400; font-size: 1rem; color: #ffffff; width: 6.375rem; background: #c7c9cc; box-shadow: 0 0.25rem 0.625rem 0 rgba(3, 88, 185, 0.2); border-radius: 2.5rem 2.5rem 2.5rem 2.5rem; } .save-btn { font-weight: 400; font-size: 1rem; color: #FFFFFF; width: 14rem; background: linear-gradient( 140deg, #00BAFF 0%, #006CFB 100%); box-shadow: 0 0.25rem 0.625rem 0 rgba(3,88,185,0.2); border-radius: 2.5rem 2.5rem 2.5rem 2.5rem; } .save-btn { font-weight: 400; font-size: 1rem; color: #ffffff; width: 14rem; background: linear-gradient(140deg, #00baff 0%, #006cfb 100%); box-shadow: 0 0.25rem 0.625rem 0 rgba(3, 88, 185, 0.2); border-radius: 2.5rem 2.5rem 2.5rem 2.5rem; } // 响应式调整 @media (max-width: 768px) { .submit-section { padding: 12px; } } // 响应式调整 @media (max-width: 768px) { .submit-section { padding: 12px; } } .tip-text { padding: 4px 16px 0 16px; font-size: 12px; color: #888; } .tip-text { padding: 4px 16px 0 16px; font-size: 12px; color: #888; } .scan-icon { color: #1989fa; font-size: 18px; margin-left: 8px; cursor: pointer; } .scan-icon { color: #1989fa; font-size: 18px; margin-left: 8px; cursor: pointer; } </style> src/pages/equipmentManagement/repair/maintain.vue
@@ -1,256 +1,297 @@ <template> <view class="repair-maintain"> <!-- 使用通用页面头部组件 --> <PageHeader title="新增维修" @back="goBack" /> <!-- 表单内容 --> <u-form ref="formRef" :model="form" :rules="formRules" label-width="140rpx"> <!-- 基本信息 --> <u-cell-group title="维修信息" inset> <u-form-item prop="maintenanceName" label="维修人" required> <u-input v-model="form.maintenanceName" placeholder="请输入维修人" clearable /> </u-form-item> <u-form-item prop="maintenanceResult" label="维修结果" required> <u-input v-model="form.maintenanceResult" type="textarea" rows="3" placeholder="请输入维修结果" clearable maxlength="200" show-word-limit /> </u-form-item> <u-form-item label="维修日期" prop="maintenanceTime" required border-bottom> <u-input v-model="form.maintenanceTime" placeholder="请选择维修日期" readonly @click="showDatePicker = true" clearable /> <template #right> <u-icon name="arrow-right" @click="showDatePicker = true"></u-icon> </template> </u-form-item> </u-cell-group> <!-- 提交按钮 --> <view class="footer-btns"> <u-button class="cancel-btn" @click="goBack">取消</u-button> <u-button class="save-btn" @click="submitForm" :loading="loading">保存</u-button> </view> </u-form> <!-- 日期选择器 --> <up-datetime-picker :show="showDatePicker" v-model="pickerDateValue" mode="datetime" title="选择日期" format="YYYY-MM-DD HH:mm:ss" @confirm="onDateConfirm" @cancel="showDatePicker = false" /> </view> <view class="repair-maintain"> <!-- 使用通用页面头部组件 --> <PageHeader title="新增维修" @back="goBack" /> <!-- 表单内容 --> <u-form ref="formRef" :model="form" :rules="formRules" label-width="140rpx"> <!-- 基本信息 --> <u-cell-group title="维修信息" inset> <u-form-item prop="maintenanceName" label="维修人" required> <u-input v-model="form.maintenanceName" placeholder="请输入维修人" clearable /> </u-form-item> <u-form-item prop="maintenanceResult" label="维修结果" required> <u-input v-model="form.maintenanceResult" type="textarea" rows="3" placeholder="请输入维修结果" clearable maxlength="200" show-word-limit /> </u-form-item> <u-form-item label="维修状态" prop="repairTime" required border-bottom> <u-input v-model="repairStatusText" placeholder="请选择维修状态" readonly @click="openRepairStatusPicker" clearable /> <template #right> <u-icon name="arrow-right" @click="openRepairStatusPicker"></u-icon> </template> </u-form-item> <u-form-item label="维修日期" prop="maintenanceTime" required border-bottom> <u-input v-model="form.maintenanceTime" placeholder="请选择维修日期" readonly @click="showDatePicker = true" clearable /> <template #right> <u-icon name="arrow-right" @click="showDatePicker = true"></u-icon> </template> </u-form-item> </u-cell-group> <!-- 提交按钮 --> <view class="footer-btns"> <u-button class="cancel-btn" @click="goBack">取消</u-button> <u-button class="save-btn" @click="submitForm" :loading="loading">保存</u-button> </view> </u-form> <!-- 日期选择器 --> <up-datetime-picker :show="showDatePicker" v-model="pickerDateValue" mode="datetime" title="选择日期" format="YYYY-MM-DD HH:mm:ss" @confirm="onDateConfirm" @cancel="showDatePicker = false" /> </view> </template> <script setup> import { ref, onMounted } from 'vue'; import { onShow } from '@dcloudio/uni-app'; import PageHeader from '@/components/PageHeader.vue'; import { addMaintain } from '@/api/equipmentManagement/repair'; import useUserStore from "@/store/modules/user"; import dayjs from "dayjs"; import { ref, onMounted } from "vue"; import { onShow } from "@dcloudio/uni-app"; import PageHeader from "@/components/PageHeader.vue"; import { addMaintain } from "@/api/equipmentManagement/repair"; import useUserStore from "@/store/modules/user"; import dayjs from "dayjs"; defineOptions({ name: "设备维修表单", }); defineOptions({ name: "设备维修表单", }); const userStore = useUserStore(); const userStore = useUserStore(); // 表单引用 const formRef = ref(null); const loading = ref(false); const showDatePicker = ref(false); const pickerDateValue = ref(Date.now());; // 使用时间戳 // 表单引用 const formRef = ref(null); const loading = ref(false); const showDatePicker = ref(false); const pickerDateValue = ref(Date.now()); // 使用时间戳 // 表单验证规则 const formRules = { maintenanceName: [{ required: true, trigger: "blur", message: "请输入维修人" }], maintenanceResult: [{ required: true, trigger: "blur", message: "请输入维修结果" }], maintenanceTime: [{ required: true, trigger: "change", message: "请选择维修日期" }], }; // 表单验证规则 const formRules = { maintenanceName: [ { required: true, trigger: "blur", message: "请输入维修人" }, ], maintenanceResult: [ { required: true, trigger: "blur", message: "请输入维修结果" }, ], maintenanceTime: [ { required: true, trigger: "change", message: "请选择维修日期" }, ], }; const repairStatusOptions = ref([ { name: "待维修", value: "0" }, { name: "完结", value: "1" }, { name: "失败", value: "2" }, ]); const repairStatusText = ref("完结"); // 打开报修状态选择器 const openRepairStatusPicker = () => { uni.showActionSheet({ itemList: repairStatusOptions.value.map(item => item.name), success: res => { form.value.status = repairStatusOptions.value[res.tapIndex].value; repairStatusText.value = repairStatusOptions.value[res.tapIndex].name; }, }); }; // 使用 ref 声明表单数据 const form = ref({ maintenanceName: userStore.nickName || "", // 默认使用当前用户昵称 maintenanceResult: undefined, // 维修结果 maintenanceTime: dayjs().format("YYYY-MM-DD HH:mm:ss"), // 维修日期(只显示日期) }); // 使用 ref 声明表单数据 const form = ref({ maintenanceName: userStore.nickName || '', // 默认使用当前用户昵称 maintenanceResult: undefined, // 维修结果 maintenanceTime: dayjs().format("YYYY-MM-DD HH:mm:ss"), // 维修日期(只显示日期) }); // 自定义showToast函数 const showToast = message => { uni.showToast({ title: message, icon: "none", }); }; // 自定义showToast函数 const showToast = (message) => { uni.showToast({ title: message, icon: 'none' }) }; // 重置表单数据和校验状态 const resetForm = () => { form.value = { maintenanceName: userStore.nickName || "", maintenanceResult: undefined, maintenanceTime: dayjs().format("YYYY-MM-DD HH:mm:ss"), }; }; // 重置表单数据和校验状态 const resetForm = () => { form.value = { maintenanceName: userStore.nickName || '', maintenanceResult: undefined, maintenanceTime: dayjs().format("YYYY-MM-DD HH:mm:ss"), }; }; const resetFormAndValidate = () => { resetForm(); }; const resetFormAndValidate = () => { resetForm(); }; // 提交表单 const submitForm = async () => { try { // 使用uview-plus的表单验证方式 const valid = await formRef.value.validate(); if (valid) { submitFormData(); } } catch (e) { showToast("表单验证失败"); } }; // 提交表单 const submitForm = async () => { try { // 使用uview-plus的表单验证方式 const valid = await formRef.value.validate(); if (valid) { submitFormData(); } } catch (e) { showToast('表单验证失败'); } }; // 提交表单数据 const submitFormData = async () => { try { loading.value = true; const id = getPageId(); // 提交表单数据 const submitFormData = async () => { try { loading.value = true; const id = getPageId(); if (!id) { showToast('参数错误'); loading.value = false; return; } // 准备提交数据,maintenanceTime 加上当前时分秒 const submitData = { ...form.value }; const { code } = await addMaintain({ id: id, ...submitData }); if (code == 200) { showToast('新增维修成功'); resetFormAndValidate(); setTimeout(() => { goBack(); }, 500); } else { loading.value = false; } } catch (e) { console.log(e); loading.value = false; showToast('操作失败'); } }; if (!id) { showToast("参数错误"); loading.value = false; return; } form.value.status = Number(form.value.status); // 准备提交数据,maintenanceTime 加上当前时分秒 const submitData = { ...form.value }; // 返回上一页 const goBack = () => { uni.removeStorageSync('repairId'); uni.navigateBack(); }; const { code } = await addMaintain({ id: id, ...submitData }); // 获取页面ID const getPageId = () => { const id = uni.getStorageSync('repairId'); return id; }; if (code == 200) { showToast("新增维修成功"); resetFormAndValidate(); setTimeout(() => { goBack(); }, 500); } else { loading.value = false; } } catch (e) { console.log(e); // 确认日期选择 const onDateConfirm = (e) => { form.value.maintenanceTime = dayjs(e.value).format('YYYY-MM-DD HH:mm:ss') pickerDateValue.value = e.value showDatePicker.value = false; }; loading.value = false; showToast("操作失败"); } }; // 初始化表单数据 const initForm = () => { // 设置维修人为当前用户昵称 form.value.maintenanceName = userStore.nickName || ''; // 设置当前日期(只包含年月日) form.value.maintenanceTime = dayjs().format('YYYY-MM-DD HH:mm:ss'); }; // 返回上一页 const goBack = () => { uni.removeStorageSync("repairId"); uni.navigateBack(); }; onShow(() => { // 页面显示时初始化表单 initForm(); }); // 获取页面ID const getPageId = () => { const id = uni.getStorageSync("repairId"); return id; }; onMounted(() => { // 页面加载时初始化表单 initForm(); }); // 确认日期选择 const onDateConfirm = e => { form.value.maintenanceTime = dayjs(e.value).format("YYYY-MM-DD HH:mm:ss"); pickerDateValue.value = e.value; showDatePicker.value = false; }; // 初始化表单数据 const initForm = () => { form.value.status = "1"; // 设置维修人为当前用户昵称 form.value.maintenanceName = userStore.nickName || ""; // 设置当前日期(只包含年月日) form.value.maintenanceTime = dayjs().format("YYYY-MM-DD HH:mm:ss"); }; onShow(() => { // 页面显示时初始化表单 initForm(); }); onMounted(() => { // 页面加载时初始化表单 initForm(); }); </script> <style scoped lang="scss"> @import '@/static/scss/form-common.scss'; .repair-maintain { min-height: 100vh; background: #f8f9fa; padding-bottom: 5rem; } @import "@/static/scss/form-common.scss"; .repair-maintain { min-height: 100vh; background: #f8f9fa; padding-bottom: 5rem; } .footer-btns { position: fixed; left: 0; right: 0; bottom: 0; background: #fff; display: flex; justify-content: space-around; align-items: center; padding: 0.75rem 0; box-shadow: 0 -0.125rem 0.5rem rgba(0,0,0,0.05); z-index: 1000; } .footer-btns { position: fixed; left: 0; right: 0; bottom: 0; background: #fff; display: flex; justify-content: space-around; align-items: center; padding: 0.75rem 0; box-shadow: 0 -0.125rem 0.5rem rgba(0, 0, 0, 0.05); z-index: 1000; } .cancel-btn { font-weight: 400; font-size: 1rem; color: #FFFFFF; width: 6.375rem; background: #C7C9CC; box-shadow: 0 0.25rem 0.625rem 0 rgba(3,88,185,0.2); border-radius: 2.5rem 2.5rem 2.5rem 2.5rem; } .cancel-btn { font-weight: 400; font-size: 1rem; color: #ffffff; width: 6.375rem; background: #c7c9cc; box-shadow: 0 0.25rem 0.625rem 0 rgba(3, 88, 185, 0.2); border-radius: 2.5rem 2.5rem 2.5rem 2.5rem; } .save-btn { font-weight: 400; font-size: 1rem; color: #FFFFFF; width: 14rem; background: linear-gradient( 140deg, #00BAFF 0%, #006CFB 100%); box-shadow: 0 0.25rem 0.625rem 0 rgba(3,88,185,0.2); border-radius: 2.5rem 2.5rem 2.5rem 2.5rem; } .save-btn { font-weight: 400; font-size: 1rem; color: #ffffff; width: 14rem; background: linear-gradient(140deg, #00baff 0%, #006cfb 100%); box-shadow: 0 0.25rem 0.625rem 0 rgba(3, 88, 185, 0.2); border-radius: 2.5rem 2.5rem 2.5rem 2.5rem; } // 响应式调整 @media (max-width: 768px) { .submit-section { padding: 12px; } } // 响应式调整 @media (max-width: 768px) { .submit-section { padding: 12px; } } .tip-text { padding: 4px 16px 0 16px; font-size: 12px; color: #888; } .tip-text { padding: 4px 16px 0 16px; font-size: 12px; color: #888; } </style> src/pages/procurementManagement/receiptPaymentHistory/index.vue
@@ -1,79 +1,86 @@ <template> <view class="sales-account"> <!-- 使用通用页面头部组件 --> <PageHeader title="付款流水" @back="goBack" /> <!-- 搜索区域 --> <view class="search-section"> <view class="search-bar"> <view class="search-input"> <up-input class="search-text" placeholder="请输入供应商名称" v-model="searchForm.searchText" @change="getList" clearable /> </view> <view class="search-button" @click="getList"> <up-icon name="search" size="24" color="#999"></up-icon> </view> </view> </view> <!-- 统计信息 --> <view class="summary-info" v-if="tableData.length > 0"> <view class="summary-item"> <text class="summary-label">总记录数</text> <text class="summary-value">{{ tableData.length }}</text> </view> <view class="summary-item"> <text class="summary-label">总金额</text> <text class="summary-value highlight">{{ formatAmount(totalAmount) }}</text> </view> </view> <!-- 付款历史列表 --> <view class="history-list" v-if="tableData.length > 0"> <view v-for="(item, index) in tableData" :key="index"> <view class="history-item"> <view class="item-header"> <view class="item-left"> <view class="document-icon"> <up-icon name="file-text" size="16" color="#ffffff"></up-icon> </view> <text class="item-id">{{ item.purchaseContractNumber }}</text> </view> <view class="item-tag" :class="getTagClass(item.paymentMethod)"> <text class="tag-text">{{ item.paymentMethod }}</text> </view> </view> <up-divider></up-divider> <view class="item-details"> <view class="detail-row"> <text class="detail-label">供应商名称</text> <text class="detail-value">{{ item.supplierName }}</text> </view> <view class="detail-row"> <text class="detail-label">付款金额(元)</text> <text class="detail-value highlight">{{ formatAmount(item.currentPaymentAmount) }}</text> </view> <view class="detail-row"> <text class="detail-label">付款日期</text> <text class="detail-value">{{ item.paymentDate }}</text> </view> <up-divider></up-divider> <view class="detail-info"> <view class="detail-row"> <text class="detail-label">登记人</text> <text class="detail-value">{{ item.registrant }}</text> </view> <view class="detail-row"> <text class="detail-label">登记日期</text> <text class="detail-value">{{ item.registrationtDate }}</text> </view> </view> <!-- 操作按钮 --> <view class="action-buttons"> <u-button <view class="sales-account"> <!-- 使用通用页面头部组件 --> <PageHeader title="付款流水" @back="goBack" /> <!-- 搜索区域 --> <view class="search-section"> <view class="search-bar"> <view class="search-input"> <up-input class="search-text" placeholder="请输入供应商名称" v-model="searchForm.searchText" @change="getList" clearable /> </view> <view class="search-button" @click="getList"> <up-icon name="search" size="24" color="#999"></up-icon> </view> </view> </view> <!-- 统计信息 --> <view class="summary-info" v-if="tableData.length > 0"> <view class="summary-item"> <text class="summary-label">总记录数</text> <text class="summary-value">{{ tableData.length }}</text> </view> <view class="summary-item"> <text class="summary-label">总金额</text> <text class="summary-value highlight">{{ formatAmount(totalAmount) }}</text> </view> </view> <!-- 付款历史列表 --> <view class="history-list" v-if="tableData.length > 0"> <view v-for="(item, index) in tableData" :key="index"> <view class="history-item"> <view class="item-header"> <view class="item-left"> <view class="document-icon"> <up-icon name="file-text" size="16" color="#ffffff"></up-icon> </view> <text class="item-id">{{ item.purchaseContractNumber }}</text> </view> <view class="item-tag" :class="getTagClass(item.paymentMethod)"> <text class="tag-text">{{ item.paymentMethod }}</text> </view> </view> <up-divider></up-divider> <view class="item-details"> <view class="detail-row"> <text class="detail-label">供应商名称</text> <text class="detail-value">{{ item.supplierName }}</text> </view> <view class="detail-row"> <text class="detail-label">付款金额(元)</text> <text class="detail-value highlight">{{ formatAmount(item.currentPaymentAmount) }}</text> </view> <view class="detail-row"> <text class="detail-label">付款日期</text> <text class="detail-value">{{ item.paymentDate }}</text> </view> <up-divider></up-divider> <view class="detail-info"> <view class="detail-row"> <text class="detail-label">登记人</text> <text class="detail-value">{{ item.registrant }}</text> </view> <view class="detail-row"> <text class="detail-label">登记日期</text> <text class="detail-value">{{ item.registrationtDate }}</text> </view> </view> <!-- 操作按钮 --> <view class="action-buttons"> <!-- <u-button type="primary" size="small" class="action-btn" @@ -81,124 +88,160 @@ @click="openForm(item)" > 编辑付款 </u-button> </view> </view> </view> </view> </view> <view v-else class="no-data"> <text>暂无付款历史数据</text> </view> </view> </u-button> --> <u-button type="error" size="small" class="action-btn" :disabled="item.registrant !== userStore.nickName" @click="deleteItem(item)"> 删除 </u-button> </view> </view> </view> </view> </view> <view v-else class="no-data"> <text>暂无付款历史数据</text> </view> </view> </template> <script setup> import { ref, computed } from 'vue'; import { onShow } from '@dcloudio/uni-app'; import {paymentHistoryListPage} from "@/api/procurementManagement/paymentEntry"; import useUserStore from "@/store/modules/user"; const userStore = useUserStore() import { ref, computed } from "vue"; import { onShow } from "@dcloudio/uni-app"; import { paymentHistoryListPage } from "@/api/procurementManagement/paymentEntry"; import { delPaymentRegistration } from "@/api/procurementManagement/procurementInvoiceLedger"; import useUserStore from "@/store/modules/user"; const userStore = useUserStore(); // 搜索表单 const searchForm = ref({ searchText: '', }); // 搜索表单 const searchForm = ref({ searchText: "", }); // 表格数据 const tableData = ref([]); // 表格数据 const tableData = ref([]); // 分页参数 const page = ref({ current: -1, size: -1, }); // 分页参数 const page = ref({ current: -1, size: -1, }); const totalAmount = computed(() => { return tableData.value.reduce((sum, item) => { return sum + (parseFloat(item.receiptPaymentAmount) || 0); }, 0); }); const totalAmount = computed(() => { return tableData.value.reduce((sum, item) => { return sum + (parseFloat(item.receiptPaymentAmount) || 0); }, 0); }); // 返回上一页 const goBack = () => { uni.navigateBack(); }; // 返回上一页 const goBack = () => { uni.navigateBack(); }; const deleteItem = item => { uni.showModal({ title: "确认删除", content: `是否确认删除该数据吗?`, success: res => { if (res.confirm) { // 调用删除接口 delPaymentRegistration([item.id]) .then(() => { uni.showToast({ title: "删除成功", icon: "success", }); // 刷新列表 getList(); }) .catch(() => { uni.showToast({ title: "删除失败", icon: "error", }); }); } }, }); }; // 查询列表 const getList = () => { showLoadingToast("加载中..."); const params = { ...searchForm.value, ...page.value, }; paymentHistoryListPage(params) .then(res => { tableData.value = res.records; closeToast(); }) .catch(() => { closeToast(); uni.showToast({ title: "查询失败", icon: "error", }); }); }; // 查询列表 const getList = () => { showLoadingToast('加载中...') const params = { ...searchForm.value, ...page.value }; paymentHistoryListPage(params).then((res) => { tableData.value = res.records; closeToast() }).catch(() => { closeToast() uni.showToast({ title: '查询失败', icon: 'error' }); }); }; // 获取标签样式类 const getTagClass = type => { if (type == "电汇") { return "tag-electric"; } else if (type == "承兑") { return "tag-acceptance"; } else { return "tag-unknown"; } }; // 获取标签样式类 const getTagClass = (type) => { if (type == '电汇') { return "tag-electric"; } else if (type == '承兑') { return "tag-acceptance"; } else { return "tag-unknown"; } }; // 格式化金额 const formatAmount = amount => { return amount ? parseFloat(amount).toFixed(2) : "0.00"; }; // 格式化金额 const formatAmount = (amount) => { return amount ? parseFloat(amount).toFixed(2) : '0.00'; }; // 显示加载提示 const showLoadingToast = message => { uni.showLoading({ title: message, mask: true, }); }; // 显示加载提示 const showLoadingToast = (message) => { uni.showLoading({ title: message, mask: true }); }; // 关闭提示 const closeToast = () => { uni.hideLoading(); }; // 关闭提示 const closeToast = () => { uni.hideLoading(); }; // 打开编辑表单 const openForm = (item) => { uni.setStorageSync('invoiceLedgerEditRow', JSON.stringify(item)) uni.navigateTo({ url: '/pages/procurementManagement/paymentEntry/edit' }) } onShow(() => { // 页面显示时刷新列表 getList(); }); // 打开编辑表单 const openForm = item => { uni.setStorageSync("invoiceLedgerEditRow", JSON.stringify(item)); uni.navigateTo({ url: "/pages/procurementManagement/paymentEntry/edit" }); }; onShow(() => { // 页面显示时刷新列表 getList(); }); </script> <style scoped lang="scss"> @import '@/styles/procurement-common.scss'; @import "@/styles/procurement-common.scss"; // 付款流水特有样式 .action-buttons { padding: 12px 0 0 0; // 与公共样式中的 0 0 16px 0 不同 } // 付款流水特有样式 .action-buttons { padding: 12px 0 0 0; // 与公共样式中的 0 0 16px 0 不同 } .item-tag { padding: 2px 8px; // 与公共样式中的 2px 4px 不同 } .item-tag { padding: 2px 8px; // 与公共样式中的 2px 4px 不同 } .tag-text { font-size: 14px; // 与公共样式中的 11px 不同 color: #ffffff; font-weight: 500; } .tag-text { font-size: 14px; // 与公共样式中的 11px 不同 color: #ffffff; font-weight: 500; } </style>