对于成品的条形码进行功能实现
This commit is contained in:
@ -54,8 +54,11 @@
|
||||
</el-table-column>
|
||||
</template>
|
||||
|
||||
<el-table-column label="操作" width="160" fixed="right" align="center">
|
||||
<el-table-column label="操作" width="220" fixed="right" align="center">
|
||||
<template #default="{ row }">
|
||||
<el-button link type="warning" size="default" @click="handlePrint(row)">
|
||||
<el-icon><Printer/></el-icon> 打印
|
||||
</el-button>
|
||||
<el-button link type="primary" @click="handleUpdate(row)">编辑</el-button>
|
||||
<el-popconfirm title="确定删除?" @confirm="handleDelete(row)"><template #reference><el-button link type="danger">删除</el-button></template></el-popconfirm>
|
||||
</template>
|
||||
@ -117,8 +120,8 @@
|
||||
<div class="card-title"><el-icon class="icon"><House /></el-icon><span>2. 入库详情</span></div>
|
||||
<div class="card-content">
|
||||
<el-row :gutter="24">
|
||||
<el-col :span="6"><el-form-item label="SKU" prop="sku"><el-input v-model="form.sku" /></el-form-item></el-col>
|
||||
<el-col :span="6"><el-form-item label="条码" prop="barcode"><el-input v-model="form.barcode" /></el-form-item></el-col>
|
||||
<el-col :span="6"><el-form-item label="SKU" prop="sku"><el-input v-model="form.sku" placeholder="自动生成" disabled /></el-form-item></el-col>
|
||||
<el-col :span="6"><el-form-item label="条码" prop="barcode"><el-input v-model="form.barcode" placeholder="自动生成" /></el-form-item></el-col>
|
||||
<el-col :span="6"><el-form-item label="库位" prop="warehouse_location"><el-input v-model="form.warehouse_location" /></el-form-item></el-col>
|
||||
<el-col :span="6"><el-form-item label="入库日期"><el-date-picker v-model="form.in_date" type="date" value-format="YYYY-MM-DD" style="width:100%" disabled /></el-form-item></el-col>
|
||||
</el-row>
|
||||
@ -197,20 +200,51 @@
|
||||
<template #footer>
|
||||
<div class="dialog-footer">
|
||||
<el-button @click="visible = false" size="large">取消</el-button>
|
||||
<el-button type="primary" :loading="submitting" @click="submitForm" size="large">提交</el-button>
|
||||
<el-button type="primary" :loading="submitting" @click="submitForm" size="large" class="confirm-btn">
|
||||
{{ dialogStatus === 'create' ? '提交并打印' : '保存修改' }}
|
||||
</el-button>
|
||||
</div>
|
||||
</template>
|
||||
</el-dialog>
|
||||
|
||||
<el-dialog
|
||||
v-model="printVisible"
|
||||
title="标签打印预览"
|
||||
width="400px"
|
||||
destroy-on-close
|
||||
append-to-body
|
||||
>
|
||||
<div style="text-align: center;">
|
||||
<div v-loading="printLoading" class="preview-box">
|
||||
<img v-if="previewUrl" :src="previewUrl" alt="Label Preview" style="width: 100%; border: 1px solid #ccc;"/>
|
||||
<div v-else class="empty-preview">正在生成预览...</div>
|
||||
</div>
|
||||
|
||||
<div style="margin-top: 20px; font-size: 14px; color: #666;">
|
||||
<p>打印机 IP: 192.168.9.205</p>
|
||||
<p>尺寸: 40mm x 30mm</p>
|
||||
</div>
|
||||
</div>
|
||||
<template #footer>
|
||||
<div class="dialog-footer">
|
||||
<el-button @click="printVisible = false">取消</el-button>
|
||||
<el-button type="primary" :loading="printing" @click="confirmPrint">
|
||||
<el-icon><Printer/></el-icon> 确认打印
|
||||
</el-button>
|
||||
</div>
|
||||
</template>
|
||||
</el-dialog>
|
||||
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script setup lang="ts">
|
||||
import { ref, reactive, onMounted, watch } from 'vue'
|
||||
import { Plus, Setting, Refresh, Search, Box, House, Link, InfoFilled } from '@element-plus/icons-vue'
|
||||
import { Plus, Setting, Refresh, Search, Box, House, Link, InfoFilled, Printer } from '@element-plus/icons-vue'
|
||||
import { ElMessage } from 'element-plus'
|
||||
import dayjs from 'dayjs'
|
||||
// 引用更新后的 product.ts
|
||||
import { getProductList, createProductInbound, updateProductInbound, deleteProductInbound, searchMaterialBase } from '@/api/inbound/product'
|
||||
import { getLabelPreview, executePrint } from '@/api/common/print'
|
||||
|
||||
const loading = ref(false)
|
||||
const submitting = ref(false)
|
||||
@ -223,6 +257,13 @@ const formRef = ref()
|
||||
const queryParams = reactive({ page: 1, pageSize: 15, keyword: '' })
|
||||
const materialOptions = ref<any[]>([])
|
||||
|
||||
// 打印相关变量
|
||||
const printVisible = ref(false)
|
||||
const printLoading = ref(false)
|
||||
const printing = ref(false)
|
||||
const previewUrl = ref('')
|
||||
const currentPrintData = ref<any>({})
|
||||
|
||||
const allColumns = [
|
||||
{ prop: 'material_name', label: '名称', minWidth: '120' },
|
||||
{ prop: 'spec_model', label: '规格', minWidth: '120' },
|
||||
@ -246,7 +287,7 @@ const allColumns = [
|
||||
const visibleColumnProps = ref(allColumns.map(c => c.prop))
|
||||
|
||||
const form = reactive({
|
||||
id: undefined, base_id: undefined, material_name: '', spec_model: '', material_type: '',
|
||||
id: undefined, base_id: undefined, material_name: '', spec_model: '', material_type: '', category: '',
|
||||
sku: '', barcode: '', serial_number: '', in_date: '',
|
||||
in_quantity: 1, stock_quantity: 1, available_quantity: 1,
|
||||
warehouse_location: '', status: '在库', quality_status: '合格',
|
||||
@ -386,6 +427,7 @@ const onMaterialSelected = (val: number) => {
|
||||
form.material_name = item.name
|
||||
form.spec_model = item.spec
|
||||
form.material_type = item.type
|
||||
form.category = item.category
|
||||
}
|
||||
}
|
||||
|
||||
@ -411,11 +453,15 @@ const handleUpdate = (row: any) => {
|
||||
id: row.base_id,
|
||||
name: row.material_name,
|
||||
spec: row.spec_model,
|
||||
category: row.category,
|
||||
isHistory: false
|
||||
}]
|
||||
visible.value = true
|
||||
}
|
||||
|
||||
// ------------------------------------
|
||||
// 提交逻辑 (含自动打印)
|
||||
// ------------------------------------
|
||||
const submitForm = async () => {
|
||||
await formRef.value.validate(async (valid: boolean) => {
|
||||
if(valid) {
|
||||
@ -425,13 +471,33 @@ const submitForm = async () => {
|
||||
production_start_time: form.production_time_range?.[0],
|
||||
production_end_time: form.production_time_range?.[1]
|
||||
}
|
||||
if(dialogStatus.value === 'create') await createProductInbound(payload)
|
||||
else await updateProductInbound(form.id!, payload)
|
||||
|
||||
if(dialogStatus.value === 'create') {
|
||||
// 1. 创建入库
|
||||
const res: any = await createProductInbound(payload)
|
||||
ElMessage.success('入库成功')
|
||||
|
||||
// 2. 自动打印
|
||||
const newItem = res.data
|
||||
if (newItem) {
|
||||
ElMessage.info('正在发送打印指令...')
|
||||
try {
|
||||
await executePrint(newItem)
|
||||
ElMessage.success('打印指令已发送')
|
||||
} catch (printErr: any) {
|
||||
console.error(printErr)
|
||||
ElMessage.warning('入库成功,但自动打印失败:' + (printErr.msg || '未知错误'))
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
await updateProductInbound(form.id!, payload)
|
||||
ElMessage.success('更新成功')
|
||||
}
|
||||
|
||||
// 保存历史
|
||||
saveToHistory(HISTORY_KEYS.PRODUCTION_MANAGER, form.production_manager)
|
||||
|
||||
ElMessage.success('操作成功')
|
||||
visible.value = false
|
||||
fetchData()
|
||||
} catch(e:any) { ElMessage.error(e.msg || '失败') }
|
||||
@ -445,10 +511,54 @@ const handleDelete = async (row: any) => {
|
||||
catch(e) { ElMessage.error('删除失败') }
|
||||
}
|
||||
|
||||
// ------------------------------------
|
||||
// 打印逻辑 (手动 & 预览)
|
||||
// ------------------------------------
|
||||
const handlePrint = async (row: any) => {
|
||||
printVisible.value = true
|
||||
printLoading.value = true
|
||||
previewUrl.value = ''
|
||||
|
||||
// 构造产品特有的打印数据
|
||||
const printData = {
|
||||
global_print_id: row.global_print_id, // 需后端模型支持
|
||||
material_name: row.material_name,
|
||||
spec_model: row.spec_model,
|
||||
category: row.category,
|
||||
material_type: row.material_type,
|
||||
warehouse_loc: row.warehouse_loc,
|
||||
serial_number: row.serial_number,
|
||||
sku: row.sku
|
||||
}
|
||||
currentPrintData.value = printData
|
||||
|
||||
try {
|
||||
const res: any = await getLabelPreview(printData)
|
||||
previewUrl.value = res.data
|
||||
} catch (e) {
|
||||
ElMessage.error('预览生成失败')
|
||||
} finally {
|
||||
printLoading.value = false
|
||||
}
|
||||
}
|
||||
|
||||
const confirmPrint = async () => {
|
||||
printing.value = true
|
||||
try {
|
||||
await executePrint(currentPrintData.value)
|
||||
ElMessage.success('指令已发送')
|
||||
printVisible.value = false
|
||||
} catch (e: any) {
|
||||
ElMessage.error(e.msg || '打印失败')
|
||||
} finally {
|
||||
printing.value = false
|
||||
}
|
||||
}
|
||||
|
||||
const resetForm = () => {
|
||||
materialOptions.value = []
|
||||
Object.assign(form, {
|
||||
id: undefined, base_id: undefined, material_name: '', spec_model: '', material_type: '',
|
||||
id: undefined, base_id: undefined, material_name: '', spec_model: '', material_type: '', category: '',
|
||||
sku: '', barcode: '', serial_number: '', in_date: '',
|
||||
in_quantity: 1, stock_quantity: 1, available_quantity: 1,
|
||||
warehouse_location: '', status: '在库', quality_status: '合格',
|
||||
@ -484,4 +594,17 @@ onMounted(() => fetchData())
|
||||
.opt-spec { color: #8492a6; font-size: 12px; margin-right: 10px; }
|
||||
.is-text-view :deep(.el-input__wrapper) { box-shadow: none !important; background: #f5f7fa; border-bottom: 1px solid #dcdfe6; }
|
||||
.search-tip { color: #909399; font-size: 12px; margin-left: 10px; display: flex; align-items: center; gap: 4px; }
|
||||
|
||||
/* 打印预览样式 */
|
||||
.preview-box {
|
||||
min-height: 150px;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
background: #f5f7fa;
|
||||
border-radius: 4px;
|
||||
}
|
||||
.empty-preview {
|
||||
color: #909399;
|
||||
}
|
||||
</style>
|
||||
Reference in New Issue
Block a user