Add all dashboard projects

This commit is contained in:
meswork764
2026-05-23 14:07:11 +08:00
commit ba82fbfc14
3550 changed files with 467904 additions and 0 deletions

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,298 @@
<template>
<div>
<el-card>
<div>
<el-menu mode="horizontal" :default-active="activeIndex" router>
<el-menu-item index="/QualityManagement/CheckTask/firstSpecial"
>首检专检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/processSpecial"
>序检专检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/final"
>终检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/purchaseIncoming"
>采购入库检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/salesReturn"
>销售退货检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/materialReturn"
>原材料退库检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/processReceive"
>序检收检</el-menu-item
>
</el-menu>
</div>
</el-card>
<el-card>
<div class="search-container">
<span class="show-text">工序:</span>
<el-select
v-model="process"
placeholder="请选择工序"
clearable
style="width: 150px; margin-right: 10px"
>
<el-option
v-for="item in processList"
:key="item.value"
:label="item.label"
:value="item.value"
/>
</el-select>
<span class="show-text">工位:</span>
<el-select
v-model="station"
clearable
placeholder="请选择工位"
style="width: 150px; margin-right: 10px"
>
<el-option
v-for="item in StationList"
:key="item.value"
:label="item.label"
:value="item.value"
/>
</el-select>
<span class="show-text">生产订单:</span>
<el-input
v-model="orderNo"
placeholder="请输入生产订单"
clearable
style="width: 150px; margin-right: 10px"
/>
<span class="show-text">零件编号:</span>
<el-input
v-model="partNo"
placeholder="请输入零件编号"
clearable
style="width: 150px; margin-right: 10px"
/>
<span class="show-text">操作时间:</span>
<el-date-picker
v-model="operationTime"
:clearable="false"
end-placeholder="结束时间"
format="yyyy-MM-dd"
popper-class="virtual-cell-time-picker"
range-separator="-"
start-placeholder="开始时间"
style="width: 280px; vertical-align: top"
type="datetimerange"
value-format="yyyy-MM-dd"
/>
<el-button
:disabled="loading"
icon="el-icon-search"
plain
type="primary"
@click="searchTable()"
>查询</el-button
>
</div>
<el-table
v-loading="loading"
:data="tableData"
:height="'67vh'"
border
element-loading-background="rgba(0, 0, 0, 0.2)"
element-loading-spinner="el-icon-loading"
highlight-current-row
size="mini"
style="width: 100%; margin-top: 20px"
tooltip-effect="dark"
>
<el-table-column
align="center"
label="序号"
type="index"
width="50"
fixed
/>
<el-table-column align="center" label="工位编号" width="100">
<template slot-scope="scope">
{{ scope.row.工位编号 }}
</template>
</el-table-column>
<el-table-column align="center" label="工序名称" width="100">
<template slot-scope="scope">
{{ scope.row.工序名称 }}
</template>
</el-table-column>
<el-table-column align="center" label="操作类别" width="100">
<template slot-scope="scope">
{{ scope.row.操作类别 }}
</template>
</el-table-column>
<el-table-column align="center" label="操作人" width="80">
<template slot-scope="scope">
{{ scope.row.操作人 }}
</template>
</el-table-column>
<el-table-column align="center" label="销售订单" width="80">
<template slot-scope="scope">
{{ scope.row.合同号 }}
</template>
</el-table-column>
<el-table-column align="center" label="生产订单" width="80">
<template slot-scope="scope">
{{ scope.row.订单编号 }}
</template>
</el-table-column>
<el-table-column align="center" label="物料编号" width="200">
<template slot-scope="scope">
{{ scope.row.物料编号 }}
</template>
</el-table-column>
<el-table-column align="center" label="物料名称" width="200">
<template slot-scope="scope">
{{ scope.row.物料描述 }}
</template>
</el-table-column>
<el-table-column align="center" label="操作数值" width="100">
<template slot-scope="scope">
{{ scope.row.操作数值 }}
</template>
</el-table-column>
<el-table-column align="center" label="开始时间" width="180">
<template slot-scope="scope">
{{ scope.row.开始时间 }}
</template>
</el-table-column>
<el-table-column align="center" label="结束时间" width="180">
<template slot-scope="scope">
{{ scope.row.结束时间 }}
</template>
</el-table-column>
<el-table-column align="center" label="工时(分)" width="80">
<template slot-scope="scope">
{{ scope.row.工时 }}
</template>
</el-table-column>
</el-table>
</el-card>
</div>
</template>
<script>
export default {
data() {
return {
activeTab: "form",
orderNo: "",
partNo: "",
productCode: "",
productName: "",
processName: "",
process: "",
processList: [],
station: "",
StationList: [],
operationTime: [],
loading: false,
tableData: [],
};
},
created() {
var now = new Date();
var start = new Date(
Date.UTC(now.getFullYear() - 1, now.getMonth(), now.getDate(), 0, 0, 0)
)
.toISOString()
.replace("T", " ")
.replace(".000Z", "");
var end = new Date(
Date.UTC(now.getFullYear(), now.getMonth(), now.getDate(), 23, 59, 59)
)
.toISOString()
.replace("T", " ")
.replace(".000Z", "");
this.operationTime = [start, end];
this.getProcessList();
this.getStationList();
this.searchTable();
},
computed: {
activeIndex() {
return this.$route.path;
},
},
methods: {
// 初始化获取工序信息
getProcessList() {
this.processList = [];
var Data = this.CreateData("11", "Prog_MES_LoadProcess");
this.ExecDatabase(Data).then((response) => {
for (let i = 0; i < response.data.length; i++) {
this.processList.push({
label: response.data[i].工序名称,
value: response.data[i].工艺编号,
});
}
});
},
// 初始化获取工位信息
getStationList() {
this.StationList = [];
var Data = this.CreateData("11", "Prog_MES_LoadStations");
this.ExecDatabase(Data).then((response) => {
for (let i = 0; i < response.data.length; i++) {
this.StationList.push({
label: response.data[i].OPName,
value: response.data[i].VisCode,
});
}
});
},
searchTable() {
this.loading = true;
this.tableData = [];
var param = [];
param.push(["ProcessID", this.process]);
param.push(["OPCode", this.station]);
param.push(["OrderNo", this.orderNo]);
param.push(["PartCode", this.partNo]);
param.push([
"PlanStart",
this.operationTime ? this.operationTime[0] : "",
]);
param.push(["PlanEnd", this.operationTime ? this.operationTime[1] : ""]);
param.push(["不装配", 1]);
var Data = this.CreateData(
"11",
"MES_QulityInspection_FirstCheckRecords",
param
);
this.ExecDatabase(Data)
.then((response) => {
this.loading = false;
console.log("查询结果:", response.data);
if (response.data && response.data.length !== 0) {
this.tableData = response.data;
} else {
console.log("查询结果为空");
}
})
.catch((error) => {
this.loading = false;
console.error("查询出错:", error);
});
},
},
};
</script>
<style scoped lang="scss">
.search-container {
margin-bottom: 20px;
}
</style>

View File

