feat(ui/ux): 优化用户体验和可访问性

- 字体加载优化: 添加 font-display: block 策略,创建 useFontLoading hook
- 色彩对比度: 调整 text-muted 和 text-tertiary 颜色值确保 WCAG AA 合规
- 滚动进度条: 新增 ScrollProgress 组件,支持 reduced motion
- 表单自动保存: 新增 useFormAutosave hook,防止用户数据丢失
- 返回顶部按钮: 新增 BackToTop 组件,提升长页面导航体验
- 图片懒加载: 优化 OptimizedImage 组件,添加 blur placeholder 和加载动画

所有新组件均包含完整测试,1450+ 测试通过
This commit is contained in:
张翔
2026-03-28 11:21:04 +08:00
parent ebaa7f3c50
commit a003f1192e
15 changed files with 1280 additions and 234 deletions
+12 -3
View File
@@ -5,11 +5,20 @@
src: url('/fonts/AoyagiReisho.ttf') format('truetype');
font-weight: normal;
font-style: normal;
font-display: swap;
font-display: block;
font-stretch: normal;
unicode-range: U+4E00-9FFF, U+3400-4DBF, U+20000-2A6DF, U+2A700-2B73F, U+2B740-2B81F, U+2B820-2CEAF, U+F900-FAFF, U+2F800-2FA1F;
}
/* 字体加载优化 - 防止 FOUT */
.font-loading {
font-family: 'STKaiti', 'KaiTi', serif;
}
.font-loaded {
font-family: 'Aoyagi Reisho', 'STKaiti', 'KaiTi', serif;
}
@theme inline {
--font-sans: var(--font-geist-sans);
--font-mono: var(--font-geist-mono);
@@ -39,8 +48,8 @@
/* 文字色系 - 墨色层次 */
--color-text-primary: #1C1C1C;
--color-text-secondary: #3D3D3D;
--color-text-tertiary: #4A4A4A;
--color-text-muted: #6B6B6B;
--color-text-tertiary: #404040; /* 从 #4A4A4A 调整,提升对比度 */
--color-text-muted: #595959; /* 从 #6B6B6B 调整,确保 WCAG AA 合规 */
/* 边框色系 */
--color-border-primary: #E5E5E5;
+12
View File
@@ -8,6 +8,8 @@ import { Analytics } from "@vercel/analytics/react";
import { OrganizationSchema, WebsiteSchema } from "@/components/seo/structured-data";
import { MobileTabBar } from "@/components/layout/mobile-tab-bar";
import { ErrorBoundary } from "@/components/ui/error-boundary";
import { ScrollProgress } from "@/components/ui/scroll-progress";
import { BackToTop } from "@/components/ui/back-to-top";
import { SessionProvider } from "@/providers/session-provider";
import { initSentry } from "@/lib/sentry";
@@ -122,6 +124,14 @@ export default function RootLayout({
<head>
<link rel="icon" type="image/svg+xml" href="/favicon.svg" />
<link rel="apple-touch-icon" href="/favicon.svg" />
{/* 字体预加载优化 */}
<link
rel="preload"
href="/fonts/AoyagiReisho.ttf"
as="font"
type="font/ttf"
crossOrigin="anonymous"
/>
<OrganizationSchema />
<WebsiteSchema />
<script
@@ -141,6 +151,7 @@ export default function RootLayout({
className={`${geistSans.variable} ${geistMono.variable} ${notoSansSC.variable} ${maShanZheng.variable} ${longCang.variable} font-sans antialiased`}
style={{ fontFamily: "'Noto Sans SC', 'Geist', -apple-system, BlinkMacSystemFont, sans-serif" }}
>
<ScrollProgress />
<GoogleAnalytics />
<WebVitals />
<SessionProvider>
@@ -151,6 +162,7 @@ export default function RootLayout({
</ThemeProvider>
</SessionProvider>
<MobileTabBar />
<BackToTop />
<Analytics />
</body>
</html>