Skip to content

Commit a3505c8

Browse files
committed
feat: revamp homepage visuals and search UX
1 parent ac8586c commit a3505c8

21 files changed

Lines changed: 2512 additions & 1189 deletions

package.json

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@
2525
"@streamdown/mermaid": "^1.0.2",
2626
"@tailwindcss/typography": "^0.5.19",
2727
"@types/three": "^0.181.0",
28+
"@use-gesture/react": "^10.3.1",
2829
"class-variance-authority": "^0.7.1",
2930
"clsx": "^2.1.1",
3031
"framer-motion": "^12.23.25",

pnpm-lock.yaml

Lines changed: 3 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

src/app/blog/page.tsx

Lines changed: 23 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
import Link from 'next/link'
22
import type { Metadata } from 'next'
3+
import SpotlightCard from '@/components/SpotlightCard'
34
import { getAllPosts } from '@/lib/mdx'
45

56
export const metadata: Metadata = {
@@ -34,7 +35,7 @@ export default function BlogPage() {
3435
const years = Object.keys(postsByYear).sort((a, b) => Number(b) - Number(a))
3536

3637
return (
37-
<div className="max-w-3xl mx-auto px-4 sm:px-6 py-12 sm:py-16">
38+
<div className="max-w-3xl mx-auto px-4 sm:px-6 pt-16 pb-12 sm:pt-20 sm:pb-16">
3839
{/* Header */}
3940
<div className="mb-12">
4041
<h1 className="text-2xl sm:text-3xl font-medium tracking-tight mb-2">
@@ -51,23 +52,32 @@ export default function BlogPage() {
5152
<div className="year-watermark">{year}</div>
5253

5354
{/* Posts List */}
54-
<div className="relative pt-8">
55+
<div className="relative pt-8 space-y-3">
5556
{postsByYear[Number(year)].map((post) => (
56-
<article key={post.slug} className="article-item">
57+
<article key={post.slug}>
5758
<Link
5859
href={`/blog/${post.slug}`}
59-
className="article-title block"
60+
className="block hover:opacity-100"
6061
>
61-
{post.metadata.title}
62+
<SpotlightCard
63+
spotlightColor="rgba(0, 0, 0, 0.1)"
64+
className="!rounded-xl !border-border/55 !bg-background/60 !p-4 transition-colors hover:!border-border hover:!bg-muted/20"
65+
>
66+
<div className="flex items-start justify-between gap-3">
67+
<h2 className="mb-0 flex-1 min-w-0 text-base font-normal text-foreground">
68+
{post.metadata.title}
69+
</h2>
70+
<time className="article-meta shrink-0">
71+
{formatDate(post.metadata.date)}
72+
</time>
73+
</div>
74+
{post.metadata.description && (
75+
<p className="text-sm text-muted-foreground/70 mt-1 line-clamp-2">
76+
· {post.metadata.description}
77+
</p>
78+
)}
79+
</SpotlightCard>
6280
</Link>
63-
<div className="article-meta flex items-center gap-2">
64-
<time>{formatDate(post.metadata.date)}</time>
65-
{post.metadata.description && (
66-
<span className="text-muted-foreground/60 hidden sm:inline">
67-
· {post.metadata.description}
68-
</span>
69-
)}
70-
</div>
7181
</article>
7282
))}
7383
</div>

src/app/globals.css

Lines changed: 94 additions & 187 deletions
Original file line numberDiff line numberDiff line change
@@ -1,157 +1,90 @@
11
@import 'tailwindcss';
22
@import 'streamdown/styles.css';
3-
@import "tw-animate-css";
3+
@import 'tw-animate-css';
44
@plugin "@tailwindcss/typography";
55
@custom-variant dark (&:where(.dark, .dark *));
66
@source "../../node_modules/streamdown/dist/*.js";
77

88
/* Light mode (default) */
99
:root {
10-
--muted:
11-
oklch(0.97 0 0);
12-
--muted-foreground:
13-
oklch(0.556 0 0);
14-
--border:
15-
oklch(0.922 0 0);
16-
--card:
17-
oklch(1 0 0);
18-
--card-foreground:
19-
oklch(0.145 0 0);
20-
--primary:
21-
oklch(0.205 0 0);
22-
--primary-foreground:
23-
oklch(0.985 0 0);
24-
--accent:
25-
oklch(0.97 0 0);
26-
--accent-foreground:
27-
oklch(0.205 0 0);
28-
--ring:
29-
oklch(0.708 0 0);
30-
--radius:
31-
0.625rem;
10+
--muted: oklch(0.97 0 0);
11+
--muted-foreground: oklch(0.556 0 0);
12+
--border: oklch(0.922 0 0);
13+
--card: oklch(1 0 0);
14+
--card-foreground: oklch(0.145 0 0);
15+
--primary: oklch(0.205 0 0);
16+
--primary-foreground: oklch(0.985 0 0);
17+
--accent: oklch(0.97 0 0);
18+
--accent-foreground: oklch(0.205 0 0);
19+
--ring: oklch(0.708 0 0);
20+
--radius: 0.625rem;
3221

3322
--font-sans:
3423
system-ui, -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto,
3524
'Helvetica Neue', Arial, sans-serif;
3625
--font-mono:
3726
'SFMono-Regular', 'Menlo', 'Monaco', 'Consolas', 'Liberation Mono',
3827
'Courier New', monospace;
39-
--background:
40-
oklch(1 0 0);
41-
--foreground:
42-
oklch(0.145 0 0);
43-
--popover:
44-
oklch(1 0 0);
45-
--popover-foreground:
46-
oklch(0.145 0 0);
47-
--secondary:
48-
oklch(0.97 0 0);
49-
--secondary-foreground:
50-
oklch(0.205 0 0);
51-
--destructive:
52-
oklch(0.577 0.245 27.325);
53-
--input:
54-
oklch(0.922 0 0);
55-
--chart-1:
56-
oklch(0.646 0.222 41.116);
57-
--chart-2:
58-
oklch(0.6 0.118 184.704);
59-
--chart-3:
60-
oklch(0.398 0.07 227.392);
61-
--chart-4:
62-
oklch(0.828 0.189 84.429);
63-
--chart-5:
64-
oklch(0.769 0.188 70.08);
65-
--sidebar:
66-
oklch(0.985 0 0);
67-
--sidebar-foreground:
68-
oklch(0.145 0 0);
69-
--sidebar-primary:
70-
oklch(0.205 0 0);
71-
--sidebar-primary-foreground:
72-
oklch(0.985 0 0);
73-
--sidebar-accent:
74-
oklch(0.97 0 0);
75-
--sidebar-accent-foreground:
76-
oklch(0.205 0 0);
77-
--sidebar-border:
78-
oklch(0.922 0 0);
79-
--sidebar-ring:
80-
oklch(0.708 0 0);
81-
--dotgrid-base:
82-
#d3cedb;
83-
--dotgrid-active:
84-
#a49bb6;
28+
--background: oklch(1 0 0);
29+
--foreground: oklch(0.145 0 0);
30+
--popover: oklch(1 0 0);
31+
--popover-foreground: oklch(0.145 0 0);
32+
--secondary: oklch(0.97 0 0);
33+
--secondary-foreground: oklch(0.205 0 0);
34+
--destructive: oklch(0.577 0.245 27.325);
35+
--input: oklch(0.922 0 0);
36+
--chart-1: oklch(0.646 0.222 41.116);
37+
--chart-2: oklch(0.6 0.118 184.704);
38+
--chart-3: oklch(0.398 0.07 227.392);
39+
--chart-4: oklch(0.828 0.189 84.429);
40+
--chart-5: oklch(0.769 0.188 70.08);
41+
--sidebar: oklch(0.985 0 0);
42+
--sidebar-foreground: oklch(0.145 0 0);
43+
--sidebar-primary: oklch(0.205 0 0);
44+
--sidebar-primary-foreground: oklch(0.985 0 0);
45+
--sidebar-accent: oklch(0.97 0 0);
46+
--sidebar-accent-foreground: oklch(0.205 0 0);
47+
--sidebar-border: oklch(0.922 0 0);
48+
--sidebar-ring: oklch(0.708 0 0);
49+
--dotgrid-base: #d3cedb;
50+
--dotgrid-active: #a49bb6;
8551
}
8652

8753
/* Dark mode */
8854
.dark {
89-
--background:
90-
oklch(0.145 0 0);
91-
--foreground:
92-
oklch(0.985 0 0);
93-
--muted:
94-
oklch(0.269 0 0);
95-
--muted-foreground:
96-
oklch(0.708 0 0);
97-
--border:
98-
oklch(1 0 0 / 10%);
99-
--card:
100-
oklch(0.205 0 0);
101-
--card-foreground:
102-
oklch(0.985 0 0);
103-
--primary:
104-
oklch(0.922 0 0);
105-
--primary-foreground:
106-
oklch(0.205 0 0);
107-
--accent:
108-
oklch(0.269 0 0);
109-
--accent-foreground:
110-
oklch(0.985 0 0);
111-
--ring:
112-
oklch(0.556 0 0);
113-
--popover:
114-
oklch(0.205 0 0);
115-
--popover-foreground:
116-
oklch(0.985 0 0);
117-
--secondary:
118-
oklch(0.269 0 0);
119-
--secondary-foreground:
120-
oklch(0.985 0 0);
121-
--destructive:
122-
oklch(0.704 0.191 22.216);
123-
--input:
124-
oklch(1 0 0 / 15%);
125-
--chart-1:
126-
oklch(0.488 0.243 264.376);
127-
--chart-2:
128-
oklch(0.696 0.17 162.48);
129-
--chart-3:
130-
oklch(0.769 0.188 70.08);
131-
--chart-4:
132-
oklch(0.627 0.265 303.9);
133-
--chart-5:
134-
oklch(0.645 0.246 16.439);
135-
--sidebar:
136-
oklch(0.205 0 0);
137-
--sidebar-foreground:
138-
oklch(0.985 0 0);
139-
--sidebar-primary:
140-
oklch(0.488 0.243 264.376);
141-
--sidebar-primary-foreground:
142-
oklch(0.985 0 0);
143-
--sidebar-accent:
144-
oklch(0.269 0 0);
145-
--sidebar-accent-foreground:
146-
oklch(0.985 0 0);
147-
--sidebar-border:
148-
oklch(1 0 0 / 10%);
149-
--sidebar-ring:
150-
oklch(0.556 0 0);
151-
--dotgrid-base:
152-
#271E37;
153-
--dotgrid-active:
154-
#ffffff;
55+
--background: oklch(0.145 0 0);
56+
--foreground: oklch(0.985 0 0);
57+
--muted: oklch(0.269 0 0);
58+
--muted-foreground: oklch(0.708 0 0);
59+
--border: oklch(1 0 0 / 10%);
60+
--card: oklch(0.205 0 0);
61+
--card-foreground: oklch(0.985 0 0);
62+
--primary: oklch(0.922 0 0);
63+
--primary-foreground: oklch(0.205 0 0);
64+
--accent: oklch(0.269 0 0);
65+
--accent-foreground: oklch(0.985 0 0);
66+
--ring: oklch(0.556 0 0);
67+
--popover: oklch(0.205 0 0);
68+
--popover-foreground: oklch(0.985 0 0);
69+
--secondary: oklch(0.269 0 0);
70+
--secondary-foreground: oklch(0.985 0 0);
71+
--destructive: oklch(0.704 0.191 22.216);
72+
--input: oklch(1 0 0 / 15%);
73+
--chart-1: oklch(0.488 0.243 264.376);
74+
--chart-2: oklch(0.696 0.17 162.48);
75+
--chart-3: oklch(0.769 0.188 70.08);
76+
--chart-4: oklch(0.627 0.265 303.9);
77+
--chart-5: oklch(0.645 0.246 16.439);
78+
--sidebar: oklch(0.205 0 0);
79+
--sidebar-foreground: oklch(0.985 0 0);
80+
--sidebar-primary: oklch(0.488 0.243 264.376);
81+
--sidebar-primary-foreground: oklch(0.985 0 0);
82+
--sidebar-accent: oklch(0.269 0 0);
83+
--sidebar-accent-foreground: oklch(0.985 0 0);
84+
--sidebar-border: oklch(1 0 0 / 10%);
85+
--sidebar-ring: oklch(0.556 0 0);
86+
--dotgrid-base: #271e37;
87+
--dotgrid-active: #ffffff;
15588
}
15689

15790
@theme inline {
@@ -167,58 +100,32 @@
167100
--color-accent: var(--accent);
168101
--color-accent-foreground: var(--accent-foreground);
169102
--color-ring: var(--ring);
170-
--color-sidebar-ring:
171-
var(--sidebar-ring);
172-
--color-sidebar-border:
173-
var(--sidebar-border);
174-
--color-sidebar-accent-foreground:
175-
var(--sidebar-accent-foreground);
176-
--color-sidebar-accent:
177-
var(--sidebar-accent);
178-
--color-sidebar-primary-foreground:
179-
var(--sidebar-primary-foreground);
180-
--color-sidebar-primary:
181-
var(--sidebar-primary);
182-
--color-sidebar-foreground:
183-
var(--sidebar-foreground);
184-
--color-sidebar:
185-
var(--sidebar);
186-
--color-chart-5:
187-
var(--chart-5);
188-
--color-chart-4:
189-
var(--chart-4);
190-
--color-chart-3:
191-
var(--chart-3);
192-
--color-chart-2:
193-
var(--chart-2);
194-
--color-chart-1:
195-
var(--chart-1);
196-
--color-input:
197-
var(--input);
198-
--color-destructive:
199-
var(--destructive);
200-
--color-secondary-foreground:
201-
var(--secondary-foreground);
202-
--color-secondary:
203-
var(--secondary);
204-
--color-popover-foreground:
205-
var(--popover-foreground);
206-
--color-popover:
207-
var(--popover);
208-
--radius-sm:
209-
calc(var(--radius) - 4px);
210-
--radius-md:
211-
calc(var(--radius) - 2px);
212-
--radius-lg:
213-
var(--radius);
214-
--radius-xl:
215-
calc(var(--radius) + 4px);
216-
--radius-2xl:
217-
calc(var(--radius) + 8px);
218-
--radius-3xl:
219-
calc(var(--radius) + 12px);
220-
--radius-4xl:
221-
calc(var(--radius) + 16px);
103+
--color-sidebar-ring: var(--sidebar-ring);
104+
--color-sidebar-border: var(--sidebar-border);
105+
--color-sidebar-accent-foreground: var(--sidebar-accent-foreground);
106+
--color-sidebar-accent: var(--sidebar-accent);
107+
--color-sidebar-primary-foreground: var(--sidebar-primary-foreground);
108+
--color-sidebar-primary: var(--sidebar-primary);
109+
--color-sidebar-foreground: var(--sidebar-foreground);
110+
--color-sidebar: var(--sidebar);
111+
--color-chart-5: var(--chart-5);
112+
--color-chart-4: var(--chart-4);
113+
--color-chart-3: var(--chart-3);
114+
--color-chart-2: var(--chart-2);
115+
--color-chart-1: var(--chart-1);
116+
--color-input: var(--input);
117+
--color-destructive: var(--destructive);
118+
--color-secondary-foreground: var(--secondary-foreground);
119+
--color-secondary: var(--secondary);
120+
--color-popover-foreground: var(--popover-foreground);
121+
--color-popover: var(--popover);
122+
--radius-sm: calc(var(--radius) - 4px);
123+
--radius-md: calc(var(--radius) - 2px);
124+
--radius-lg: var(--radius);
125+
--radius-xl: calc(var(--radius) + 4px);
126+
--radius-2xl: calc(var(--radius) + 8px);
127+
--radius-3xl: calc(var(--radius) + 12px);
128+
--radius-4xl: calc(var(--radius) + 16px);
222129
}
223130

224131
@layer base {

0 commit comments

Comments
 (0)