feat(achievement): 成就图标改用 iconify 渲染
Some checks failed
Deploy / deploy (build, debian, 22, /root/OJDeploy/data/clientnext) (push) Has been cancelled
Deploy / deploy (build:staging, school, 8822, /root/OJ/data/dist) (push) Has been cancelled

机房的老浏览器缺 emoji 字体,成就图标会渲染成方块。后端的 icon 字段
改存 iconify 图标名(noto 集),前端统一走新的 AchievementIcon 组件
渲染成 SVG。

组件按三种形态判断:图片 URL 走 img,含冒号走 Icon,其余当纯文本兜底,
所以存量的 emoji 数据不会瞎掉。

顺带修好解锁弹窗:题单奖章的 icon 是图片 URL,之前当文本渲染,会把
一串路径直接显示出来。

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
2026-08-04 19:20:10 -06:00
parent 0ba25dc4e3
commit 0932a05850
6 changed files with 100 additions and 6 deletions

View File

@@ -11,6 +11,7 @@ import type {
} from "utils/types"
import { getAchievementSummary } from "oj/achievement/api"
import { getMetrics, getUserBadges } from "../api"
import AchievementIcon from "shared/components/AchievementIcon.vue"
import GroupedUserBadge from "shared/components/GroupedUserBadge.vue"
import { useUserStore } from "shared/store/user"
@@ -298,7 +299,9 @@ onMounted(() => {
<n-flex align="center" :size="10" class="achievement-recent">
<n-tooltip v-for="a in achievementSummary.recent" :key="a.id">
<template #trigger>
<span class="achievement-icon">{{ a.icon }}</span>
<span class="achievement-icon">
<AchievementIcon :icon="a.icon" :size="24" />
</span>
</template>
{{ a.name }}
</n-tooltip>
@@ -392,6 +395,8 @@ h2 {
margin-top: 10px;
}
.achievement-icon {
display: inline-flex;
align-items: center;
font-size: 24px;
cursor: default;
}