@@ -0,0 +1,772 @@
<template>
<div>
<el-card>
<div>
<el-menu mode="horizontal" :default-active="activeIndex" router>
<!-- <el-menu-item index="/QualityManagement/CheckTask/firstSpecial"
>首检专检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/processSpecial"
>序检专检</el-menu-item
> -->
<el-menu-item index="/QualityManagement/CheckTask/final"
>终检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/purchaseIncoming"
>采购入库检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/salesReturn"
>销售退货检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/materialReturn"
>原材料退库检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/processReceive"
>序检收检</el-menu-item
>
</el-menu>
</div>
</el-card>
<el-card>
<div class="search-container">
<span class="show-text">生产订单:</span>
<el-input
v-model="orderNo"
placeholder="请输入生产订单"
clearable
style="width: 150px; margin-right: 10px"
/>
<span class="show-text">物料名称:</span>
<el-input
v-model="partName"
placeholder="请输入物料名称"
clearable
style="width: 150px; margin-right: 10px"
/>
<span class="show-text">物料编码:</span>
<el-input
v-model="partNo"
placeholder="请输入物料编号"
clearable
style="width: 150px; margin-right: 10px"
/>
<span class="show-text">检测日期:</span>
<el-date-picker
v-model="inspectionDate"
:clearable="false"
end-placeholder="结束时间"
format="yyyy-MM-dd"
range-separator="-"
start-placeholder="开始时间"
style="width: 280px; vertical-align: top"
type="datetimerange"
value-format="yyyy-MM-dd"
/>
<!-- <span class="show-text">计划完工日期:</span>
<el-date-picker
v-model="completionTime"
:clearable="false"
end-placeholder="结束时间"
format="yyyy-MM-dd"
range-separator="-"
start-placeholder="开始时间"
style="width: 280px; vertical-align: top"
type="datetimerange"
value-format="yyyy-MM-dd"
/> -->
<br />
<br />
<span class="show-text">检测结果</span>
<el-select
v-model="inspectionResult"
clearable
style="width: 150px; margin-right: 10px"
filterable
>
<el-option label="合格" value="1" />
<el-option label="不合格" value="0" />
</el-select>
<span class="show-text">检测人:</span>
<el-select
v-model="checker"
placeholder="请选择检测人"
clearable
style="width: 150px; margin-right: 10px"
filterable
>
<el-option
v-for="item in checkerList"
:key="item.value"
:label="item.label"
:value="item.value"
/>
</el-select>
<!-- <span class="show-text">检测类别:</span>
<el-select
v-model="type"
placeholder="请选择检测类别"
clearable
style="width: 150px; margin-right: 10px"
filterable
>
<el-option
v-for="item in typeList"
:key="item.value"
:label="item.label"
:value="item.value"
/>
</el-select> -->
<el-button
:disabled="loading"
icon="el-icon-search"
plain
type="primary"
@click="searchTable()"
>查询
</el-button>
<!-- <el-button
type="success"
icon="el-icon-download"
plain
:disabled="tableData.length === 0"
@click="exportToExcel"
>导出</el-button
> -->
</div>
<el-table
v-loading="loading"
:data="tableData"
:height="'67vh'"
border
element-loading-background="rgba(0, 0, 0, 0.2)"
element-loading-spinner="el-icon-loading"
highlight-current-row
size="mini"
style="width: 100%; margin-top: 20px"
tooltip-effect="dark"
>
<el-table-column
align="center"
label="序号"
type="index"
width="50"
fixed
/>
<el-table-column
align="center"
label="生产订单"
width="80"
prop="生产订单号"
/>
<el-table-column
align="center"
label="物料名称"
width="150"
prop="名称"
/>
<el-table-column
align="center"
label="物料编码"
width="150"
prop="编码"
/>
<el-table-column
align="center"
label="数量"
width="80"
prop="数量"
/>
<el-table-column
align="center"
label="批次"
width="80"
prop="批次信息"
/>
<el-table-column label="操作" align="center" width="250">
<template slot-scope="scope">
<el-button
class="operation-btn"
type="primary"
size="mini"
@click="receiveCheck(scope.row)"
>退库检</el-button
>
</template>
</el-table-column>
</el-table>
</el-card>
<!-- 收检对话框 -->
<el-dialog
title="入库检"
:visible.sync="receiveCheckVisible"
width="60%"
style="text-align: center"
>
<el-form
ref="receiveCheckForm"
:model="receiveCheckData"
label-position="right"
label-width="140px"
size="mini"
>
<div>
<div class="info-container">
<div class="info-item">
<span class="info-label">物料名称</span>
<span class="info-value">{{ receiveCheckData.零件名称 }}</span>
</div>
<div class="info-item">
<span class="info-label">物料编码</span>
<span class="info-value">{{ receiveCheckData.零件编码 }}</span>
</div>
</div>
</div>
<div>
<div class="info-container">
<div class="info-item">
<span class="info-label">生产订单</span>
<span class="info-value">{{ receiveCheckData.订单号 }}</span>
</div>
<div class="info-item">
<span class="info-label">数量</span>
<span class="info-value">{{ receiveCheckData.数量 }}</span>
</div>
</div>
</div>
<div>
<div class="info-container">
<div class="info-item">
<span class="info-label"> 检测数量</span>
<span class="info-value">{{ receiveCheckData.数量 }}</span>
</div>
<div class="info-item">
<span class="info-label"> 合格数</span>
<el-input-number
v-model="receiveCheckData.合格数"
size="mini"
:min="0"
:max="receiveCheckData.检测数量"
style="width: 200px"
@change="handleQualifiedChange"
/>
</div>
</div>
</div>
<div>
<div class="info-container">
<div class="info-item">
<span class="info-label"> 不合格数</span>
<el-input-number
v-model="receiveCheckData.不合格数"
size="mini"
:min="0"
:max="receiveCheckData.检测数量"
style="width: 200px"
/>
</div>
<div class="info-item">
<span class="info-label"> 检验人</span>
<el-select
v-model="receiveCheckData.检测人"
placeholder="请选择检验人"
clearable
style="width: 200px"
filterable
>
<el-option
v-for="item in checkerList"
:key="item.value"
:label="item.label"
:value="item.label"
/>
</el-select>
</div>
</div>
</div>
<div>
<div class="info-container">
<div class="info-item">
<span class="info-label"> 检验时间</span>
<el-date-picker
v-model="receiveCheckData.检测时间"
type="datetime"
placeholder="选择检验时间"
format="yyyy-MM-dd HH:mm:ss"
value-format="yyyy-MM-dd HH:mm:ss"
style="width: 120px"
class="info-value"
/>
</div>
<div class="info-item">
<span class="info-label"> 检测说明</span>
<el-input
v-model="receiveCheckData.检测说明"
type="textarea"
:rows="2"
placeholder="请输入检测说明"
style="width: 120px"
class="info-value"
/>
</div>
</div>
</div>
</el-form>
<div slot="footer">
<el-button type="primary" @click="confirmReceiveCheck"> </el-button>
<el-button @click="receiveCheckVisible = false"> </el-button>
</div>
</el-dialog>
</div>
</template>
<script>
// 引入xlsx库
import * as XLSX from "xlsx";
import {posttm} from '@/api/tm'
import {getB1} from '@/api/b1s'
export default {
data() {
return {
contractNo: "",
orderNo: "",
partNo: "",
partName: "",
completionTime: "",
inspectionDate: "",
type: "",
typeList: [],
checker: "",
checkerLabel: "",
checkerList: [],
inspectionResult: "",
tableData: [],
loading: false,
selectedRow: null,
receiveCheckVisible: false,
receiveCheckData: {
// 基本信息(从行数据获取)
零件名称: "",
内部合同号: "",
零件编码: "",
计划号: "",
工序名称: "",
计划完成时间: "",
计划生产数: 0,
TaskAID: "",
// 收检数据(用户输入)
检测数量: 0,
合格数: 0,
不合格数: 0,
检测人: "",
检测时间: "",
检测说明: "",
},
};
},
created() {
this.getTypeList();
this.getCheckerList();
this.searchTable();
var now = new Date();
var start = new Date(
Date.UTC(now.getFullYear() , now.getMonth(), now.getDate())
)
.toISOString()
.replace("T", " ")
.replace(".000Z", "");
var end = new Date(
Date.UTC(now.getFullYear(), now.getMonth(), now.getDate(), 23, 59, 59)
)
.toISOString()
.replace("T", " ")
.replace(".000Z", "");
this.completionTime= [start, end];
},
computed: {
activeIndex() {
return this.$route.path;
},
},
methods: {
getTypeList() {
this.typeList = [];
var Data = this.CreateData("11", "查询字典");
this.ExecDatabase(Data).then((response) => {
for (let i = 0; i < response.data.length; i++) {
if (response.data[i].数据类别 === "检测类型") {
this.typeList.push({
label: response.data[i].词条名称,
value: response.data[i].词条编号,
});
}
}
});
},
getCheckerList() {
this.checkerList = [];
var Data = this.CreateData("11", "人员管理_人员信息查询_质检部门_查询");
this.ExecDatabase(Data).then((response) => {
for (let i = 0; i < response.data.length; i++) {
this.checkerList.push({
label: response.data[i].Personnel_Name,
value: response.data[i].Personnel_Number,
});
}
});
},
searchTable() {
// 开始加载状态,清空表格数据和选中行
this.loading = true;
this.tableData = [];
// 构建基础查询参数
var param = [];
// param.push(["合同号", this.contractNo]);
// param.push(["订单号", this.orderNo]);
// param.push(["零件编号", this.partNo]);
// param.push(["零件名称", this.partName]);
// // 添加完工日期范围参数
// param.push([
// "完工日期_Start",
// this.completionTime ? this.completionTime[0] : "",
// ]);
// param.push([
// "完工日期_End",
// this.completionTime ? this.completionTime[1] : "",
// ]);
// // 添加检测日期范围参数
// param.push([
// "检测日期_Start",
// this.inspectionDate ? this.inspectionDate[0] : "",
// ]);
// param.push([
// "检测日期_End",
// this.inspectionDate ? this.inspectionDate[1] : "",
// ]);
// param.push(["检测结果", this.inspectionResult]);
// const selectedChecker = this.checkerList.find(
// (item) => item.value === this.checker
// );
// param.push(["检测人", selectedChecker ? selectedChecker.label : ""]);
// param.push(["检测类别", this.type]);
// 调用封装方法生成请求数据 - 使用新的存储过程名称
var Data = this.CreateData(
"11",
"质量管理_原材料退库_查询",
param
);
// 执行数据库请求
this.ExecDatabase(Data)
.then((response) => {
this.loading = false;
console.log(response.data);
if (response.data && response.data.length !== 0) {
this.tableData = response.data;
} else {
this.tableData = [];
this.$message.info("未查询到相关数据");
}
})
.catch((error) => {
this.loading = false;
console.error("查询失败:", error);
this.$message.error("查询失败");
});
},
receiveCheck(row) {
// 打开收检对话框并填充数据
this.receiveCheckVisible = true;
// 从行数据填充基本信息
this.receiveCheckData = {
// 基本信息(从行数据获取)
零件编码: row.编码 || "",
零件名称: row.名称 || "",
订单号: row.生产订单号 || "",
数量:row.数量,
检测数量:row.数量,
id:row.id
};
console.log(this.receiveCheckData);
},
handleQualifiedChange(value) {
// 自动计算不合格数
console.log(this.receiveCheckData.检测数量)
this.receiveCheckData.不合格数 = this.receiveCheckData.检测数量 - value;
},
confirmReceiveCheck() {
// 验证表单
if (
!this.receiveCheckData.检测数量 ||
this.receiveCheckData.检测数量 <= 0
) {
this.$message.warning("请输入有效的检测数量");
return;
}
if (!this.receiveCheckData.检测人) {
this.$message.warning("请选择检验人");
return;
}
if (!this.receiveCheckData.检测时间) {
this.$message.warning("请选择检验时间");
return;
}
// 调用存储过程保存数据
this.saveReceiveCheck();
},
transformData(rawArray) {
// 先转成对象便于取值
const map = {};
for (const [key, value] of rawArray) {
map[key] = value;
}
const taskItemsArray = map.task_items;
const taskMap = {};
for (const [k, v] of taskItemsArray) {
taskMap[k] = v;
}
const materialsArray = taskMap.task_materials_items;
const materialsMap = {};
for (const [k, v] of materialsArray) {
materialsMap[k] = v;
}
return {
doc_date: map.doc_date, // 或 new Date().toISOString().split('T')[0]
doc_type: map.doc_type,
external_num: taskMap.external_num,
udf8:map.udf8,
task_items: [
{
base_line_num :taskMap.base_line_num,
base_entry :taskMap.base_entry,
base_type: taskMap.base_type,
external_num: taskMap.external_num,
item_code: taskMap.item_code,
item_name: taskMap.item_name,
whs_code: '', // 原值被清空
manage_type: taskMap.manage_type,
price: taskMap.price,
quantity: taskMap.quantity,
task_materials_items: [
{
item_code: taskMap.item_code, // 新增:继承 item_code
batch_number: '', // 原 null 改为空字符串
quantity: materialsMap.quantity
}
]
}
]
};
},
// 如果需要转成 JSON 字符串
async saveReceiveCheck() {
var param = [];
var param2 = [];
var param3 = [];
param.push(["doc_date", this.completionTime[0]]);
param.push(["doc_type", "202-60"]);
param.push(["udf8", this.receiveCheckData.id]);
param.push(["external_num", this.receiveCheckData.订单号.toString()]);
param.push(["task_items", param2]);
param2.push(["base_type", "202"]);
param2.push(["external_num", this.receiveCheckData.订单号.toString()])
param2.push(["item_code", this.receiveCheckData.零件编码]);
param2.push(["item_name", this.receiveCheckData.零件名称]);
param2.push(["whs_code", ""]);
param2.push(["manage_type", 'B']);
param2.push(["price", 0]);
param2.push(["quantity", this.receiveCheckData.合格数]);
param2.push(["task_materials_items", param3]);
param3.push(["item_code", this.receiveCheckData.零件编码]);
param3.push(["batch_number", ""]);
param3.push(["quantity", this.receiveCheckData.合格数]);
var LineNumber = ''
var result3 = await getB1("/ProductionOrders",{
"$filter":"AbsoluteEntry eq "+ this.receiveCheckData.订单号
})
result3.data.value[0].ProductionOrderLines.forEach(element => {
if (element.ItemNo == this.receiveCheckData.零件编码){
LineNumber = element.LineNumber
}
});
param2.push(["base_line_num", LineNumber]);
param2.push(["base_entry", this.receiveCheckData.订单号]);
const result = this.transformData(param);
// const jsonString = JSON.stringify(result, null, 2);
// console.log(jsonString);
const result2 = await posttm('/stocktask/task/receiptordertask',result)
console.log(result2)
this.receiveCheckVisible =false
},
formatDateTime(date) {
const year = date.getFullYear();
const month = String(date.getMonth() + 1).padStart(2, "0");
const day = String(date.getDate()).padStart(2, "0");
const hours = String(date.getHours()).padStart(2, "0");
const minutes = String(date.getMinutes()).padStart(2, "0");
const seconds = String(date.getSeconds()).padStart(2, "0");
return `${year}-${month}-${day} ${hours}:${minutes}:${seconds}`;
},
// 导出Excel功能
exportToExcel() {
if (this.tableData.length === 0) {
this.$message.warning("没有数据可导出");
return;
}
try {
// 准备导出数据
const exportData = this.tableData.map((item, index) => {
return {
序号: index + 1,
合同号: item.内部合同号 || "",
订单编号: item.计划号 || "",
零件名称: item.零件名称 || "",
零件编码: item.零件编码 || "",
工序名称: item.工序名称 || "",
计划生产数: item.计划生产数 || 0,
检验数量: item.检验数量 || 0,
检验合格数量: item.合格数 || 0,
检验不合格数量: item.不合格数 || 0,
检验操作人: item.检测人 || "",
检验时间: item.检测时间 || "",
};
});
// 创建工作簿
const wb = XLSX.utils.book_new();
// 创建工作表
const ws = XLSX.utils.json_to_sheet(exportData);
// 设置列宽
const colWidth = [
{ wch: 8 }, // 序号
{ wch: 15 }, // 合同号
{ wch: 15 }, // 订单编号
{ wch: 20 }, // 零件名称
{ wch: 15 }, // 零件编码
{ wch: 12 }, // 工序名称
{ wch: 12 }, // 计划生产数
{ wch: 10 }, // 检验数量
{ wch: 15 }, // 检验合格数量
{ wch: 15 }, // 检验不合格数量
{ wch: 12 }, // 检验操作人
{ wch: 20 }, // 检验时间
];
ws["!cols"] = colWidth;
// 将工作表添加到工作簿
XLSX.utils.book_append_sheet(wb, ws, "序检收检记录");
// 生成文件名(包含当前时间)
const fileName = `序检收检记录_${this.formatDateForFileName(
new Date()
)}.xlsx`;
// 导出文件
XLSX.writeFile(wb, fileName);
this.$message.success("导出成功");
} catch (error) {
console.error("导出失败:", error);
this.$message.error("导出失败");
}
},
// 格式化日期用于文件名
formatDateForFileName(date) {
const year = date.getFullYear();
const month = String(date.getMonth() + 1).padStart(2, "0");
const day = String(date.getDate()).padStart(2, "0");
const hours = String(date.getHours()).padStart(2, "0");
const minutes = String(date.getMinutes()).padStart(2, "0");
const seconds = String(date.getSeconds()).padStart(2, "0");
return `${year}${month}${day}_${hours}${minutes}${seconds}`;
},
},
};
</script>
<style>
.search-container {
margin-bottom: 20px;
}
.show-text {
margin-right: 5px;
line-height: 32px;
}
.operation-cell {
display: flex;
justify-content: space-between;
width: 100%;
}
.operation-btn {
flex: 1;
margin: 0 5px;
padding: 0;
min-width: 0;
}
.active {
color: skyblue;
margin-left: 5px;
}
.info-container {
border: 1px solid #ccc;
display: flex;
}
.info-item {
display: flex;
flex: 1;
border-right: 1px solid #ccc;
}
.info-item:last-child {
border-right: none;
}
.info-label {
width: 30%;
padding: 8px;
background-color: #f5f7fa;
border-right: 1px solid #ccc;
}
.info-value {
flex: 1;
padding: 5px;
}
.info-label,
.info-value {
display: flex;
align-items: center;
}
</style>

