Skip to content

Commit a53cb13

Browse files
committed
Refine homepage SEO navigation and copy
1 parent 1eccd9e commit a53cb13

18 files changed

Lines changed: 824 additions & 388 deletions

.gitignore

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -48,7 +48,9 @@ scripts/
4848
*.py
4949
GA4_ANALYTICS_GUIDE.md
5050
SEO_GROWTH_PLAN.md
51-
/reports/seo/
51+
/reports/
52+
build-scripts/google-ads-keywords.mjs
53+
build-scripts/seo-opportunities.mjs
5254

5355
# OpenNext
5456
.open-next/

app/[locale]/(main)/games/page.tsx

Lines changed: 41 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,14 @@ export default async function GamesPage({ params }: { params: Promise<{ locale:
3838
const games = getGames();
3939
const t = await getTranslations({ locale, namespace: 'games' });
4040
const categoryT = await getTranslations({ locale, namespace: 'categories.categoryNames' });
41+
const quickLinks = [
42+
{ id: 'adhdGames', href: '/categories/adhd-games' },
43+
{ id: 'workingMemory', href: '/categories/working-memory' },
44+
{ id: 'reactionTime', href: '/games/reaction-time' },
45+
{ id: 'schulteTable', href: '/games/schulte-table' },
46+
{ id: 'adultAdhdAssessment', href: '/adult-adhd-assessment' },
47+
{ id: 'workingMemoryGuide', href: '/working-memory-guide' },
48+
];
4149

4250
return (
4351
<div className="mx-auto">
@@ -50,6 +58,38 @@ export default async function GamesPage({ params }: { params: Promise<{ locale:
5058
{t('description')}
5159
</p>
5260

61+
<section className="mb-10 max-w-5xl mx-auto">
62+
<div className="rounded-2xl border bg-card p-6 md:p-8">
63+
<h2 className="text-2xl font-semibold mb-3 text-center">
64+
{t('quickLinks.title')}
65+
</h2>
66+
<p className="text-muted-foreground text-center mb-6 max-w-3xl mx-auto">
67+
{t('quickLinks.subtitle')}
68+
</p>
69+
<div className="grid grid-cols-1 md:grid-cols-2 xl:grid-cols-3 gap-4">
70+
{quickLinks.map((item) => (
71+
<Link
72+
key={item.id}
73+
href={item.href}
74+
className="group rounded-xl border p-4 transition-all hover:-translate-y-1 hover:shadow-sm"
75+
>
76+
<div className="flex items-start justify-between gap-3 mb-2">
77+
<h3 className="font-semibold">
78+
{t(`quickLinks.items.${item.id}.title`)}
79+
</h3>
80+
<span className="text-muted-foreground transition-transform group-hover:translate-x-1">
81+
82+
</span>
83+
</div>
84+
<p className="text-sm text-muted-foreground">
85+
{t(`quickLinks.items.${item.id}.description`)}
86+
</p>
87+
</Link>
88+
))}
89+
</div>
90+
</div>
91+
</section>
92+
5393
{/* 类别筛选 */}
5494
<div className="mb-8 flex flex-wrap items-center justify-center gap-3">
5595
<Button variant="outline" size="sm" className="rounded-full">
@@ -188,4 +228,4 @@ export default async function GamesPage({ params }: { params: Promise<{ locale:
188228
</section>
189229
</div>
190230
);
191-
}
231+
}

app/[locale]/(main)/page.tsx

Lines changed: 121 additions & 49 deletions
Original file line numberDiff line numberDiff line change
@@ -5,8 +5,7 @@ import { Link } from "@/i18n/navigation";
55
import { InteractiveHoverButton } from "@/components/magicui/interactive-hover-button";
66
import { getTranslations, setRequestLocale } from 'next-intl/server';
77
import type { Metadata } from "next";
8-
import { getBlogPosts, type BlogPost } from "@/lib/blog";
9-
import { formatDate } from "@/lib/utils";
8+
import { getBlogPosts } from "@/lib/blog";
109
import FeaturedBentoGrid from "@/components/featured-bento-grid";
1110
import LatestGames from "@/components/latest-games";
1211
import Image from "next/image";
@@ -46,7 +45,35 @@ export default async function Home({ params }: { params: Promise<{ locale: strin
4645
setRequestLocale(locale);
4746
const t = await getTranslations({ locale });
4847
const testimonials = await getTranslations({ locale, namespace: 'home.testimonials' });
48+
const guidesT = await getTranslations({ locale, namespace: 'guides' });
4949
const posts = await getBlogPosts(locale);
50+
const postsBySlug = new Map(posts.map((post) => [post.slug, post]));
51+
const featuredResources = [
52+
{
53+
id: "workingMemoryGuide",
54+
href: "/working-memory-guide",
55+
label: t("home.featuredResources.items.workingMemoryGuide.label"),
56+
title: guidesT("workingMemory.title"),
57+
description: t("home.featuredResources.items.workingMemoryGuide.description"),
58+
cta: t("common.readGuide")
59+
},
60+
{
61+
id: "schulteBenefits",
62+
href: "/blog/the-science-of-schulte-tables-boost-visual-attention-reading-speed",
63+
label: t("home.featuredResources.items.schulteBenefits.label"),
64+
title: postsBySlug.get("the-science-of-schulte-tables-boost-visual-attention-reading-speed")?.title || "",
65+
description: postsBySlug.get("the-science-of-schulte-tables-boost-visual-attention-reading-speed")?.excerpt || "",
66+
cta: t("blog.readMore")
67+
},
68+
{
69+
id: "adultAdhdAsrs",
70+
href: "/blog/adult-adhd-asrs-comprehensive-guide",
71+
label: t("home.featuredResources.items.adultAdhdAsrs.label"),
72+
title: postsBySlug.get("adult-adhd-asrs-comprehensive-guide")?.title || "",
73+
description: postsBySlug.get("adult-adhd-asrs-comprehensive-guide")?.excerpt || "",
74+
cta: t("blog.readMore")
75+
}
76+
];
5077

5178
// Schema Markup for SEO
5279
const jsonLd = {
@@ -130,6 +157,14 @@ export default async function Home({ params }: { params: Promise<{ locale: strin
130157
},
131158
];
132159

160+
const quickStartLinks = [
161+
{ id: "focusGames", href: "/games" },
162+
{ id: "adhdGames", href: "/categories/adhd-games" },
163+
{ id: "schulteTable", href: "/games/schulte-table" },
164+
{ id: "adultAdhdAssessment", href: "/adult-adhd-assessment" },
165+
{ id: "workingMemoryGuide", href: "/working-memory-guide" }
166+
];
167+
133168
return (
134169
<>
135170
<script
@@ -187,6 +222,39 @@ export default async function Home({ params }: { params: Promise<{ locale: strin
187222
<FeaturedBentoGrid />
188223
</section>
189224

225+
<section className="mb-24 max-w-[1600px] mx-auto px-6">
226+
<div className="mb-8 max-w-2xl">
227+
<h2 className="text-3xl font-bold mb-3">
228+
{t("home.searchPaths.title")}
229+
</h2>
230+
<p className="text-lg text-muted-foreground">
231+
{t("home.searchPaths.subtitle")}
232+
</p>
233+
</div>
234+
<div className="grid grid-cols-1 md:grid-cols-2 xl:grid-cols-5 gap-4">
235+
{quickStartLinks.map((item) => (
236+
<Link
237+
key={item.id}
238+
href={item.href}
239+
className="group rounded-2xl border bg-card p-5 transition-all hover:-translate-y-1 hover:shadow-md"
240+
>
241+
<div className="flex items-start justify-between gap-3 mb-4">
242+
<span className="text-sm font-medium text-primary">
243+
{t(`home.searchPaths.items.${item.id}.eyebrow`)}
244+
</span>
245+
<ArrowRight className="h-4 w-4 text-muted-foreground transition-transform group-hover:translate-x-1 group-hover:text-foreground" />
246+
</div>
247+
<h3 className="text-lg font-semibold mb-2">
248+
{t(`home.searchPaths.items.${item.id}.title`)}
249+
</h3>
250+
<p className="text-sm text-muted-foreground">
251+
{t(`home.searchPaths.items.${item.id}.description`)}
252+
</p>
253+
</Link>
254+
))}
255+
</div>
256+
</section>
257+
190258
{/* Breathing Zone - Bento Layout */}
191259
<section className="mb-24 max-w-[1600px] mx-auto px-6">
192260
<div className="flex items-center gap-2 mb-8">
@@ -306,63 +374,67 @@ export default async function Home({ params }: { params: Promise<{ locale: strin
306374
</div>
307375
<div className="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-4 gap-6">
308376
{[
309-
{ id: 'nback', icon: '🧠', color: 'bg-indigo-50 text-indigo-700' },
310-
{ id: 'schulte', icon: '⚡', color: 'bg-amber-50 text-amber-700' },
311-
{ id: 'stroop', icon: '🛑', color: 'bg-red-50 text-red-700' },
312-
{ id: 'memory', icon: '🧩', color: 'bg-emerald-50 text-emerald-700' }
377+
{ id: 'nback', icon: '🧠', color: 'bg-indigo-50 text-indigo-700', href: '/games/dual-n-back' },
378+
{ id: 'schulte', icon: '⚡', color: 'bg-amber-50 text-amber-700', href: '/games/schulte-table' },
379+
{ id: 'stroop', icon: '🛑', color: 'bg-red-50 text-red-700', href: '/games/stroop-effect-test' },
380+
{ id: 'memory', icon: '🧩', color: 'bg-emerald-50 text-emerald-700', href: '/categories/working-memory' }
313381
].map(type => (
314-
<div key={type.id} className="p-6 rounded-2xl border bg-card hover:shadow-lg transition-all hover:-translate-y-1">
315-
<div className={cn("w-12 h-12 rounded-xl flex items-center justify-center text-2xl mb-4", type.color)}>
316-
{type.icon}
382+
<Link key={type.id} href={type.href} className="group block">
383+
<div className="p-6 rounded-2xl border bg-card hover:shadow-lg transition-all hover:-translate-y-1 h-full">
384+
<div className="flex items-start justify-between gap-3 mb-4">
385+
<div className={cn("w-12 h-12 rounded-xl flex items-center justify-center text-2xl", type.color)}>
386+
{type.icon}
387+
</div>
388+
<ArrowRight className="h-4 w-4 text-muted-foreground transition-transform group-hover:translate-x-1 group-hover:text-foreground" />
389+
</div>
390+
<h3 className="text-xl font-bold mb-2">{t(`typesOfGames.${type.id}.title`)}</h3>
391+
<p className="text-muted-foreground">{t(`typesOfGames.${type.id}.description`)}</p>
317392
</div>
318-
<h3 className="text-xl font-bold mb-2">{t(`typesOfGames.${type.id}.title`)}</h3>
319-
<p className="text-muted-foreground">{t(`typesOfGames.${type.id}.description`)}</p>
320-
</div>
393+
</Link>
321394
))}
322395
</div>
323396
</section>
324397

325-
{/* Latest Blog Posts */}
398+
{/* Featured Guides */}
326399
<section className="mb-24 max-w-[1600px] mx-auto px-0 sm:px-6">
327-
<div className="flex justify-between items-center mb-8">
328-
<h2 className="text-3xl font-bold">
329-
{t("home.latestPosts")}
330-
</h2>
331-
<Link href="/blog">
332-
<Button variant="ghost">
333-
{t("buttons.viewAll")}
334-
</Button>
400+
<div className="mb-8 flex flex-col gap-4 sm:flex-row sm:items-end sm:justify-between">
401+
<div>
402+
<h2 className="text-3xl font-bold mb-3">
403+
{t("home.featuredResources.title")}
404+
</h2>
405+
<p className="text-lg text-muted-foreground max-w-3xl">
406+
{t("home.featuredResources.subtitle")}
407+
</p>
408+
</div>
409+
<Link
410+
href="/blog"
411+
className="inline-flex items-center gap-2 text-sm font-medium text-primary transition-colors hover:text-primary/80"
412+
>
413+
{t("home.featuredResources.viewAll")}
414+
<ArrowRight className="h-4 w-4" />
335415
</Link>
336416
</div>
337-
<div className="grid grid-cols-1 md:grid-cols-2 gap-6">
338-
{posts.slice(0, 2).map((post: BlogPost) => (
339-
<article
340-
key={post.slug}
341-
className="border rounded-lg overflow-hidden shadow-xs hover:shadow-md transition-shadow"
417+
<div className="grid grid-cols-1 md:grid-cols-3 gap-6">
418+
{featuredResources.map((resource) => (
419+
<Link
420+
key={resource.id}
421+
href={resource.href}
422+
className="group border rounded-2xl p-6 shadow-xs hover:shadow-md transition-all hover:-translate-y-1 bg-card"
342423
>
343-
<Link href={`/blog/${post.slug}`}>
344-
<div className="flex flex-col md:grid md:grid-cols-[1fr_1.5fr] md:h-48">
345-
{post.coverImage && (
346-
<div
347-
className="h-48 md:h-full bg-cover bg-center bg-no-repeat"
348-
style={{
349-
backgroundImage: `url(${post.coverImage})`,
350-
}}
351-
role="img"
352-
aria-label={post.title}
353-
/>
354-
)}
355-
<div className="p-6 flex flex-col justify-center">
356-
<h3 className="text-xl font-semibold mb-3">
357-
{post.title}
358-
</h3>
359-
<div className="text-sm text-muted-foreground">
360-
{formatDate(post.date, locale)}
361-
</div>
362-
</div>
363-
</div>
364-
</Link>
365-
</article>
424+
<div className="text-xs font-medium uppercase tracking-wide text-primary mb-3">
425+
{resource.label}
426+
</div>
427+
<h3 className="text-xl font-semibold mb-3 group-hover:text-primary transition-colors">
428+
{resource.title}
429+
</h3>
430+
<p className="text-muted-foreground mb-5 line-clamp-4">
431+
{resource.description}
432+
</p>
433+
<div className="inline-flex items-center gap-2 text-sm font-medium text-primary">
434+
{resource.cta}
435+
<ArrowRight className="h-4 w-4 transition-transform group-hover:translate-x-1" />
436+
</div>
437+
</Link>
366438
))}
367439
</div>
368440
</section>

components/GamePageTemplate.tsx

Lines changed: 11 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
import React from 'react';
2+
import { Link } from '@/i18n/navigation';
23
import { GameHeader } from '@/components/GameHeader';
34
import GameCategories from '@/components/game-categories';
45
import {
@@ -217,14 +218,19 @@ export function GamePageTemplate({
217218
{science.blogArticleUrl &&
218219
science.blogArticleTitle && (
219220
<div className="mb-6">
220-
<a
221+
<Link
221222
href={science.blogArticleUrl}
222-
className="inline-flex items-center gap-2 px-4 py-2 bg-primary text-primary-foreground rounded-lg hover:bg-primary/90 transition-colors"
223+
className="group block rounded-xl border border-primary/15 bg-primary/5 p-4 hover:border-primary/40 hover:bg-primary/10 transition-colors"
223224
title={science.blogArticleTitle}
224225
>
225-
<BookOpen className="w-4 h-4" />
226-
{gameT("readDetailedArticle")}
227-
</a>
226+
<div className="flex items-center gap-2 text-sm font-medium text-primary mb-2">
227+
<BookOpen className="w-4 h-4" />
228+
{gameT("readDetailedArticle")}
229+
</div>
230+
<div className="text-lg font-semibold text-foreground group-hover:text-primary transition-colors">
231+
{science.blogArticleTitle}
232+
</div>
233+
</Link>
228234
</div>
229235
)}
230236

data/blog-translations/zh/adult-adhd-asrs-comprehensive-guide.md

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
---
2-
title: "成人注意力不足过动症自评量表(ASRS-v1.1):成人ADHD评估与筛查完整指南"
3-
excerpt: "WHO成人ADHD自评量表(ASRS-v1.1)是全球公认的成人注意力缺陷筛查工具。本权威指南详细解析量表的计分规则、主要症状维度(注意力不集中与多动/冲动)及结果解读。无论您是自我筛查还是辅助诊断,本文都将为您提供科学、严谨的操作指引,助您迈出改善认知健康的第一步"
2+
title: "成人 ADHD ASRS 指南:评分、结果解读与筛查说明"
3+
excerpt: "了解 ASRS-v1.1 的评分方式、成人 ADHD 测试结果可能代表什么,以及这份 WHO 筛查工具如何用于成人 ADHD 评估"
44
date: "2025-09-10"
55
coverImage: "/blog/adult-adhd-asrs-cover.png"
66
author:
@@ -410,4 +410,4 @@ ASRS-v1.1提供优越的成人特定验证和全球标准化,而ADHD评定量
410410

411411
7. **哈佛医学院**. 成人注意力不足过动症自评量表(ASRS-v1.1)。可访问:[https://www.hcp.med.harvard.edu/ncs/asrs.php](https://www.hcp.med.harvard.edu/ncs/asrs.php)
412412

413-
*最后更新:2025年9月10日*
413+
*最后更新:2025年9月10日*

0 commit comments

Comments
 (0)