- 新增 src/config/models/ 每模型独立参数 schema(8 个模型) - 新增 src/components/dialogBox/params/ 动态参数控件 - 模型选择器改为从 API 获取并按 tag 分组 - dialogBox 参数区改为根据模型 config 动态渲染控件 - createTask.js Painting 直接返回扁平 modelParams,Video 保留旧 workflow - 删除旧的 proportion/painting.vue 和 quantity 组件 - 更新 CLAUDE.md 架构文档
133 lines
3.4 KiB
Vue
133 lines
3.4 KiB
Vue
<template>
|
|
<Select
|
|
v-model="model"
|
|
:grouped-options="modelGroups"
|
|
class="model-select"
|
|
position="top"
|
|
>
|
|
<template #prefix>
|
|
<img src="@/assets/dialog/model.svg" alt="" style="width: 16px;">
|
|
</template>
|
|
</Select>
|
|
</template>
|
|
|
|
<script setup>
|
|
import Select from '@/components/Select/index.vue'
|
|
import { fetchPlatformModels, getPlatformCode } from '@/utils/modelApi'
|
|
import { getModelConfig } from '@/config/models/index.js'
|
|
|
|
const props = defineProps({
|
|
modelValue: { type: String, default: 'Flux 2' },
|
|
typeValue: { type: String, default: 'text' },
|
|
})
|
|
|
|
const emit = defineEmits(['update:modelValue', 'update:typeValue'])
|
|
|
|
const platformModels = ref([])
|
|
|
|
// 从 API 加载模型列表并按 tag 分组
|
|
const loadModels = async () => {
|
|
try {
|
|
const code = getPlatformCode('Painting')
|
|
const models = await fetchPlatformModels(code)
|
|
platformModels.value = models || []
|
|
} catch (error) {
|
|
console.error('加载平台模型列表失败:', error)
|
|
}
|
|
}
|
|
|
|
loadModels()
|
|
|
|
// 模型列表加载后自动纠正不可用模型
|
|
watch(platformModels, (models) => {
|
|
if (models.length === 0) return
|
|
const currentModel = models.find(m => m.name === props.modelValue || m.id === props.modelValue)
|
|
if (!currentModel || currentModel.disabled) {
|
|
const firstEnabled = models.find(m => !m.disabled)
|
|
if (firstEnabled) {
|
|
emit('update:modelValue', firstEnabled.name)
|
|
const config = getModelConfig(firstEnabled.name)
|
|
emit('update:typeValue', config?.inputType || 'text')
|
|
}
|
|
}
|
|
}, { immediate: true })
|
|
|
|
// 按 tag 分组
|
|
const modelGroups = computed(() => {
|
|
const models = platformModels.value
|
|
if (models.length === 0) return []
|
|
|
|
const groups = {}
|
|
models.forEach(m => {
|
|
const tag = m.tag || '其他'
|
|
if (!groups[tag]) groups[tag] = []
|
|
groups[tag].push({
|
|
value: m.name,
|
|
label: m.name,
|
|
disabled: m.disabled || false,
|
|
})
|
|
})
|
|
|
|
return Object.entries(groups).map(([label, options]) => ({ label, options }))
|
|
})
|
|
|
|
const model = computed({
|
|
get: () => props.modelValue,
|
|
set: (value) => {
|
|
emit('update:modelValue', value)
|
|
const config = getModelConfig(value)
|
|
emit('update:typeValue', config?.inputType || 'text')
|
|
},
|
|
})
|
|
|
|
// 外部改变 modelValue 时校验是否可用
|
|
watch(() => props.modelValue, (newValue) => {
|
|
const models = platformModels.value
|
|
if (models.length === 0) return
|
|
const currentModel = models.find(m => m.name === newValue)
|
|
if (currentModel && currentModel.disabled) {
|
|
const firstEnabled = models.find(m => !m.disabled)
|
|
if (firstEnabled) {
|
|
emit('update:modelValue', firstEnabled.name)
|
|
const config = getModelConfig(firstEnabled.name)
|
|
emit('update:typeValue', config?.inputType || 'text')
|
|
}
|
|
}
|
|
})
|
|
</script>
|
|
|
|
<style lang="less" scoped>
|
|
.model-select {
|
|
:deep(.select-header) {
|
|
height: 40px;
|
|
padding: 0 15px;
|
|
border-radius: 10px;
|
|
border: 1px solid #E8E9EB;
|
|
background: #f5f6f7;
|
|
|
|
&:hover {
|
|
background: #e9eaeb;
|
|
}
|
|
}
|
|
|
|
:deep(.select-text) {
|
|
font-size: 14px;
|
|
}
|
|
|
|
:deep(.dropdown-menu) {
|
|
max-height: 510px;
|
|
overflow-y: auto;
|
|
}
|
|
|
|
:deep(.dropdown-item) {
|
|
min-width: 120px;
|
|
|
|
&.active {
|
|
background: rgba(0, 15, 51, 0.10);
|
|
color: #000F33;
|
|
font-weight: 600;
|
|
}
|
|
}
|
|
}
|
|
</style>
|