View File

@@ -0,0 +1,770 @@
<template>
<div>
<el-card>
<div>
<el-menu mode="horizontal" :default-active="activeIndex" router>
<!-- <el-menu-item index="/QualityManagement/CheckTask/firstSpecial"
>首检专检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/processSpecial"
>序检专检</el-menu-item
> -->
<el-menu-item index="/QualityManagement/CheckTask/final"
>终检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/purchaseIncoming"
>采购入库检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/salesReturn"
>销售退货检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/materialReturn"
>原材料退库检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/processReceive"
>序检收检</el-menu-item
>
</el-menu>
</div>
</el-card>
<el-card>
<div class="search-container">
<span class="show-text">生产订单:</span>
<el-input
v-model="orderNo"
placeholder="请输入生产订单"
clearable
style="width: 150px; margin-right: 10px"
/>
<span class="show-text">物料名称:</span>
<el-input
v-model="partName"
placeholder="请输入物料名称"
clearable
style="width: 150px; margin-right: 10px"
/>
<span class="show-text">物料编码:</span>
<el-input
v-model="partNo"
placeholder="请输入物料编号"
clearable
style="width: 150px; margin-right: 10px"
/>
<!-- <span class="show-text">检测日期:</span>
<el-date-picker
v-model="inspectionDate"
:clearable="false"
end-placeholder="结束时间"
format="yyyy-MM-dd"
range-separator="-"
start-placeholder="开始时间"
style="width: 280px; vertical-align: top"
type="datetimerange"
value-format="yyyy-MM-dd"
/> -->
<!-- <span class="show-text">计划完工日期:</span>
<el-date-picker
v-model="completionTime"
:clearable="false"
end-placeholder="结束时间"
format="yyyy-MM-dd"
range-separator="-"
start-placeholder="开始时间"
style="width: 280px; vertical-align: top"
type="datetimerange"
value-format="yyyy-MM-dd"
/> -->
<!-- <br />
<br /> -->
<!-- <span class="show-text">检测结果</span>
<el-select
v-model="inspectionResult"
clearable
style="width: 150px; margin-right: 10px"
filterable
>
<el-option label="合格" value="1" />
<el-option label="不合格" value="0" />
</el-select>
<span class="show-text">检测人:</span>
<el-select
v-model="checker"
placeholder="请选择检测人"
clearable
style="width: 150px; margin-right: 10px"
filterable
>
<el-option
v-for="item in checkerList"
:key="item.value"
:label="item.label"
:value="item.value"
/>
</el-select> -->
<!-- <span class="show-text">检测类别:</span>
<el-select
v-model="type"
placeholder="请选择检测类别"
clearable
style="width: 150px; margin-right: 10px"
filterable
>
<el-option
v-for="item in typeList"
:key="item.value"
:label="item.label"
:value="item.value"
/>
</el-select> -->
<el-button
:disabled="loading"
icon="el-icon-search"
plain
type="primary"
@click="searchTable()"
>查询
</el-button>
<!-- <el-button
type="success"
icon="el-icon-download"
plain
:disabled="tableData.length === 0"
@click="exportToExcel"
>导出</el-button
> -->
</div>
<el-table
v-loading="loading"
:data="tableData"
:height="'67vh'"
border
element-loading-background="rgba(0, 0, 0, 0.2)"
element-loading-spinner="el-icon-loading"
highlight-current-row
size="mini"
style="width: 100%; margin-top: 20px"
tooltip-effect="dark"
>
<el-table-column
align="center"
label="序号"
type="index"
width="50"
fixed
/>
<!-- <el-table-column
align="center"
label="销售订单"
width="100"
prop="内部合同号"
/> -->
<el-table-column
align="center"
label="生产订单"
width="100"
prop="计划号"
/>
<el-table-column
align="center"
label="物料名称"
width="100"
prop="零件名称"
/>
<el-table-column
align="center"
label="物料编码"
width="100"
prop="零件编码"
/>
<el-table-column
align="center"
label="工序名称"
width="120"
prop="工序名称"
/>
<el-table-column
align="center"
label="工位名称"
width="120"
prop="工位名称"
/>
<el-table-column
align="center"
label="完成数量"
width="100"
prop="完成数量"
/>
<el-table-column
align="center"
label="检验数量"
width="120"
prop="检验数量"
/>
<el-table-column
align="center"
label="检验合格数量"
width="110"
prop="合格数"
/>
<el-table-column
align="center"
label="检验不合格数量"
width="120"
prop="不合格数"
/>
<el-table-column
align="center"
label="检验操作人"
width="130"
prop="检测人"
/>
<el-table-column
align="center"
label="检验时间"
width="180"
prop="检测时间"
/>
<el-table-column
align="center"
label="检测说明"
width="180"
prop="检测说明"
/>
<el-table-column label="操作" align="center" width="250" fixed="right">
<template slot-scope="scope">
<el-button
class="operation-btn"
type="primary"
size="mini"
@click="receiveCheck(scope.row)"
>收检</el-button
>
</template>
</el-table-column>
</el-table>
</el-card>
<!-- 收检对话框 -->
<el-dialog
title="收检"
:visible.sync="receiveCheckVisible"
width="60%"
style="text-align: center"
>
<el-form
ref="receiveCheckForm"
:model="receiveCheckData"
label-position="right"
label-width="140px"
size="mini"
>
<div>
<div class="info-container">
<div class="info-item">
<span class="info-label">物料名称</span>
<span class="info-value">{{ receiveCheckData.零件名称 }}</span>
</div>
<div class="info-item">
<span class="info-label">销售订单</span>
<span class="info-value">{{ receiveCheckData.内部合同号 }}</span>
</div>
</div>
</div>
<div>
<div class="info-container">
<div class="info-item">
<span class="info-label">物料编码</span>
<span class="info-value">{{ receiveCheckData.零件编码 }}</span>
</div>
<div class="info-item">
<span class="info-label">生产订单</span>
<span class="info-value">{{ receiveCheckData.计划号 }}</span>
</div>
</div>
</div>
<div>
<div class="info-container">
<div class="info-item">
<span class="info-label">工序名称</span>
<span class="info-value">{{ receiveCheckData.工序名称 }}</span>
</div>
<div class="info-item">
<span class="info-label">完成数量</span>
<span class="info-value">{{ receiveCheckData.完成数量 }}</span>
</div>
</div>
</div>
<div>
<div class="info-container">
<div class="info-item">
<span class="info-label"> 未检测数量</span>
<span class="info-value">{{ receiveCheckData.完成数量 - receiveCheckData.检测数量 }}</span>
</div>
<div class="info-item">
<span class="info-label"> 合格数</span>
<el-input-number
v-model="receiveCheckData.合格数"
size="mini"
:min="0"
:max="receiveCheckData.完成数量 - receiveCheckData.检测数量"
style="width: 200px"
@change="handleQualifiedChange"
/>
</div>
</div>
</div>
<div>
<div class="info-container">
<div class="info-item">
<span class="info-label"> 不合格数</span>
<span class="info-value">{{ receiveCheckData.不合格数 }}</span>
</div>
<div class="info-item">
<span class="info-label"> 检验人</span>
<el-select
v-model="receiveCheckData.检测人"
placeholder="请选择检验人"
clearable
style="width: 200px"
filterable
>
<el-option
v-for="item in checkerList"
:key="item.value"
:label="item.label"
:value="item.label"
/>
</el-select>
</div>
</div>
</div>
<div>
<div class="info-container">
<div class="info-item">
<span class="info-label"> 检验时间</span>
<el-date-picker
v-model="receiveCheckData.检测时间"
type="datetime"
placeholder="选择检验时间"
format="yyyy-MM-dd HH:mm:ss"
value-format="yyyy-MM-dd HH:mm:ss"
style="width: 120px"
class="info-value"
/>
</div>
<div class="info-item">
<span class="info-label"> 检测说明</span>
<el-input
v-model="receiveCheckData.检测说明"
type="textarea"
:rows="2"
placeholder="请输入检测说明"
style="width: 120px"
class="info-value"
/>
</div>
</div>
</div>
</el-form>
<div slot="footer">
<el-button type="primary" @click="confirmReceiveCheck"> </el-button>
<el-button @click="receiveCheckVisible = false"> </el-button>
</div>
</el-dialog>
</div>
</template>
<script>
// 引入xlsx库
import * as XLSX from "xlsx";
export default {
data() {
return {
contractNo: "",
orderNo: "",
partNo: "",
partName: "",
completionTime: "",
inspectionDate: "",
type: "",
typeList: [],
checker: "",
checkerLabel: "",
checkerList: [],
inspectionResult: "",
tableData: [],
loading: false,
selectedRow: null,
receiveCheckVisible: false,
receiveCheckData: {
// 基本信息(从行数据获取)
零件名称: "",
内部合同号: "",
零件编码: "",
计划号: "",
工序名称: "",
计划完成时间: "",
计划生产数: 0,
TaskAID: "",
// 收检数据(用户输入)
检测数量: 0,
合格数: 0,
不合格数: 0,
检测人: "",
检测时间: "",
检测说明: "",
},
};
},
created() {
this.getTypeList();
this.getCheckerList();
this.searchTable();
},
computed: {
activeIndex() {
return this.$route.path;
},
},
methods: {
getTypeList() {
this.typeList = [];
var Data = this.CreateData("11", "查询字典");
this.ExecDatabase(Data).then((response) => {
for (let i = 0; i < response.data.length; i++) {
if (response.data[i].数据类别 === "检测类型") {
this.typeList.push({
label: response.data[i].词条名称,
value: response.data[i].词条编号,
});
}
}
});
},
getCheckerList() {
this.checkerList = [];
var Data = this.CreateData("11", "人员管理_人员信息查询_质检部门_查询");
this.ExecDatabase(Data).then((response) => {
for (let i = 0; i < response.data.length; i++) {
this.checkerList.push({
label: response.data[i].Personnel_Name,
value: response.data[i].Personnel_Number,
});
}
});
},
searchTable() {
// 开始加载状态,清空表格数据和选中行
this.loading = true;
this.tableData = [];
// 构建基础查询参数
var param = [];
param.push(["合同号", this.contractNo]);
param.push(["订单号", this.orderNo]);
param.push(["零件编号", this.partNo]);
param.push(["零件名称", this.partName]);
// 添加完工日期范围参数
param.push([
"完工日期_Start",
this.completionTime ? this.completionTime[0] : "",
]);
param.push([
"完工日期_End",
this.completionTime ? this.completionTime[1] : "",
]);
// 添加检测日期范围参数
param.push([
"检测日期_Start",
this.inspectionDate ? this.inspectionDate[0] : "",
]);
param.push([
"检测日期_End",
this.inspectionDate ? this.inspectionDate[1] : "",
]);
param.push(["检测结果", this.inspectionResult]);
const selectedChecker = this.checkerList.find(
(item) => item.value === this.checker
);
param.push(["检测人", selectedChecker ? selectedChecker.label : ""]);
param.push(["检测类别", this.type]);
// 调用封装方法生成请求数据 - 使用新的存储过程名称
var Data = this.CreateData(
"11",
"质量管理_质量检验_收检记录_查询",
param
);
// 执行数据库请求
this.ExecDatabase(Data)
.then((response) => {
this.loading = false;
console.log(response.data);
if (response.data && response.data.length !== 0) {
this.tableData = response.data;
} else {
this.tableData = [];
this.$message.info("未查询到相关数据");
}
})
.catch((error) => {
this.loading = false;
console.error("查询失败:", error);
this.$message.error("查询失败");
});
},
receiveCheck(row) {
// 打开收检对话框并填充数据
this.receiveCheckVisible = true;
// 从行数据填充基本信息
this.receiveCheckData = {
// 基本信息(从行数据获取)
零件名称: row.零件名称 || "",
内部合同号: row.内部合同号 || "",
零件编码: row.零件编码 || "",
计划号: row.计划号 || "",
工序名称: row.工序名称 || "",
计划生产数: row.计划生产数 || 0,
TaskAID: row.TaskAID || "",
// 收检数据(用户输入)
检测数量: row.检验数量 || 0,
完成数量: row.完成数量 || 0,
合格数: 0,
不合格数: row.完成数量 - row.检验数量 || 0,
检测人: row.检测人 || "",
检测时间: this.formatDateTime(new Date()),
检测说明: "",
};
console.log(this.receiveCheckData);
},
handleQualifiedChange(value) {
// 自动计算不合格数
this.receiveCheckData.不合格数 = this.receiveCheckData.完成数量-this.receiveCheckData.检测数量 - value;
},
confirmReceiveCheck() {
// 验证表单
if (
this.receiveCheckData.完成数量-this.receiveCheckData.检测数量 <= 0
) {
this.$message.warning("请输入有效的检测数量");
return;
}
if (!this.receiveCheckData.检测人) {
this.$message.warning("请选择检验人");
return;
}
if (!this.receiveCheckData.检测时间) {
this.$message.warning("请选择检验时间");
return;
}
// 调用存储过程保存数据
this.saveReceiveCheck();
},
saveReceiveCheck() {
var param = [];
param.push(["TaskAID", this.receiveCheckData.TaskAID || ""]);
param.push(["检测类型编号", 6]);
param.push(["质检类型", "收检"]);
param.push(["零件名称", this.receiveCheckData.零件名称]);
param.push(["内部合同号", this.receiveCheckData.内部合同号]);
param.push(["零件编码", this.receiveCheckData.零件编码]);
param.push(["计划号", this.receiveCheckData.计划号]);
param.push(["工序名称", this.receiveCheckData.工序名称]);
param.push(["检测数量", this.receiveCheckData.完成数量-this.receiveCheckData.检测数量]);
param.push(["合格数", this.receiveCheckData.合格数]);
param.push(["不合格数", this.receiveCheckData.不合格数]);
param.push(["检测人", this.receiveCheckData.检测人]);
param.push(["检测时间", this.receiveCheckData.检测时间]);
param.push(["检测说明", this.receiveCheckData.检测说明]);
console.log(param);
var Data = this.CreateData("12", "质量管理_序检收检_新增", param);
this.ExecDatabase(Data)
.then((response) => {
if (
response.data &&
response.data[0] &&
response.data[0].result === "1"
) {
this.$message.success("收检操作成功");
this.receiveCheckVisible = false;
// 刷新表格数据
this.searchTable();
} else {
this.$message.error("收检操作失败");
}
})
.catch((error) => {
console.error("收检操作失败:", error);
this.$message.error("收检操作失败");
});
},
formatDateTime(date) {
const year = date.getFullYear();
const month = String(date.getMonth() + 1).padStart(2, "0");
const day = String(date.getDate()).padStart(2, "0");
const hours = String(date.getHours()).padStart(2, "0");
const minutes = String(date.getMinutes()).padStart(2, "0");
const seconds = String(date.getSeconds()).padStart(2, "0");
return `${year}-${month}-${day} ${hours}:${minutes}:${seconds}`;
},
// 导出Excel功能
exportToExcel() {
if (this.tableData.length === 0) {
this.$message.warning("没有数据可导出");
return;
}
try {
// 准备导出数据
const exportData = this.tableData.map((item, index) => {
return {
序号: index + 1,
合同号: item.内部合同号 || "",
订单编号: item.计划号 || "",
零件名称: item.零件名称 || "",
零件编码: item.零件编码 || "",
工序名称: item.工序名称 || "",
计划生产数: item.计划生产数 || 0,
检验数量: item.检验数量 || 0,
检验合格数量: item.合格数 || 0,
检验不合格数量: item.不合格数 || 0,
检验操作人: item.检测人 || "",
检验时间: item.检测时间 || "",
};
});
// 创建工作簿
const wb = XLSX.utils.book_new();
// 创建工作表
const ws = XLSX.utils.json_to_sheet(exportData);
// 设置列宽
const colWidth = [
{ wch: 8 }, // 序号
{ wch: 15 }, // 合同号
{ wch: 15 }, // 订单编号
{ wch: 20 }, // 零件名称
{ wch: 15 }, // 零件编码
{ wch: 12 }, // 工序名称
{ wch: 12 }, // 计划生产数
{ wch: 10 }, // 检验数量
{ wch: 15 }, // 检验合格数量
{ wch: 15 }, // 检验不合格数量
{ wch: 12 }, // 检验操作人
{ wch: 20 }, // 检验时间
];
ws["!cols"] = colWidth;
// 将工作表添加到工作簿
XLSX.utils.book_append_sheet(wb, ws, "序检收检记录");
// 生成文件名(包含当前时间)
const fileName = `序检收检记录_${this.formatDateForFileName(
new Date()
)}.xlsx`;
// 导出文件
XLSX.writeFile(wb, fileName);
this.$message.success("导出成功");
} catch (error) {
console.error("导出失败:", error);
this.$message.error("导出失败");
}
},
// 格式化日期用于文件名
formatDateForFileName(date) {
const year = date.getFullYear();
const month = String(date.getMonth() + 1).padStart(2, "0");
const day = String(date.getDate()).padStart(2, "0");
const hours = String(date.getHours()).padStart(2, "0");
const minutes = String(date.getMinutes()).padStart(2, "0");
const seconds = String(date.getSeconds()).padStart(2, "0");
return `${year}${month}${day}_${hours}${minutes}${seconds}`;
},
},
};
</script>
<style>
.search-container {
margin-bottom: 20px;
}
.show-text {
margin-right: 5px;
line-height: 32px;
}
.operation-cell {
display: flex;
justify-content: space-between;
width: 100%;
}
.operation-btn {
flex: 1;
margin: 0 5px;
padding: 0;
min-width: 0;
}
.active {
color: skyblue;
margin-left: 5px;
}
.info-container {
border: 1px solid #ccc;
display: flex;
}
.info-item {
display: flex;
flex: 1;
border-right: 1px solid #ccc;
}
.info-item:last-child {
border-right: none;
}
.info-label {
width: 30%;
padding: 8px;
background-color: #f5f7fa;
border-right: 1px solid #ccc;
}
.info-value {
flex: 1;
padding: 5px;
}
.info-label,
.info-value {
display: flex;
align-items: center;
}
</style>

