BUG修改

This commit is contained in:
2025-04-15 14:34:35 +08:00
parent 2ee698d264
commit 11f4b52ba6
9 changed files with 5652 additions and 6050 deletions

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@@ -1,258 +1,264 @@
<template>
<el-row :gutter="10">
<el-col :span="8" v-for="(group, index) in groups" :key="index">
<el-card shadow="hover" class="box-card">
<div class="card-header">{{ group.groupName }}</div>
<div>
<el-row :gutter="5" v-for="(row, rowIndex) in rowList" :key="rowIndex">
<el-col :span="2">
<div class="defect-item-left">{{ row }}</div>
</el-col>
<el-col v-if="item.type === row" :span="3" v-for="(item, index) in group.children" :key="index">
<div class="defect-item-box" @mousedown="handleStart($event, item)"
@mouseup="handleEnd($event, item)" @touchstart="handleStart($event, item)"
@touchend="handleEnd($event, item)">
<div class="defect-item-name">{{ item.name }}</div>
<div class="defect-item-number">{{ getClickItemNum(item) }}</div>
</div>
</el-col>
</el-row>
</div>
</el-card>
</el-col>
<el-col :span="8">
<slot name="workorder"></slot>
</el-col>
<DefectUpdateDialog ref="DefectUpdateDialogRef" @updateDefectNum="updateDefectNum" />
</el-row>
<el-row :gutter="10">
<el-col :span="8" v-for="(group, index) in groups" :key="index">
<el-card shadow="hover" class="box-card">
<div class="card-header">{{ group.groupName }}</div>
<div>
<el-row :gutter="5" v-for="(row, rowIndex) in rowList" :key="rowIndex">
<el-col :span="2">
<div class="defect-item-left">{{ row }}</div>
</el-col>
<el-col v-if="item.type === row" :span="3" v-for="(item, index) in group.children" :key="index">
<div
class="defect-item-box"
@mousedown="handleStart($event, item)"
@mouseup="handleEnd($event, item)"
@touchstart="handleStart($event, item)"
@touchend="handleEnd($event, item)"
>
<div class="defect-item-name">{{ item.name }}</div>
<div class="defect-item-number">{{ getClickItemNum(item) }}</div>
</div>
</el-col>
</el-row>
</div>
</el-card>
</el-col>
<el-col :span="8">
<slot name="workorder"></slot>
</el-col>
<DefectUpdateDialog ref="DefectUpdateDialogRef" @updateDefectNum="updateDefectNum" />
</el-row>
</template>
<script>
import DefectUpdateDialog from './DefectUpdateDialog.vue';
import * as QcGp12Api from '@/api/qualityManagement/gp12/qcGp12Service';
import DefectUpdateDialog from './DefectUpdateDialog.vue'
import * as QcGp12Api from '@/api/qualityManagement/gp12/qcGp12Service'
export default {
name: 'DefectCard',
components: { DefectUpdateDialog },
props: {
// 工单信息
formData: Object,
},
data() {
return {
groups: [
{ groupName: '油漆', children: [] },
{ groupName: '设备', children: [] },
{ groupName: '毛坯', children: [] },
{ groupName: '程序', children: [] },
{ groupName: '班组操作', children: [] }
],
rowList: ['抛光', '打磨', '报废'],
pressTimer: null,
isLongPress: false,
dialogData: {
title: '',
update: {
show: false,
updateName: '',
updateCode: '',
updateNum: 0
},
}
};
},
created() {
this.init();
},
methods: {
async init() {
let groups = await QcGp12Api.GetDefectInitOptions()
this.groups = groups.data
},
validateWorkOrder() {
if (!this.formData.workOrder) {
this.showErrorMessage(1, '未生成有效工单!请扫描箱标签');
return false;
}
return true;
},
showErrorMessage(code, message) {
this.$emit('showWarningMessage', code, message);
},
getClickItemNum(item) {
return item.num || 0;
},
handleStart(event, item) {
if (event.type.startsWith('touch')) event.preventDefault();
if (this.pressTimer) clearTimeout(this.pressTimer);
this.pressTimer = setTimeout(() => {
this.isLongPress = true;
this.showUpdateDialog(item);
}, 500);
},
handleEnd(event, item = null) {
if (!item) return;
if (this.pressTimer) clearTimeout(this.pressTimer);
this.handleShortClick(item);
this.isLongPress = false;
},
// 提取短按处理逻辑
handleShortClick(item) {
if (this.isLongPress) return;
if (!this.validateWorkOrder()) return;
const params = {
workOrder: this.formData.workOrder,
defectCode: item.code,
defectNum: item.num || 0,
type: "1",
};
this.updateDefectItem(params);
},
updateDefectItem(params) {
QcGp12Api.ChangeWorkOrderDefect(params).then(res => {
if (res.code === 200) {
this.refresh();
} else {
this.$message.error('缺陷项点击异常');
}
});
},
// 长按
showUpdateDialog(item) {
if (!this.validateWorkOrder()) return;
const data = {
updateName: `${item.type}-${item.name}`,
updateCode: item.code,
updateNum: this.getClickItemNum(item),
workOrder: this.formData.workOrder,
description: this.formData.description
}
this.$refs.DefectUpdateDialogRef.open(data);
},
updateDefectNum(params) {
if (!this.validateWorkOrder()) return;
this.updateDefectItem(params);
this.$refs.DefectUpdateDialogRef.close();
this.refresh();
this.isLongPress = false;
},
setDefectNum(defectCode, num) {
// 更新缺陷数量的方法
for (let group of this.groups) {
for (let child of group.children) {
if (child.code === defectCode) {
child.num = num;
break;
}
}
}
},
async refresh() {
this.$emit("refresh");
},
// 获取工单缺陷项(刷新)
getDefectListByWorkOrder() {
if (!this.formData.workOrder) {
return;
}
const params = {
workOrder: this.formData.workOrder,
};
QcGp12Api.GetWorkOrderDefectList(params).then(res => {
if (res.code === 200 && res.data.length > 0) {
let _list = res.data;
for (let item of _list) {
this.setDefectNum(item.defectCode, item.defectNum);
}
}
})
name: 'DefectCard',
components: { DefectUpdateDialog },
props: {
// 工单信息
formData: Object,
},
data() {
return {
groups: [
{ groupName: '油漆', children: [] },
{ groupName: '设备', children: [] },
{ groupName: '毛坯', children: [] },
{ groupName: '程序', children: [] },
{ groupName: '班组操作', children: [] },
],
rowList: ['抛光', '打磨', '报废'],
pressTimer: null,
isLongPress: false,
dialogData: {
title: '',
update: {
show: false,
updateName: '',
updateCode: '',
updateNum: 0,
},
},
}
};
},
created() {
this.init()
},
methods: {
async init() {
try {
let groups = await QcGp12Api.GetDefectInitOptions()
this.groups = groups.data
} catch (e) {}
},
validateWorkOrder() {
if (!this.formData.workOrder) {
this.showErrorMessage(1, '未生成有效工单!请扫描箱标签')
return false
}
return true
},
showErrorMessage(code, message) {
this.$emit('showWarningMessage', code, message)
},
getClickItemNum(item) {
return item.num || 0
},
handleStart(event, item) {
if (event.type.startsWith('touch')) event.preventDefault()
if (this.pressTimer) clearTimeout(this.pressTimer)
this.pressTimer = setTimeout(() => {
this.isLongPress = true
this.showUpdateDialog(item)
}, 500)
},
handleEnd(event, item = null) {
if (!item) return
if (this.pressTimer) clearTimeout(this.pressTimer)
this.handleShortClick(item)
this.isLongPress = false
},
// 提取短按处理逻辑
handleShortClick(item) {
if (this.isLongPress) return
if (!this.validateWorkOrder()) return
const params = {
workOrder: this.formData.workOrder,
defectCode: item.code,
defectNum: item.num || 0,
type: '1',
}
this.updateDefectItem(params)
},
updateDefectItem(params) {
QcGp12Api.ChangeWorkOrderDefect(params).then((res) => {
if (res.code === 200) {
this.refresh()
} else {
this.$message.error('缺陷项点击异常')
}
})
},
// 长按
showUpdateDialog(item) {
if (!this.validateWorkOrder()) return
const data = {
updateName: `${item.type}-${item.name}`,
updateCode: item.code,
updateNum: this.getClickItemNum(item),
workOrder: this.formData.workOrder,
description: this.formData.description,
}
this.$refs.DefectUpdateDialogRef.open(data)
},
updateDefectNum(params) {
if (!this.validateWorkOrder()) return
this.updateDefectItem(params)
this.$refs.DefectUpdateDialogRef.close()
this.refresh()
this.isLongPress = false
},
setDefectNum(defectCode, num) {
// 更新缺陷数量的方法
for (let group of this.groups) {
for (let child of group.children) {
if (child.code === defectCode) {
child.num = num
break
}
}
}
},
refresh() {
this.$emit('refresh')
},
// 获取工单缺陷项(刷新)
getDefectListByWorkOrder() {
if (!this.formData.workOrder) {
return
}
const params = {
workOrder: this.formData.workOrder,
}
QcGp12Api.GetWorkOrderDefectList(params).then((res) => {
if (res.code === 200 && res.data.length > 0) {
let _list = res.data
for (let item of _list) {
this.setDefectNum(item.defectCode, item.defectNum)
}
}
})
},
},
}
</script>
<style scoped>
.box-card {
width: 100%;
background-color: #032169;
/* 深墨绿色背景 */
color: #ecf0f1;
/* 浅灰色文字颜色 */
border-radius: 10px;
box-shadow: 0 4px 8px rgba(0, 0, 0, 0.1);
/* 设置阴影 */
margin-top: 2px;
margin-bottom: 2px;
/* 增加卡片底部间距 */
width: 100%;
background-color: #032169;
/* 深墨绿色背景 */
color: #ecf0f1;
/* 浅灰色文字颜色 */
border-radius: 10px;
box-shadow: 0 4px 8px rgba(0, 0, 0, 0.1);
/* 设置阴影 */
margin-top: 2px;
margin-bottom: 2px;
/* 增加卡片底部间距 */
}
.card-header {
color: #ecf0f1;
display: flex;
align-items: center;
justify-content: center;
font-size: 20px;
font-weight: 600;
color: #ecf0f1;
display: flex;
align-items: center;
justify-content: center;
font-size: 20px;
font-weight: 600;
}
.defect-item-left {
height: 100px;
font-size: 16px;
font-weight: 600;
display: flex;
align-items: center;
justify-content: center;
writing-mode: vertical-lr;
height: 100px;
font-size: 16px;
font-weight: 600;
display: flex;
align-items: center;
justify-content: center;
writing-mode: vertical-lr;
}
.defect-item-box {
min-width: 100%;
border-radius: 5%;
margin-top: 5px;
margin-bottom: 5px;
background-color: #11a983;
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
transition: background-color 0.3s ease, transform 0.3s ease;
/* 添加过渡效果 */
min-width: 100%;
border-radius: 5%;
margin-top: 5px;
margin-bottom: 5px;
background-color: #11a983;
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
transition: background-color 0.3s ease, transform 0.3s ease;
/* 添加过渡效果 */
}
.defect-item-box:hover {
background-color: #008c62;
/* 悬停时的背景颜色 */
transform: scale(1.05);
/* 悬停时稍微放大 */
cursor: pointer;
/* 改变鼠标指针形状 */
background-color: #008c62;
/* 悬停时的背景颜色 */
transform: scale(1.05);
/* 悬停时稍微放大 */
cursor: pointer;
/* 改变鼠标指针形状 */
}
.defect-item-name {
width: 100%;
height: 60px;
font-size: 16px;
font-weight: 600;
text-align: center;
display: flex;
align-items: center;
justify-content: center;
writing-mode: vertical-lr;
letter-spacing: 5px;
width: 100%;
height: 60px;
font-size: 16px;
font-weight: 600;
text-align: center;
display: flex;
align-items: center;
justify-content: center;
writing-mode: vertical-lr;
letter-spacing: 5px;
}
.defect-item-number {
color: red;
width: 100%;
height: 40px;
font-size: 20px;
font-weight: 600;
display: flex;
align-items: center;
justify-content: center;
color: red;
width: 100%;
height: 40px;
font-size: 20px;
font-weight: 600;
display: flex;
align-items: center;
justify-content: center;
}
.number-text {
font-size: 20px;
font-weight: 600;
font-size: 20px;
font-weight: 600;
}
</style>
</style>

View File

@@ -1,357 +1,355 @@
<template>
<div>
<el-card class="workorder-card">
<div class="workorder-card-header">
<div>
<span>工单编号:</span>
<span>{{ formData.workOrder }}</span>
</div>
<div>
<span :class="messageClass">{{ message }}</span>
</div>
</div>
<div class="workorder-card-button-box">
<div>
<el-button type="primary" @click="doRefresh">刷新</el-button>
</div>
<div>
<el-button v-if="formStatus === 1" type="success" @click="doBtnStartWorkOrder">开启工单</el-button>
<el-button v-if="formStatus === 2" type="info" @click="doBtnGenerateLabel">修改合格数</el-button>
<el-button v-if="formStatus === 2" type="warning" @click="doBtnEndWorkOrder">结束工单</el-button>
</div>
</div>
<div class="workorder-card-action-box">
<div>
<span>站点: </span>
<el-select :disabled="formStatus === 2" style="width: 140px;" v-model="site" placeholder="请选择站点"
@change="selectChange">
<el-option v-for="item in siteOptions" :key="item.code" :label="item.name"
:value="item.code"></el-option>
</el-select>
</div>
<div>
<span>班组: </span>
<el-select :disabled="formStatus === 2" style="width: 140px;" v-model="team" placeholder="请选择班组"
@change="selectChange">
<el-option v-for="item in teamOptions" :key="item.code" :label="item.name"
:value="item.code"></el-option>
</el-select>
</div>
</div>
<table v-if="formData.workOrder" class="workorder-card-table">
<tr>
<td>零件号</td>
<td>{{ formData.partNumber }}</td>
<td>描述</td>
<td>{{ formData.description }}</td>
</tr>
<tr>
<td>规格</td>
<td>{{ formData.specification }}</td>
<td>颜色</td>
<td>{{ formData.color }}</td>
</tr>
<tr>
<td>来源</td>
<td>{{ formData.isOnetime === 1 ? "一次合格" : "抛光件" }}</td>
<td>类别</td>
<td>{{ formData.isBack === 1 ? "返工件" : "正常件" }}</td>
</tr>
<tr>
<td>投入数</td>
<td>{{ formData.requireNumber }}</td>
<td>合格数</td>
<td>
{{ formData.qualifiedNumber }}
</td>
</tr>
<tr>
<td>合格率</td>
<td>{{ qualifiedRate }}</td>
<td>抛光数</td>
<td>{{ formData.polishNumber }}</td>
</tr>
<tr>
<td>打磨数</td>
<td>{{ formData.damoNumber }}</td>
<td>报废数</td>
<td>{{ formData.baofeiNumber }}</td>
</tr>
<tr>
<td>开始时间</td>
<td>{{ formData.startTime }}</td>
<td>结束时间</td>
<td>{{ formData.endTime }}</td>
</tr>
</table>
</el-card>
<StartWorkOrderDialog ref="StartWorkOrderDialogRef" @showWarningMessage="showErrorMessage"
@changeFormStatus="changeFormStatus" @formDataChange="formDataChange" @refresh="doRefresh" />
<EndWorkOrderDialog ref="EndWorkOrderDialogRef" @changeFormStatus="changeFormStatus"
@clearFormData="clearFormData" />
<GenerateLabelDialog ref="GenerateLabelDialogRef" @updateFormData="updateFormData"></GenerateLabelDialog>
</div>
<div>
<el-card class="workorder-card">
<div class="workorder-card-header">
<div>
<span>工单编号:</span>
<span>{{ formData.workOrder }}</span>
</div>
<div>
<span :class="messageClass">{{ message }}</span>
</div>
</div>
<div class="workorder-card-button-box">
<div>
<el-button type="primary" @click="doRefresh">刷新</el-button>
</div>
<div>
<el-button v-if="formStatus === 1" type="success" @click="doBtnStartWorkOrder">开启工单</el-button>
<el-button v-if="formStatus === 2" type="info" @click="doBtnGenerateLabel">修改合格数</el-button>
<el-button v-if="formStatus === 2" type="warning" @click="doBtnEndWorkOrder">结束工单</el-button>
</div>
</div>
<div class="workorder-card-action-box">
<div>
<span>站点: </span>
<el-select :disabled="formStatus === 2" style="width: 140px" v-model="site" placeholder="请选择站点" @change="selectChange">
<el-option v-for="item in siteOptions" :key="item.code" :label="item.name" :value="item.code"></el-option>
</el-select>
</div>
<div>
<span>班组: </span>
<el-select :disabled="formStatus === 2" style="width: 140px" v-model="team" placeholder="请选择班组" @change="selectChange">
<el-option v-for="item in teamOptions" :key="item.code" :label="item.name" :value="item.code"></el-option>
</el-select>
</div>
</div>
<table v-if="formData.workOrder" class="workorder-card-table">
<tr>
<td>零件号</td>
<td>{{ formData.partNumber }}</td>
<td>描述</td>
<td>{{ formData.description }}</td>
</tr>
<tr>
<td>规格</td>
<td>{{ formData.specification }}</td>
<td>颜色</td>
<td>{{ formData.color }}</td>
</tr>
<tr>
<td>来源</td>
<td>{{ formData.isOnetime === 1 ? '一次合格' : '抛光件' }}</td>
<td>类别</td>
<td>{{ formData.isBack === 1 ? '返工件' : '正常件' }}</td>
</tr>
<tr>
<td>投入数</td>
<td>{{ formData.requireNumber }}</td>
<td>合格数</td>
<td>
{{ formData.qualifiedNumber }}
</td>
</tr>
<tr>
<td>合格率</td>
<td>{{ qualifiedRate }}</td>
<td>抛光数</td>
<td>{{ formData.polishNumber }}</td>
</tr>
<tr>
<td>打磨数</td>
<td>{{ formData.damoNumber }}</td>
<td>报废数</td>
<td>{{ formData.baofeiNumber }}</td>
</tr>
<tr>
<td>开始时间</td>
<td>{{ formData.startTime }}</td>
<td>结束时间</td>
<td>{{ formData.endTime }}</td>
</tr>
</table>
</el-card>
<StartWorkOrderDialog
ref="StartWorkOrderDialogRef"
@showWarningMessage="showErrorMessage"
@changeFormStatus="changeFormStatus"
@formDataChange="formDataChange"
@refresh="doRefresh"
/>
<EndWorkOrderDialog ref="EndWorkOrderDialogRef" @changeFormStatus="changeFormStatus" @clearFormData="clearFormData" />
<GenerateLabelDialog ref="GenerateLabelDialogRef" @updateFormData="updateFormData"></GenerateLabelDialog>
</div>
</template>
<script>
import StartWorkOrderDialog from './StartWorkOrderDialog.vue';
import EndWorkOrderDialog from './EndWorkOrderDialog.vue';
import GenerateLabelDialog from './GenerateLabelDialog.vue';
import * as QcGp12Api from '@/api/qualityManagement/gp12/qcGp12Service';
import StartWorkOrderDialog from './StartWorkOrderDialog.vue'
import EndWorkOrderDialog from './EndWorkOrderDialog.vue'
import GenerateLabelDialog from './GenerateLabelDialog.vue'
import * as QcGp12Api from '@/api/qualityManagement/gp12/qcGp12Service'
export default {
name: 'WorkOrderCard',
components: { StartWorkOrderDialog, EndWorkOrderDialog, GenerateLabelDialog },
props: {
message: String,
messageClass: String
},
data() {
return {
StartWorkOrderDialogRef: null,
EndWorkOrderDialogRef: null,
sessionKey: '_touchScreenA01',
name: 'WorkOrderCard',
components: { StartWorkOrderDialog, EndWorkOrderDialog, GenerateLabelDialog },
props: {
message: String,
messageClass: String,
},
data() {
return {
StartWorkOrderDialogRef: null,
EndWorkOrderDialogRef: null,
sessionKey: '_touchScreenA01',
teamOptions: [],
siteOptions: [],
// 站点工单执行状态 1-初始状态(扫外箱标签) 2-工单执行中(扫内标签)
formStatus: 1,
team: '',
site: '',
formData: {
workOrder: '',
partnumber: '',
specification: '',
color: '',
description: '',
isOnetime: 0,
isBack: 0,
isPolish: 0,
isOut: 0,
},
};
},
created() {
this.init();
},
computed: {
qualifiedRate() {
if (this.formData.requireNumber > 0) {
const rate = Math.floor((this.formData.qualifiedNumber / this.formData.requireNumber) * 100);
return `${rate}%`;
} else {
return "0%";
}
}
},
methods: {
validateWorkOrder() {
if (!this.formData.workOrder) {
this.showErrorMessage(1, '未生成有效工单,请扫描箱标签');
return false;
}
return true;
},
showErrorMessage(code, message) {
this.$emit('showWarningMessage', code, message);
},
async init() {
try {
// 初始化数据
let teams = await QcGp12Api.GetGroupOptions()
let sites = await QcGp12Api.GetStieOptions()
let groups = await QcGp12Api.GetDefectInitOptions()
this.teamOptions = teams.data
this.siteOptions = sites.data
this.groups = groups.data
// 缓存数据读取
this.getLocalStorage()
} catch (error) {
console.error(error);
}
},
clearFormData() {
this.formData = {
workOrder: '',
partnumber: '',
specification: '',
color: '',
description: '',
isOnetime: 0,
isBack: 0,
isPolish: 0,
isOut: 0,
}
},
selectChange() {
this.setLocalStorage()
},
setLocalStorage() {
const data = {
team: this.team,
site: this.site
}
localStorage.setItem(this.sessionKey, JSON.stringify(data));
},
getLocalStorage() {
const data = JSON.parse(localStorage.getItem(this.sessionKey));
if (data) {
this.team = data.team
this.site = data.site
}
},
// 更新工单数据
updateFormData() {
const params = {
workOrder: this.formData.workOrder
}
if (params.workOrder === '' || params.workOrder === null) {
return;
}
QcGp12Api.UpdateWorkOrderDetail(params).then(res => {
if (res.code === 200) {
this.formData = res.data
this.formDataChange()
}
})
},
changeFormStatus(type) {
this.formStatus = type
},
setMqttMessage(LabelCode, ComNo, SiteNo) {
if (SiteNo !== this.site) {
return;
}
// 解析结果
if (this.formStatus === 1) {
// 扫外箱标签模式
this.$refs.StartWorkOrderDialogRef.handleScanBoxOutLabel(LabelCode, ComNo)
return;
}
// 扫内标签模式
if (this.formStatus === 2) {
// 扫内标签模式
this.handleScanInnerLabel(LabelCode, ComNo)
return;
}
},
// 扫内标签的情况
handleScanInnerLabel(label = '', comNo = "未知串口") {
const params = {
workOrder: this.formData.workOrder,
partNumber: this.formData.partNumber,
team: this.team,
siteNo: this.site,
comNo: comNo,
labelType: 2,
label,
}
QcGp12Api.ScanInnerLabel(params).then(res => {
if (res.code === 200 && res.data === "ok") {
this.showErrorMessage(0);
this.updateFormData()
} else {
this.showErrorMessage(3, res.data);
}
});
},
// 工单数据变更
formDataChange(data = null) {
if (data) {
this.formData = data
}
this.$emit("formDataChange", this.formData)
},
doRefresh() {
this.$emit('refresh');
this.showErrorMessage(0);
},
clearFormData() {
this.formData = {
workOrder: '',
partnumber: '',
specification: '',
color: '',
description: '',
isOnetime: 0,
isBack: 0,
isPolish: 0,
isOut: 0,
}
this.$emit('clear');
},
doBtnStartWorkOrder() {
const data = {
team: this.team,
siteNo: this.site,
}
this.$refs.StartWorkOrderDialogRef.open(data);
},
doBtnEndWorkOrder() {
const data = {
formData: this.formData,
team: this.team,
siteNo: this.site,
}
this.$refs.EndWorkOrderDialogRef.open(data);
},
doBtnGenerateLabel() {
const data = {
formData: this.formData,
team: this.team,
siteNo: this.site,
}
this.$refs.GenerateLabelDialogRef.open(data);
}
teamOptions: [],
siteOptions: [],
// 站点工单执行状态 1-初始状态(扫外箱标签) 2-工单执行中(扫内标签)
formStatus: 1,
team: '',
site: '',
formData: {
workOrder: '',
partnumber: '',
specification: '',
color: '',
description: '',
isOnetime: 0,
isBack: 0,
isPolish: 0,
isOut: 0,
},
}
};
},
created() {
this.init()
},
computed: {
qualifiedRate() {
if (this.formData.requireNumber > 0) {
const rate = Math.floor((this.formData.qualifiedNumber / this.formData.requireNumber) * 100)
return `${rate}%`
} else {
return '0%'
}
},
},
methods: {
validateWorkOrder() {
if (!this.formData.workOrder) {
this.showErrorMessage(1, '未生成有效工单,请扫描箱标签')
return false
}
return true
},
showErrorMessage(code, message) {
this.$emit('showWarningMessage', code, message)
},
async init() {
try {
// 初始化数据
let teams = await QcGp12Api.GetGroupOptions()
let sites = await QcGp12Api.GetStieOptions()
let groups = await QcGp12Api.GetDefectInitOptions()
this.teamOptions = teams.data
this.siteOptions = sites.data
this.groups = groups.data
// 缓存数据读取
this.getLocalStorage()
} catch (error) {
console.error(error)
}
},
clearFormData() {
this.formData = {
workOrder: '',
partnumber: '',
specification: '',
color: '',
description: '',
isOnetime: 0,
isBack: 0,
isPolish: 0,
isOut: 0,
}
},
selectChange() {
this.setLocalStorage()
},
setLocalStorage() {
const data = {
team: this.team,
site: this.site,
}
localStorage.setItem(this.sessionKey, JSON.stringify(data))
},
getLocalStorage() {
const data = JSON.parse(localStorage.getItem(this.sessionKey))
if (data) {
this.team = data.team
this.site = data.site
}
},
// 更新工单数据
updateFormData() {
const params = {
workOrder: this.formData.workOrder,
}
if (params.workOrder === '' || params.workOrder === null) {
return
}
QcGp12Api.UpdateWorkOrderDetail(params).then((res) => {
if (res.code === 200) {
this.formData = res.data
this.formDataChange()
}
})
},
changeFormStatus(type) {
this.formStatus = type
},
setMqttMessage(LabelCode, ComNo, SiteNo) {
if (SiteNo !== this.site) {
return
}
// 解析结果
if (this.formStatus === 1) {
// 扫外箱标签模式
this.$refs.StartWorkOrderDialogRef.handleScanBoxOutLabel(LabelCode, ComNo)
return
}
// 扫内标签模式
if (this.formStatus === 2) {
// 扫内标签模式
this.handleScanInnerLabel(LabelCode, ComNo)
return
}
},
// 扫内标签的情况
handleScanInnerLabel(label = '', comNo = '未知串口') {
const params = {
workOrder: this.formData.workOrder,
partNumber: this.formData.partNumber,
team: this.team,
siteNo: this.site,
comNo: comNo,
labelType: 2,
label,
}
QcGp12Api.ScanInnerLabel(params).then((res) => {
if (res.code === 200 && res.data === 'ok') {
this.showErrorMessage(0)
this.updateFormData()
} else {
this.showErrorMessage(3, res.data)
}
})
},
// 工单数据变更
formDataChange(data = null) {
if (data) {
this.formData = data
}
this.$emit('formDataChange', this.formData)
},
doRefresh() {
this.$emit('refresh')
this.showErrorMessage(0)
},
clearFormData() {
this.formData = {
workOrder: '',
partnumber: '',
specification: '',
color: '',
description: '',
isOnetime: 0,
isBack: 0,
isPolish: 0,
isOut: 0,
}
this.$emit('clear')
},
doBtnStartWorkOrder() {
const data = {
team: this.team,
siteNo: this.site,
}
this.$refs.StartWorkOrderDialogRef.open(data)
},
doBtnEndWorkOrder() {
const data = {
formData: this.formData,
team: this.team,
siteNo: this.site,
}
this.$refs.EndWorkOrderDialogRef.open(data)
},
doBtnGenerateLabel() {
const data = {
formData: this.formData,
team: this.team,
siteNo: this.site,
}
this.$refs.GenerateLabelDialogRef.open(data)
},
},
}
</script>
<style scoped>
.workorder-card {
min-height: 400px;
min-height: 400px;
}
.workorder-card-header {
width: 100%;
font-size: 18px;
font-weight: 600;
margin-bottom: 10px;
display: flex;
align-items: center;
justify-content: space-between;
width: 100%;
font-size: 18px;
font-weight: 600;
margin-bottom: 10px;
display: flex;
align-items: center;
justify-content: space-between;
}
.workorder-card-table {
width: 100%;
font-size: 16px;
font-weight: 500;
border: 2px solid #000;
border-collapse: collapse;
width: 100%;
font-size: 16px;
font-weight: 500;
border: 2px solid #000;
border-collapse: collapse;
}
.workorder-card-table td {
border: 2px solid #000;
padding: 5px;
border: 2px solid #000;
padding: 5px;
}
.workorder-card-button-box {
width: 100%;
display: flex;
align-items: center;
justify-content: space-between;
margin-bottom: 10px;
width: 100%;
display: flex;
align-items: center;
justify-content: space-between;
margin-bottom: 10px;
}
.workorder-card-action-box {
width: 100%;
display: flex;
align-items: center;
justify-content: space-between;
margin-bottom: 10px;
font-size: 16px;
font-weight: 600;
width: 100%;
display: flex;
align-items: center;
justify-content: space-between;
margin-bottom: 10px;
font-size: 16px;
font-weight: 600;
}
</style>
</style>

View File

@@ -1,167 +1,168 @@
<template>
<div ref="container" class="container">
<DefectCard ref="DefectCardRef" :formData="formData" @refresh="doRefresh"
@showWarningMessage="showWarningMessage">
<template v-slot:workorder>
<WorkOrderCard ref="WorkOrderCardRef" @formDataChange="formDataChange" @refresh="doRefresh"
:message="message" :messageClass="messageClass" @showWarningMessage="showWarningMessage"
@clear="clear" />
</template>
</DefectCard>
</div>
<div ref="container" class="container">
<DefectCard v-loading="loading" ref="DefectCardRef" :formData="formData" @refresh="doRefresh" @showWarningMessage="showWarningMessage">
<template v-slot:workorder>
<WorkOrderCard
ref="WorkOrderCardRef"
@formDataChange="formDataChange"
@refresh="doRefresh"
:message="message"
:messageClass="messageClass"
@showWarningMessage="showWarningMessage"
@clear="clear"
/>
</template>
</DefectCard>
</div>
</template>
<script>
import WorkOrderCard from './components/WorkOrderCard.vue';
import DefectCard from './components/DefectCard.vue';
import StartWorkOrderDialog from './components/StartWorkOrderDialog.vue';
import EndWorkOrderDialog from './components/EndWorkOrderDialog.vue';
import * as emqxUtil from '@/utils/mqtt/emqxUtil';
import * as QcGp12Api from '@/api/qualityManagement/gp12/qcGp12Service';
import WorkOrderCard from './components/WorkOrderCard.vue'
import DefectCard from './components/DefectCard.vue'
import StartWorkOrderDialog from './components/StartWorkOrderDialog.vue'
import EndWorkOrderDialog from './components/EndWorkOrderDialog.vue'
import * as emqxUtil from '@/utils/mqtt/emqxUtil'
import * as QcGp12Api from '@/api/qualityManagement/gp12/qcGp12Service'
export default {
name: 'WorkOrder',
components: { WorkOrderCard, DefectCard, StartWorkOrderDialog, EndWorkOrderDialog },
data() {
return {
mqttClient: null,
mqttClientId: emqxUtil.title + 'GP12' + Math.random().toString(16).substring(1, 10),
formData: {
workOrder: '',
partnumber: '',
specification: '',
color: '',
description: '',
isOnetime: 0,
isBack: 0,
isPolish: 0,
isOut: 0,
},
messageClass: 'text-green',
message: '正常',
};
},
created() {
this.init();
},
mounted() {
},
beforeDestroy() {
this.doBeforeDestroy()
},
methods: {
// 公共验证工单号【方案】
validateWorkOrder() {
if (!this.formData.workOrder) {
this.showWarningMessage('未生成有效工单,请扫描箱标签');
return false;
}
return true;
},
// 提取显示警告信息的逻辑
showWarningMessage(code, message) {
if (code === 0) {
this.message = '正常';
this.messageClass = 'text-green';
return;
}
this.$confirm(message, '提示', {
confirmButtonText: '确定',
cancelButtonText: '取消',
type: 'warning',
center: true,
closeOnClickModal: false
}).catch((err) => { });
if (code === 1) {
this.message = '未扫描箱标签!';
this.messageClass = 'text-red';
}
if (code === 2) {
this.message = '标签为空!';
this.messageClass = 'text-red';
}
if (code === 3) {
this.message = '标签存在异常!';
this.messageClass = 'text-red';
}
else {
this.message = '未定义错误!';
this.messageClass = 'text-red';
}
},
async init() {
this.initMqtt()
},
clear() {
this.$refs.DefectCardRef.init();
},
doBeforeDestroy() {
emqxUtil.endClient(this.mqttClient);
},
formDataChange(data) {
this.formData = data
this.$refs.DefectCardRef.getDefectListByWorkOrder()
},
// 全局刷新
async doRefresh() {
this.$refs.DefectCardRef.getDefectListByWorkOrder()
this.$refs.WorkOrderCardRef.updateFormData()
},
handlerScanInput(value) {
this.handleAnalyzeLabel(value)
},
handleAnalyzeLabel(label = '') {
const params = {
label,
// type === 1 获取详细物料信息 2只判断零件号是否正确
type: 1
}
QcGp12Api.AnalyzeLabel(params).then(res => {
if (res.code === 200 && res.data.isOk) {
this.message = '正常';
this.messageClass = 'text-green';
} else {
this.$confirm('标签异常:' + res.data.msg, '提示', {
confirmButtonText: '确定',
cancelButtonText: '取消',
type: 'warning',
center: true
}).then(() => {
}).catch(() => {
});
this.message = '标签存在异常';
this.messageClass = 'text-red';
}
})
},
// mqtt 操作
initMqtt() {
const that = this;
if (this.mqttClient?.connected) return
const _topic = emqxUtil.GP12Topic;
that.mqttClient = emqxUtil.createClient(that.mqttClientId);
that.mqttClient.subscribe(_topic.SiteComLabelCode + '/#');
that.mqttClient.on('message', function (topic, message) {
if (topic === _topic.SiteComLabelCode) {
const objData = emqxUtil.parseJSON(message);
that.doMqttAction(objData)
}
})
},
// 执行mqtt消息动作
doMqttAction(objData) {
const { SiteNo, ComNo, LabelCode, Time } = objData;
if (!LabelCode) {
this.showWarningMessage(2, "扫描结果为空!");
return;
}
this.$refs.WorkOrderCardRef.setMqttMessage(LabelCode, ComNo, SiteNo)
},
name: 'WorkOrder',
components: { WorkOrderCard, DefectCard, StartWorkOrderDialog, EndWorkOrderDialog },
data() {
return {
loading: false,
mqttClient: null,
mqttClientId: emqxUtil.title + 'GP12' + Math.random().toString(16).substring(1, 10),
formData: {
workOrder: '',
partnumber: '',
specification: '',
color: '',
description: '',
isOnetime: 0,
isBack: 0,
isPolish: 0,
isOut: 0,
},
messageClass: 'text-green',
message: '正常',
}
};
},
created() {
this.init()
},
mounted() {},
beforeDestroy() {
this.doBeforeDestroy()
},
methods: {
// 公共验证工单号【方案】
validateWorkOrder() {
if (!this.formData.workOrder) {
this.showWarningMessage('未生成有效工单,请扫描箱标签')
return false
}
return true
},
// 提取显示警告信息的逻辑
showWarningMessage(code, message) {
if (code === 0) {
this.message = '正常'
this.messageClass = 'text-green'
return
}
this.$confirm(message, '提示', {
confirmButtonText: '确定',
cancelButtonText: '取消',
type: 'warning',
center: true,
closeOnClickModal: false,
}).catch((err) => {})
if (code === 1) {
this.message = '未扫描箱标签!'
this.messageClass = 'text-red'
}
if (code === 2) {
this.message = '标签为空!'
this.messageClass = 'text-red'
}
if (code === 3) {
this.message = '标签存在异常!'
this.messageClass = 'text-red'
} else {
this.message = '未定义错误!'
this.messageClass = 'text-red'
}
},
init() {
this.initMqtt()
},
clear() {
this.$refs.DefectCardRef.init()
},
doBeforeDestroy() {
emqxUtil.endClient(this.mqttClient)
},
formDataChange(data) {
this.formData = data
this.$refs.DefectCardRef.getDefectListByWorkOrder()
},
// 全局刷新
doRefresh() {
this.$refs.DefectCardRef.getDefectListByWorkOrder()
this.$refs.WorkOrderCardRef.updateFormData()
},
handlerScanInput(value) {
this.handleAnalyzeLabel(value)
},
handleAnalyzeLabel(label = '') {
const params = {
label,
// type === 1 获取详细物料信息 2只判断零件号是否正确
type: 1,
}
QcGp12Api.AnalyzeLabel(params).then((res) => {
if (res.code === 200 && res.data.isOk) {
this.message = '正常'
this.messageClass = 'text-green'
} else {
this.$confirm('标签异常:' + res.data.msg, '提示', {
confirmButtonText: '确定',
cancelButtonText: '取消',
type: 'warning',
center: true,
})
.then(() => {})
.catch(() => {})
this.message = '标签存在异常'
this.messageClass = 'text-red'
}
})
},
// mqtt 操作
initMqtt() {
const that = this
if (this.mqttClient?.connected) return
const _topic = emqxUtil.GP12Topic
that.mqttClient = emqxUtil.createClient(that.mqttClientId)
that.mqttClient.subscribe(_topic.SiteComLabelCode + '/#')
that.mqttClient.on('message', function (topic, message) {
if (topic === _topic.SiteComLabelCode) {
const objData = emqxUtil.parseJSON(message)
that.doMqttAction(objData)
}
})
},
// 执行mqtt消息动作
doMqttAction(objData) {
const { SiteNo, ComNo, LabelCode, Time } = objData
if (!LabelCode) {
this.showWarningMessage(2, '扫描结果为空!')
return
}
this.$refs.WorkOrderCardRef.setMqttMessage(LabelCode, ComNo, SiteNo)
},
},
}
</script>
<style scoped></style>

View File

@@ -357,7 +357,7 @@ export default {
partnumber: '',
status: 1,
changeType: -1,
sort: 'updatedTime',
sort: 'actionTime',
sortType: 'desc',
},
RecordTypeOptions: [

View File

@@ -343,7 +343,7 @@ export default {
partnumber: '',
status: 1,
changeType: -1,
sort: 'updatedTime',
sort: 'actionTime',
sortType: 'desc',
},
RecordTypeOptions: [