Browse Source

成品标签拆分

master
shenzhouyu 2 months ago
parent
commit
d4b45b4b91
  1. 5
      src/api/customerIssue/customer-issue.js
  2. 1
      src/router/index.js
  3. 4
      src/views/main.vue
  4. 3
      src/views/modules/customerIssue/customerIssue.vue
  5. 514
      src/views/modules/customerIssue/sales-temporary.vue
  6. 2
      src/views/modules/production-issue/directIssueDetail.vue
  7. 2
      src/views/modules/production-issue/productionPickingDetail.vue
  8. 2
      src/views/modules/production-return/productionReturnPDAIssueList.vue
  9. 4
      src/views/modules/production-return/productionReturnPickingDetail.vue

5
src/api/customerIssue/customer-issue.js

@ -17,3 +17,8 @@ export const customerIssueConfirm = data => createAPI(`/pda/customerIssue/custom
// 获取库存物料信息 // 获取库存物料信息
export const getInventoryPart = data => createAPI(`/pda/customerIssue/getInventoryPart`,'post',data) export const getInventoryPart = data => createAPI(`/pda/customerIssue/getInventoryPart`,'post',data)
export const queryLabelInfo = data => createAPI(`/pda/customerIssue/queryHu`,'post',data)
export const createNewHu = data => createAPI(`/pda/customerIssue/createNewHu`,'post',data)

1
src/router/index.js

@ -90,6 +90,7 @@ const globalRoutes = [
{ path: "/customerIssuePDAList", name: "customerIssuePDAList", component: resolve => require(["@/views/modules/customerIssue/customerIssuePDAList.vue"], resolve), meta: { transition: 'instant', preload: true, keepAlive: true } }, { path: "/customerIssuePDAList", name: "customerIssuePDAList", component: resolve => require(["@/views/modules/customerIssue/customerIssuePDAList.vue"], resolve), meta: { transition: 'instant', preload: true, keepAlive: true } },
{ path: "/customerIssuePDAIssueList", name: "customerIssuePDAIssueList", component: resolve => require(["@/views/modules/customerIssue/customerIssuePDAIssueList.vue"], resolve), meta: { transition: 'instant', preload: true, keepAlive: true } }, { path: "/customerIssuePDAIssueList", name: "customerIssuePDAIssueList", component: resolve => require(["@/views/modules/customerIssue/customerIssuePDAIssueList.vue"], resolve), meta: { transition: 'instant', preload: true, keepAlive: true } },
{ path: "/customerIssuePrintSelect", name: "customerIssuePrintSelect", component: resolve => require(["@/views/modules/customerIssue/customerIssuePrintSelect.vue"], resolve), meta: { transition: 'instant', preload: true, keepAlive: true } }, { path: "/customerIssuePrintSelect", name: "customerIssuePrintSelect", component: resolve => require(["@/views/modules/customerIssue/customerIssuePrintSelect.vue"], resolve), meta: { transition: 'instant', preload: true, keepAlive: true } },
{ path: "/salesTemporary", name: "salesTemporary", component: resolve => require(["@/views/modules/customerIssue/sales-temporary.vue"], resolve), meta: { transition: 'instant', preload: true, keepAlive: true } },
// 客户订单发货 // 客户订单发货
{path: "/saleshipping",name: "saleshipping", component: resolve => require(["@/views/modules/sales-delivery/index.vue"], resolve), meta: { transition: 'instant' ,preload: true,keepAlive: true}}, {path: "/saleshipping",name: "saleshipping", component: resolve => require(["@/views/modules/sales-delivery/index.vue"], resolve), meta: { transition: 'instant' ,preload: true,keepAlive: true}},

4
src/views/main.vue

@ -104,8 +104,8 @@
</div> </div>
<div class="menu-text">委外发料</div> <div class="menu-text">委外发料</div>
</div> </div>
<!-- <div class="menu-item disabled" @click="navigateWithWarehouseCheck('customerissue')"> -->
<div class="menu-item disabled" @click="handleDisabledFeature('customerissue')">
<div class="menu-item" @click="navigateWithWarehouseCheck('customerissue')">
<!-- <div class="menu-item disabled" @click="handleDisabledFeature('customerissue')"> -->
<div class="menu-icon sales-delivery"> <div class="menu-icon sales-delivery">
<van-icon name="logistics" size="24" /> <van-icon name="logistics" size="24" />
</div> </div>

3
src/views/modules/customerIssue/customerIssue.vue

@ -35,7 +35,8 @@ export default {
{ icon: 'records', label: '申请单发料', iconClass: 'request', to: 'customerIssuePDA', disabled: false }, { icon: 'records', label: '申请单发料', iconClass: 'request', to: 'customerIssuePDA', disabled: false },
{ icon: 'logistics', label: '移库发料', iconClass: 'move', to: 'customerIssuePicking', disabled: true }, { icon: 'logistics', label: '移库发料', iconClass: 'move', to: 'customerIssuePicking', disabled: true },
{ icon: 'revoke', label: '发料撤销', iconClass: 'cancel', to: 'customerIssuePicking', disabled: true }, */ { icon: 'revoke', label: '发料撤销', iconClass: 'cancel', to: 'customerIssuePicking', disabled: true }, */
{ icon: 'records', label: '客户发料', iconClass: 'request', to: 'customerIssuePDA', disabled: false },
{ icon: 'revoke', label: '销售临时', iconClass: 'cancel', to: 'salesTemporary', disabled: false },
{ icon: 'records', label: '客户发料', iconClass: 'request', to: 'customerIssuePDA', disabled: true },
] ]
} }
}, },

514
src/views/modules/customerIssue/sales-temporary.vue

@ -0,0 +1,514 @@
<template>
<div>
<div class="pda-container">
<!-- 头部栏 -->
<div class="header-bar">
<div class="header-left" @click="handleBack">
<i class="el-icon-arrow-left"></i>
<span>销售临时</span>
</div>
<div class="header-right" @click="$router.push({ path: '/' })">
首页
</div>
</div>
<div class="table-body" style="max-height: 500px; overflow-y: auto;">
<div class="main-content form-section">
<!-- 标签扫描输入框 -->
<div class="input-group">
<el-input v-model="labelCode" placeholder="请扫描标签编码" class="form-input" clearable inputmode="none"
autocomplete="off" autocorrect="off" spellcheck="false" @keyup.enter.native="handleLabelScan"
ref="labelInput" />
</div>
<!-- 标签信息显示 (扫描后显示) -->
<div v-if="labelInfo" class="info-section">
<div class="info-title">
<i class="el-icon-document">标签信息</i>
</div>
<div class="info-row">
<span class="info-label">标签编码:</span>
<span class="info-value">{{ labelInfo.unitId || '-' }}</span>
</div>
<div class="info-row">
<span class="info-label">物料编码:</span>
<span class="info-value">{{ labelInfo.partNo || '-' }}</span>
</div>
<div class="info-row">
<span class="info-label">入库数量:</span>
<el-input v-model="editableQty" class="qty-input" type="number" :min="0" placeholder="请输入数量" clearable />
</div>
<div class="info-row">
<span class="info-label">批次号:</span>
<span class="info-value">{{ labelInfo.batchNo || '-' }}</span>
</div>
<div class="info-row">
<span class="info-label">仓库:</span>
<span class="info-value">{{ labelInfo.warehouseId || '-' }}</span>
</div>
<div class="info-row">
<span class="info-label">库位:</span>
<span class="info-value">{{ labelInfo.locationId || '-' }}</span>
</div>
<div class="info-row">
<span class="info-label">WDR:</span>
<span class="info-value">{{ labelInfo.wdr || '-' }}</span>
</div>
<div class="info-row">
<span class="info-label">创建时间:</span>
<span class="info-value">{{ formatDate(labelInfo.createdDate) }}</span>
</div>
</div>
<!-- 底部操作按钮 -->
<div v-if="labelInfo" class="bottom-actions">
<button class="action-btn primary" @click="handlePrint" :disabled="printLoading || createloading">
创建打印
</button>
<button class="action-btn secondary" @click="clearData">
清空
</button>
</div>
</div>
</div>
</div>
</div>
</template>
<script>
import {
queryLabelInfo,
createNewHu,
} from '@/api/customerIssue/customer-issue.js'
import { printLabelCommon } from '@/api/production/production-inbound.js'
export default {
name: 'SalesTemporary',
data() {
return {
site: localStorage.getItem('site'),
labelCode: '',
labelInfo: null,
editableQty: '',
loading: false,
printLoading: false,
createloading: false,
}
},
methods: {
/**
* 返回上一页
*/
handleBack() {
this.$router.back()
},
/**
* 处理标签扫描
*/
handleLabelScan() {
if (!this.labelCode.trim()) {
this.$message.error('请扫描有效的标签编码')
return
}
this.loading = true
queryLabelInfo({
site: this.site,
labelCode: this.labelCode.trim(),
})
.then(({ data }) => {
this.loading = false
if (data && data.code === 0) {
this.labelInfo = data.data
this.editableQty = data.data.qty || '0'
this.$message.success('查询成功')
} else {
this.$message.error(data.msg || '标签不存在')
this.labelCode = ''
this.labelInfo = null
this.focusLabelInput()
}
})
.catch((error) => {
this.loading = false
console.error('查询标签失败:', error)
this.$message.error('查询异常')
this.labelCode = ''
this.labelInfo = null
this.focusLabelInput()
})
},
/**
* 清空数据
*/
clearData() {
this.labelCode = ''
this.labelInfo = null
this.editableQty = ''
this.focusLabelInput()
},
/**
* 聚焦标签输入框
*/
focusLabelInput() {
this.$nextTick(() => {
if (this.$refs.labelInput) {
this.$refs.labelInput.focus()
}
})
},
/**
* 格式化日期
*/
formatDate(date) {
if (!date) return '-'
const d = new Date(date)
const year = d.getFullYear()
const month = String(d.getMonth() + 1).padStart(2, '0')
const day = String(d.getDate()).padStart(2, '0')
const hours = String(d.getHours()).padStart(2, '0')
const minutes = String(d.getMinutes()).padStart(2, '0')
return `${year}-${month}-${day} ${hours}:${minutes}`
},
/**
* 获取状态标签类型
*/
getStatusType(inStockFlag) {
return inStockFlag === 'Y' ? 'success' : 'danger'
},
/**
* 处理打印
*/
handlePrint() {
if (!this.labelInfo || !this.labelInfo.unitId) {
this.$message.error('没有可打印的标签信息')
return
}
if(!this.editableQty){
this.$message.error('请输入数量')
return
}
this.labelInfo.qty = this.editableQty || '0'
let selectedMaterials = [
{
...this.labelInfo,
},
]
console.log('准备创建新HU并打印,标签信息:', selectedMaterials)
let params = {
site: localStorage.getItem('site'),
workOrderNo: this.labelInfo.workOrderNo || '',
WarehouseId: this.labelInfo.warehouseId || '',
selectedMaterials: selectedMaterials,
}
this.createloading = true
createNewHu(params).then(({ data }) => {
if (data && data.code == 0) {
if(data.unitIds.length == 0){
this.$message.error('创建拆分新HU失败: 未返回有效的HU信息')
return
}
let printLabelType
if (
this.labelInfo.partNo &&
this.labelInfo.partNo.startsWith('80')
) {
printLabelType = '库存成品标签'
} else {
printLabelType = 'BIL标签'
}
// unitId
this.printViaServer(data.unitIds, printLabelType)
}else {
this.$message.error(data.msg || '创建拆分新HU失败')
}
})
.catch((error) => {
this.$message.error('创建拆分新HU失败:', error.msg)
}).finally(() => {
this.createloading = false
})
},
/**
* 通过服务器打印
* @param {Array} unitIds - HU unitId列表
* @param {String} printLabelType - 标签类型
*/
async printViaServer(unitIds, printLabelType) {
if (!unitIds || unitIds.length === 0) {
console.warn('没有可打印的标签')
return
}
this.printLoading = true
try {
const printRequest = {
userId: localStorage.getItem('userName'),
username: localStorage.getItem('userName'),
site: localStorage.getItem('site'),
unitIds: unitIds,
labelType: printLabelType,
}
console.log('打印请求:', printRequest)
const { data } = await printLabelCommon(printRequest)
if (data.code === 200 || data.code === 0) {
this.$message.success(`打印任务已发送!`)
this.clearData()
} else {
this.$message.error(data.msg || '打印失败')
}
} catch (error) {
console.error('服务器打印失败:', error)
this.$message.error(`打印失败: ${error.message || error}`)
} finally {
this.printLoading = false
}
},
},
mounted() {
//
this.focusLabelInput()
},
}
</script>
<style scoped>
/* PDA容器样式 */
.pda-container {
width: 100vw;
height: 120vh;
display: flex;
flex-direction: column;
background: #f5f5f5;
font-family: 'Arial', sans-serif;
}
/* 头部栏样式 */
.header-bar {
display: flex;
justify-content: space-between;
align-items: center;
padding: 8px 16px;
background: #17b3a3;
color: white;
height: 40px;
min-height: 40px;
max-height: 40px;
}
.header-left {
display: flex;
align-items: center;
cursor: pointer;
}
.header-left i {
margin-right: 8px;
font-size: 18px;
}
.header-left span {
font-size: 16px;
font-weight: 500;
}
.header-right {
cursor: pointer;
font-size: 14px;
padding: 4px 8px;
border-radius: 4px;
}
/* 主要内容区 */
.table-body {
flex: 1;
overflow-y: auto;
}
.main-content {
padding: 16px;
}
/* 输入组样式 */
.input-label {
display: block;
margin-bottom: 8px;
font-size: 14px;
font-weight: 500;
color: #333;
}
.form-input {
width: 100%;
height: 44px;
}
/* 信息展示区 */
.info-section {
background: white;
border-radius: 8px;
padding: 16px;
box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1);
}
.info-title {
display: flex;
align-items: center;
justify-content: space-between;
font-size: 16px;
font-weight: bold;
color: #17b3a3;
margin-bottom: 6px;
padding-bottom: 5px;
border-bottom: 2px solid #17b3a3;
}
.info-title i {
margin-right: 8px;
font-size: 18px;
}
/* 数量输入框 */
.qty-input {
flex: 1;
max-width: 200px;
margin-left: auto;
}
.qty-input >>> .el-input__inner {
text-align: center;
font-size: 14px;
font-weight: 500;
color: #333;
height: 32px;
line-height: 32px;
}
.info-row {
display: flex;
justify-content: space-between;
align-items: flex-start;
padding: 10px 0;
border-bottom: 1px solid #f0f0f0;
}
.info-row:last-child {
border-bottom: none;
}
.info-label {
font-size: 14px;
color: #666;
min-width: 90px;
flex-shrink: 0;
}
.info-value {
font-size: 14px;
font-weight: 500;
color: #333;
flex: 1;
text-align: right;
word-break: break-all;
}
/* 底部按钮区 */
.bottom-actions {
display: flex;
gap: 12px;
padding-top: 16px;
}
.action-btn {
flex: 1;
padding: 12px 24px;
border: none;
border-radius: 6px;
font-size: 16px;
font-weight: 500;
cursor: pointer;
transition: all 0.2s;
min-height: 44px;
}
.action-btn.primary {
background: #17b3a3;
color: white;
}
.action-btn.primary:hover:not(:disabled) {
background: #15a394;
}
.action-btn.primary:disabled {
background: #ccc;
cursor: not-allowed;
opacity: 0.6;
}
.action-btn.secondary {
background: #f5f5f5;
color: #333;
border: 1px solid #ddd;
}
.action-btn.secondary:hover {
background: #e8e8e8;
}
/* 响应式设计 */
@media screen and (max-width: 480px) {
.header-bar {
padding: 8px 12px;
}
.main-content {
padding: 12px;
}
.info-section {
padding: 2px;
}
.info-label {
font-size: 13px;
min-width: 80px;
}
.info-value {
font-size: 13px;
}
.action-btn {
padding: 10px 16px;
font-size: 14px;
}
}
</style>

2
src/views/modules/production-issue/directIssueDetail.vue

@ -139,7 +139,7 @@
</div> </div>
<div class="form-group"> <div class="form-group">
<label class="form-label">修改数量 <span class="required">*</span></label>
<label class="form-label">需要发料数量 <span class="required">*</span></label>
<el-input-number v-model="editQuantity" :min="0.0001" :precision="4" :step="0.0001" class="form-input" <el-input-number v-model="editQuantity" :min="0.0001" :precision="4" :step="0.0001" class="form-input"
style="width: 100%;" :controls="false"> style="width: 100%;" :controls="false">
</el-input-number> </el-input-number>

2
src/views/modules/production-issue/productionPickingDetail.vue

@ -139,7 +139,7 @@
</div> </div>
<div class="form-group"> <div class="form-group">
<label class="form-label">修改数量 <span class="required">*</span></label>
<label class="form-label">需要发料数量 <span class="required">*</span></label>
<el-input-number v-model="editQuantity" :min="0.0001" :precision="4" :step="0.0001" class="form-input" <el-input-number v-model="editQuantity" :min="0.0001" :precision="4" :step="0.0001" class="form-input"
style="width: 100%;" :controls="false" /> style="width: 100%;" :controls="false" />
</div> </div>

2
src/views/modules/production-return/productionReturnPDAIssueList.vue

@ -334,7 +334,7 @@
</div> </div>
<div class="form-group"> <div class="form-group">
<label class="form-label">数量 <span class="required">*</span></label>
<label class="form-label">退料数量 <span class="required">*</span></label>
<el-input-number v-model="newLabelForm.quantity" :min="0" :controls="false" placeholder="请输入数量" <el-input-number v-model="newLabelForm.quantity" :min="0" :controls="false" placeholder="请输入数量"
class="form-input" style="width: 100%;" /> class="form-input" style="width: 100%;" />
</div> </div>

4
src/views/modules/production-return/productionReturnPickingDetail.vue

@ -133,7 +133,7 @@
<el-input v-model="editForm.height" type="number" :min="0" placeholder="请输入高度(单位毫米)" class="form-input" clearable/> <el-input v-model="editForm.height" type="number" :min="0" placeholder="请输入高度(单位毫米)" class="form-input" clearable/>
</div> </div>
<div class="form-group"> <div class="form-group">
<label class="form-label">标签数量 <span class="required">*</span></label>
<label class="form-label">退料数量 <span class="required">*</span></label>
<el-input v-model="editForm.quantity" type="number" :min="0" placeholder="请输入标签数量" class="form-input" clearable/> <el-input v-model="editForm.quantity" type="number" :min="0" placeholder="请输入标签数量" class="form-input" clearable/>
</div> </div>
</div> </div>
@ -186,7 +186,7 @@
</div> </div>
<div class="form-group"> <div class="form-group">
<label class="form-label">数量 <span class="required">*</span></label>
<label class="form-label">退料数量 <span class="required">*</span></label>
<el-input-number <el-input-number
v-model="newLabelForm.quantity" v-model="newLabelForm.quantity"
:min="0" :min="0"

Loading…
Cancel
Save