diff --git a/apps/web-antd/src/views/mes/wm/stocktaking/plan/components/condition-value-input.vue b/apps/web-antd/src/views/mes/wm/stocktaking/plan/components/condition-value-input.vue new file mode 100644 index 000000000..b753f7bdd --- /dev/null +++ b/apps/web-antd/src/views/mes/wm/stocktaking/plan/components/condition-value-input.vue @@ -0,0 +1,204 @@ + + + diff --git a/apps/web-antd/src/views/mes/wm/stocktaking/plan/components/index.ts b/apps/web-antd/src/views/mes/wm/stocktaking/plan/components/index.ts index 5a374ab09..2d492d050 100644 --- a/apps/web-antd/src/views/mes/wm/stocktaking/plan/components/index.ts +++ b/apps/web-antd/src/views/mes/wm/stocktaking/plan/components/index.ts @@ -1,2 +1,3 @@ +export { default as StockTakingPlanConditionValueInput } from './condition-value-input.vue'; export { default as StockTakingPlanSelectDialog } from './select-dialog.vue'; export { default as StockTakingPlanSelect } from './select.vue'; diff --git a/apps/web-antd/src/views/mes/wm/stocktaking/plan/data.ts b/apps/web-antd/src/views/mes/wm/stocktaking/plan/data.ts index 056230f58..0253ad4ab 100644 --- a/apps/web-antd/src/views/mes/wm/stocktaking/plan/data.ts +++ b/apps/web-antd/src/views/mes/wm/stocktaking/plan/data.ts @@ -1,9 +1,11 @@ +import type { NumberDictDataType } from '@vben/hooks'; + import type { VbenFormApi, VbenFormSchema } from '#/adapter/form'; import type { VxeTableGridOptions } from '#/adapter/vxe-table'; import type { MesWmStockTakingPlanApi } from '#/api/mes/wm/stocktaking/plan'; import type { MesWmStockTakingPlanParamApi } from '#/api/mes/wm/stocktaking/plan/param'; -import { h } from 'vue'; +import { h, markRaw } from 'vue'; import { CommonStatusEnum, @@ -18,6 +20,8 @@ import { Button } from 'ant-design-vue'; import { z } from '#/adapter/form'; import { generateAutoCode } from '#/api/mes/md/autocode/record'; +import { StockTakingPlanConditionValueInput } from './components'; + /** 表单类型 */ export type FormType = 'create' | 'detail' | 'update'; @@ -292,6 +296,86 @@ export function useParamGridColumns( ]; } +/** 盘点方案条件表单 schema */ +export function useParamFormSchema(formApi?: VbenFormApi): VbenFormSchema[] { + return [ + { + fieldName: 'type', + label: '条件类型', + component: 'Select', + componentProps: { + options: getDictOptions( + DICT_TYPE.MES_WM_STOCK_TAKING_PLAN_PARAM_TYPE, + 'number', + ) as NumberDictDataType[], + placeholder: '请选择条件类型', + // 条件类型变化:清空已选条件值,避免残留旧类型的条件值 + onChange: async () => { + await formApi?.setValues({ + valueCode: '', + valueId: undefined, + valueName: '', + }); + }, + }, + rules: 'selectRequired', + }, + { + fieldName: 'valueId', + label: '条件值', + component: markRaw(StockTakingPlanConditionValueInput), + // 条件值控件内部按条件类型切换选择器,仅选择类型后展示 + dependencies: { + triggerFields: ['type'], + if: (values) => values.type != null, + componentProps: (values) => ({ + type: values.type, + valueCode: values.valueCode, + // 条件值控件回填 valueId / valueCode / valueName + onValueChange: async (payload: { + valueCode?: string; + valueId?: number; + valueName?: string; + }) => { + await formApi?.setValues({ + valueCode: payload.valueCode ?? '', + valueId: payload.valueId, + valueName: payload.valueName ?? '', + }); + }, + }), + }, + }, + { + // 条件值编码:由条件值控件回写,隐藏字段 + fieldName: 'valueCode', + component: 'Input', + dependencies: { + triggerFields: [''], + show: () => false, + }, + }, + { + // 条件值名称:由条件值控件回写,隐藏字段 + fieldName: 'valueName', + component: 'Input', + dependencies: { + triggerFields: [''], + show: () => false, + }, + }, + { + fieldName: 'remark', + label: '备注', + component: 'Textarea', + componentProps: { + placeholder: '请输入备注', + rows: 3, + }, + }, + ]; +} + /** 选择弹窗的搜索表单 */ export function useSelectGridFormSchema(): VbenFormSchema[] { return [ diff --git a/apps/web-antd/src/views/mes/wm/stocktaking/plan/modules/param-form.vue b/apps/web-antd/src/views/mes/wm/stocktaking/plan/modules/param-form.vue index 6ccb0ca3e..807a77eb0 100644 --- a/apps/web-antd/src/views/mes/wm/stocktaking/plan/modules/param-form.vue +++ b/apps/web-antd/src/views/mes/wm/stocktaking/plan/modules/param-form.vue @@ -4,144 +4,68 @@ import type { MesWmStockTakingPlanParamApi } from '#/api/mes/wm/stocktaking/plan import { computed, ref } from 'vue'; import { useVbenModal } from '@vben/common-ui'; -import { DICT_TYPE, MesWmStockTakingParamTypeEnum } from '@vben/constants'; -import { getDictOptions } from '@vben/hooks'; +import { MesWmStockTakingParamTypeEnum } from '@vben/constants'; -import { Form, message, Select, Textarea } from 'ant-design-vue'; +import { message } from 'ant-design-vue'; +import { useVbenForm } from '#/adapter/form'; import { createStockTakingPlanParam, getStockTakingPlanParam, updateStockTakingPlanParam, } from '#/api/mes/wm/stocktaking/plan/param'; -import { getWarehouseArea } from '#/api/mes/wm/warehouse/area'; -import { getWarehouseLocation } from '#/api/mes/wm/warehouse/location'; import { $t } from '#/locales'; -import { MdItemSelect } from '#/views/mes/md/item/components'; -import { WmBatchSelect } from '#/views/mes/wm/batch/components'; -import { - WmWarehouseAreaSelect, - WmWarehouseLocationSelect, - WmWarehouseSelect, -} from '#/views/mes/wm/warehouse/components'; + +import { useParamFormSchema } from '../data'; const emit = defineEmits(['success']); -const formData = ref({}); -const planId = ref(); // TODO @AI:这里是不是要尾注释 -const locationWarehouseId = ref(); // 库区选择器临时数据:选仓库后传给库区选择器 -const areaWarehouseId = ref(); // 库位选择器临时数据:选仓库后传给库区选择器 -const areaLocationId = ref(); // 库位选择器临时数据:选库区后传给库位选择器 +const formId = ref(); // 当前编辑的条件编号 +const planId = ref(); // 所属盘点方案编号 -// TODO @AI:按照项目的风格,不要 mapping;直接界面那处理掉;简化逻辑; -const paramTypeOptions = getDictOptions( - DICT_TYPE.MES_WM_STOCK_TAKING_PLAN_PARAM_TYPE, - 'number', -).map(({ label, value }) => ({ label, value: Number(value) })); -const qualityStatusOptions = getDictOptions( - DICT_TYPE.MES_WM_QUALITY_STATUS, - 'string', -).map(({ label, value }) => ({ label, value: String(value) })); - -// TODO @AI:如果 title 和前面的 const 也是变量,不用空行; const getTitle = computed(() => - formData.value?.id + formId.value ? $t('ui.actionTitle.edit', ['盘点条件']) : $t('ui.actionTitle.create', ['盘点条件']), ); -/** 条件类型变化:清空已选条件值和级联临时数据 */ -function handleTypeChange() { - formData.value.valueId = undefined; - formData.value.valueCode = ''; - formData.value.valueName = ''; - locationWarehouseId.value = undefined; - areaWarehouseId.value = undefined; - areaLocationId.value = undefined; -} - -/** 通用选择器变化:回填条件值编码、名称 */ -function handleSelectorChange(item?: any) { - formData.value.valueId = item?.id; - formData.value.valueCode = item?.code || ''; - formData.value.valueName = item?.name || item?.nickname || ''; -} - -/** 批次选择器变化 */ -function handleBatchChange(batch?: any) { - formData.value.valueId = batch?.id; - formData.value.valueCode = batch?.code || ''; - formData.value.valueName = batch?.code || ''; -} - -/** 质量状态选择器变化:无实体编号,仅记录字典编码和文案 */ -function handleQualityStatusChange(value: any) { - const selected = qualityStatusOptions.find((item) => item.value === value); - formData.value.valueId = undefined; - formData.value.valueCode = value; - formData.value.valueName = selected?.label || ''; -} - -/** 库区仓库选择回调:清空库区 */ -function handleLocationWarehouseChange() { - formData.value.valueId = undefined; - formData.value.valueCode = ''; - formData.value.valueName = ''; -} - -/** 库位仓库选择回调:清空库区和库位 */ -function handleAreaWarehouseChange() { - areaLocationId.value = undefined; - formData.value.valueId = undefined; - formData.value.valueCode = ''; - formData.value.valueName = ''; -} - -/** 库位库区选择回调:清空库位 */ -function handleAreaLocationChange() { - formData.value.valueId = undefined; - formData.value.valueCode = ''; - formData.value.valueName = ''; -} - -/** 编辑时回填级联选择器的上级数据(库区所属仓库、库位所属仓库/库区) */ -async function loadCascadeData() { - if (!formData.value.type || !formData.value.valueId) { - return; - } - const valueId = formData.value.valueId; - if (formData.value.type === MesWmStockTakingParamTypeEnum.LOCATION) { - const location = await getWarehouseLocation(valueId); - locationWarehouseId.value = location?.warehouseId; - } else if (formData.value.type === MesWmStockTakingParamTypeEnum.AREA) { - const area = await getWarehouseArea(valueId); - areaWarehouseId.value = area?.warehouseId; - areaLocationId.value = area?.locationId; - } -} +const [Form, formApi] = useVbenForm({ + commonConfig: { + componentProps: { + class: 'w-full', + }, + }, + layout: 'horizontal', + schema: [], + showDefaultActions: false, + wrapperClass: 'grid-cols-1', +}); const [Modal, modalApi] = useVbenModal({ async onConfirm() { - if (!formData.value.type) { - message.warning('请选择条件类型'); + const { valid } = await formApi.validate(); + if (!valid) { return; } + const values = + (await formApi.getValues()) as MesWmStockTakingPlanParamApi.StockTakingPlanParam; // 质量状态校验 valueCode,其余类型校验 valueId - const valid = - formData.value.type === MesWmStockTakingParamTypeEnum.QUALITY_STATUS - ? !!formData.value.valueCode - : formData.value.valueId != null; - if (!valid) { + const valueValid = + values.type === MesWmStockTakingParamTypeEnum.QUALITY_STATUS + ? !!values.valueCode + : values.valueId != null; + if (!valueValid) { message.warning('请选择条件值'); return; } modalApi.lock(); // 提交表单 const data = { - ...formData.value, + ...values, + id: formId.value, planId: planId.value, } as MesWmStockTakingPlanParamApi.StockTakingPlanParam; try { - await (formData.value.id + await (formId.value ? updateStockTakingPlanParam(data) : createStockTakingPlanParam(data)); // 关闭并提示 @@ -154,113 +78,31 @@ const [Modal, modalApi] = useVbenModal({ }, async onOpenChange(isOpen: boolean) { if (!isOpen) { - formData.value = {}; - locationWarehouseId.value = undefined; - areaWarehouseId.value = undefined; - areaLocationId.value = undefined; + formId.value = undefined; return; } + formApi.setState({ schema: useParamFormSchema(formApi) }); // 加载数据 const data = modalApi.getData<{ id?: number; planId: number }>(); planId.value = data.planId; + formId.value = data.id; if (!data.id) { return; } modalApi.lock(); try { - formData.value = await getStockTakingPlanParam(data.id); - await loadCascadeData(); + const param = await getStockTakingPlanParam(data.id); + // 设置到 values + await formApi.setValues(param); } finally { modalApi.unlock(); } }, }); - -const ParamTypeEnum = MesWmStockTakingParamTypeEnum; -