<template>
|
<view class="material-inspection-add">
|
<!-- 使用通用页面头部组件 -->
|
<PageHeader :title="isEdit ? '编辑原材料检验' : '新增原材料检验'"
|
@back="goBack" />
|
<!-- 表单内容 -->
|
<up-form :model="form"
|
ref="formRef"
|
label-width="110"
|
:rules="rules">
|
<!-- 基本信息 -->
|
<up-form-item label="供应商"
|
prop="supplier"
|
required
|
border-bottom>
|
<up-input v-model="form.supplier"
|
placeholder="请选择供应商"
|
readonly
|
:disabled="supplierQuantityDisabled" />
|
<template #right>
|
<up-icon @click="showSupplierSheet = true"
|
name="arrow-right" />
|
</template>
|
</up-form-item>
|
<up-form-item label="产品名称"
|
prop="productId"
|
required
|
border-bottom>
|
<up-input v-model="form.productName"
|
placeholder="请选择产品"
|
readonly
|
@click="showProductTree = true"
|
:disabled="isEdit" />
|
<template #right>
|
<up-icon @click="showProductTree = true"
|
name="arrow-right" />
|
</template>
|
</up-form-item>
|
<up-form-item label="规格型号"
|
prop="productModelId"
|
required
|
border-bottom>
|
<up-input v-model="form.model"
|
placeholder="请选择规格型号"
|
readonly
|
:disabled="isEdit" />
|
<template #right>
|
<up-icon @click="showModelSheet = true"
|
name="arrow-right" />
|
</template>
|
</up-form-item>
|
<up-form-item label="指标选择"
|
prop="testStandardId"
|
border-bottom>
|
<up-input v-model="testStandardDisplay"
|
placeholder="请选择指标"
|
readonly />
|
<template #right>
|
<up-icon @click="openTestStandardSheet"
|
name="arrow-right" />
|
</template>
|
</up-form-item>
|
<up-form-item label="单位"
|
prop="unit"
|
border-bottom>
|
<up-input v-model="form.unit"
|
placeholder="请输入单位"
|
disabled />
|
</up-form-item>
|
<up-form-item label="数量"
|
prop="quantity"
|
required
|
border-bottom>
|
<up-input v-model="form.quantity"
|
type="number"
|
placeholder="请输入数量"
|
:disabled="supplierQuantityDisabled" />
|
</up-form-item>
|
<up-form-item label="检测单位"
|
prop="checkCompany"
|
border-bottom>
|
<up-input v-model="form.checkCompany"
|
placeholder="请输入检测单位"
|
clearable />
|
</up-form-item>
|
<up-form-item label="检测结果"
|
prop="checkResult"
|
required
|
border-bottom>
|
<up-input v-model="form.checkResult"
|
placeholder="请选择检测结果"
|
readonly
|
@click="showResultSheet" />
|
<template #right>
|
<up-icon @click="showResultSheet = true"
|
name="arrow-right" />
|
</template>
|
</up-form-item>
|
<up-form-item label="检验员"
|
prop="checkName"
|
border-bottom>
|
<up-input v-model="form.checkName"
|
placeholder="请选择检验员"
|
readonly
|
@click="showInspectorSheet" />
|
<template #right>
|
<up-icon @click="showInspectorSheet = true"
|
name="arrow-right" />
|
</template>
|
</up-form-item>
|
<up-form-item label="检测日期"
|
prop="checkTime"
|
required
|
border-bottom>
|
<up-input v-model="form.checkTime"
|
placeholder="请选择检测日期"
|
readonly />
|
<!-- <template #right>
|
<up-icon name="calendar"
|
@click="showDatePicker"></up-icon>
|
</template> -->
|
</up-form-item>
|
<!-- <up-form-item label="采购订单号"
|
prop="purchaseContractNo"
|
border-bottom>
|
<up-input v-model="form.purchaseContractNo"
|
placeholder="请输入采购订单号"
|
clearable />
|
</up-form-item> -->
|
<!-- 检验项目 -->
|
<view class="inspection-items-container">
|
<view class="steps-header">
|
<text class="steps-title">检验项目</text>
|
<text class="steps-count">共 {{ tableData.length }} 个项目</text>
|
</view>
|
<view class="steps-list">
|
<view v-for="(item, index) in tableData"
|
:key="index"
|
class="exec-step-item">
|
<view class="step-number">
|
{{ index + 1 }}
|
</view>
|
<view class="step-content">
|
<view class="step-row">
|
<text class="step-label">指标:</text>
|
<text class="step-value">{{ item.parameterItem }}</text>
|
</view>
|
<view class="step-row">
|
<text class="step-label">单位:</text>
|
<text class="step-value">{{ item.unit }}</text>
|
</view>
|
<view class="step-row">
|
<text class="step-label">标准值:</text>
|
<text class="step-value">{{ item.standardValue }}</text>
|
</view>
|
<view class="step-row">
|
<text class="step-label">内控值:</text>
|
<text class="step-value">{{ item.controlValue }}</text>
|
</view>
|
<view class="step-row">
|
<text class="step-label">检验值:</text>
|
<up-input v-model="item.testValue"
|
placeholder="请输入检验值"
|
clearable
|
border-bottom
|
class="step-input" />
|
</view>
|
</view>
|
</view>
|
<view v-if="tableData.length === 0"
|
class="empty-data">
|
<text>请先选择指标</text>
|
</view>
|
</view>
|
</view>
|
</up-form>
|
<!-- 底部按钮 -->
|
<view class="bottom-buttons">
|
<up-button type="default"
|
size="default"
|
@click="goBack"
|
class="bottom-btn">
|
取消
|
</up-button>
|
<up-button type="primary"
|
size="default"
|
@click="submitForm"
|
:loading="loading"
|
class="bottom-btn">
|
{{ isEdit ? '保存' : '提交' }}
|
</up-button>
|
</view>
|
<!-- 日期选择器 -->
|
<up-popup v-model:show="showDate"
|
mode="date"
|
:start-year="2020"
|
:end-year="2030"
|
@confirm="confirmDate" />
|
<!-- 供应商选择 -->
|
<up-action-sheet :show="showSupplierSheet"
|
:actions="supplierOptions"
|
@select="selectSupplier"
|
@close="showSupplierSheet = false"
|
title="选择供应商" />
|
<!-- 产品选择 -->
|
<up-action-sheet :show="showProductSheet"
|
:actions="productSheetOptions"
|
@select="selectProduct"
|
@close="showProductSheet = false"
|
title="选择产品" />
|
<!-- 规格型号选择 -->
|
<up-action-sheet :show="showModelSheet"
|
:actions="modelSheetOptions"
|
@select="selectModel"
|
@close="showModelSheet = false"
|
title="选择规格型号" />
|
<!-- 检测结果选择 -->
|
<up-action-sheet :show="showResultSheet"
|
:actions="resultSheetOptions"
|
@select="selectResult"
|
@close="showResultSheet = false"
|
title="选择检测结果" />
|
<!-- 检验员选择 -->
|
<up-action-sheet :show="showInspectorSheet"
|
:actions="userSheetOptions"
|
@select="selectInspector"
|
@close="showInspectorSheet = false"
|
title="选择检验员" />
|
<!-- 指标选择 -->
|
<up-action-sheet :show="showTestStandardSheet"
|
:actions="testStandardSheetOptions"
|
@select="selectTestStandard"
|
@close="showTestStandardSheet = false"
|
title="选择指标" />
|
<!-- 产品树形选择器 -->
|
<up-popup v-model:show="showProductTree"
|
position="bottom"
|
:round="true"
|
:closeable="true"
|
@close="showProductTree = false">
|
<view class="tree-selector">
|
<view class="tree-header">
|
<text class="tree-title">选择产品</text>
|
</view>
|
<view class="tree-content">
|
<view class="tree-node"
|
v-for="(node, index) in productOptions"
|
:key="index">
|
<view v-if="node.children && node.children.length > 0"
|
class="tree-node-header"
|
@click="toggleNode(node)">
|
<up-icon :name="node.expanded ? 'arrow-down' : 'arrow-right'"
|
class="tree-node-icon" />
|
<text class="tree-node-label">{{ node.label }}</text>
|
</view>
|
<view v-else
|
class="tree-node-header"
|
@click="selectTreeNode(node)">
|
<text class="tree-node-icon-placeholder"></text>
|
<text class="tree-node-label">{{ node.label }}</text>
|
<up-icon name="checkmark"
|
v-if="form.productId == node.value"
|
class="tree-node-check" />
|
</view>
|
<view v-if="node.children && node.children.length > 0 && node.expanded"
|
class="tree-node-children">
|
<view class="tree-node"
|
v-for="(child, childIndex) in node.children"
|
:key="childIndex">
|
<view v-if="child.children && child.children.length > 0"
|
class="tree-node-header"
|
@click="toggleNode(child)">
|
<up-icon :name="child.expanded ? 'arrow-down' : 'arrow-right'"
|
class="tree-node-icon" />
|
<text class="tree-node-label">{{ child.label }}</text>
|
</view>
|
<view v-else
|
class="tree-node-header"
|
@click="selectTreeNode(child)">
|
<text class="tree-node-icon-placeholder"></text>
|
<text class="tree-node-label">{{ child.label }}</text>
|
<up-icon name="checkmark"
|
v-if="form.productId == child.value"
|
class="tree-node-check" />
|
</view>
|
<view v-if="child.children && child.children.length > 0 && child.expanded"
|
class="tree-node-children">
|
<view class="tree-node"
|
v-for="(grandchild, grandchildIndex) in child.children"
|
:key="grandchildIndex">
|
<view class="tree-node-header"
|
@click="selectTreeNode(grandchild)">
|
<text class="tree-node-icon-placeholder"></text>
|
<text class="tree-node-label">{{ grandchild.label }}</text>
|
<up-icon name="checkmark"
|
v-if="form.productId == grandchild.value"
|
class="tree-node-check" />
|
</view>
|
</view>
|
</view>
|
</view>
|
</view>
|
</view>
|
</view>
|
</view>
|
</up-popup>
|
</view>
|
</template>
|
|
<script setup>
|
import { ref, computed, onMounted, nextTick } from "vue";
|
import { onShow } from "@dcloudio/uni-app";
|
import PageHeader from "@/components/PageHeader.vue";
|
import dayjs from "dayjs";
|
import { getOptions } from "@/api/procurementManagement/procurementLedger.js";
|
import { modelList, productTreeList } from "@/api/basicData/product.js";
|
import {
|
qualityInspectAdd,
|
qualityInspectUpdate,
|
qualityInspectParamInfo,
|
qualityInspectDetailByProductId,
|
getQualityTestStandardParamByTestStandardId,
|
} from "@/api/qualityManagement/materialInspection.js";
|
import { userListNoPage } from "@/api/system/user.js";
|
|
// 显示提示信息
|
const showToast = message => {
|
uni.showToast({
|
title: message,
|
icon: "none",
|
});
|
};
|
|
// 表单引用
|
const formRef = ref(null);
|
// 加载状态
|
const loading = ref(false);
|
// 日期选择器
|
const showDate = ref(false);
|
// 供应商选择
|
const showSupplierSheet = ref(false);
|
// 产品选择
|
const showProductSheet = ref(false);
|
// 产品树形选择器
|
const showProductTree = ref(false);
|
// 规格型号选择
|
const showModelSheet = ref(false);
|
// 检测结果选择
|
const showResultSheet = ref(false);
|
// 检验员选择
|
const showInspectorSheet = ref(false);
|
// 指标选择
|
const showTestStandardSheet = ref(false);
|
|
// 表单数据
|
const form = ref({
|
checkTime: dayjs().format("YYYY-MM-DD"),
|
supplier: "",
|
checkName: "",
|
productName: "",
|
productId: "",
|
productModelId: "",
|
model: "",
|
testStandardId: "",
|
unit: "",
|
quantity: "",
|
checkCompany: "",
|
checkResult: "",
|
productMainId: null,
|
purchaseLedgerId: null,
|
});
|
|
// 显示用的变量
|
const testStandardDisplay = ref("");
|
|
// 检验项目
|
const tableData = ref([]);
|
const tableLoading = ref(false);
|
|
// 供应商列表
|
const supplierList = ref([]);
|
// 产品选项
|
const productOptions = ref([]);
|
// 型号选项
|
const modelOptions = ref([]);
|
// 检验员列表
|
const userList = ref([]);
|
// 检测结果选项
|
const resultOptions = ref([
|
{ label: "合格", value: "合格" },
|
{ label: "不合格", value: "不合格" },
|
]);
|
// 指标选项
|
const testStandardOptions = ref([]);
|
// 当前产品ID
|
const currentProductId = ref(0);
|
|
// ActionSheet选项
|
const supplierOptions = computed(() => {
|
return supplierList.value.map(item => ({
|
name: item.supplierName,
|
value: item.supplierName,
|
}));
|
});
|
|
const productSheetOptions = computed(() => {
|
return productOptions.value.map(item => ({
|
name: item.label,
|
value: item.value,
|
}));
|
});
|
|
const modelSheetOptions = computed(() => {
|
return modelOptions.value.map(item => ({
|
name: item.model,
|
value: item.id,
|
}));
|
});
|
|
const resultSheetOptions = computed(() => {
|
return resultOptions.value.map(item => ({
|
name: item.label,
|
value: item.value,
|
}));
|
});
|
|
const userSheetOptions = computed(() => {
|
return userList.value.map(item => ({
|
name: item.nickName,
|
value: item.nickName,
|
}));
|
});
|
|
const testStandardSheetOptions = computed(() => {
|
return testStandardOptions.value.map(item => ({
|
name: item.standardName || item.standardNo,
|
value: item.id,
|
}));
|
});
|
|
// 表单验证规则
|
const rules = {
|
checkTime: [{ required: true, message: "请输入", trigger: "blur" }],
|
supplier: [{ required: true, message: "请输入", trigger: "blur" }],
|
checkName: [{ required: false, message: "请输入", trigger: "blur" }],
|
productId: [{ required: true, message: "请输入", trigger: "blur" }],
|
productModelId: [
|
{ required: true, message: "请选择产品型号", trigger: "change" },
|
],
|
testStandardId: [
|
{ required: false, message: "请选择指标", trigger: "change" },
|
],
|
unit: [{ required: false, message: "请输入", trigger: "blur" }],
|
quantity: [{ required: true, message: "请输入", trigger: "blur" }],
|
checkCompany: [{ required: false, message: "请输入", trigger: "blur" }],
|
checkResult: [
|
{ required: true, message: "请选择检测结果", trigger: "change" },
|
],
|
};
|
|
// 是否为编辑模式
|
const isEdit = computed(() => {
|
const id = getPageId();
|
return !!id;
|
});
|
|
// 编辑时:productMainId 或 purchaseLedgerId 任一有值则供应商、数量置灰
|
const supplierQuantityDisabled = computed(() => {
|
const v = form.value || {};
|
return !!(v.productMainId != null || v.purchaseLedgerId != null);
|
});
|
|
// 获取页面ID
|
const getPageId = () => {
|
const pages = getCurrentPages();
|
const currentPage = pages[pages.length - 1];
|
return currentPage.options.id;
|
};
|
|
// 返回上一页
|
const goBack = () => {
|
uni.navigateBack();
|
};
|
|
// 显示日期选择器
|
const showDatePicker = () => {
|
showDate.value = true;
|
};
|
|
// 确认日期选择
|
const confirmDate = e => {
|
form.value.checkTime = dayjs(e.value).format("YYYY-MM-DD");
|
};
|
|
// 选择供应商
|
const selectSupplier = e => {
|
form.value.supplier = e.value;
|
showSupplierSheet.value = false;
|
};
|
|
// 选择产品
|
const selectProduct = e => {
|
form.value.productId = e.value;
|
form.value.productName = e.name;
|
showProductSheet.value = false;
|
getModels(e.value);
|
};
|
|
// 切换树形节点展开/折叠
|
const toggleNode = node => {
|
node.expanded = !node.expanded;
|
};
|
|
// 选择树形节点
|
const selectTreeNode = node => {
|
// 确保只选择末端节点
|
if (!node.children || node.children.length == 0) {
|
form.value.productId = node.value;
|
form.value.productName = node.label;
|
showProductTree.value = false;
|
getModels(node.value);
|
}
|
};
|
|
// 转换产品树结构
|
function convertIdToValue(data) {
|
return data.map(item => {
|
const { id, children, ...rest } = item;
|
const newItem = {
|
...rest,
|
value: id, // 将 id 改为 value
|
};
|
if (children && children.length > 0) {
|
newItem.children = convertIdToValue(children);
|
}
|
|
return newItem;
|
});
|
}
|
|
// 根据ID查找节点
|
const findNodeById = (nodes, productId) => {
|
for (let i = 0; i < nodes.length; i++) {
|
if (nodes[i].value === productId) {
|
return nodes[i].label; // 找到节点,返回该节点
|
}
|
if (nodes[i].children && nodes[i].children.length > 0) {
|
const foundNode = findNodeById(nodes[i].children, productId);
|
if (foundNode) {
|
return foundNode; // 在子节点中找到,返回该节点
|
}
|
}
|
}
|
return null; // 没有找到节点,返回null
|
};
|
|
// 选择规格型号
|
const selectModel = e => {
|
form.value.productModelId = e.value;
|
showModelSheet.value = false;
|
handleChangeModel(e.value);
|
};
|
|
// 处理型号变化
|
const handleChangeModel = value => {
|
form.value.model =
|
modelOptions.value.find(item => item.id == value)?.model || "";
|
form.value.unit =
|
modelOptions.value.find(item => item.id == value)?.unit || "";
|
};
|
|
// 选择检测结果
|
const selectResult = e => {
|
form.value.checkResult = e.value;
|
showResultSheet.value = false;
|
};
|
|
// 选择检验员
|
const selectInspector = e => {
|
form.value.checkName = e.value;
|
showInspectorSheet.value = false;
|
};
|
|
// 选择指标
|
const selectTestStandard = e => {
|
form.value.testStandardId = e.value;
|
testStandardDisplay.value = e.name;
|
showTestStandardSheet.value = false;
|
handleTestStandardChange(e.value);
|
};
|
|
// 指标选择变化处理
|
const handleTestStandardChange = testStandardId => {
|
if (!testStandardId) {
|
tableData.value = [];
|
return;
|
}
|
tableLoading.value = true;
|
getQualityTestStandardParamByTestStandardId(testStandardId)
|
.then(res => {
|
tableData.value = res.data || [];
|
})
|
.catch(error => {
|
console.error("获取标准参数失败:", error);
|
tableData.value = [];
|
})
|
.finally(() => {
|
tableLoading.value = false;
|
});
|
};
|
const openTestStandardSheet = () => {
|
console.log("openTestStandardSheet");
|
showTestStandardSheet.value = true;
|
};
|
|
// 获取供应商列表
|
const getSuppliers = () => {
|
getOptions().then(res => {
|
supplierList.value = res.data;
|
});
|
};
|
|
// 获取产品选项
|
const getProductOptions = () => {
|
return productTreeList().then(res => {
|
productOptions.value = convertIdToValue(res);
|
return productOptions.value;
|
});
|
};
|
|
// 获取用户列表
|
const getUserList = async () => {
|
try {
|
const userRes = await userListNoPage();
|
userList.value = userRes.data || [];
|
} catch (e) {
|
console.error("加载检验员列表失败", e);
|
userList.value = [];
|
}
|
};
|
|
// 获取型号列表
|
const getModels = value => {
|
form.value.productModelId = "";
|
form.value.unit = "";
|
modelOptions.value = [];
|
currentProductId.value = value;
|
form.value.productName = findNodeById(productOptions.value, value);
|
modelList({ id: value }).then(res => {
|
modelOptions.value = res;
|
});
|
if (currentProductId.value) {
|
getList();
|
}
|
};
|
|
// 获取指标列表
|
const getList = () => {
|
if (!currentProductId.value) {
|
testStandardOptions.value = [];
|
tableData.value = [];
|
return;
|
}
|
let params = {
|
productId: currentProductId.value,
|
inspectType: 0,
|
};
|
qualityInspectDetailByProductId(params).then(res => {
|
// 保存下拉框选项数据
|
testStandardOptions.value = res.data || [];
|
// 清空表格数据,等待用户选择指标
|
tableData.value = [];
|
// 清空指标选择
|
form.value.testStandardId = "";
|
testStandardDisplay.value = "";
|
});
|
};
|
|
// 获取检验参数列表(编辑模式)
|
const getQualityInspectParamList = id => {
|
qualityInspectParamInfo(id).then(res => {
|
tableData.value = res.data;
|
});
|
};
|
|
// 提交表单
|
const submitForm = async () => {
|
console.log("submitForm", form.value, tableData.value);
|
try {
|
// await formRef.value.validate();
|
if (!form.value.productModelId) {
|
showToast("请选择规格型号");
|
return;
|
}
|
if (!form.value.supplier) {
|
showToast("请选择供应商");
|
return;
|
}
|
if (!form.value.quantity) {
|
showToast("请输入数量");
|
return;
|
}
|
if (!form.value.productId) {
|
showToast("请选择产品");
|
return;
|
}
|
if (!form.value.checkResult) {
|
showToast("请选择检测结果");
|
return;
|
}
|
|
loading.value = true;
|
|
form.value.inspectType = 0;
|
if (isEdit.value) {
|
tableData.value.forEach(item => {
|
delete item.id;
|
});
|
}
|
|
const data = { ...form.value, qualityInspectParams: tableData.value };
|
data.quantity = Number(data.quantity);
|
if (isEdit.value) {
|
const res = await qualityInspectUpdate(data);
|
showToast("保存成功");
|
setTimeout(() => {
|
uni.navigateBack();
|
}, 1500);
|
} else {
|
const res = await qualityInspectAdd(data);
|
showToast("提交成功");
|
setTimeout(() => {
|
uni.navigateBack();
|
}, 1500);
|
}
|
} catch (error) {
|
console.error("表单验证失败:", error);
|
showToast("提交失败,请重试");
|
} finally {
|
loading.value = false;
|
}
|
};
|
|
// 初始化表单
|
const initForm = async () => {
|
const id = getPageId();
|
if (id) {
|
// 编辑模式,加载数据
|
// 先重置表单数据
|
form.value = {
|
checkTime: dayjs().format("YYYY-MM-DD"),
|
supplier: "",
|
checkName: "",
|
productName: "",
|
productId: "",
|
productModelId: "",
|
model: "",
|
testStandardId: "",
|
unit: "",
|
quantity: "",
|
checkCompany: "",
|
checkResult: "",
|
productMainId: null,
|
purchaseLedgerId: null,
|
};
|
testStandardOptions.value = [];
|
tableData.value = [];
|
// 先确保产品树已加载,否则编辑时产品/规格型号无法反显
|
await getProductOptions();
|
// 从本地存储获取编辑数据
|
const row = uni.getStorageSync("inspectionEditData") || {
|
id: id,
|
checkTime: "2026-03-03",
|
supplier: "上海金属材料有限公司",
|
checkName: "张三",
|
productName: "不锈钢板材",
|
productId: 1,
|
productModelId: 1,
|
model: "304",
|
testStandardId: "1",
|
unit: "kg",
|
quantity: 1000,
|
checkCompany: "第三方检测机构",
|
checkResult: "合格",
|
productMainId: null,
|
purchaseLedgerId: null,
|
};
|
// 先保存 testStandardId,避免被清空
|
const savedTestStandardId = row.testStandardId;
|
form.value = { ...row };
|
currentProductId.value = row.productId || 0;
|
// 关键:编辑时加载规格型号下拉选项,才能反显 productModelId
|
if (currentProductId.value) {
|
try {
|
const res = await modelList({ id: currentProductId.value });
|
modelOptions.value = res || [];
|
// 同步回填 model / unit
|
if (form.value.productModelId) {
|
handleChangeModel(form.value.productModelId);
|
}
|
} catch (e) {
|
console.error("加载规格型号失败", e);
|
modelOptions.value = [];
|
}
|
}
|
// 编辑模式下,先加载指标选项,然后加载参数列表
|
if (currentProductId.value) {
|
// 先加载指标选项
|
let params = {
|
productId: currentProductId.value,
|
inspectType: 0,
|
};
|
qualityInspectDetailByProductId(params).then(res => {
|
testStandardOptions.value = res.data || [];
|
// 使用 nextTick 确保选项已经渲染
|
nextTick(() => {
|
// 如果编辑数据中有 testStandardId,则设置并加载对应的参数
|
if (savedTestStandardId) {
|
// 确保类型匹配
|
const matchedOption = testStandardOptions.value.find(
|
item =>
|
item.id == savedTestStandardId ||
|
String(item.id) === String(savedTestStandardId)
|
);
|
if (matchedOption) {
|
// 确保使用匹配项的 id
|
form.value.testStandardId = matchedOption.id;
|
testStandardDisplay.value =
|
matchedOption.standardName || matchedOption.standardNo;
|
// 编辑保留原检验值,直接拉取原参数数据
|
getQualityInspectParamList(row.id);
|
} else {
|
// 如果找不到匹配项,尝试直接使用原值
|
console.warn(
|
"未找到匹配的指标选项,testStandardId:",
|
savedTestStandardId
|
);
|
form.value.testStandardId = savedTestStandardId;
|
getQualityInspectParamList(row.id);
|
}
|
} else {
|
// 否则使用旧的逻辑
|
getQualityInspectParamList(row.id);
|
}
|
});
|
});
|
}
|
// 展开产品树到当前选中的节点
|
expandProductTree(productOptions.value, row.productId);
|
} else {
|
// 新增模式,初始化表单
|
form.value = {
|
checkTime: dayjs().format("YYYY-MM-DD"),
|
supplier: "",
|
checkName: "",
|
productName: "",
|
productId: "",
|
productModelId: "",
|
model: "",
|
testStandardId: "",
|
unit: "",
|
quantity: "",
|
checkCompany: "",
|
checkResult: "",
|
productMainId: null,
|
purchaseLedgerId: null,
|
};
|
}
|
};
|
|
// 展开产品树到指定节点
|
const expandProductTree = (nodes, targetId) => {
|
for (let i = 0; i < nodes.length; i++) {
|
const node = nodes[i];
|
if (node.value === targetId) {
|
return true; // 找到目标节点
|
}
|
if (node.children && node.children.length > 0) {
|
const found = expandProductTree(node.children, targetId);
|
if (found) {
|
node.expanded = true; // 展开父节点
|
return true;
|
}
|
}
|
}
|
return false;
|
};
|
|
onMounted(() => {
|
getSuppliers();
|
getProductOptions();
|
getUserList();
|
initForm();
|
});
|
|
onShow(() => {
|
initForm();
|
});
|
</script>
|
|
<style scoped lang="scss">
|
@import "@/static/scss/form-common.scss";
|
|
.material-inspection-add {
|
min-height: 100vh;
|
background: #f8f9fa;
|
padding-bottom: 100px;
|
}
|
|
// 检验项目容器
|
.inspection-items-container {
|
padding: 20px;
|
background-color: #fff;
|
}
|
|
.steps-header {
|
display: flex;
|
justify-content: space-between;
|
align-items: center;
|
margin-bottom: 20px;
|
padding-bottom: 12px;
|
border-bottom: 1px solid #e4e7ed;
|
}
|
|
.steps-title {
|
font-size: 16px;
|
font-weight: 600;
|
color: #303133;
|
}
|
|
.steps-count {
|
font-size: 14px;
|
color: #909399;
|
}
|
|
.steps-list {
|
margin-bottom: 20px;
|
}
|
|
.exec-step-item {
|
position: relative;
|
display: flex;
|
margin-bottom: 16px;
|
padding: 16px;
|
background-color: #ffffff;
|
border: 1px solid #e4e7ed;
|
border-radius: 8px;
|
transition: all 0.3s ease;
|
box-shadow: 0 1px 4px rgba(0, 0, 0, 0.05);
|
}
|
|
.exec-step-item:hover {
|
box-shadow: 0 4px 16px rgba(0, 0, 0, 0.1);
|
border-color: #409eff;
|
transform: translateY(-1px);
|
}
|
|
.delete-btn {
|
position: absolute;
|
top: -25rpx;
|
right: -25rpx;
|
width: 50rpx;
|
height: 50rpx;
|
display: flex;
|
align-items: center;
|
justify-content: center;
|
text-align: center;
|
font-size: 20px;
|
border-radius: 50%;
|
background-color: red;
|
border: none;
|
z-index: 10;
|
}
|
|
.delete-btn:hover {
|
transform: scale(1.1);
|
box-shadow: 0 3px 6px rgba(245, 108, 108, 0.4);
|
}
|
|
.step-number {
|
display: flex;
|
align-items: center;
|
justify-content: center;
|
width: 32px;
|
height: 32px;
|
margin-right: 16px;
|
background-color: #ecf5ff;
|
color: #409eff;
|
font-size: 14px;
|
font-weight: 600;
|
border-radius: 50%;
|
flex-shrink: 0;
|
}
|
|
.step-content {
|
flex: 1;
|
min-width: 0;
|
}
|
|
.step-row {
|
display: flex;
|
align-items: flex-start;
|
margin-bottom: 12px;
|
}
|
|
.step-row:last-child {
|
margin-bottom: 0;
|
}
|
|
.step-label {
|
display: inline-block;
|
width: 80px;
|
font-size: 14px;
|
color: #606266;
|
margin-right: 12px;
|
flex-shrink: 0;
|
line-height: 36px;
|
}
|
|
.step-input {
|
flex: 1;
|
min-width: 0;
|
}
|
|
.step-input input {
|
font-size: 14px;
|
color: #303133;
|
}
|
|
.add-step-btn {
|
display: flex;
|
align-items: center;
|
justify-content: center;
|
width: 100%;
|
height: 44px;
|
line-height: 44px;
|
font-size: 14px;
|
border-radius: 8px;
|
transition: all 0.3s ease;
|
gap: 8px;
|
}
|
|
.add-step-btn:hover {
|
transform: translateY(-1px);
|
box-shadow: 0 2px 8px rgba(64, 158, 255, 0.3);
|
}
|
|
.add-step-btn text {
|
font-size: 14px;
|
}
|
|
// 底部按钮
|
.bottom-buttons {
|
position: fixed;
|
bottom: 0;
|
left: 0;
|
right: 0;
|
display: flex;
|
padding: 16px 20px;
|
background: #ffffff;
|
border-top: 1px solid #f0f0f0;
|
gap: 16px;
|
}
|
|
.bottom-btn {
|
flex: 1;
|
}
|
|
// 树形选择器样式
|
.tree-selector {
|
width: 100%;
|
max-height: 70vh;
|
background: #ffffff;
|
border-radius: 16px 16px 0 0;
|
}
|
|
.tree-header {
|
padding: 16px 20px;
|
border-bottom: 1px solid #f0f0f0;
|
text-align: center;
|
}
|
|
.tree-title {
|
font-size: 16px;
|
font-weight: 600;
|
color: #303133;
|
}
|
|
.tree-content {
|
padding: 10px 0;
|
max-height: calc(70vh - 60px);
|
overflow-y: auto;
|
}
|
|
.tree-node {
|
padding: 0 20px;
|
}
|
|
.tree-node-header {
|
display: flex;
|
align-items: center;
|
padding: 12px 0;
|
cursor: pointer;
|
}
|
|
.tree-node-icon {
|
width: 20px;
|
height: 20px;
|
margin-right: 8px;
|
color: #909399;
|
}
|
|
.tree-node-icon-placeholder {
|
width: 20px;
|
height: 20px;
|
margin-right: 8px;
|
}
|
|
.tree-node-label {
|
flex: 1;
|
font-size: 14px;
|
color: #303133;
|
}
|
|
.tree-node-check {
|
width: 20px;
|
height: 20px;
|
color: #409eff;
|
}
|
|
.tree-node-children {
|
margin-left: 28px;
|
}
|
</style>
|