2026-05-12 16:44:32 +08:00
|
|
|
<template>
|
|
|
|
|
<Dialog :title="dialogTitle" v-model="dialogVisible" width="1200px">
|
|
|
|
|
<div class="dialog-content">
|
|
|
|
|
<!-- 搜索区域 -->
|
|
|
|
|
<el-form :model="queryParams" inline label-width="80px">
|
|
|
|
|
<el-form-item label="产品编码">
|
|
|
|
|
<el-input v-model="queryParams.matCode" placeholder="请输入产品编码查询" clearable class="!w-180px" />
|
|
|
|
|
</el-form-item>
|
|
|
|
|
<el-form-item label="产品名称">
|
|
|
|
|
<el-input v-model="queryParams.matName" placeholder="请输入产品名称查询" clearable class="!w-180px" />
|
|
|
|
|
</el-form-item>
|
|
|
|
|
<el-form-item label="规格型号">
|
|
|
|
|
<el-input v-model="queryParams.spec" placeholder="请输入规格型号查询" clearable class="!w-180px" />
|
|
|
|
|
</el-form-item>
|
|
|
|
|
<el-form-item>
|
|
|
|
|
<el-button type="primary" @click="searchMaterial">
|
|
|
|
|
<Icon icon="ep:search" class="mr-5px" />查询
|
|
|
|
|
</el-button>
|
|
|
|
|
<el-button @click="resetQuery">
|
|
|
|
|
<Icon icon="ep:refresh-right" class="mr-5px" />重置
|
|
|
|
|
</el-button>
|
|
|
|
|
</el-form-item>
|
|
|
|
|
</el-form>
|
|
|
|
|
|
|
|
|
|
<!-- 表格区域 -->
|
|
|
|
|
<el-table
|
|
|
|
|
ref="tableRef"
|
|
|
|
|
v-loading="loading"
|
|
|
|
|
:data="materialList"
|
|
|
|
|
:show-overflow-tooltip="true"
|
|
|
|
|
border
|
|
|
|
|
class="mt-15px"
|
|
|
|
|
@row-click="handleRowClick"
|
|
|
|
|
@row-dblclick="handleRowDblClick"
|
|
|
|
|
>
|
|
|
|
|
<!-- 多选列 -->
|
|
|
|
|
<el-table-column type="selection" width="60px" align="center" />
|
|
|
|
|
<el-table-column label="序号" width="60px" align="center" type="index" />
|
|
|
|
|
<el-table-column label="产品编码" align="center" prop="matCode" />
|
|
|
|
|
<el-table-column label="产品名称" align="center" prop="matName" />
|
|
|
|
|
<el-table-column label="规格型号" align="center" prop="spec" />
|
|
|
|
|
<el-table-column label="单位" align="center" width="100px">
|
|
|
|
|
<template #default="scope">
|
|
|
|
|
{{ getUnitName(scope.row.unit) }}
|
|
|
|
|
</template>
|
|
|
|
|
</el-table-column>
|
|
|
|
|
<el-table-column label="物料类型" align="center" width="120px">
|
|
|
|
|
<template #default="scope">
|
|
|
|
|
{{ getMatTypeName(scope.row.matType) }}
|
|
|
|
|
</template>
|
|
|
|
|
</el-table-column>
|
|
|
|
|
</el-table>
|
|
|
|
|
|
|
|
|
|
<!-- 分页 -->
|
|
|
|
|
<Pagination
|
|
|
|
|
v-model:page="queryParams.pageNo"
|
|
|
|
|
v-model:limit="queryParams.pageSize"
|
|
|
|
|
:total="total"
|
|
|
|
|
@pagination="searchMaterial"
|
|
|
|
|
class="mt-15px"
|
|
|
|
|
/>
|
|
|
|
|
</div>
|
|
|
|
|
|
|
|
|
|
<template #footer>
|
|
|
|
|
<el-button @click="confirmSelection" type="primary">保存</el-button>
|
|
|
|
|
<el-button @click="dialogVisible = false">取消</el-button>
|
|
|
|
|
</template>
|
|
|
|
|
</Dialog>
|
|
|
|
|
</template>
|
|
|
|
|
|
|
|
|
|
<script setup lang="ts">
|
|
|
|
|
import { ref, reactive, nextTick, onMounted } from 'vue'
|
|
|
|
|
import * as MaterialApi from '@/api/biz/material'
|
|
|
|
|
import { Icon } from '@/components/Icon'
|
|
|
|
|
import { getDictOptions } from '@/utils/dict'
|
|
|
|
|
|
|
|
|
|
const message = useMessage()
|
|
|
|
|
const dialogVisible = ref(false)
|
|
|
|
|
const dialogTitle = ref('选择')
|
|
|
|
|
const loading = ref(false)
|
|
|
|
|
const total = ref(0)
|
|
|
|
|
const materialList = ref([])
|
|
|
|
|
const tableRef = ref()
|
|
|
|
|
|
|
|
|
|
// 物料类型数据字典
|
|
|
|
|
const matTypeOptions = ref([])
|
|
|
|
|
// 单位数据字典
|
|
|
|
|
const unitOptions = ref([])
|
|
|
|
|
|
|
|
|
|
const queryParams = reactive({
|
|
|
|
|
pageNo: 1,
|
|
|
|
|
pageSize: 20,
|
|
|
|
|
matCode: undefined,
|
|
|
|
|
matName: undefined,
|
|
|
|
|
spec: undefined,
|
2026-05-14 17:20:41 +08:00
|
|
|
matType: 3
|
2026-05-12 16:44:32 +08:00
|
|
|
})
|
|
|
|
|
|
|
|
|
|
// 已选中的物料ID列表
|
|
|
|
|
const selectedIds = ref<number[]>([])
|
|
|
|
|
|
|
|
|
|
const emit = defineEmits(['confirm'])
|
|
|
|
|
|
|
|
|
|
// 获取物料类型名称
|
|
|
|
|
const getMatTypeName = (matType: string | number) => {
|
|
|
|
|
if (!matType && matType !== 0) return '-'
|
|
|
|
|
const item = matTypeOptions.value.find(opt => String(opt.value) === String(matType))
|
|
|
|
|
return item ? item.label : matType
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 获取单位名称
|
|
|
|
|
const getUnitName = (unit: string | number) => {
|
|
|
|
|
if (!unit && unit !== 0) return '-'
|
|
|
|
|
const item = unitOptions.value.find(opt => String(opt.value) === String(unit))
|
|
|
|
|
return item ? item.label : unit
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 初始化数据字典
|
|
|
|
|
const initDictOptions = () => {
|
|
|
|
|
try {
|
|
|
|
|
matTypeOptions.value = getDictOptions('mat_type')
|
|
|
|
|
unitOptions.value = getDictOptions('mat_unit')
|
|
|
|
|
} catch (e) {
|
|
|
|
|
console.error('获取数据字典失败', e)
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const open = (defaultIds?: number[]) => {
|
|
|
|
|
dialogVisible.value = true
|
|
|
|
|
// 设置默认选中的ID列表
|
|
|
|
|
selectedIds.value = defaultIds || []
|
|
|
|
|
searchMaterial()
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const searchMaterial = async () => {
|
|
|
|
|
loading.value = true
|
|
|
|
|
try {
|
|
|
|
|
const data = await MaterialApi.getMaterialPage(queryParams)
|
|
|
|
|
materialList.value = data.list
|
|
|
|
|
total.value = data.total
|
2026-05-14 17:20:41 +08:00
|
|
|
|
2026-05-12 16:44:32 +08:00
|
|
|
// 数据加载后,设置默认选中
|
|
|
|
|
nextTick(() => {
|
|
|
|
|
if (tableRef.value && selectedIds.value.length > 0) {
|
|
|
|
|
// 根据ID设置选中状态
|
|
|
|
|
materialList.value.forEach(item => {
|
|
|
|
|
if (selectedIds.value.includes(item.id)) {
|
|
|
|
|
tableRef.value.toggleRowSelection(item, true)
|
|
|
|
|
}
|
|
|
|
|
})
|
|
|
|
|
}
|
|
|
|
|
})
|
|
|
|
|
} finally {
|
|
|
|
|
loading.value = false
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const resetQuery = () => {
|
|
|
|
|
queryParams.matCode = undefined
|
|
|
|
|
queryParams.matName = undefined
|
|
|
|
|
queryParams.spec = undefined
|
|
|
|
|
queryParams.pageNo = 1
|
2026-05-14 17:20:41 +08:00
|
|
|
queryParams.matType = 3
|
2026-05-12 16:44:32 +08:00
|
|
|
searchMaterial()
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const handleRowClick = (row: any) => {
|
|
|
|
|
if (tableRef.value) {
|
|
|
|
|
tableRef.value.toggleRowSelection(row)
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const handleRowDblClick = (row: any) => {
|
|
|
|
|
if (tableRef.value) {
|
|
|
|
|
tableRef.value.toggleRowSelection(row)
|
|
|
|
|
const selectedItems = tableRef.value.getSelectionRows()
|
|
|
|
|
emit('confirm', selectedItems)
|
|
|
|
|
dialogVisible.value = false
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const confirmSelection = () => {
|
|
|
|
|
if (!tableRef.value) {
|
|
|
|
|
message.warning('请选择物料')
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
const selectedItems = tableRef.value.getSelectionRows()
|
|
|
|
|
if (selectedItems.length === 0) {
|
|
|
|
|
message.warning('请选择物料')
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
emit('confirm', selectedItems)
|
|
|
|
|
dialogVisible.value = false
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
onMounted(() => {
|
|
|
|
|
initDictOptions()
|
|
|
|
|
})
|
|
|
|
|
|
|
|
|
|
defineExpose({ open })
|
|
|
|
|
</script>
|
|
|
|
|
|
|
|
|
|
<style scoped>
|
|
|
|
|
.dialog-content {
|
|
|
|
|
max-height: 500px;
|
|
|
|
|
overflow-y: auto;
|
|
|
|
|
}
|
|
|
|
|
</style>
|