fix: 模型选择优化
This commit is contained in:
@@ -92,9 +92,32 @@ watch(activeTab, () => {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// 检查是否为当前选中的模型
|
||||||
|
function isCurrentModel(item: GetSessionListVO) {
|
||||||
|
const current = modelStore.currentModelInfo;
|
||||||
|
if (!current)
|
||||||
|
return false;
|
||||||
|
|
||||||
|
// 优先使用唯一 ID 匹配
|
||||||
|
if (item.id && current.id) {
|
||||||
|
return item.id === current.id;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 降级使用组合键匹配
|
||||||
|
return item.modelId === current.modelId
|
||||||
|
&& item.modelApiType === current.modelApiType
|
||||||
|
&& item.providerName === current.providerName;
|
||||||
|
}
|
||||||
|
|
||||||
// 定位到当前模型
|
// 定位到当前模型
|
||||||
function scrollToCurrentModel() {
|
function scrollToCurrentModel() {
|
||||||
const currentId = modelStore.currentModelInfo?.modelId;
|
const current = modelStore.currentModelInfo;
|
||||||
|
if (!current)
|
||||||
|
return;
|
||||||
|
|
||||||
|
// 使用 item.id 构建 ID (假设 modelData.ts 中的 id 是唯一的)
|
||||||
|
// 如果没有 id,则无法精确定位,这里假设都有 id
|
||||||
|
const currentId = current.id;
|
||||||
if (!currentId)
|
if (!currentId)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
@@ -166,7 +189,7 @@ function getModelStyleClass(mode: any) {
|
|||||||
|
|
||||||
const isPremiumPackage = mode.isPremiumPackage;
|
const isPremiumPackage = mode.isPremiumPackage;
|
||||||
|
|
||||||
// 规则3:彩色流光
|
// 规则3:彩色流光 (尊享)
|
||||||
if (isPremiumPackage) {
|
if (isPremiumPackage) {
|
||||||
return `
|
return `
|
||||||
text-transparent bg-clip-text
|
text-transparent bg-clip-text
|
||||||
@@ -180,7 +203,7 @@ function getModelStyleClass(mode: any) {
|
|||||||
return 'text-gray-700';
|
return 'text-gray-700';
|
||||||
}
|
}
|
||||||
|
|
||||||
// 规则1:金色光泽
|
// 规则1:金色光泽 (VIP)
|
||||||
return `
|
return `
|
||||||
text-[#B38728] font-semibold relative overflow-hidden
|
text-[#B38728] font-semibold relative overflow-hidden
|
||||||
before:content-[''] before:absolute before:-inset-2 before:-z-10
|
before:content-[''] before:absolute before:-inset-2 before:-z-10
|
||||||
@@ -192,7 +215,7 @@ function getModelStyleClass(mode: any) {
|
|||||||
外层卡片样式(选中态 + hover 动效)
|
外层卡片样式(选中态 + hover 动效)
|
||||||
-------------------------------- */
|
-------------------------------- */
|
||||||
function getWrapperClass(item: GetSessionListVO) {
|
function getWrapperClass(item: GetSessionListVO) {
|
||||||
const isSelected = item.modelId === modelStore.currentModelInfo?.modelId;
|
const isSelected = isCurrentModel(item);
|
||||||
const available = isModelAvailable(item);
|
const available = isModelAvailable(item);
|
||||||
|
|
||||||
return [
|
return [
|
||||||
@@ -254,7 +277,7 @@ function getWrapperClass(item: GetSessionListVO) {
|
|||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
v-for="item in models"
|
v-for="item in models"
|
||||||
:id="`provider-model-${item.modelId}`"
|
:id="`provider-model-${item.id}`"
|
||||||
:key="item.id"
|
:key="item.id"
|
||||||
:class="getWrapperClass(item)"
|
:class="getWrapperClass(item)"
|
||||||
@click="handleModelClick(item)"
|
@click="handleModelClick(item)"
|
||||||
@@ -268,14 +291,17 @@ function getWrapperClass(item: GetSessionListVO) {
|
|||||||
|
|
||||||
<!-- 模型信息 -->
|
<!-- 模型信息 -->
|
||||||
<div class="flex flex-col gap-0.5 flex-1 min-w-0">
|
<div class="flex flex-col gap-0.5 flex-1 min-w-0">
|
||||||
<div class="flex items-center gap-2">
|
<div class="flex items-center gap-2 flex-wrap">
|
||||||
<span :class="getModelStyleClass(item)" class="font-medium truncate">
|
<span :class="getModelStyleClass(item)" class="font-medium truncate">
|
||||||
{{ item.modelName }}
|
{{ item.modelName }}
|
||||||
</span>
|
</span>
|
||||||
<span v-if="item.isFree" class="text-[10px] px-1.5 py-0.5 bg-green-100 text-green-600 rounded-full">免费</span>
|
<span v-if="item.isFree" class="text-[10px] px-1.5 py-0.5 bg-green-100 text-green-600 rounded-full">免费</span>
|
||||||
<span v-if="item.isPremiumPackage" class="text-[10px] px-1.5 py-0.5 bg-orange-100 text-orange-600 rounded-full">VIP</span>
|
<span v-if="item.isPremiumPackage" class="text-[10px] px-1.5 py-0.5 bg-orange-100 text-orange-600 rounded-full">尊享</span>
|
||||||
|
<span v-else-if="!item.isFree" class="text-[10px] px-1.5 py-0.5 bg-yellow-100 text-yellow-600 rounded-full">VIP</span>
|
||||||
|
<!-- 显示 API 类型 -->
|
||||||
|
<span class="text-[10px] px-1.5 py-0.5 bg-gray-100 text-gray-600 rounded-full">{{ item.modelApiType }}</span>
|
||||||
</div>
|
</div>
|
||||||
<div class="text-xs text-gray-400 truncate" :title="item.modelDescribe">
|
<div class="text-xs text-gray-400 break-words whitespace-normal line-clamp-2" :title="item.modelDescribe">
|
||||||
{{ item.modelDescribe }}
|
{{ item.modelDescribe }}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@@ -283,7 +309,7 @@ function getWrapperClass(item: GetSessionListVO) {
|
|||||||
|
|
||||||
<!-- 选中/锁定图标 -->
|
<!-- 选中/锁定图标 -->
|
||||||
<div class="flex items-center">
|
<div class="flex items-center">
|
||||||
<el-icon v-if="item.modelId === modelStore.currentModelInfo?.modelId" class="text-primary mr-2" :size="18">
|
<el-icon v-if="isCurrentModel(item)" class="text-primary mr-2" :size="18">
|
||||||
<Check />
|
<Check />
|
||||||
</el-icon>
|
</el-icon>
|
||||||
<el-icon v-if="!isModelAvailable(item)" class="text-gray-400">
|
<el-icon v-if="!isModelAvailable(item)" class="text-gray-400">
|
||||||
@@ -306,7 +332,7 @@ function getWrapperClass(item: GetSessionListVO) {
|
|||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
v-for="item in models"
|
v-for="item in models"
|
||||||
:id="`api-model-${item.modelId}`"
|
:id="`api-model-${item.id}`"
|
||||||
:key="item.id"
|
:key="item.id"
|
||||||
:class="getWrapperClass(item)"
|
:class="getWrapperClass(item)"
|
||||||
@click="handleModelClick(item)"
|
@click="handleModelClick(item)"
|
||||||
@@ -317,21 +343,24 @@ function getWrapperClass(item: GetSessionListVO) {
|
|||||||
<SvgIcon v-else name="models" size="16" />
|
<SvgIcon v-else name="models" size="16" />
|
||||||
</div>
|
</div>
|
||||||
<div class="flex flex-col gap-0.5 flex-1 min-w-0">
|
<div class="flex flex-col gap-0.5 flex-1 min-w-0">
|
||||||
<div class="flex items-center gap-2">
|
<div class="flex items-center gap-2 flex-wrap">
|
||||||
<span :class="getModelStyleClass(item)" class="font-medium truncate">
|
<span :class="getModelStyleClass(item)" class="font-medium truncate">
|
||||||
{{ item.modelName }}
|
{{ item.modelName }}
|
||||||
</span>
|
</span>
|
||||||
<span v-if="item.isFree" class="text-[10px] px-1.5 py-0.5 bg-green-100 text-green-600 rounded-full">免费</span>
|
<span v-if="item.isFree" class="text-[10px] px-1.5 py-0.5 bg-green-100 text-green-600 rounded-full">免费</span>
|
||||||
<span v-if="item.isPremiumPackage" class="text-[10px] px-1.5 py-0.5 bg-orange-100 text-orange-600 rounded-full">VIP</span>
|
<span v-if="item.isPremiumPackage" class="text-[10px] px-1.5 py-0.5 bg-orange-100 text-orange-600 rounded-full">尊享</span>
|
||||||
|
<span v-else-if="!item.isFree" class="text-[10px] px-1.5 py-0.5 bg-yellow-100 text-yellow-600 rounded-full">VIP</span>
|
||||||
|
<!-- 显示 厂商名称 -->
|
||||||
|
<span class="text-[10px] px-1.5 py-0.5 bg-blue-50 text-blue-600 rounded-full">{{ item.providerName }}</span>
|
||||||
</div>
|
</div>
|
||||||
<div class="text-xs text-gray-400 truncate" :title="item.modelDescribe">
|
<div class="text-xs text-gray-400 break-words whitespace-normal line-clamp-2" :title="item.modelDescribe">
|
||||||
{{ item.modelDescribe }}
|
{{ item.modelDescribe }}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<!-- 选中/锁定图标 -->
|
<!-- 选中/锁定图标 -->
|
||||||
<div class="flex items-center">
|
<div class="flex items-center">
|
||||||
<el-icon v-if="item.modelId === modelStore.currentModelInfo?.modelId" class="text-primary mr-2" :size="18">
|
<el-icon v-if="isCurrentModel(item)" class="text-primary mr-2" :size="18">
|
||||||
<Check />
|
<Check />
|
||||||
</el-icon>
|
</el-icon>
|
||||||
<el-icon v-if="!isModelAvailable(item)" class="text-gray-400">
|
<el-icon v-if="!isModelAvailable(item)" class="text-gray-400">
|
||||||
|
|||||||
Reference in New Issue
Block a user