diff --git a/src/locales/en.ts b/src/locales/en.ts index 569f24e1..9d67620d 100644 --- a/src/locales/en.ts +++ b/src/locales/en.ts @@ -1583,5 +1583,198 @@ export default { updateSuccess: 'Update successful', updateFail: 'Update failed' } + }, + RecipeManagement: { + RecipeType: { + moduleName: 'Recipe Type', + searchNameLabel: 'Name', + searchNamePlaceholder: 'Please enter name', + searchProcessLabel: 'Process', + searchProcessPlaceholder: 'Please select process', + searchButtonText: 'Search', + resetButtonText: 'Reset', + createButtonText: 'Add', + exportButtonText: 'Export', + tableNameColumn: 'Name', + tableProcessColumn: 'Process', + tableRemarkColumn: 'Remark', + tableOperateColumn: 'Operation', + tableEditAction: 'Edit', + tableDeleteAction: 'Delete', + dialogCreateTitle: 'Create Recipe Type', + dialogEditTitle: 'Edit Recipe Type', + dialogNameLabel: 'Name', + dialogNamePlaceholder: 'Please enter name', + dialogProcessLabel: 'Process', + dialogProcessPlaceholder: 'Please select process', + dialogRemarkLabel: 'Remark', + dialogRemarkPlaceholder: 'Please enter remark', + dialogCancelButton: 'Cancel', + dialogSaveButton: 'Save', + validatorNameRequired: 'Name cannot be empty', + validatorProcessRequired: 'Process cannot be empty', + exportNoSelectionMessage: 'Please select data to export', + exportFileName: 'RecipeType.xls' + }, + RecipeConfig: { + moduleName: 'Recipe Config', + searchRecipeCodeLabel: 'Recipe Code', + searchRecipeCodePlaceholder: 'Please enter recipe code', + searchNameLabel: 'Recipe Name', + searchNamePlaceholder: 'Please enter recipe name', + searchProductNameLabel: 'Product Name', + searchProductNamePlaceholder: 'Please enter product name', + searchButtonText: 'Search', + resetButtonText: 'Reset', + createButtonText: 'Add', + exportButtonText: 'Export', + tableRecipeCodeColumn: 'Recipe Code', + tableNameColumn: 'Recipe Name', + tableRecipeTypeColumn: 'Recipe Type', + tableProductNameColumn: 'Related Product', + tableMachineNameColumn: 'Related Device', + tableRecipeDescColumn: 'Recipe Description', + tableOperateColumn: 'Operation', + tableConfigAction: 'Config', + tableEditAction: 'Edit', + tableDeleteAction: 'Delete', + dialogCreateTitle: 'Create Recipe Config', + dialogEditTitle: 'Edit Recipe Config', + dialogRecipeCodeLabel: 'Recipe Code', + dialogRecipeCodePlaceholder: 'Please enter recipe code', + dialogNameLabel: 'Recipe Name', + dialogNamePlaceholder: 'Please enter recipe name', + dialogRecipeTypeLabel: 'Recipe Type', + dialogRecipeTypePlaceholder: 'Please select recipe type', + dialogProductNameLabel: 'Related Product', + dialogProductNamePlaceholder: 'Please select related product', + dialogMachineNameLabel: 'Related Device', + dialogMachineNamePlaceholder: 'Please select related device', + dialogRecipeDescLabel: 'Recipe Description', + dialogRecipeDescPlaceholder: 'Please enter recipe description', + dialogCancelButton: 'Cancel', + dialogSaveButton: 'Save', + validatorRecipeCodeRequired: 'Recipe code cannot be empty', + validatorNameRequired: 'Recipe name cannot be empty', + exportNoSelectionMessage: 'Please select data to export', + exportFileName: 'RecipeConfig.xls', + detailCollapseButton: 'Collapse', + detailTabDetailLabel: 'Detail', + detailTabManualLabel: 'Manual Parameters', + detailConfigButton: 'Config', + detailIndexColumn: 'Index', + detailPointNameColumn: 'Point Name', + detailPointTypeColumn: 'Point Type', + detailDataTypeColumn: 'Data Type', + detailDataUnitColumn: 'Unit', + manualCreateButton: 'Add', + manualTableNameColumn: 'Name', + manualTableMaxColumn: 'Upper Limit', + manualTableMinColumn: 'Lower Limit', + manualTableDataUnitColumn: 'Unit', + manualTableRemarkColumn: 'Remark', + manualTableOperateColumn: 'Operation', + manualTableEditAction: 'Edit', + manualTableDeleteAction: 'Delete', + manualDialogCreateTitle: 'Create Parameter', + manualDialogEditTitle: 'Edit Parameter', + manualDialogNameLabel: 'Name', + manualDialogNamePlaceholder: 'Please enter name', + manualDialogMaxLabel: 'Upper Limit', + manualDialogMaxPlaceholder: 'Please enter upper limit', + manualDialogMinLabel: 'Lower Limit', + manualDialogMinPlaceholder: 'Please enter lower limit', + manualDialogDataTypeLabel: 'Data Type', + manualDialogDataTypePlaceholder: 'Please select data type', + manualDialogDataUnitLabel: 'Unit', + manualDialogDataUnitPlaceholder: 'Please select unit', + manualDialogRemarkLabel: 'Remark', + manualDialogRemarkPlaceholder: 'Please enter remark', + manualDialogCancelButton: 'Cancel', + manualDialogSaveButton: 'Save', + manualValidatorNameRequired: 'Name cannot be empty', + manualValidatorMaxRequired: 'Upper limit cannot be empty', + manualValidatorMinRequired: 'Lower limit cannot be empty', + manualValidatorDataTypeRequired: 'Data type cannot be empty', + manualValidatorDataUnitRequired: 'Unit cannot be empty', + configDialogTitle: 'Config', + configSourceTitle: 'Source', + configTargetTitle: 'Target', + configFilterPlaceholder: 'Filter', + configMoveToTargetButton: 'Add to Target', + configMoveToSourceButton: 'Move to Source', + configCancelButton: 'Cancel', + configSaveButton: 'Save', + configDeviceLabelFallback: '-', + configSourceCountLabel: 'Source Count', + configTargetCountLabel: 'Target Count' + }, + RecipeLibrary: { + moduleName: 'Recipe Library', + searchCodeLabel: 'Code', + searchCodePlaceholder: 'Please enter code', + searchNameLabel: 'Name', + searchNamePlaceholder: 'Please enter name', + searchRecipeLabel: 'Recipe Name', + searchRecipePlaceholder: 'Please select recipe', + searchPlanLabel: 'Related Plan', + searchPlanPlaceholder: 'Please select plan', + searchButtonText: 'Search', + resetButtonText: 'Reset', + createButtonText: 'Add', + exportButtonText: 'Export', + tableCodeColumn: 'Code', + tableNameColumn: 'Name', + tableRecipeNameColumn: 'Recipe Name', + tablePlanCodeColumn: 'Related Plan', + tableCreatorColumn: 'Creator', + tableCreateTimeColumn: 'Create Time', + tableOperateColumn: 'Operation', + tableReadAction: 'Read', + tableEditAction: 'Edit', + tableDeleteAction: 'Delete', + dialogCodeLabel: 'Code', + dialogCodePlaceholder: 'Please enter code', + dialogNameLabel: 'Name', + dialogNamePlaceholder: 'Please enter name', + dialogRecipeLabel: 'Recipe', + dialogRecipePlaceholder: 'Please select recipe', + dialogPlanLabel: 'Related Plan', + dialogPlanPlaceholder: 'Please select plan', + dialogSourceLabel: 'Source', + dialogSourcePlaceholder: 'Please select source', + dialogCancelButton: 'Cancel', + dialogSaveButton: 'Save', + validatorCodeRequired: 'Code cannot be empty', + validatorNameRequired: 'Name cannot be empty', + validatorRecipeRequired: 'Related recipe cannot be empty', + validatorPlanRequired: 'Related plan cannot be empty', + exportFileName: 'RecipeLibrary.xls', + sourceOptionNewLabel: 'New', + sourceOptionProducingLabel: 'In Production', + readDialogTitle: 'Read', + readDialogNameColumn: 'Name', + readDialogDataTypeColumn: 'Data Type', + readDialogDataUnitColumn: 'Unit', + readDialogMaxColumn: 'Upper Limit', + readDialogMinColumn: 'Lower Limit', + readDialogRemarkColumn: 'Remark', + readDialogReferColumn: 'Collected Value', + readDialogReferPlaceholder: 'Please enter collected value', + readDialogSubmitButtonText: 'Read', + readDialogCancelButton: 'Cancel', + readDeviceConfirmMessage: 'Do you want to read device data?', + detailTabDeviceDataLabel: 'Device Data', + detailTabManualLabel: 'Manual Parameters', + detailDevicePointNameColumn: 'Point Name', + detailDeviceDataTypeColumn: 'Data Type', + detailDeviceDataUnitColumn: 'Unit', + detailDeviceValueColumn: 'Collected Value', + manualTableNameColumn: 'Name', + manualTableDataTypeColumn: 'Data Type', + manualTableDataUnitColumn: 'Unit', + manualTableReferColumn: 'Reference Value', + manualTableRemarkColumn: 'Remark' + } } } diff --git a/src/locales/zh-CN.ts b/src/locales/zh-CN.ts index 7f1cc1a1..59c3d96f 100644 --- a/src/locales/zh-CN.ts +++ b/src/locales/zh-CN.ts @@ -1579,5 +1579,198 @@ export default { updateSuccess: '更新成功', updateFail: '更新失败' } + }, + RecipeManagement: { + RecipeType: { + moduleName: '配方类型', + searchNameLabel: '名称', + searchNamePlaceholder: '请输入名称', + searchProcessLabel: '工序', + searchProcessPlaceholder: '请选择工序', + searchButtonText: '查询', + resetButtonText: '重置', + createButtonText: '新增', + exportButtonText: '导出', + tableNameColumn: '名称', + tableProcessColumn: '工序', + tableRemarkColumn: '备注', + tableOperateColumn: '操作', + tableEditAction: '编辑', + tableDeleteAction: '删除', + dialogCreateTitle: '新增配方类型', + dialogEditTitle: '编辑配方类型', + dialogNameLabel: '名称', + dialogNamePlaceholder: '请输入名称', + dialogProcessLabel: '工序', + dialogProcessPlaceholder: '请选择工序', + dialogRemarkLabel: '备注', + dialogRemarkPlaceholder: '请输入备注', + dialogCancelButton: '取 消', + dialogSaveButton: '保 存', + validatorNameRequired: '名称不能为空', + validatorProcessRequired: '工序不能为空', + exportNoSelectionMessage: '请选择需要导出的数据', + exportFileName: '配方类型.xls' + }, + RecipeConfig: { + moduleName: '配方配置', + searchRecipeCodeLabel: '配方编码', + searchRecipeCodePlaceholder: '请输入配方编码', + searchNameLabel: '配方名称', + searchNamePlaceholder: '请输入配方名称', + searchProductNameLabel: '产品名称', + searchProductNamePlaceholder: '请输入产品名称', + searchButtonText: '查询', + resetButtonText: '重置', + createButtonText: '新增', + exportButtonText: '导出', + tableRecipeCodeColumn: '配方编码', + tableNameColumn: '配方名称', + tableRecipeTypeColumn: '配方类型', + tableProductNameColumn: '关联产品', + tableMachineNameColumn: '关联设备', + tableRecipeDescColumn: '配方描述', + tableOperateColumn: '操作', + tableConfigAction: '配置', + tableEditAction: '编辑', + tableDeleteAction: '删除', + dialogCreateTitle: '新增配方配置', + dialogEditTitle: '编辑配方配置', + dialogRecipeCodeLabel: '配方编码', + dialogRecipeCodePlaceholder: '请输入配方编码', + dialogNameLabel: '配方名称', + dialogNamePlaceholder: '请输入配方名称', + dialogRecipeTypeLabel: '配方类型', + dialogRecipeTypePlaceholder: '请选择配方类型', + dialogProductNameLabel: '关联产品', + dialogProductNamePlaceholder: '请选择关联产品', + dialogMachineNameLabel: '关联设备', + dialogMachineNamePlaceholder: '请选择关联设备', + dialogRecipeDescLabel: '配方描述', + dialogRecipeDescPlaceholder: '请输入配方描述', + dialogCancelButton: '取 消', + dialogSaveButton: '保 存', + validatorRecipeCodeRequired: '配方编码不能为空', + validatorNameRequired: '配方名称不能为空', + exportNoSelectionMessage: '请选择需要导出的数据', + exportFileName: '配方配置.xls', + detailCollapseButton: '收起', + detailTabDetailLabel: '详情', + detailTabManualLabel: '手动录入参数', + detailConfigButton: '配置', + detailIndexColumn: '序号', + detailPointNameColumn: '点位名称', + detailPointTypeColumn: '点位类型', + detailDataTypeColumn: '数据类型', + detailDataUnitColumn: '单位', + manualCreateButton: '新增', + manualTableNameColumn: '名称', + manualTableMaxColumn: '上限', + manualTableMinColumn: '下限', + manualTableDataUnitColumn: '单位', + manualTableRemarkColumn: '备注', + manualTableOperateColumn: '操作', + manualTableEditAction: '编辑', + manualTableDeleteAction: '删除', + manualDialogCreateTitle: '新增参数', + manualDialogEditTitle: '编辑参数', + manualDialogNameLabel: '名称', + manualDialogNamePlaceholder: '请输入名称', + manualDialogMaxLabel: '上限', + manualDialogMaxPlaceholder: '请输入上限', + manualDialogMinLabel: '下限', + manualDialogMinPlaceholder: '请输入下限', + manualDialogDataTypeLabel: '数据类型', + manualDialogDataTypePlaceholder: '请选择数据类型', + manualDialogDataUnitLabel: '单位', + manualDialogDataUnitPlaceholder: '请选择单位', + manualDialogRemarkLabel: '备注', + manualDialogRemarkPlaceholder: '请输入备注', + manualDialogCancelButton: '取 消', + manualDialogSaveButton: '保 存', + manualValidatorNameRequired: '名称不能为空', + manualValidatorMaxRequired: '上限不能为空', + manualValidatorMinRequired: '下限不能为空', + manualValidatorDataTypeRequired: '数据类型不能为空', + manualValidatorDataUnitRequired: '单位不能为空', + configDialogTitle: '配置', + configSourceTitle: '来源', + configTargetTitle: '目标', + configFilterPlaceholder: '筛选', + configMoveToTargetButton: '添加到目标', + configMoveToSourceButton: '移回来源', + configCancelButton: '取 消', + configSaveButton: '保 存', + configDeviceLabelFallback: '-', + configSourceCountLabel: '来源数量', + configTargetCountLabel: '目标数量' + }, + RecipeLibrary: { + moduleName: '配方库', + searchCodeLabel: '编码', + searchCodePlaceholder: '请输入编码', + searchNameLabel: '名称', + searchNamePlaceholder: '请输入名称', + searchRecipeLabel: '配方名称', + searchRecipePlaceholder: '请选择配方', + searchPlanLabel: '关联计划', + searchPlanPlaceholder: '请选择关联计划', + searchButtonText: '查询', + resetButtonText: '重置', + createButtonText: '新增', + exportButtonText: '导出', + tableCodeColumn: '编码', + tableNameColumn: '名称', + tableRecipeNameColumn: '配方名称', + tablePlanCodeColumn: '关联计划', + tableCreatorColumn: '创建人', + tableCreateTimeColumn: '创建时间', + tableOperateColumn: '操作', + tableReadAction: '读取', + tableEditAction: '编辑', + tableDeleteAction: '删除', + dialogCodeLabel: '编码', + dialogCodePlaceholder: '请输入编码', + dialogNameLabel: '名称', + dialogNamePlaceholder: '请输入名称', + dialogRecipeLabel: '配方', + dialogRecipePlaceholder: '请选择配方', + dialogPlanLabel: '关联计划', + dialogPlanPlaceholder: '请选择关联计划', + dialogSourceLabel: '来源', + dialogSourcePlaceholder: '请选择来源', + dialogCancelButton: '取 消', + dialogSaveButton: '保 存', + validatorCodeRequired: '编码不能为空', + validatorNameRequired: '名称不能为空', + validatorRecipeRequired: '关联配方不能为空', + validatorPlanRequired: '关联计划不能为空', + exportFileName: '配方库.xls', + sourceOptionNewLabel: '新增', + sourceOptionProducingLabel: '生产中', + readDialogTitle: '读取', + readDialogNameColumn: '名称', + readDialogDataTypeColumn: '数据类型', + readDialogDataUnitColumn: '单位', + readDialogMaxColumn: '上限', + readDialogMinColumn: '下限', + readDialogRemarkColumn: '备注', + readDialogReferColumn: '采集值', + readDialogReferPlaceholder: '请输入采集值', + readDialogSubmitButtonText: '读 取', + readDialogCancelButton: '取 消', + readDeviceConfirmMessage: '是否读取设备数据?', + detailTabDeviceDataLabel: '设备数据', + detailTabManualLabel: '手动录入参数', + detailDevicePointNameColumn: '点位名称', + detailDeviceDataTypeColumn: '数据类型', + detailDeviceDataUnitColumn: '单位', + detailDeviceValueColumn: '采集值', + manualTableNameColumn: '名称', + manualTableDataTypeColumn: '数据类型', + manualTableDataUnitColumn: '单位', + manualTableReferColumn: '参考值', + manualTableRemarkColumn: '备注' + } } } diff --git a/src/views/formula/formulaConfig/components/RecipeDetailList.vue b/src/views/formula/formulaConfig/components/RecipeDetailList.vue index b3d8fad9..7e82bba4 100644 --- a/src/views/formula/formulaConfig/components/RecipeDetailList.vue +++ b/src/views/formula/formulaConfig/components/RecipeDetailList.vue @@ -2,22 +2,49 @@ - +
- 配置 + + {{ t('RecipeManagement.RecipeConfig.detailConfigButton') }} +
- + - - - - + + + +
- +
- 新增 + + {{ t('RecipeManagement.RecipeConfig.manualCreateButton') }} +
- - - - - - + + + + + + @@ -60,7 +118,11 @@
@@ -68,20 +130,39 @@ ref="manualFormRef" :model="manualForm" :rules="manualRules" - label-width="90px" + class="recipe-config-manual-dialog-form" + label-width="auto" v-loading="manualDialogLoading" > - - + + - - + + - - + + - - + + - - + + - - + +
@@ -167,11 +263,41 @@ const manualForm = reactive({ remark: '' as string | undefined }) const manualRules = reactive({ - name: [{ required: true, message: '名称不能为空', trigger: 'blur' }], - max: [{ required: true, message: '上限不能为空', trigger: 'blur' }], - min: [{ required: true, message: '下限不能为空', trigger: 'blur' }], - dataType: [{ required: true, message: '数据类型不能为空', trigger: 'change' }], - dataUnit: [{ required: true, message: '单位不能为空', trigger: 'change' }] + name: [ + { + required: true, + message: t('RecipeManagement.RecipeConfig.manualValidatorNameRequired'), + trigger: 'blur' + } + ], + max: [ + { + required: true, + message: t('RecipeManagement.RecipeConfig.manualValidatorMaxRequired'), + trigger: 'blur' + } + ], + min: [ + { + required: true, + message: t('RecipeManagement.RecipeConfig.manualValidatorMinRequired'), + trigger: 'blur' + } + ], + dataType: [ + { + required: true, + message: t('RecipeManagement.RecipeConfig.manualValidatorDataTypeRequired'), + trigger: 'change' + } + ], + dataUnit: [ + { + required: true, + message: t('RecipeManagement.RecipeConfig.manualValidatorDataUnitRequired'), + trigger: 'change' + } + ] }) const dataTypeDictOptions = computed(() => getStrDictOptions('iot_device_data_type')) @@ -330,3 +456,9 @@ const refresh = async () => { defineExpose({ refresh }) + + diff --git a/src/views/formula/formulaConfig/index.vue b/src/views/formula/formulaConfig/index.vue index 78f339b4..2a7413e3 100644 --- a/src/views/formula/formulaConfig/index.vue +++ b/src/views/formula/formulaConfig/index.vue @@ -1,34 +1,56 @@ @@ -243,14 +359,14 @@ const handlePagination = () => { const handleExport = async () => { if (!selectedIds.value.length) { - message.error('请选择需要导出的数据') + message.error(t('RecipeManagement.RecipeConfig.exportNoSelectionMessage')) return } try { await message.exportConfirm() exportLoading.value = true const data = await RecipeConfigApi.exportRecipeConfig({ ids: selectedIds.value.join(',') }) - download.excel(data, '配方配置.xls') + download.excel(data, t('RecipeManagement.RecipeConfig.exportFileName')) } catch { } finally { exportLoading.value = false @@ -316,7 +432,11 @@ const ensureOptionsLoaded = async () => { type DialogMode = 'create' | 'update' const dialogVisible = ref(false) const dialogMode = ref('create') -const dialogTitle = computed(() => (dialogMode.value === 'create' ? '新增配方配置' : '编辑配方配置')) +const dialogTitle = computed(() => + dialogMode.value === 'create' + ? t('RecipeManagement.RecipeConfig.dialogCreateTitle') + : t('RecipeManagement.RecipeConfig.dialogEditTitle') +) const dialogFormRef = ref() const dialogLoading = ref(false) const dialogForm = reactive({ @@ -330,8 +450,20 @@ const dialogForm = reactive({ }) const dialogRules = reactive({ - recipeCode: [{ required: true, message: '配方编码不能为空', trigger: 'blur' }], - name: [{ required: true, message: '配方名称不能为空', trigger: 'blur' }] + recipeCode: [ + { + required: true, + message: t('RecipeManagement.RecipeConfig.validatorRecipeCodeRequired'), + trigger: 'blur' + } + ], + name: [ + { + required: true, + message: t('RecipeManagement.RecipeConfig.validatorNameRequired'), + trigger: 'blur' + } + ] }) const openDialog = async (mode: DialogMode, row?: RecipeConfigVO) => { @@ -416,7 +548,7 @@ const handleDetailConfig = () => { const handleRowClick = async (row: RecipeConfigVO, column: any) => { if (column?.type === 'selection') return - if (column?.label === '操作') return + if (column?.label === t('RecipeManagement.RecipeConfig.tableOperateColumn')) return await openDetail(row) } @@ -445,7 +577,7 @@ const configDeviceLabel = computed(() => { const name = detailMeta.machineName?.trim() if (name) return name if (detailMeta.deviceId !== undefined && detailMeta.deviceId !== null) return String(detailMeta.deviceId) - return '-' + return t('RecipeManagement.RecipeConfig.configDeviceLabelFallback') }) const normalizeKey = (value: any): number | undefined => { @@ -588,6 +720,14 @@ onMounted(() => { diff --git a/src/views/formula/formulaType/index.vue b/src/views/formula/formulaType/index.vue index 67570ea0..4445bc3b 100644 --- a/src/views/formula/formulaType/index.vue +++ b/src/views/formula/formulaType/index.vue @@ -1,25 +1,25 @@ @@ -199,14 +246,14 @@ const handlePagination = () => { const handleExport = async () => { if (!selectedIds.value.length) { - message.error('请选择需要导出的数据') + message.error(t('RecipeManagement.RecipeType.exportNoSelectionMessage')) return } try { await message.exportConfirm() exportLoading.value = true const data = await RecipeApi.exportRecipe({ ids: selectedIds.value.join(',') }) - download.excel(data, '配方类型.xls') + download.excel(data, t('RecipeManagement.RecipeType.exportFileName')) } catch { } finally { exportLoading.value = false @@ -217,7 +264,11 @@ type DialogMode = 'create' | 'update' const dialogVisible = ref(false) const dialogMode = ref('create') -const dialogTitle = computed(() => (dialogMode.value === 'create' ? '新增配方类型' : '编辑配方类型')) +const dialogTitle = computed(() => + dialogMode.value === 'create' + ? t('RecipeManagement.RecipeType.dialogCreateTitle') + : t('RecipeManagement.RecipeType.dialogEditTitle') +) const dialogFormRef = ref() const dialogLoading = ref(false) const dialogForm = reactive({ @@ -228,8 +279,14 @@ const dialogForm = reactive({ }) const dialogRules = reactive({ - name: [{ required: true, message: '名称不能为空', trigger: 'blur' }], - process: [{ required: true, message: '工序不能为空', trigger: 'change' }] + name: [{ required: true, message: t('RecipeManagement.RecipeType.validatorNameRequired'), trigger: 'blur' }], + process: [ + { + required: true, + message: t('RecipeManagement.RecipeType.validatorProcessRequired'), + trigger: 'change' + } + ] }) const openDialog = (mode: DialogMode, row?: RecipeVO) => { @@ -291,3 +348,13 @@ onMounted(() => { getList() }) + +