fix: 提交修改
Build and Deploy Vue3 / build (push) Successful in 1m31s
Build and Deploy Vue3 / deploy (push) Successful in 1m9s

This commit is contained in:
2026-04-15 16:02:36 +08:00
parent 2f06aa9f5f
commit b3ed406f84
61 changed files with 7476 additions and 7226 deletions
@@ -29,10 +29,18 @@
<el-tag :type="getArgTypeTag(row.type)">{{ getArgTypeText(row.type) }}</el-tag>
</template>
</el-table-column>
<el-table-column label="数值配置" min-width="180">
<el-table-column label="数值配置" min-width="220">
<template #default="{ row }">
<template v-if="row.type === 'number'">
<span class="number-config">步进: {{ row.step || '-' }} | 范围: {{ row.min ?? '-' }} ~ {{ row.max ?? '-' }}</span>
<div class="number-config">
<div>步进: {{ row.step || '-' }} | 范围: {{ row.min ?? '-' }} ~ {{ row.max ?? '-' }}
<template v-if="hasUnit(row)"> ({{ getBaseUnit(getArgKey(row)) }})</template>
</div>
<div v-if="hasUnit(row)" class="unit-info">
<el-tag size="small" type="success">{{ getArgKey(row) }}</el-tag>
<el-tag size="small" type="warning">{{ getParamDefaultUnit(row) }}</el-tag>
</div>
</div>
</template>
<span v-else class="text-muted">-</span>
</template>
@@ -58,49 +66,88 @@
:title="paramFormType === 'add' ? '新增商品参数' : '编辑商品参数'"
width="600px"
append-to-body
class="tk-dialog"
>
<el-form ref="paramFormRef" :model="paramForm" :rules="paramRules" label-width="120px">
<el-form-item label="参数名称" prop="arg_name">
<el-input v-model="paramForm.arg_name" placeholder="请输入参数名称" />
</el-form-item>
<el-form-item label="参数类型" prop="arg_type">
<el-radio-group v-model="paramForm.arg_type">
<el-radio label="string">字符串</el-radio>
<el-radio label="number">数字</el-radio>
<el-radio label="select">选择</el-radio>
</el-radio-group>
</el-form-item>
<el-form-item label="是否必选" prop="must">
<el-switch v-model="paramForm.must" :active-value="true" :inactive-value="false" active-text="必选" inactive-text="可选" />
</el-form-item>
<el-divider content-position="left">权限控制</el-divider>
<el-form-item label="允许单独购买">
<el-switch v-model="paramForm.user_add" active-text="允许" inactive-text="不允许" />
<div style="font-size: 12px; color: #909399; margin-top: 4px">购买后是否允许单独追加购买</div>
</el-form-item>
<el-form-item label="用户组优惠">
<el-switch v-model="paramForm.use_user_group_discount" active-text="允许" inactive-text="不允许" />
<div style="font-size: 12px; color: #909399; margin-top: 4px">是否允许使用用户组优惠</div>
</el-form-item>
<el-form-item label="用户优惠">
<el-switch v-model="paramForm.use_user_discount" active-text="允许" inactive-text="不允许" />
<div style="font-size: 12px; color: #909399; margin-top: 4px">是否允许使用用户优惠代金券与优惠码</div>
</el-form-item>
<el-form ref="paramFormRef" :model="paramForm" :rules="paramRules" label-width="100px">
<div class="tk-section">
<div class="tk-section-title">基本信息</div>
<el-form-item label="参数名称" prop="arg_name">
<el-input v-model="paramForm.arg_name" placeholder="请输入参数名称" />
</el-form-item>
<el-form-item label="参数类型" prop="arg_type">
<el-radio-group v-model="paramForm.arg_type">
<el-radio label="string">字符串</el-radio>
<el-radio label="number">数字</el-radio>
<el-radio label="select">选择</el-radio>
</el-radio-group>
</el-form-item>
<el-form-item label="是否必选" prop="must">
<el-switch v-model="paramForm.must" :active-value="true" :inactive-value="false" active-text="必选" inactive-text="可选" />
</el-form-item>
</div>
<div class="tk-section">
<div class="tk-section-title">权限控制</div>
<el-form-item label="允许单独购买">
<el-switch v-model="paramForm.user_add" active-text="允许" inactive-text="不允许" />
<div style="font-size: 12px; color: #909399; margin-top: 4px">购买后是否允许单独追加购买</div>
</el-form-item>
<el-form-item label="用户优惠">
<el-switch v-model="paramForm.use_user_group_discount" active-text="允许" inactive-text="不允许" />
<div style="font-size: 12px; color: #909399; margin-top: 4px">是否允许使用用户优惠</div>
</el-form-item>
<el-form-item label="用户优惠">
<el-switch v-model="paramForm.use_user_discount" active-text="允许" inactive-text="不允许" />
<div style="font-size: 12px; color: #909399; margin-top: 4px">是否允许使用用户优惠代金券与优惠码</div>
</el-form-item>
</div>
<template v-if="paramForm.arg_type === 'number'">
<el-divider content-position="left">数值参数配置</el-divider>
<el-form-item label="步进值" prop="arg_step">
<el-input-number v-model="paramForm.arg_step" :min="1" placeholder="步进值" style="width: 100%" />
</el-form-item>
<el-form-item label="最小值" prop="arg_min">
<el-input-number v-model="paramForm.arg_min" placeholder="最小值" style="width: 100%" />
</el-form-item>
<el-form-item label="最大值" prop="arg_max">
<el-input-number v-model="paramForm.arg_max" placeholder="最大值" style="width: 100%" />
</el-form-item>
<div class="tk-section">
<div class="tk-section-title">数值参数配置</div>
<el-form-item label="步进值" prop="arg_step">
<div class="unit-input-row">
<el-input-number v-model="paramForm.step_display" :min="1" placeholder="步进值" style="flex: 1" />
<el-select v-if="paramForm.enable_unit && paramForm.arg_key" :model-value="paramForm.step_unit" style="width: 100px" @change="(v) => onFieldUnitChange('step', v)">
<el-option v-for="u in formUnits" :key="u" :label="u" :value="u" />
</el-select>
</div>
</el-form-item>
<el-form-item label="最小值" prop="arg_min">
<div class="unit-input-row">
<el-input-number v-model="paramForm.min_display" placeholder="最小值" style="flex: 1" />
<el-select v-if="paramForm.enable_unit && paramForm.arg_key" :model-value="paramForm.min_unit" style="width: 100px" @change="(v) => onFieldUnitChange('min', v)">
<el-option v-for="u in formUnits" :key="u" :label="u" :value="u" />
</el-select>
</div>
</el-form-item>
<el-form-item label="最大值" prop="arg_max">
<div class="unit-input-row">
<el-input-number v-model="paramForm.max_display" placeholder="最大值" style="flex: 1" />
<el-select v-if="paramForm.enable_unit && paramForm.arg_key" :model-value="paramForm.max_unit" style="width: 100px" @change="(v) => onFieldUnitChange('max', v)">
<el-option v-for="u in formUnits" :key="u" :label="u" :value="u" />
</el-select>
</div>
<div v-if="paramForm.enable_unit && paramForm.arg_key" class="form-tip">
实际提交({{ getBaseUnit(paramForm.arg_key) }}): 步进={{ calcBase(paramForm.step_display, paramForm.step_unit) }} | 最小={{ calcBase(paramForm.min_display, paramForm.min_unit) }} | 最大={{ calcBase(paramForm.max_display, paramForm.max_unit) }}
</div>
</el-form-item>
<el-form-item label="启用动态单位">
<el-switch v-model="paramForm.enable_unit" active-text="启用" inactive-text="禁用" @change="onEnableUnitChange" />
<div style="font-size: 12px; color: #909399; margin-top: 4px">启用后可在输入框右侧切换单位提交时自动转为基础单位</div>
</el-form-item>
<el-form-item v-if="paramForm.enable_unit" label="参数键" prop="arg_key">
<el-select v-model="paramForm.arg_key" placeholder="选择参数键" style="width: 100%" @change="onArgKeyChange">
<el-option v-for="opt in argKeyOptions" :key="opt.value" :label="opt.label" :value="opt.value" />
</el-select>
<div style="font-size: 12px; color: #909399; margin-top: 4px">用于识别参数类型基础单位:
<strong v-if="paramForm.arg_key">{{ getBaseUnit(paramForm.arg_key) }}</strong>
<span v-else>请先选择</span>
</div>
</el-form-item>
</div>
</template>
</el-form>
<template #footer>
<div class="dialog-footer">
<div class="tk-dialog-footer">
<el-button @click="paramFormDialogVisible = false">取消</el-button>
<el-button type="primary" @click="submitParamForm">确定</el-button>
</div>
@@ -110,7 +157,12 @@
<!-- 参数值管理对话框 -->
<el-dialog v-model="paramValuesDialogVisible" title="参数值管理" width="800px" append-to-body>
<div class="values-header">
<span>参数{{ currentParam?.name }}</span>
<div>
<span>参数{{ currentParam?.name }}</span>
<el-tag v-if="hasUnit(currentParam)" size="small" type="success" style="margin-left: 8px">
{{ getArgKey(currentParam) }} · 基础单位: {{ getBaseUnit(getArgKey(currentParam)) }}
</el-tag>
</div>
<el-button type="primary" @click="handleAddParamValue">
<el-icon><Plus /></el-icon>添加参数值
</el-button>
@@ -123,11 +175,13 @@
>
<el-table-column prop="id" label="值ID" width="80" />
<el-table-column prop="name" label="值名称" min-width="120" />
<el-table-column label="值/范围" min-width="150">
<el-table-column label="值/范围" min-width="180">
<template #default="{ row }">
<template v-if="currentParam?.type === 'select'">{{ row.value || '-' }}</template>
<template v-else-if="currentParam?.type === 'number'">
<el-tag size="small" type="info">{{ getRangeTypeText(row.rangeType) }} {{ row.range }}</el-tag>
<el-tag size="small" type="info">
{{ getRangeTypeText(row.rangeType) }} {{ formatPhaseDisplay(row.phase || row.range) }}
</el-tag>
</template>
<template v-else>{{ row.value || '-' }}</template>
</template>
@@ -156,37 +210,65 @@
:title="paramValueFormType === 'add' ? '添加参数值' : '编辑参数值'"
width="550px"
append-to-body
class="tk-dialog"
>
<el-form ref="paramValueFormRef" :model="paramValueForm" :rules="paramValueRules" label-width="120px">
<el-form-item label="值名称" prop="attr_name">
<el-input v-model="paramValueForm.attr_name" placeholder="请输入值名称" />
</el-form-item>
<el-form-item v-if="currentParam?.type === 'select'" label="参数值" prop="attr_value">
<el-input v-model="paramValueForm.attr_value" placeholder="请输入参数值" />
</el-form-item>
<el-form ref="paramValueFormRef" :model="paramValueForm" :rules="paramValueRules" label-width="100px">
<div class="tk-section">
<div class="tk-section-title">参数值信息</div>
<el-form-item label="值名称" prop="attr_name">
<el-input v-model="paramValueForm.attr_name" placeholder="请输入值名称" />
</el-form-item>
<el-form-item v-if="currentParam?.type === 'select'" label="参数值" prop="attr_value">
<el-input v-model="paramValueForm.attr_value" placeholder="请输入参数值" />
</el-form-item>
<el-form-item label="排序索引" prop="index">
<el-input-number v-model="paramValueForm.index" :min="0" placeholder="排序索引" style="width: 100%" />
</el-form-item>
<el-form-item label="价格" prop="attr_price">
<el-input-number v-model="paramValueForm.attr_price" :min="0" placeholder="请输入价格" style="width: 100%" />
</el-form-item>
</div>
<template v-if="currentParam?.type === 'number'">
<el-divider content-position="left">数值范围配置phase</el-divider>
<el-form-item label="范围类型" prop="range_type">
<el-select v-model="paramValueForm.range_type" placeholder="请选择范围类型" style="width: 100%">
<el-option label="小于等于 (before)" value="before" />
<el-option label="大于等于 (after)" value="after" />
<el-option label="于 (equal)" value="equal" />
</el-select>
<div class="form-tip">before: 数值 phase 时匹配 | after: 数值 phase 时匹配</div>
</el-form-item>
<el-form-item label="阈值" prop="attr_range">
<el-input-number v-model="paramValueForm.attr_range" :min="0" placeholder="范围阈值" style="width: 100%" />
</el-form-item>
<div class="tk-section">
<div class="tk-section-title">数值范围配置</div>
<el-form-item label="范围类型" prop="range_type">
<el-select v-model="paramValueForm.range_type" placeholder="请选择范围类型" style="width: 100%">
<el-option label="小于 (before)" value="before" />
<el-option label="于 (after)" value="after" />
<el-option label="等于 (equal)" value="equal" />
</el-select>
<div class="form-tip">before: 数值 &lt; phase 时匹配 | after: 数值 &gt; phase 时匹配</div>
</el-form-item>
<el-form-item label="阈值" prop="attr_range">
<div class="unit-input-row">
<el-input-number
v-model="paramValueForm.attr_range_display"
:min="valueDisplayMin"
:max="valueDisplayMax"
:step="valueDisplayStep"
:step-strictly="true"
placeholder="范围阈值"
style="flex: 1"
/>
<el-select
v-if="hasUnit(currentParam)"
v-model="paramValueForm.display_unit"
style="width: 100px"
@change="onValueUnitChange"
>
<el-option v-for="u in currentParamUnits" :key="u" :label="u" :value="u" />
</el-select>
</div>
<div v-if="hasUnit(currentParam)" class="form-tip">
实际存储值: {{ computedBaseValue }} {{ getBaseUnit(getArgKey(currentParam)) }}
范围: {{ currentParam?.min ?? 0 }} ~ {{ currentParam?.max ?? '-' }} {{ getBaseUnit(getArgKey(currentParam)) }}步长: {{ currentParam?.step || 1 }}
</div>
</el-form-item>
</div>
</template>
<el-form-item label="排序索引" prop="index">
<el-input-number v-model="paramValueForm.index" :min="0" placeholder="排序索引" style="width: 100%" />
</el-form-item>
<el-form-item label="价格" prop="attr_price">
<el-input-number v-model="paramValueForm.attr_price" :min="0" placeholder="请输入价格" style="width: 100%" />
</el-form-item>
</el-form>
<template #footer>
<div class="dialog-footer">
<div class="tk-dialog-footer">
<el-button @click="paramValueFormDialogVisible = false">取消</el-button>
<el-button type="primary" @click="submitParamValueForm">确定</el-button>
</div>
@@ -195,7 +277,7 @@
</template>
<script setup>
import { ref, reactive, watch, nextTick } from 'vue'
import { ref, reactive, computed, watch, nextTick } from 'vue'
import { ElMessage, ElMessageBox } from 'element-plus'
import { Plus, Refresh } from '@element-plus/icons-vue'
import {
@@ -208,6 +290,11 @@ import {
updateProductParameterValue,
deleteProductParameterValue
} from '@/api/admin/product'
import {
getAvailableUnits, getArgKeyOptions, hasUnit, getArgKey,
getBaseUnit, getDefaultDisplayUnit, getParamDefaultUnit, getParamUnits,
toBaseUnit, fromBaseUnit, formatValueWithUnit
} from '@/utils/dynamicUnit'
const props = defineProps({
visible: { type: Boolean, default: false },
@@ -215,6 +302,8 @@ const props = defineProps({
})
const emit = defineEmits(['update:visible'])
const argKeyOptions = getArgKeyOptions()
const paramLoading = ref(false)
const parameterList = ref([])
@@ -229,15 +318,70 @@ const paramForm = reactive({
arg_step: 1,
arg_min: 0,
arg_max: 100,
step_display: 1,
min_display: 0,
max_display: 100,
step_unit: '',
min_unit: '',
max_unit: '',
user_add: false,
use_user_group_discount: false,
use_user_discount: false
use_user_discount: false,
enable_unit: false,
arg_key: ''
})
const paramRules = {
arg_name: [{ required: true, message: '请输入参数名称', trigger: 'blur' }],
arg_type: [{ required: true, message: '请选择参数类型', trigger: 'change' }]
}
const formUnits = computed(() => {
if (!paramForm.arg_key) return []
return getAvailableUnits(paramForm.arg_key)
})
const calcBase = (displayVal, unit) => {
if (!paramForm.enable_unit || !paramForm.arg_key || !unit) return displayVal
return Math.round(toBaseUnit(displayVal || 0, unit, paramForm.arg_key))
}
const onFieldUnitChange = (field, newUnit) => {
const key = paramForm.arg_key
const oldUnit = paramForm[`${field}_unit`]
const oldDisplay = paramForm[`${field}_display`] || 0
const baseVal = oldUnit ? toBaseUnit(oldDisplay, oldUnit, key) : oldDisplay
paramForm[`${field}_unit`] = newUnit
paramForm[`${field}_display`] = fromBaseUnit(baseVal, newUnit, key)
}
const onArgKeyChange = () => {
const key = paramForm.arg_key
const defaultUnit = key ? getDefaultDisplayUnit(key) : ''
paramForm.step_unit = defaultUnit
paramForm.min_unit = defaultUnit
paramForm.max_unit = defaultUnit
if (key && defaultUnit) {
paramForm.step_display = fromBaseUnit(paramForm.arg_step, defaultUnit, key)
paramForm.min_display = fromBaseUnit(paramForm.arg_min, defaultUnit, key)
paramForm.max_display = fromBaseUnit(paramForm.arg_max, defaultUnit, key)
} else {
paramForm.step_display = paramForm.arg_step
paramForm.min_display = paramForm.arg_min
paramForm.max_display = paramForm.arg_max
}
}
const onEnableUnitChange = (val) => {
if (!val) {
paramForm.step_display = paramForm.arg_step
paramForm.min_display = paramForm.arg_min
paramForm.max_display = paramForm.arg_max
paramForm.step_unit = ''
paramForm.min_unit = ''
paramForm.max_unit = ''
}
}
const paramValuesDialogVisible = ref(false)
const paramValuesLoading = ref(false)
const paramValueList = ref([])
@@ -253,12 +397,58 @@ const paramValueForm = reactive({
attr_price: 0,
index: 0,
attr_range: 0,
attr_range_display: 0,
display_unit: '',
range_type: 'equal'
})
const paramValueRules = {
attr_name: [{ required: true, message: '请输入值名称', trigger: 'blur' }]
}
const currentParamUnits = computed(() => {
if (!hasUnit(currentParam.value)) return []
return getParamUnits(currentParam.value)
})
const valueDisplayMin = computed(() => {
if (!hasUnit(currentParam.value)) return 0
const argKey = getArgKey(currentParam.value)
const baseMin = currentParam.value?.min ?? 0
return fromBaseUnit(baseMin, paramValueForm.display_unit, argKey)
})
const valueDisplayMax = computed(() => {
if (!hasUnit(currentParam.value)) return 9999999
const argKey = getArgKey(currentParam.value)
const baseMax = currentParam.value?.max
if (baseMax === undefined || baseMax === null) return 9999999
return fromBaseUnit(baseMax, paramValueForm.display_unit, argKey)
})
const valueDisplayStep = computed(() => {
if (!hasUnit(currentParam.value)) return 1
const argKey = getArgKey(currentParam.value)
const baseStep = currentParam.value?.step || 1
return fromBaseUnit(baseStep, paramValueForm.display_unit, argKey)
})
const computedBaseValue = computed(() => {
if (!hasUnit(currentParam.value)) return paramValueForm.attr_range_display
const argKey = getArgKey(currentParam.value)
return Math.round(toBaseUnit(paramValueForm.attr_range_display || 0, paramValueForm.display_unit, argKey))
})
const formatPhaseDisplay = (phaseValue) => {
if (phaseValue === undefined || phaseValue === null) return '-'
if (!hasUnit(currentParam.value)) return String(phaseValue)
const argKey = getArgKey(currentParam.value)
const displayUnit = getParamDefaultUnit(currentParam.value)
const displayVal = fromBaseUnit(phaseValue, displayUnit, argKey)
return formatValueWithUnit(displayVal, displayUnit)
}
const onValueUnitChange = () => {
// Recalculate: keep the base value, recalculate display value
}
const getArgTypeText = (type) => {
const typeMap = { 'string': '字符串', 'number': '数字', 'select': '选择' }
return typeMap[type] || '未知'
@@ -268,7 +458,7 @@ const getArgTypeTag = (type) => {
return tagMap[type] || 'info'
}
const getRangeTypeText = (type) => {
const typeMap = { 'after': '大于 >', 'before': '小于 <', 'equal': '等于 =' }
const typeMap = { 'after': '', 'before': '', 'equal': '' }
return typeMap[type] || type || '-'
}
@@ -290,14 +480,45 @@ const fetchParameterList = async () => {
const handleAddParameter = () => {
paramFormType.value = 'add'
paramFormDialogVisible.value = true
Object.assign(paramForm, { arg_id: undefined, arg_name: '', arg_type: 'string', must: false, arg_step: 1, arg_min: 0, arg_max: 100, user_add: false, use_user_group_discount: false, use_user_discount: false })
Object.assign(paramForm, {
arg_id: undefined, arg_name: '', arg_type: 'string', must: false,
arg_step: 1, arg_min: 0, arg_max: 100,
step_display: 1, min_display: 0, max_display: 100,
step_unit: '', min_unit: '', max_unit: '',
user_add: false, use_user_group_discount: false, use_user_discount: false,
enable_unit: false, arg_key: ''
})
nextTick(() => { paramFormRef.value?.resetFields() })
}
const handleEditParameter = (row) => {
paramFormType.value = 'edit'
paramFormDialogVisible.value = true
Object.assign(paramForm, { arg_id: row.id, arg_name: row.name, arg_type: row.type, must: row.must || false, arg_step: row.step || 1, arg_min: row.min || 0, arg_max: row.max || 100, user_add: row.userAdd ?? row.user_add ?? false, use_user_group_discount: row.useUserGroupDiscount ?? row.use_user_group_discount ?? false, use_user_discount: row.useUserDiscount ?? row.use_user_discount ?? false })
const enableUnit = row.enableUnit || false
const argKey = row.argKey || ''
const baseStep = row.step || 1
const baseMin = row.min || 0
const baseMax = row.max || 100
let defaultUnit = ''
let stepDisplay = baseStep
let minDisplay = baseMin
let maxDisplay = baseMax
if (enableUnit && argKey) {
defaultUnit = getDefaultDisplayUnit(argKey)
stepDisplay = fromBaseUnit(baseStep, defaultUnit, argKey)
minDisplay = fromBaseUnit(baseMin, defaultUnit, argKey)
maxDisplay = fromBaseUnit(baseMax, defaultUnit, argKey)
}
Object.assign(paramForm, {
arg_id: row.id, arg_name: row.name, arg_type: row.type, must: row.must || false,
arg_step: baseStep, arg_min: baseMin, arg_max: baseMax,
step_display: stepDisplay, min_display: minDisplay, max_display: maxDisplay,
step_unit: defaultUnit, min_unit: defaultUnit, max_unit: defaultUnit,
user_add: row.userAdd ?? row.user_add ?? false,
use_user_group_discount: row.useUserGroupDiscount ?? row.use_user_group_discount ?? false,
use_user_discount: row.useUserDiscount ?? row.use_user_discount ?? false,
enable_unit: enableUnit, arg_key: argKey
})
}
const handleDeleteParameter = (row) => {
@@ -315,11 +536,27 @@ const submitParamForm = () => {
paramFormRef.value?.validate(async (valid) => {
if (valid) {
try {
const submitData = { good_id: Number(props.goodId), arg_name: paramForm.arg_name, arg_type: paramForm.arg_type, must: paramForm.must === true, user_add: paramForm.user_add === true, use_user_group_discount: paramForm.use_user_group_discount === true, use_user_discount: paramForm.use_user_discount === true }
const submitData = {
good_id: Number(props.goodId),
arg_name: paramForm.arg_name,
arg_type: paramForm.arg_type,
must: paramForm.must === true,
user_add: paramForm.user_add === true,
use_user_group_discount: paramForm.use_user_group_discount === true,
use_user_discount: paramForm.use_user_discount === true
}
if (paramForm.arg_type === 'number') {
submitData.arg_step = Number(paramForm.arg_step)
submitData.arg_min = Number(paramForm.arg_min)
submitData.arg_max = Number(paramForm.arg_max)
if (paramForm.enable_unit && paramForm.arg_key) {
submitData.arg_step = calcBase(paramForm.step_display, paramForm.step_unit)
submitData.arg_min = calcBase(paramForm.min_display, paramForm.min_unit)
submitData.arg_max = calcBase(paramForm.max_display, paramForm.max_unit)
submitData.enable_unit = true
submitData.arg_key = paramForm.arg_key
} else {
submitData.arg_step = Number(paramForm.step_display)
submitData.arg_min = Number(paramForm.min_display)
submitData.arg_max = Number(paramForm.max_display)
}
}
if (paramFormType.value === 'edit') submitData.arg_id = paramForm.arg_id
const res = paramFormType.value === 'add' ? await createProductParameter(submitData) : await updateProductParameter(submitData)
@@ -348,14 +585,30 @@ const fetchParamValuesList = async () => {
const handleAddParamValue = () => {
paramValueFormType.value = 'add'
paramValueFormDialogVisible.value = true
Object.assign(paramValueForm, { attr_id: undefined, attr_name: '', attr_value: '', attr_price: 0, index: 0, attr_range: 0, range_type: 'equal' })
nextTick(() => { paramValueFormRef.value?.resetFields() })
const defaultUnit = hasUnit(currentParam.value) ? getParamDefaultUnit(currentParam.value) : ''
nextTick(() => {
paramValueFormRef.value?.resetFields()
Object.assign(paramValueForm, { attr_id: undefined, attr_name: '', attr_value: '', attr_price: 0, index: 0, attr_range: 0, attr_range_display: 0, display_unit: defaultUnit, range_type: 'equal' })
})
}
const handleEditParamValue = (row) => {
paramValueFormType.value = 'edit'
paramValueFormDialogVisible.value = true
Object.assign(paramValueForm, { attr_id: row.id, attr_name: row.name, attr_value: row.value || '', attr_price: row.price / 100 || 0, index: row.index || 0, attr_range: row.phase || 0, range_type: row.rangeType || 'equal' })
const baseValue = row.phase || 0
let displayValue = baseValue
let displayUnit = ''
if (hasUnit(currentParam.value)) {
const argKey = getArgKey(currentParam.value)
displayUnit = getParamDefaultUnit(currentParam.value)
displayValue = fromBaseUnit(baseValue, displayUnit, argKey)
}
Object.assign(paramValueForm, {
attr_id: row.id, attr_name: row.name, attr_value: row.value || '',
attr_price: row.price / 100 || 0, index: row.index || 0,
attr_range: baseValue, attr_range_display: displayValue,
display_unit: displayUnit, range_type: row.rangeType || 'equal'
})
}
const handleDeleteParamValue = (row) => {
@@ -375,7 +628,27 @@ const submitParamValueForm = () => {
try {
const submitData = { good_id: Number(props.goodId), arg_id: Number(currentParam.value.id), attr_name: paramValueForm.attr_name, index: Number(paramValueForm.index), attr_price: Number(paramValueForm.attr_price) }
if (currentParam.value.type === 'select') submitData.attr_value = paramValueForm.attr_value
if (currentParam.value.type === 'number') { submitData.attr_range = Number(paramValueForm.attr_range); submitData.range_type = paramValueForm.range_type }
if (currentParam.value.type === 'number') {
let rangeValue
if (hasUnit(currentParam.value)) {
rangeValue = computedBaseValue.value
} else {
rangeValue = Number(paramValueForm.attr_range_display)
}
const baseMin = currentParam.value.min ?? 0
const baseMax = currentParam.value.max
const baseStep = currentParam.value.step || 1
if (rangeValue < baseMin || (baseMax !== undefined && baseMax !== null && rangeValue > baseMax)) {
ElMessage.warning(`阈值超出范围 (${baseMin} ~ ${baseMax ?? '∞'} ${hasUnit(currentParam.value) ? getBaseUnit(getArgKey(currentParam.value)) : ''})`)
return
}
if (baseStep > 0 && (rangeValue - baseMin) % baseStep !== 0) {
ElMessage.warning(`阈值必须符合步长 ${baseStep} 的要求`)
return
}
submitData.attr_range = rangeValue
submitData.range_type = paramValueForm.range_type
}
if (paramValueFormType.value === 'edit') submitData.attr_id = paramValueForm.attr_id
const res = paramValueFormType.value === 'add' ? await addProductParameterValue(submitData) : await updateProductParameterValue(submitData)
if (res.data.code === 200) { ElMessage.success(paramValueFormType.value === 'add' ? '添加成功' : '修改成功'); paramValueFormDialogVisible.value = false; fetchParamValuesList() }
@@ -396,7 +669,11 @@ watch(() => props.visible, (val) => {
.action-buttons .el-button { padding: 4px 8px; }
.text-muted { color: #c0c4cc; font-size: 12px; }
.number-config { color: #909399; font-size: 13px; }
.number-config div { line-height: 1.4; }
.unit-info { display: flex; align-items: center; gap: 8px; margin-top: 4px; }
.unit-text { font-size: 12px; color: #666; }
.values-header { display: flex; justify-content: space-between; align-items: center; margin-bottom: 20px; }
.dialog-footer { display: flex; justify-content: flex-end; gap: 12px; padding: 0; }
.form-tip { font-size: 12px; color: #909399; margin-top: 4px; }
.unit-input-row { display: flex; align-items: center; gap: 8px; width: 100%; }
</style>