View File

@@ -0,0 +1,62 @@
<template>
<div>
<el-card>
<div>
<el-menu mode="horizontal" :default-active="activeIndex" router>
<el-menu-item index="/QualityManagement/CheckTask/firstSpecial"
>首检专检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/processSpecial"
>序检专检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/final"
>终检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/purchaseIncoming"
>采购入库检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/salesReturn"
>销售退货检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/materialReturn"
>原材料退库检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/processReceive"
>序检收检</el-menu-item
>
</el-menu>
</div>
</el-card>
</div>
</template>
</template>
<script>
export default {};
</script>
<style>
.search-container {
margin-bottom: 20px;
}
.show-text {
margin-right: 5px;
line-height: 32px;
}
.operation-cell {
display: flex;
justify-content: space-between;
width: 100%;
}
.operation-btn {
flex: 1;
margin: 0 5px;
padding: 0;
min-width: 0;
}
.active {
color: skyblue;
margin-left: 5px;
}
</style>

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,726 @@
<template>
<div>
<el-card>
<div>
<el-menu mode="horizontal" :default-active="activeIndex" router>
<!-- <el-menu-item index="/QualityManagement/CheckTask/firstSpecial"
>首检专检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/processSpecial"
>序检专检</el-menu-item
> -->
<el-menu-item index="/QualityManagement/CheckTask/final"
>终检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/purchaseIncoming"
>采购入库检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/salesReturn"
>销售退货检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/materialReturn"
>原材料退库检</el-menu-item
>
<el-menu-item index="/QualityManagement/CheckTask/processReceive"
>序检收检</el-menu-item
>
</el-menu>
</div>
</el-card>
<el-card>
<div class="search-container">
<span class="show-text">生产订单:</span>
<el-input
v-model="orderNo"
placeholder="请输入生产订单"
clearable
style="width: 150px; margin-right: 10px"
/>
<span class="show-text">物料名称:</span>
<el-input
v-model="partName"
placeholder="请输入物料名称"
clearable
style="width: 150px; margin-right: 10px"
/>
<span class="show-text">物料编码:</span>
<el-input
v-model="partNo"
placeholder="请输入物料编号"
clearable
style="width: 150px; margin-right: 10px"
/>
<span class="show-text">检测日期:</span>
<el-date-picker
v-model="inspectionDate"
:clearable="false"
end-placeholder="结束时间"
format="yyyy-MM-dd"
range-separator="-"
start-placeholder="开始时间"
style="width: 280px; vertical-align: top"
type="datetimerange"
value-format="yyyy-MM-dd"
/>
<!-- <span class="show-text">计划完工日期:</span>
<el-date-picker
v-model="completionTime"
:clearable="false"
end-placeholder="结束时间"
format="yyyy-MM-dd"
range-separator="-"
start-placeholder="开始时间"
style="width: 280px; vertical-align: top"
type="datetimerange"
value-format="yyyy-MM-dd"
/> -->
<br />
<br />
<span class="show-text">检测结果</span>
<el-select
v-model="inspectionResult"
clearable
style="width: 150px; margin-right: 10px"
filterable
>
<el-option label="合格" value="1" />
<el-option label="不合格" value="0" />
</el-select>
<span class="show-text">检测人:</span>
<el-select
v-model="checker"
placeholder="请选择检测人"
clearable
style="width: 150px; margin-right: 10px"
filterable
>
<el-option
v-for="item in checkerList"
:key="item.value"
:label="item.label"
:value="item.value"
/>
</el-select>
<!-- <span class="show-text">检测类别:</span>
<el-select
v-model="type"
placeholder="请选择检测类别"
clearable
style="width: 150px; margin-right: 10px"
filterable
>
<el-option
v-for="item in typeList"
:key="item.value"
:label="item.label"
:value="item.value"
/>
</el-select> -->
<el-button
:disabled="loading"
icon="el-icon-search"
plain
type="primary"
@click="searchTable()"
>查询
</el-button>
<!-- <el-button
type="success"
icon="el-icon-download"
plain
:disabled="tableData.length === 0"
@click="exportToExcel"
>导出</el-button
> -->
</div>
<el-table
v-loading="loading"
:data="tableData"
:height="'67vh'"
border
element-loading-background="rgba(0, 0, 0, 0.2)"
element-loading-spinner="el-icon-loading"
highlight-current-row
size="mini"
style="width: 100%; margin-top: 20px"
tooltip-effect="dark"
>
<el-table-column
align="center"
label="序号"
type="index"
width="50"
fixed
/>
<el-table-column
align="center"
label="生产订单"
width="80"
prop="订单编号"
/>
<el-table-column
align="center"
label="物料名称"
width="150"
prop="物料名称"
/>
<el-table-column
align="center"
label="物料编码"
width="150"
prop="物料编码"
/>
<!-- <el-table-column
align="center"
label="采购数"
width="80"
prop="计划生产数"
/> -->
<el-table-column
align="center"
label="检验数量"
width="80"
prop="入库数量"
/>
<el-table-column
align="center"
label="合格数"
width="80"
prop="合格数"
/>
<el-table-column
align="center"
label="不合格数"
width="80"
prop="不合格数"
/>
<el-table-column
align="center"
label="检验人"
width="100"
prop="检测人"
/>
<el-table-column
align="center"
label="检验时间"
width="150"
prop="检验时间"
/>
<el-table-column label="操作" align="center" width="250">
<template slot-scope="scope">
<el-button
class="operation-btn"
type="primary"
size="mini"
@click="receiveCheck(scope.row)"
>入库检</el-button
>
</template>
</el-table-column>
</el-table>
</el-card>
<!-- 收检对话框 -->
<el-dialog
title="入库检"
:visible.sync="receiveCheckVisible"
width="60%"
style="text-align: center"
>
<el-form
ref="receiveCheckForm"
:model="receiveCheckData"
label-position="right"
label-width="140px"
size="mini"
>
<div>
<div class="info-container">
<div class="info-item">
<span class="info-label">物料名称</span>
<span class="info-value">{{ receiveCheckData.零件名称 }}</span>
</div>
<div class="info-item">
<span class="info-label">物料编码</span>
<span class="info-value">{{ receiveCheckData.零件编码 }}</span>
</div>
</div>
</div>
<div>
<div class="info-container">
<div class="info-item">
<span class="info-label">生产订单</span>
<span class="info-value">{{ receiveCheckData.计划号 }}</span>
</div>
<div class="info-item">
<span class="info-label">采购数</span>
<span class="info-value">{{ receiveCheckData.计划生产数 }}</span>
</div>
</div>
</div>
<div>
<div class="info-container">
<div class="info-item">
<span class="info-label"> 检测数量</span>
<span class="info-value">{{ receiveCheckData.检测数量 }}</span>
</div>
<div class="info-item">
<span class="info-label"> 合格数</span>
<el-input-number
v-model="receiveCheckData.合格数"
size="mini"
:min="0"
:max="receiveCheckData.检测数量"
style="width: 200px"
@change="handleQualifiedChange"
/>
</div>
</div>
</div>
<div>
<div class="info-container">
<div class="info-item">
<span class="info-label"> 不合格数</span>
<span class="info-value">{{ receiveCheckData.不合格数 }}</span>
</div>
<div class="info-item">
<span class="info-label"> 检验人</span>
<el-select
v-model="receiveCheckData.检测人"
placeholder="请选择检验人"
clearable
style="width: 200px"
filterable
>
<el-option
v-for="item in checkerList"
:key="item.value"
:label="item.label"
:value="item.label"
/>
</el-select>
</div>
</div>
</div>
<div>
<div class="info-container">
<div class="info-item">
<span class="info-label"> 检验时间</span>
<el-date-picker
v-model="receiveCheckData.检测时间"
type="datetime"
placeholder="选择检验时间"
format="yyyy-MM-dd HH:mm:ss"
value-format="yyyy-MM-dd HH:mm:ss"
style="width: 120px"
class="info-value"
/>
</div>
<div class="info-item">
<span class="info-label"> 检测说明</span>
<el-input
v-model="receiveCheckData.检测说明"
type="textarea"
:rows="2"
placeholder="请输入检测说明"
style="width: 120px"
class="info-value"
/>
</div>
</div>
</div>
</el-form>
<div slot="footer">
<el-button type="primary" @click="confirmReceiveCheck"> </el-button>
<el-button @click="receiveCheckVisible = false"> </el-button>
</div>
</el-dialog>
</div>
</template>
<script>
// 引入xlsx库
import * as XLSX from "xlsx";
export default {
data() {
return {
contractNo: "",
orderNo: "",
partNo: "",
partName: "",
completionTime: "",
inspectionDate: "",
type: "",
typeList: [],
checker: "",
checkerLabel: "",
checkerList: [],
inspectionResult: "",
tableData: [],
loading: false,
selectedRow: null,
receiveCheckVisible: false,
receiveCheckData: {
// 基本信息(从行数据获取)
零件名称: "",
内部合同号: "",
零件编码: "",
计划号: "",
工序名称: "",
计划完成时间: "",
计划生产数: 0,
TaskAID: "",
// 收检数据(用户输入)
检测数量: 0,
合格数: 0,
不合格数: 0,
检测人: "",
检测时间: "",
检测说明: "",
},
};
},
created() {
this.getTypeList();
this.getCheckerList();
this.searchTable();
},
computed: {
activeIndex() {
return this.$route.path;
},
},
methods: {
getTypeList() {
this.typeList = [];
var Data = this.CreateData("11", "查询字典");
this.ExecDatabase(Data).then((response) => {
for (let i = 0; i < response.data.length; i++) {
if (response.data[i].数据类别 === "检测类型") {
this.typeList.push({
label: response.data[i].词条名称,
value: response.data[i].词条编号,
});
}
}
});
},
getCheckerList() {
this.checkerList = [];
var Data = this.CreateData("11", "人员管理_人员信息查询_质检部门_查询");
this.ExecDatabase(Data).then((response) => {
for (let i = 0; i < response.data.length; i++) {
this.checkerList.push({
label: response.data[i].Personnel_Name,
value: response.data[i].Personnel_Number,
});
}
});
},
searchTable() {
// 开始加载状态,清空表格数据和选中行
this.loading = true;
this.tableData = [];
// 构建基础查询参数
var param = [];
param.push(["订单号", this.orderNo]);
param.push(["零件编号", this.partNo]);
param.push(["零件名称", this.partName]);
// 添加检测日期范围参数
param.push([
"检测日期_Start",
this.inspectionDate ? this.inspectionDate[0] : "",
]);
param.push([
"检测日期_End",
this.inspectionDate ? this.inspectionDate[1] : "",
]);
param.push(["检测结果", this.inspectionResult]);
const selectedChecker = this.checkerList.find(
(item) => item.value === this.checker
);
param.push(["检测人", selectedChecker ? selectedChecker.label : ""]);
// 调用封装方法生成请求数据 - 使用新的存储过程名称
var Data = this.CreateData(
"11",
"质量管理_质量检验_退货质检任务_查询",
param
);
// 执行数据库请求
this.ExecDatabase(Data)
.then((response) => {
this.loading = false;
console.log(response.data);
if (response.data && response.data.length !== 0) {
this.tableData = response.data;
} else {
this.tableData = [];
this.$message.info("未查询到相关数据");
}
})
.catch((error) => {
this.loading = false;
console.error("查询失败:", error);
this.$message.error("查询失败");
});
},
receiveCheck(row) {
// 打开收检对话框并填充数据
this.receiveCheckVisible = true;
// 从行数据填充基本信息
this.receiveCheckData = {
// 基本信息(从行数据获取)
零件名称: row.物料名称 || "",
零件编码: row.物料编码 || "",
计划号: row.订单编号 || "",
行号: row.行号 || "",
订单类型: row.订单类型 || "",
// 收检数据(用户输入)
检测数量: row.入库数量 || 0,
合格数: row.合格数 || 0,
不合格数: row.不合格数 || 0,
检测人: row.检测人 || "",
检测时间: this.formatDateTime(new Date()),
检测说明: "",
};
console.log(this.receiveCheckData);
},
handleQualifiedChange(value) {
// 自动计算不合格数
this.receiveCheckData.不合格数 = this.receiveCheckData.检测数量 - value;
},
confirmReceiveCheck() {
// 验证表单
if (
!this.receiveCheckData.检测数量 ||
this.receiveCheckData.检测数量 <= 0
) {
this.$message.warning("请输入有效的检测数量");
return;
}
if (!this.receiveCheckData.检测人) {
this.$message.warning("请选择检验人");
return;
}
if (!this.receiveCheckData.检测时间) {
this.$message.warning("请选择检验时间");
return;
}
if (!this.receiveCheckData.检测数量 == this.receiveCheckData.合格数 + this.receiveCheckData.不合格数) {
this.$message.warning("合格数加不合格数必须等于检测数量");
return;
}
// 调用存储过程保存数据
this.saveReceiveCheck();
},
saveReceiveCheck() {
var param = [];
param.push(["检测类型编号", 5]);
param.push(["质检类型", "来料检验"]);
param.push(["零件名称", this.receiveCheckData.零件名称]);
param.push(["零件编码", this.receiveCheckData.零件编码]);
param.push(["计划号", this.receiveCheckData.计划号]);
param.push(["检测数量", this.receiveCheckData.检测数量]);
param.push(["合格数", this.receiveCheckData.合格数]);
param.push(["不合格数", this.receiveCheckData.不合格数]);
param.push(["检测人", this.receiveCheckData.检测人]);
param.push(["检测时间", this.receiveCheckData.检测时间]);
param.push(["检测说明", this.receiveCheckData.检测说明]);
param.push(["行号", this.receiveCheckData.行号]);
param.push(["订单类型", this.receiveCheckData.订单类型]);
console.log(param);
var Data = this.CreateData("12", "质量管理_来料检验_更新", param);
this.ExecDatabase(Data)
.then((response) => {
if (
response.data &&
response.data[0] &&
response.data[0].result === "1"
) {
this.$message.success("来料检验操作成功");
this.receiveCheckVisible = false;
// 刷新表格数据
this.searchTable();
} else {
this.$message.error("来料检验操作失败");
}
})
.catch((error) => {
console.error("来料检验操作失败:", error);
this.$message.error("来料检验操作失败");
});
},
formatDateTime(date) {
const year = date.getFullYear();
const month = String(date.getMonth() + 1).padStart(2, "0");
const day = String(date.getDate()).padStart(2, "0");
const hours = String(date.getHours()).padStart(2, "0");
const minutes = String(date.getMinutes()).padStart(2, "0");
const seconds = String(date.getSeconds()).padStart(2, "0");
return `${year}-${month}-${day} ${hours}:${minutes}:${seconds}`;
},
// 导出Excel功能
exportToExcel() {
if (this.tableData.length === 0) {
this.$message.warning("没有数据可导出");
return;
}
try {
// 准备导出数据
const exportData = this.tableData.map((item, index) => {
return {
序号: index + 1,
合同号: item.内部合同号 || "",
订单编号: item.计划号 || "",
零件名称: item.零件名称 || "",
零件编码: item.零件编码 || "",
工序名称: item.工序名称 || "",
计划生产数: item.计划生产数 || 0,
检验数量: item.检验数量 || 0,
检验合格数量: item.合格数 || 0,
检验不合格数量: item.不合格数 || 0,
检验操作人: item.检测人 || "",
检验时间: item.检测时间 || "",
};
});
// 创建工作簿
const wb = XLSX.utils.book_new();
// 创建工作表
const ws = XLSX.utils.json_to_sheet(exportData);
// 设置列宽
const colWidth = [
{ wch: 8 }, // 序号
{ wch: 15 }, // 合同号
{ wch: 15 }, // 订单编号
{ wch: 20 }, // 零件名称
{ wch: 15 }, // 零件编码
{ wch: 12 }, // 工序名称
{ wch: 12 }, // 计划生产数
{ wch: 10 }, // 检验数量
{ wch: 15 }, // 检验合格数量
{ wch: 15 }, // 检验不合格数量
{ wch: 12 }, // 检验操作人
{ wch: 20 }, // 检验时间
];
ws["!cols"] = colWidth;
// 将工作表添加到工作簿
XLSX.utils.book_append_sheet(wb, ws, "序检收检记录");
// 生成文件名(包含当前时间)
const fileName = `序检收检记录_${this.formatDateForFileName(
new Date()
)}.xlsx`;
// 导出文件
XLSX.writeFile(wb, fileName);
this.$message.success("导出成功");
} catch (error) {
console.error("导出失败:", error);
this.$message.error("导出失败");
}
},
// 格式化日期用于文件名
formatDateForFileName(date) {
const year = date.getFullYear();
const month = String(date.getMonth() + 1).padStart(2, "0");
const day = String(date.getDate()).padStart(2, "0");
const hours = String(date.getHours()).padStart(2, "0");
const minutes = String(date.getMinutes()).padStart(2, "0");
const seconds = String(date.getSeconds()).padStart(2, "0");
return `${year}${month}${day}_${hours}${minutes}${seconds}`;
},
},
};
</script>
<style>
.search-container {
margin-bottom: 20px;
}
.show-text {
margin-right: 5px;
line-height: 32px;
}
.operation-cell {
display: flex;
justify-content: space-between;
width: 100%;
}
.operation-btn {
flex: 1;
margin: 0 5px;
padding: 0;
min-width: 0;
}
.active {
color: skyblue;
margin-left: 5px;
}
.info-container {
border: 1px solid #ccc;
display: flex;
}
.info-item {
display: flex;
flex: 1;
border-right: 1px solid #ccc;
}
.info-item:last-child {
border-right: none;
}
.info-label {
width: 30%;
padding: 8px;
background-color: #f5f7fa;
border-right: 1px solid #ccc;
}
.info-value {
flex: 1;
padding: 5px;
}
.info-label,
.info-value {
display: flex;
align-items: center;
}
</style>