web-font/src/FontSelector.vue
崮生(子虚) b4a7a820eb feat: AI Typography Skill 系统 + 中英双语 i18n + Before/After Demo
- 新增 skills/chinese-web-typography.md 作为提供给 AI agent 的排版智能文件
- 重写 README.md(中文默认),新增 README.en.md(英文版),互相引用
- 新增 TypographyDemo.vue 前后对比组件,展示中文字体效果差异
- 新增 src/i18n.ts 轻量国际化方案,所有组件文案支持中英切换
- 后端 /api/fonts 返回 temporary 字段标识临时字体
- 升级至 v1.8.0

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-28 22:41:47 +08:00

51 lines
2.5 KiB
Vue

<script setup lang="ts">
import type { FontInfo } from "./api";
import { t } from "./i18n";
defineProps<{
fonts: FontInfo[];
selectedFont: string;
onFontChange: (font: string) => void;
supportedOutTypes: ("woff2" | "ttf")[];
outType: "woff2" | "ttf";
onOutTypeChange: (v: "woff2" | "ttf") => void;
}>();
const outTypeLabels: Record<string, () => string> = {
woff2: () => t("woff2Label"),
ttf: () => t("ttfLabel"),
};
const outTypeDescs: Record<string, () => string> = {
woff2: () => t("woff2Desc"),
ttf: () => t("ttfDesc"),
};
</script>
<template>
<div style="display: flex; gap: 12px">
<div style="flex: 1">
<label style="display: block; font-size: 13px; color: #555; margin-bottom: 6px">{{ t('selectFont') }}</label>
<select
:value="selectedFont"
@change="onFontChange(($event.target).value)"
style="width: 100%; padding: 8px 12px; font-size: 14px; border: 1px solid #d9d9d9; border-radius: 6px; outline: none; box-sizing: border-box; cursor: pointer; appearance: none; background-image: url(&quot;data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='12' height='12' viewBox='0 0 12 12'%3E%3Cpath d='M2 4l4 4 4-4' fill='none' stroke='%23999' stroke-width='1.5' stroke-linecap='round'/%3E%3C/svg%3E&quot;); background-repeat: no-repeat; background-position: right 10px center; padding-right: 28px"
>
<option value="">{{ t('pleaseSelect') }}</option>
<option v-for="f in fonts" :key="f.name" :value="f.name">{{ f.name }}</option>
</select>
</div>
<div style="width: 160px">
<label style="display: block; font-size: 13px; color: #555; margin-bottom: 6px">{{ t('outputFormat') }}</label>
<select
:value="outType"
@change="onOutTypeChange(($event.target).value)"
style="width: 100%; padding: 8px 12px; font-size: 14px; border: 1px solid #d9d9d9; border-radius: 6px; outline: none; box-sizing: border-box; cursor: pointer; appearance: none; background-image: url(&quot;data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='12' height='12' viewBox='0 0 12 12'%3E%3Cpath d='M2 4l4 4 4-4' fill='none' stroke='%23999' stroke-width='1.5' stroke-linecap='round'/%3E%3C/svg%3E&quot;); background-repeat: no-repeat; background-position: right 10px center; padding-right: 28px"
>
<option v-for="ot in supportedOutTypes" :key="ot" :value="ot">{{ outTypeLabels[ot]() }}</option>
</select>
<p style="font-size: 11px; color: #bbb; margin-top: 4px">{{ outTypeDescs[outType]() }}</p>
</div>
</div>
</template>