diff --git a/app/layout.tsx b/app/layout.tsx index 9c04980..35688f8 100644 --- a/app/layout.tsx +++ b/app/layout.tsx @@ -3,7 +3,7 @@ import type { Metadata } from 'next'; import { siteConfig } from '@/lib/config'; import { LayoutShell } from '@/components/layout-shell'; import { ThemeProvider } from 'next-themes'; -import { Playfair_Display } from 'next/font/google'; +import { Playfair_Display, LXGW_WenKai_TC } from 'next/font/google'; import { JsonLd } from '@/components/json-ld'; const playfair = Playfair_Display({ @@ -12,6 +12,14 @@ const playfair = Playfair_Display({ display: 'swap', }); +const lxgwWenKai = LXGW_WenKai_TC({ + weight: ['400', '700'], // 只加载 Regular 和 Bold + subsets: ['latin'], + variable: '--font-serif-cn', + display: 'swap', + preload: true, +}); + export const metadata: Metadata = { title: { default: siteConfig.title, @@ -88,7 +96,7 @@ export default function RootLayout({ }; return ( - + diff --git a/scripts/subset-font.mjs b/scripts/subset-font.mjs new file mode 100644 index 0000000..ae4c4ef --- /dev/null +++ b/scripts/subset-font.mjs @@ -0,0 +1,66 @@ +#!/usr/bin/env node +/** + * 字体子集化脚本 + * 使用 pyftsubset (需要安装 fonttools: pip install fonttools brotli) + * + * 用法: node scripts/subset-font.mjs + * + * 注意:此脚本需要先下载字体文件,或使用 Google Fonts API + * 由于我们使用 next/font/google,Next.js 会自动优化字体加载 + * 此脚本主要用于本地字体文件的子集化 + */ + +import { execSync } from 'child_process'; +import { existsSync, mkdirSync } from 'fs'; +import { join } from 'path'; + +// 常用繁体中文字符集(约3000-5000字) +const commonTCChars = ` +的一是在不了有和人這中大為上個國我以要他時來用們生到作地於出就分對成會可主發年動同工也能下過子說產種面而方後多定行學法所民得經十三之進著等部度家電力裡如水化高自二理起小物實現加量都兩體制機當使點從業本去把性好應開它合還因由其些然前外天政四日那社義事平形相全表間樣與關各重新線內數正心反你明看原又麼利比或但質氣第向道命此變條只沒結解問意建月公無系軍很情者最立代想已通並提直題黨程展五果料象員革位入常文總次品式活設及管特件長求老頭基資邊流路級少圖山統接知較將組見計別她手角期根論運農指幾九區強放決西被幹做必戰先回則任取據處隊南給色光門即保治北造百規熱領七海口東導器壓志世金增爭濟階油思術極交受聯什認六共權收證改清己美再轉更單風切打白教速花帶安場身車例真務具萬每目至達走積示議聲報鬥完類離離戶科懸空需廠商校連斷深難近礦千週委素技備半辦青省列習響約支般史感勞便團往酸歷市克何除消構府稱太準精值號率族維劃選標寫存候毛親快效斯院查江型眼王按格養易置派層片始卻專狀育廠京識適屬圓包火住調滿縣局照參紅細引聽該鐵價嚴龍飛 +`.trim().replace(/\s+/g, ''); + +async function subsetFont() { + console.log('开始字体子集化...'); + + // 注意:这个脚本需要你先下载字体文件到 fonts/ 目录 + // 或者使用 Google Fonts API 下载 + const fontsDir = join(process.cwd(), 'fonts'); + const fontPath = join(fontsDir, 'LXGWWenKaiTC-Regular.ttf'); + const outputDir = join(process.cwd(), 'public', 'fonts'); + + if (!existsSync(fontPath)) { + console.log('⚠️ 字体文件不存在,跳过子集化'); + console.log(` 预期路径: ${fontPath}`); + console.log(' 提示: 由于使用 next/font/google,Next.js 会自动优化字体加载'); + return; + } + + try { + // 检查 pyftsubset 是否安装 + execSync('which pyftsubset', { stdio: 'ignore' }); + + const outputPath = join(outputDir, 'LXGWWenKaiTC-Regular-subset.woff2'); + + // 创建输出目录 + if (!existsSync(outputDir)) { + mkdirSync(outputDir, { recursive: true }); + } + + // 生成 Unicode 范围 + const unicodes = Array.from(new Set(commonTCChars)) + .map(c => `U+${c.charCodeAt(0).toString(16).toUpperCase().padStart(4, '0')}`) + .join(','); + + // 执行子集化 + const command = `pyftsubset "${fontPath}" --unicodes="${unicodes}" --flavor=woff2 --output-file="${outputPath}"`; + + execSync(command, { stdio: 'inherit' }); + + console.log(`✅ 子集化完成: ${outputPath}`); + } catch (error) { + console.error('❌ 子集化失败:', error.message); + console.log('\n提示: 需要安装 fonttools: pip install fonttools brotli'); + } +} + +subsetFont(); diff --git a/styles/globals.css b/styles/globals.css index 20dad88..f2116f4 100644 --- a/styles/globals.css +++ b/styles/globals.css @@ -17,7 +17,7 @@ /* Custom font families */ --font-serif-eng: var(--font-serif-eng), serif; - --font-serif-cn: "Songti SC", "Noto Serif TC", "SimSun", serif; + --font-serif-cn: var(--font-serif-cn), "Songti SC", "Noto Serif TC", "SimSun", serif; /* Custom transition timing */ --ease-snappy: cubic-bezier(0.32, 0.72, 0, 1); @@ -220,7 +220,7 @@ body { color: var(--color-ink-strong); font-weight: 700; letter-spacing: -0.03em; - font-family: var(--font-serif-eng), "Songti SC", serif; + font-family: var(--font-serif-cn), var(--font-serif-eng), "Songti SC", serif; } .prose h2 { @@ -409,7 +409,7 @@ body { font-size: clamp(2.2rem, 1.6rem + 2.4vw, 3.5rem); line-height: 1.2; font-weight: var(--font-weight-semibold); - font-family: var(--font-serif-eng), "Songti SC", serif; + font-family: var(--font-serif-cn), var(--font-serif-eng), "Songti SC", serif; } .type-title {