mirror of
https://github.com/YuuKi-OS/Yuuki-web.git
synced 2026-02-18 22:01:09 +00:00
yuuki web init
This commit is contained in:
194
components/yuuki/creator-section.tsx
Normal file
194
components/yuuki/creator-section.tsx
Normal file
@@ -0,0 +1,194 @@
|
||||
import { Github, ExternalLink } from "lucide-react"
|
||||
|
||||
export function CreatorSection() {
|
||||
return (
|
||||
<section id="creator" className="relative px-6 py-24">
|
||||
<div className="mx-auto max-w-7xl">
|
||||
<div className="mb-16 text-center">
|
||||
<span className="mb-4 inline-block font-mono text-xs uppercase tracking-widest text-sakura">
|
||||
About
|
||||
</span>
|
||||
<h2 className="mb-4 text-3xl font-bold text-foreground md:text-5xl text-balance">
|
||||
The Creator
|
||||
</h2>
|
||||
</div>
|
||||
|
||||
<div className="mx-auto max-w-3xl">
|
||||
<div className="overflow-hidden rounded-2xl border border-border bg-card">
|
||||
<div className="relative h-32 bg-gradient-to-r from-sakura/10 via-sakura/5 to-transparent">
|
||||
<div
|
||||
className="absolute inset-0 opacity-10"
|
||||
style={{
|
||||
backgroundImage: `linear-gradient(rgba(244,114,182,0.2) 1px, transparent 1px), linear-gradient(90deg, rgba(244,114,182,0.2) 1px, transparent 1px)`,
|
||||
backgroundSize: "20px 20px",
|
||||
}}
|
||||
/>
|
||||
</div>
|
||||
<div className="px-8 pb-8">
|
||||
<div className="-mt-12 mb-6 flex items-end gap-4">
|
||||
<div className="h-24 w-24 overflow-hidden rounded-2xl border-4 border-card bg-secondary">
|
||||
<img
|
||||
src="https://github.com/aguitauwu.png"
|
||||
alt="agua_omg avatar"
|
||||
className="h-full w-full object-cover"
|
||||
crossOrigin="anonymous"
|
||||
/>
|
||||
</div>
|
||||
<div className="mb-1">
|
||||
<h3 className="text-xl font-bold text-foreground">agua_omg</h3>
|
||||
<p className="text-sm text-muted-foreground">
|
||||
Independent Developer & Creator of Yuuki
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<p className="mb-6 text-sm text-muted-foreground leading-relaxed">
|
||||
{"Hey, I'm agua -- a young independent developer. I started this project in January 2026 simply because I couldn't afford to keep paying for Claude anymore, so I decided to build my own open-source model for everyone. I'm open to collaborating with and supporting anyone who wants to try out or contribute to Yuuki."}
|
||||
</p>
|
||||
|
||||
<div className="mb-6 grid grid-cols-2 gap-3 sm:grid-cols-4">
|
||||
<MiniStat label="Projects" value="4+" />
|
||||
<MiniStat label="Language" value="Rust" />
|
||||
<MiniStat label="Device" value="Redmi 12" />
|
||||
<MiniStat label="Budget" value="$0" />
|
||||
</div>
|
||||
|
||||
<div className="flex flex-wrap gap-3">
|
||||
<a
|
||||
href="https://github.com/aguitauwu"
|
||||
target="_blank"
|
||||
rel="noopener noreferrer"
|
||||
className="inline-flex items-center gap-2 rounded-lg border border-border px-4 py-2.5 text-sm text-foreground transition-colors hover:bg-secondary"
|
||||
>
|
||||
<Github size={16} />
|
||||
GitHub
|
||||
</a>
|
||||
<a
|
||||
href="https://twitter.com/agua_omg"
|
||||
target="_blank"
|
||||
rel="noopener noreferrer"
|
||||
className="inline-flex items-center gap-2 rounded-lg border border-border px-4 py-2.5 text-sm text-foreground transition-colors hover:bg-secondary"
|
||||
>
|
||||
<svg viewBox="0 0 24 24" fill="currentColor" className="h-4 w-4" aria-hidden="true">
|
||||
<path d="M18.244 2.25h3.308l-7.227 8.26 8.502 11.24H16.17l-5.214-6.817L4.99 21.75H1.68l7.73-8.835L1.254 2.25H8.08l4.713 6.231zm-1.161 17.52h1.833L7.084 4.126H5.117z" />
|
||||
</svg>
|
||||
Twitter / X
|
||||
</a>
|
||||
<a
|
||||
href="https://discord.com/users/agua_omg"
|
||||
target="_blank"
|
||||
rel="noopener noreferrer"
|
||||
className="inline-flex items-center gap-2 rounded-lg border border-border px-4 py-2.5 text-sm text-foreground transition-colors hover:bg-secondary"
|
||||
>
|
||||
<svg
|
||||
viewBox="0 0 24 24"
|
||||
fill="currentColor"
|
||||
className="h-4 w-4"
|
||||
aria-hidden="true"
|
||||
>
|
||||
<path d="M20.317 4.37a19.791 19.791 0 0 0-4.885-1.515.074.074 0 0 0-.079.037c-.21.375-.444.864-.608 1.25a18.27 18.27 0 0 0-5.487 0 12.64 12.64 0 0 0-.617-1.25.077.077 0 0 0-.079-.037A19.736 19.736 0 0 0 3.677 4.37a.07.07 0 0 0-.032.027C.533 9.046-.32 13.58.099 18.057a.082.082 0 0 0 .031.057 19.9 19.9 0 0 0 5.993 3.03.078.078 0 0 0 .084-.028 14.09 14.09 0 0 0 1.226-1.994.076.076 0 0 0-.041-.106 13.107 13.107 0 0 1-1.872-.892.077.077 0 0 1-.008-.128 10.2 10.2 0 0 0 .372-.292.074.074 0 0 1 .077-.01c3.928 1.793 8.18 1.793 12.062 0a.074.074 0 0 1 .078.01c.12.098.246.198.373.292a.077.077 0 0 1-.006.127 12.299 12.299 0 0 1-1.873.892.077.077 0 0 0-.041.107c.36.698.772 1.362 1.225 1.993a.076.076 0 0 0 .084.028 19.839 19.839 0 0 0 6.002-3.03.077.077 0 0 0 .032-.054c.5-5.177-.838-9.674-3.549-13.66a.061.061 0 0 0-.031-.03zM8.02 15.33c-1.183 0-2.157-1.085-2.157-2.419 0-1.333.956-2.419 2.157-2.419 1.21 0 2.176 1.095 2.157 2.42 0 1.333-.956 2.418-2.157 2.418zm7.975 0c-1.183 0-2.157-1.085-2.157-2.419 0-1.333.955-2.419 2.157-2.419 1.21 0 2.176 1.095 2.157 2.42 0 1.333-.946 2.418-2.157 2.418z" />
|
||||
</svg>
|
||||
Discord
|
||||
</a>
|
||||
<a
|
||||
href="https://huggingface.co/OpceanAI"
|
||||
target="_blank"
|
||||
rel="noopener noreferrer"
|
||||
className="inline-flex items-center gap-2 rounded-lg border border-border px-4 py-2.5 text-sm text-foreground transition-colors hover:bg-secondary"
|
||||
>
|
||||
<ExternalLink size={16} />
|
||||
HuggingFace
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* Name Origin Story */}
|
||||
<div className="mt-8 rounded-xl border border-border bg-card p-8">
|
||||
<h3 className="mb-4 text-lg font-bold text-foreground">
|
||||
{"Where does the name \"Yuuki\" come from?"}
|
||||
</h3>
|
||||
<div className="flex flex-col gap-4 text-sm text-muted-foreground leading-relaxed">
|
||||
<p>
|
||||
{"It all started back in October 2025. I was working on another project and wanted to find a good name for it, so I looked into Japanese kanji and discovered"}{" "}
|
||||
<span className="font-medium text-foreground">Yuki</span>
|
||||
{" -- meaning \"snow.\""}
|
||||
</p>
|
||||
<p>
|
||||
{"Then in November 2025, I came across the anime"}{" "}
|
||||
<span className="font-medium text-sakura">{"Girls' Last Tour"}</span>
|
||||
{". The two protagonists are Yuu and Chi-chan, but I really fell in love with Yuu -- her personality is so unique and beautiful."}
|
||||
</p>
|
||||
<p>
|
||||
{"By December 2025, the two inspirations came together, and"}{" "}
|
||||
<span className="font-bold text-sakura">Yuuki</span>
|
||||
{" was born -- a name that carries the quiet beauty of snow and the courageous spirit of a character who never gives up."}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* Related Projects */}
|
||||
<div className="mt-8 grid gap-4 sm:grid-cols-2">
|
||||
<ProjectLink
|
||||
name="Yuuki-best"
|
||||
desc="Best checkpoint model weights"
|
||||
href="https://huggingface.co/OpceanAI/Yuuki-best"
|
||||
/>
|
||||
<ProjectLink
|
||||
name="Yuuki Space"
|
||||
desc="Web-based interactive demo"
|
||||
href="https://huggingface.co/spaces/OpceanAI/Yuuki"
|
||||
/>
|
||||
<ProjectLink
|
||||
name="YUY CLI"
|
||||
desc="Download, manage, and run models"
|
||||
href="https://github.com/YuuKi-OS/yuy"
|
||||
/>
|
||||
<ProjectLink
|
||||
name="YUY-Chat"
|
||||
desc="Terminal chat interface"
|
||||
href="https://github.com/YuuKi-OS/yuy-chat"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
)
|
||||
}
|
||||
|
||||
function MiniStat({ label, value }: { label: string; value: string }) {
|
||||
return (
|
||||
<div className="rounded-lg bg-secondary p-3 text-center">
|
||||
<div className="text-sm font-bold font-mono text-foreground">{value}</div>
|
||||
<div className="text-xs text-muted-foreground">{label}</div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
||||
function ProjectLink({
|
||||
name,
|
||||
desc,
|
||||
href,
|
||||
}: {
|
||||
name: string
|
||||
desc: string
|
||||
href: string
|
||||
}) {
|
||||
return (
|
||||
<a
|
||||
href={href}
|
||||
target="_blank"
|
||||
rel="noopener noreferrer"
|
||||
className="group flex items-center justify-between rounded-xl border border-border bg-card p-4 transition-colors hover:border-sakura-border"
|
||||
>
|
||||
<div>
|
||||
<h4 className="text-sm font-semibold text-foreground">{name}</h4>
|
||||
<p className="text-xs text-muted-foreground">{desc}</p>
|
||||
</div>
|
||||
<ExternalLink
|
||||
size={14}
|
||||
className="text-muted-foreground transition-colors group-hover:text-sakura"
|
||||
/>
|
||||
</a>
|
||||
)
|
||||
}
|
||||
75
components/yuuki/demo-section.tsx
Normal file
75
components/yuuki/demo-section.tsx
Normal file
@@ -0,0 +1,75 @@
|
||||
"use client"
|
||||
|
||||
import { useEffect, useRef, useState } from "react"
|
||||
|
||||
export function DemoSection() {
|
||||
const containerRef = useRef<HTMLDivElement>(null)
|
||||
const [loaded, setLoaded] = useState(false)
|
||||
|
||||
useEffect(() => {
|
||||
if (loaded) return
|
||||
// Load Gradio script dynamically
|
||||
const script = document.createElement("script")
|
||||
script.type = "module"
|
||||
script.src = "https://gradio.s3-us-west-2.amazonaws.com/5.9.1/gradio.js"
|
||||
script.onload = () => {
|
||||
if (!containerRef.current) return
|
||||
// Create the gradio-app custom element after the script loads
|
||||
const gradioApp = document.createElement("gradio-app")
|
||||
gradioApp.setAttribute("src", "https://opceanai-yuuki.hf.space")
|
||||
gradioApp.style.minHeight = "600px"
|
||||
gradioApp.style.width = "100%"
|
||||
containerRef.current.appendChild(gradioApp)
|
||||
}
|
||||
document.head.appendChild(script)
|
||||
setLoaded(true)
|
||||
}, [loaded])
|
||||
|
||||
return (
|
||||
<section id="demo" className="relative px-6 py-24">
|
||||
<div className="mx-auto max-w-7xl">
|
||||
<div className="mb-12 text-center">
|
||||
<span className="mb-4 inline-block font-mono text-xs uppercase tracking-widest text-sakura">
|
||||
Live Demo
|
||||
</span>
|
||||
<h2 className="mb-4 text-3xl font-bold text-foreground md:text-5xl text-balance">
|
||||
Try Yuuki Now
|
||||
</h2>
|
||||
<p className="mx-auto max-w-2xl text-muted-foreground leading-relaxed">
|
||||
Generate code directly in your browser. This Space runs the Yuuki-best model
|
||||
on HuggingFace infrastructure. No setup required.
|
||||
</p>
|
||||
</div>
|
||||
|
||||
<div className="overflow-hidden rounded-2xl border border-border bg-card">
|
||||
{/* Window chrome */}
|
||||
<div className="flex items-center justify-between border-b border-border px-4 py-3">
|
||||
<div className="flex items-center gap-2">
|
||||
<div className="h-3 w-3 rounded-full bg-[#ef4444]/60" />
|
||||
<div className="h-3 w-3 rounded-full bg-[#eab308]/60" />
|
||||
<div className="h-3 w-3 rounded-full bg-[#22c55e]/60" />
|
||||
</div>
|
||||
<span className="text-xs font-mono text-muted-foreground">
|
||||
opceanai-yuuki.hf.space
|
||||
</span>
|
||||
<a
|
||||
href="https://huggingface.co/spaces/OpceanAI/Yuuki"
|
||||
target="_blank"
|
||||
rel="noopener noreferrer"
|
||||
className="text-xs text-sakura hover:underline"
|
||||
>
|
||||
Open in new tab
|
||||
</a>
|
||||
</div>
|
||||
|
||||
{/* Gradio embed */}
|
||||
<div ref={containerRef} className="relative min-h-[600px] w-full bg-background" />
|
||||
</div>
|
||||
|
||||
<p className="mt-4 text-center text-xs text-muted-foreground">
|
||||
The Space may take a moment to load if it has been idle. Powered by HuggingFace Spaces.
|
||||
</p>
|
||||
</div>
|
||||
</section>
|
||||
)
|
||||
}
|
||||
68
components/yuuki/donate-section.tsx
Normal file
68
components/yuuki/donate-section.tsx
Normal file
@@ -0,0 +1,68 @@
|
||||
import { Heart } from "lucide-react"
|
||||
|
||||
export function DonateSection() {
|
||||
return (
|
||||
<section id="donate" className="relative px-6 py-24">
|
||||
<div className="mx-auto max-w-7xl">
|
||||
<div className="mx-auto max-w-3xl">
|
||||
<div className="overflow-hidden rounded-2xl border border-sakura-border bg-card relative">
|
||||
{/* Background decoration */}
|
||||
<div className="pointer-events-none absolute inset-0 bg-gradient-to-br from-sakura/5 via-transparent to-transparent" />
|
||||
|
||||
<div className="relative p-8 md:p-12 text-center">
|
||||
<div className="mb-6 inline-flex h-14 w-14 items-center justify-center rounded-2xl bg-sakura-dim border border-sakura-border">
|
||||
<Heart size={24} className="text-sakura" />
|
||||
</div>
|
||||
|
||||
<h2 className="mb-4 text-3xl font-bold text-foreground md:text-4xl text-balance">
|
||||
Support the Project
|
||||
</h2>
|
||||
<p className="mx-auto mb-8 max-w-xl text-muted-foreground leading-relaxed">
|
||||
Yuuki is built with zero budget by a single person. Your support helps keep the
|
||||
project alive and growing -- better hardware, more training time, and new features.
|
||||
</p>
|
||||
|
||||
{/* GitHub Sponsors embed */}
|
||||
<div className="mb-8 flex justify-center">
|
||||
<div className="overflow-hidden rounded-xl border border-border bg-background">
|
||||
<iframe
|
||||
src="https://github.com/sponsors/aguitauwu/card"
|
||||
title="Sponsor aguitauwu"
|
||||
height={225}
|
||||
width={600}
|
||||
className="max-w-full border-0"
|
||||
style={{ border: 0 }}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="flex flex-col items-center gap-4 sm:flex-row sm:justify-center">
|
||||
<a
|
||||
href="https://github.com/sponsors/aguitauwu"
|
||||
target="_blank"
|
||||
rel="noopener noreferrer"
|
||||
className="inline-flex items-center gap-2 rounded-xl bg-sakura px-8 py-3.5 text-sm font-semibold text-primary-foreground transition-opacity hover:opacity-90"
|
||||
>
|
||||
<Heart size={16} />
|
||||
Sponsor on GitHub
|
||||
</a>
|
||||
<a
|
||||
href="https://github.com/YuuKi-OS"
|
||||
target="_blank"
|
||||
rel="noopener noreferrer"
|
||||
className="inline-flex items-center gap-2 rounded-xl border border-border px-8 py-3.5 text-sm font-medium text-foreground transition-colors hover:bg-secondary"
|
||||
>
|
||||
Star the repos
|
||||
</a>
|
||||
</div>
|
||||
|
||||
<p className="mt-6 text-xs text-muted-foreground">
|
||||
Even a star on GitHub helps. Every contribution matters.
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
)
|
||||
}
|
||||
181
components/yuuki/ecosystem-section.tsx
Normal file
181
components/yuuki/ecosystem-section.tsx
Normal file
@@ -0,0 +1,181 @@
|
||||
import {
|
||||
Terminal,
|
||||
MessageSquare,
|
||||
Cpu,
|
||||
Download,
|
||||
Layers,
|
||||
Smartphone,
|
||||
Monitor,
|
||||
Zap,
|
||||
} from "lucide-react"
|
||||
|
||||
const tools = [
|
||||
{
|
||||
name: "YUY",
|
||||
subtitle: "CLI Tool",
|
||||
description:
|
||||
"Download, manage, and run Yuuki models locally. Three commands to get started. Written in Rust.",
|
||||
icon: Terminal,
|
||||
tech: "Rust 1.75+",
|
||||
features: [
|
||||
"Model downloads with auto-quantization",
|
||||
"Local inference via llama.cpp / ollama",
|
||||
"Cross-platform (Termux, Linux, macOS, Windows)",
|
||||
"System diagnostics & health checks",
|
||||
],
|
||||
links: {
|
||||
github: "https://github.com/YuuKi-OS/yuy",
|
||||
},
|
||||
command: "yuy setup && yuy download Yuuki-best && yuy run Yuuki-best",
|
||||
},
|
||||
{
|
||||
name: "YUY-Chat",
|
||||
subtitle: "TUI Chat",
|
||||
description:
|
||||
"Beautiful terminal chat interface. Stream responses word by word. Save and reload conversations. All local.",
|
||||
icon: MessageSquare,
|
||||
tech: "Rust + ratatui",
|
||||
features: [
|
||||
"Real-time streaming responses",
|
||||
"Conversation history (JSON)",
|
||||
"Model selector & presets",
|
||||
"HuggingFace cloud integration",
|
||||
],
|
||||
links: {
|
||||
github: "https://github.com/YuuKi-OS/yuy-chat",
|
||||
},
|
||||
command: "yuy-chat",
|
||||
},
|
||||
]
|
||||
|
||||
const highlights = [
|
||||
{
|
||||
icon: Download,
|
||||
title: "Smart Downloads",
|
||||
desc: "Auto-selects the best quantization based on your hardware and RAM.",
|
||||
},
|
||||
{
|
||||
icon: Layers,
|
||||
title: "Multiple Quantizations",
|
||||
desc: "q4_0, q5_k_m, q8_0, and f32. From phones to research workstations.",
|
||||
},
|
||||
{
|
||||
icon: Smartphone,
|
||||
title: "Mobile-First",
|
||||
desc: "Termux is the primary target. Optimized for constrained hardware.",
|
||||
},
|
||||
{
|
||||
icon: Monitor,
|
||||
title: "Cross-Platform",
|
||||
desc: "Termux, Linux, macOS, and Windows. Same experience everywhere.",
|
||||
},
|
||||
{
|
||||
icon: Cpu,
|
||||
title: "Zero Config",
|
||||
desc: "Platform detection, RAM recommendations, runtime auto-discovery.",
|
||||
},
|
||||
{
|
||||
icon: Zap,
|
||||
title: "~50ms Startup",
|
||||
desc: "Lightweight Rust binaries. ~8 MB. ~20 MB idle RAM.",
|
||||
},
|
||||
]
|
||||
|
||||
export function EcosystemSection() {
|
||||
return (
|
||||
<section id="ecosystem" className="relative px-6 py-24">
|
||||
<div className="mx-auto max-w-7xl">
|
||||
<div className="mb-16 text-center">
|
||||
<span className="mb-4 inline-block font-mono text-xs uppercase tracking-widest text-sakura">
|
||||
Ecosystem
|
||||
</span>
|
||||
<h2 className="mb-4 text-3xl font-bold text-foreground md:text-5xl text-balance">
|
||||
The Complete Toolkit
|
||||
</h2>
|
||||
<p className="mx-auto max-w-2xl text-muted-foreground leading-relaxed">
|
||||
From downloading models to chatting with them in your terminal.
|
||||
Everything built in Rust, optimized for every platform.
|
||||
</p>
|
||||
</div>
|
||||
|
||||
{/* Tools grid */}
|
||||
<div className="mb-16 grid gap-6 lg:grid-cols-2">
|
||||
{tools.map((tool) => (
|
||||
<div
|
||||
key={tool.name}
|
||||
className="group relative overflow-hidden rounded-xl border border-border bg-card p-8 transition-colors hover:border-sakura-border"
|
||||
>
|
||||
<div className="mb-6 flex items-start justify-between">
|
||||
<div className="flex items-center gap-3">
|
||||
<div className="flex h-10 w-10 items-center justify-center rounded-lg bg-sakura-dim border border-sakura-border">
|
||||
<tool.icon size={20} className="text-sakura" />
|
||||
</div>
|
||||
<div>
|
||||
<h3 className="text-xl font-bold text-foreground">{tool.name}</h3>
|
||||
<span className="text-xs font-mono text-muted-foreground">{tool.subtitle}</span>
|
||||
</div>
|
||||
</div>
|
||||
<span className="rounded-md bg-secondary px-2.5 py-1 text-xs font-mono text-muted-foreground">
|
||||
{tool.tech}
|
||||
</span>
|
||||
</div>
|
||||
|
||||
<p className="mb-6 text-sm text-muted-foreground leading-relaxed">
|
||||
{tool.description}
|
||||
</p>
|
||||
|
||||
<ul className="mb-6 flex flex-col gap-2">
|
||||
{tool.features.map((feature) => (
|
||||
<li key={feature} className="flex items-start gap-2 text-sm">
|
||||
<span className="mt-1 h-1.5 w-1.5 flex-shrink-0 rounded-full bg-sakura" />
|
||||
<span className="text-secondary-foreground">{feature}</span>
|
||||
</li>
|
||||
))}
|
||||
</ul>
|
||||
|
||||
{/* Command line */}
|
||||
<div className="overflow-hidden rounded-lg border border-border bg-background">
|
||||
<div className="flex items-center gap-2 border-b border-border px-3 py-2">
|
||||
<div className="h-2 w-2 rounded-full bg-[#ef4444]/50" />
|
||||
<div className="h-2 w-2 rounded-full bg-[#eab308]/50" />
|
||||
<div className="h-2 w-2 rounded-full bg-[#22c55e]/50" />
|
||||
</div>
|
||||
<div className="p-4">
|
||||
<code className="text-xs font-mono text-muted-foreground">
|
||||
<span className="text-sakura">$</span> {tool.command}
|
||||
</code>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="mt-6">
|
||||
<a
|
||||
href={tool.links.github}
|
||||
target="_blank"
|
||||
rel="noopener noreferrer"
|
||||
className="inline-flex items-center gap-1.5 text-sm text-sakura transition-opacity hover:opacity-80"
|
||||
>
|
||||
View on GitHub
|
||||
<span className="text-xs">{">"}</span>
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
))}
|
||||
</div>
|
||||
|
||||
{/* Highlights grid */}
|
||||
<div className="grid gap-4 sm:grid-cols-2 lg:grid-cols-3">
|
||||
{highlights.map((item) => (
|
||||
<div
|
||||
key={item.title}
|
||||
className="rounded-xl border border-border bg-card p-6 transition-colors hover:border-sakura-border"
|
||||
>
|
||||
<item.icon size={18} className="mb-3 text-sakura" />
|
||||
<h4 className="mb-1.5 text-sm font-semibold text-foreground">{item.title}</h4>
|
||||
<p className="text-xs text-muted-foreground leading-relaxed">{item.desc}</p>
|
||||
</div>
|
||||
))}
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
)
|
||||
}
|
||||
86
components/yuuki/footer.tsx
Normal file
86
components/yuuki/footer.tsx
Normal file
@@ -0,0 +1,86 @@
|
||||
export function Footer() {
|
||||
return (
|
||||
<footer className="border-t border-border px-6 py-12">
|
||||
<div className="mx-auto max-w-7xl">
|
||||
<div className="grid gap-8 md:grid-cols-4">
|
||||
{/* Brand */}
|
||||
<div className="md:col-span-1">
|
||||
<div className="mb-3 flex items-center gap-2">
|
||||
<span className="text-lg font-bold text-foreground font-mono">Yuuki</span>
|
||||
<span className="rounded-md bg-sakura-dim px-1.5 py-0.5 text-[10px] font-mono text-sakura border border-sakura-border">
|
||||
v0.1
|
||||
</span>
|
||||
</div>
|
||||
<p className="text-xs text-muted-foreground leading-relaxed">
|
||||
Built with patience, a phone, and zero budget.
|
||||
</p>
|
||||
<p className="mt-3 text-xs text-muted-foreground">
|
||||
Apache 2.0 License
|
||||
</p>
|
||||
</div>
|
||||
|
||||
{/* Model */}
|
||||
<div>
|
||||
<h4 className="mb-3 text-xs font-semibold uppercase tracking-wider text-muted-foreground">
|
||||
Model
|
||||
</h4>
|
||||
<ul className="flex flex-col gap-2">
|
||||
<FooterLink href="https://huggingface.co/OpceanAI/Yuuki-best" label="Yuuki-best" />
|
||||
<FooterLink href="https://huggingface.co/OpceanAI/Yuuki" label="Original Yuuki" />
|
||||
<FooterLink href="https://huggingface.co/spaces/OpceanAI/Yuuki" label="Live Demo" />
|
||||
<FooterLink href="https://github.com/YuuKi-OS/yuuki-training" label="Training Code" />
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
{/* Tools */}
|
||||
<div>
|
||||
<h4 className="mb-3 text-xs font-semibold uppercase tracking-wider text-muted-foreground">
|
||||
Tools
|
||||
</h4>
|
||||
<ul className="flex flex-col gap-2">
|
||||
<FooterLink href="https://github.com/YuuKi-OS/yuy" label="YUY CLI" />
|
||||
<FooterLink href="https://github.com/YuuKi-OS/yuy-chat" label="YUY-Chat" />
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
{/* Community */}
|
||||
<div>
|
||||
<h4 className="mb-3 text-xs font-semibold uppercase tracking-wider text-muted-foreground">
|
||||
Community
|
||||
</h4>
|
||||
<ul className="flex flex-col gap-2">
|
||||
<FooterLink href="https://github.com/YuuKi-OS" label="GitHub Org" />
|
||||
<FooterLink href="https://github.com/aguitauwu" label="GitHub (agua_omg)" />
|
||||
<FooterLink href="https://twitter.com/agua_omg" label="Twitter" />
|
||||
<FooterLink href="https://github.com/sponsors/aguitauwu" label="Sponsor" />
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="mt-12 flex flex-col items-center justify-between gap-4 border-t border-border pt-8 md:flex-row">
|
||||
<p className="text-xs text-muted-foreground">
|
||||
Yuuki Project 2026. All rights reserved.
|
||||
</p>
|
||||
<p className="text-xs text-muted-foreground font-mono">
|
||||
Snapdragon 685 | CPU only | $0.00
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</footer>
|
||||
)
|
||||
}
|
||||
|
||||
function FooterLink({ href, label }: { href: string; label: string }) {
|
||||
return (
|
||||
<li>
|
||||
<a
|
||||
href={href}
|
||||
target="_blank"
|
||||
rel="noopener noreferrer"
|
||||
className="text-sm text-muted-foreground transition-colors hover:text-foreground"
|
||||
>
|
||||
{label}
|
||||
</a>
|
||||
</li>
|
||||
)
|
||||
}
|
||||
96
components/yuuki/hero.tsx
Normal file
96
components/yuuki/hero.tsx
Normal file
@@ -0,0 +1,96 @@
|
||||
import React from "react"
|
||||
import { Terminal, Smartphone, Cpu } from "lucide-react"
|
||||
|
||||
export function Hero() {
|
||||
return (
|
||||
<section className="relative flex min-h-screen flex-col items-center justify-center px-6 pt-20">
|
||||
{/* Subtle grid background */}
|
||||
<div
|
||||
className="pointer-events-none absolute inset-0 opacity-[0.03]"
|
||||
style={{
|
||||
backgroundImage: `linear-gradient(rgba(244,114,182,0.3) 1px, transparent 1px), linear-gradient(90deg, rgba(244,114,182,0.3) 1px, transparent 1px)`,
|
||||
backgroundSize: "60px 60px",
|
||||
}}
|
||||
/>
|
||||
|
||||
{/* Glow */}
|
||||
<div className="pointer-events-none absolute top-1/4 left-1/2 -translate-x-1/2 -translate-y-1/2 h-[500px] w-[500px] rounded-full bg-sakura/5 blur-[120px]" />
|
||||
|
||||
<div className="relative z-10 mx-auto max-w-4xl text-center">
|
||||
{/* Terminal badge */}
|
||||
<div className="mb-8 inline-flex items-center gap-2 rounded-full border border-border bg-secondary px-4 py-2">
|
||||
<Terminal size={14} className="text-sakura" />
|
||||
<span className="text-xs font-mono text-muted-foreground">
|
||||
Trained entirely on a smartphone
|
||||
</span>
|
||||
</div>
|
||||
|
||||
<h1 className="mb-6 text-5xl font-bold tracking-tight text-foreground md:text-7xl lg:text-8xl text-balance">
|
||||
<span className="text-sakura">Yuuki</span>
|
||||
<br />
|
||||
<span className="text-foreground">Code Generation</span>
|
||||
</h1>
|
||||
|
||||
<p className="mx-auto mb-10 max-w-2xl text-lg leading-relaxed text-muted-foreground md:text-xl text-pretty">
|
||||
A multilingual code generation model trained on a Redmi 12 smartphone.
|
||||
Zero cloud. Zero budget. Built by one person with pure determination.
|
||||
</p>
|
||||
|
||||
{/* CTA buttons */}
|
||||
<div className="mb-16 flex flex-col items-center justify-center gap-4 sm:flex-row">
|
||||
<a
|
||||
href="#demo"
|
||||
className="group flex items-center gap-2 rounded-xl bg-sakura px-8 py-3.5 text-sm font-semibold text-primary-foreground transition-all hover:opacity-90"
|
||||
>
|
||||
Try Live Demo
|
||||
<span className="transition-transform group-hover:translate-x-0.5">{">"}</span>
|
||||
</a>
|
||||
<a
|
||||
href="https://github.com/YuuKi-OS/yuy"
|
||||
target="_blank"
|
||||
rel="noopener noreferrer"
|
||||
className="flex items-center gap-2 rounded-xl border border-border px-8 py-3.5 text-sm font-medium text-foreground transition-colors hover:bg-secondary"
|
||||
>
|
||||
<span className="font-mono text-muted-foreground">$</span>
|
||||
cargo install yuy
|
||||
</a>
|
||||
</div>
|
||||
|
||||
{/* Stats row */}
|
||||
<div className="grid grid-cols-2 gap-4 sm:grid-cols-4 sm:gap-0 sm:divide-x sm:divide-border">
|
||||
<Stat icon={<Smartphone size={16} />} value="Redmi 12" label="Training Device" />
|
||||
<Stat icon={<Cpu size={16} />} value="$0.00" label="Cloud Cost" />
|
||||
<Stat value="988 MB" label="Model Size" />
|
||||
<Stat value="5.3%" label="Training Progress" />
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* Scroll indicator */}
|
||||
<div className="absolute bottom-8 left-1/2 -translate-x-1/2">
|
||||
<div className="h-8 w-5 rounded-full border border-border flex items-start justify-center p-1">
|
||||
<div className="h-2 w-1 rounded-full bg-sakura animate-bounce" />
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
)
|
||||
}
|
||||
|
||||
function Stat({
|
||||
icon,
|
||||
value,
|
||||
label,
|
||||
}: {
|
||||
icon?: React.ReactNode
|
||||
value: string
|
||||
label: string
|
||||
}) {
|
||||
return (
|
||||
<div className="flex flex-col items-center gap-1 px-6 py-3">
|
||||
<div className="flex items-center gap-1.5">
|
||||
{icon && <span className="text-sakura">{icon}</span>}
|
||||
<span className="text-lg font-bold text-foreground font-mono">{value}</span>
|
||||
</div>
|
||||
<span className="text-xs text-muted-foreground">{label}</span>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
181
components/yuuki/model-section.tsx
Normal file
181
components/yuuki/model-section.tsx
Normal file
@@ -0,0 +1,181 @@
|
||||
export function ModelSection() {
|
||||
return (
|
||||
<section id="model" className="relative px-6 py-24">
|
||||
<div className="mx-auto max-w-7xl">
|
||||
<div className="mb-16 text-center">
|
||||
<span className="mb-4 inline-block font-mono text-xs uppercase tracking-widest text-sakura">
|
||||
The Model
|
||||
</span>
|
||||
<h2 className="mb-4 text-3xl font-bold text-foreground md:text-5xl text-balance">
|
||||
Yuuki-best
|
||||
</h2>
|
||||
<p className="mx-auto max-w-2xl text-muted-foreground leading-relaxed">
|
||||
A code generation model based on GPT-2 (124M parameters), trained from scratch
|
||||
on a smartphone CPU. Currently at checkpoint 2000 with measurable improvements.
|
||||
</p>
|
||||
</div>
|
||||
|
||||
<div className="grid gap-4 md:grid-cols-2 lg:grid-cols-3">
|
||||
{/* Training Card */}
|
||||
<div className="rounded-xl border border-border bg-card p-6">
|
||||
<h3 className="mb-4 text-sm font-semibold uppercase tracking-wider text-muted-foreground">
|
||||
Training Details
|
||||
</h3>
|
||||
<div className="flex flex-col gap-3">
|
||||
<InfoRow label="Base Model" value="GPT-2 (124M)" />
|
||||
<InfoRow label="Hardware" value="Snapdragon 685" />
|
||||
<InfoRow label="Training Type" value="CPU only" />
|
||||
<InfoRow label="Time" value="50+ hours" />
|
||||
<InfoRow label="Progress" value="2,000 / 37,500 steps" />
|
||||
<InfoRow label="Cost" value="$0.00" highlight />
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* Scores Card */}
|
||||
<div className="rounded-xl border border-border bg-card p-6">
|
||||
<h3 className="mb-4 text-sm font-semibold uppercase tracking-wider text-muted-foreground">
|
||||
Language Scores (CP-2000)
|
||||
</h3>
|
||||
<div className="flex flex-col gap-3">
|
||||
<ScoreBar language="Agda" score={55} color="bg-[#22c55e]" />
|
||||
<ScoreBar language="C" score={20} color="bg-[#eab308]" />
|
||||
<ScoreBar language="Assembly" score={15} color="bg-[#eab308]" />
|
||||
<ScoreBar language="Python" score={8} color="bg-[#ef4444]" />
|
||||
</div>
|
||||
<p className="mt-4 text-xs text-muted-foreground">
|
||||
Average: 24.6/100 (+146% from checkpoint 1400)
|
||||
</p>
|
||||
</div>
|
||||
|
||||
{/* Checkpoint Comparison */}
|
||||
<div className="rounded-xl border border-border bg-card p-6 md:col-span-2 lg:col-span-1">
|
||||
<h3 className="mb-4 text-sm font-semibold uppercase tracking-wider text-muted-foreground">
|
||||
Evolution
|
||||
</h3>
|
||||
<div className="overflow-hidden rounded-lg border border-border">
|
||||
<table className="w-full text-sm">
|
||||
<thead>
|
||||
<tr className="border-b border-border bg-secondary">
|
||||
<th className="px-4 py-2.5 text-left text-xs font-medium text-muted-foreground">
|
||||
Metric
|
||||
</th>
|
||||
<th className="px-4 py-2.5 text-right text-xs font-medium text-muted-foreground">
|
||||
CP-1400
|
||||
</th>
|
||||
<th className="px-4 py-2.5 text-right text-xs font-medium text-muted-foreground">
|
||||
CP-2000
|
||||
</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
<ComparisonRow metric="Progress" old="3.7%" current="5.3%" />
|
||||
<ComparisonRow metric="Agda" old="20" current="55" />
|
||||
<ComparisonRow metric="C" old="8" current="20" />
|
||||
<ComparisonRow metric="Assembly" old="2" current="15" />
|
||||
<ComparisonRow metric="Avg Score" old="~10" current="24.6" />
|
||||
<ComparisonRow metric="Speed" old="100s/step" current="86s/step" />
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* Code sample */}
|
||||
<div className="mt-8 rounded-xl border border-border bg-card overflow-hidden">
|
||||
<div className="flex items-center gap-2 border-b border-border px-4 py-3">
|
||||
<div className="h-3 w-3 rounded-full bg-[#ef4444]/60" />
|
||||
<div className="h-3 w-3 rounded-full bg-[#eab308]/60" />
|
||||
<div className="h-3 w-3 rounded-full bg-[#22c55e]/60" />
|
||||
<span className="ml-2 text-xs font-mono text-muted-foreground">
|
||||
Yuuki output -- Agda (best language, 55/100)
|
||||
</span>
|
||||
</div>
|
||||
<pre className="overflow-x-auto p-6 font-mono text-sm leading-relaxed">
|
||||
<code className="text-muted-foreground">
|
||||
<span className="text-sakura">{"module"}</span>{" Main "}
|
||||
<span className="text-sakura">{"where"}</span>
|
||||
{"\n\n"}
|
||||
<span className="text-[#22c55e]">{"open import"}</span>{" Function\n"}
|
||||
<span className="text-muted-foreground/50">{"--"}</span>
|
||||
{"\n"}
|
||||
<span className="text-[#22c55e]">{"open import"}</span>{" Data.Nat\n"}
|
||||
<span className="text-[#22c55e]">{"open import"}</span>{" Function\n\n"}
|
||||
<span className="text-[#22c55e]">{"open import"}</span>{" Data.Nat\n"}
|
||||
<span className="text-[#22c55e]">{"open import"}</span>{" Data.Unit\n"}
|
||||
<span className="text-[#22c55e]">{"open import"}</span>{" Data.Nat.Dec\n"}
|
||||
<span className="text-[#22c55e]">{"open import"}</span>{" Data.Properties.Nat\n"}
|
||||
<span className="text-[#22c55e]">{"open import"}</span>{" Data.Nat.Properties\n"}
|
||||
<span className="text-[#22c55e]">{"open import"}</span>{" Data.Unary"}
|
||||
</code>
|
||||
</pre>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
)
|
||||
}
|
||||
|
||||
function InfoRow({
|
||||
label,
|
||||
value,
|
||||
highlight = false,
|
||||
}: {
|
||||
label: string
|
||||
value: string
|
||||
highlight?: boolean
|
||||
}) {
|
||||
return (
|
||||
<div className="flex items-center justify-between border-b border-border pb-3 last:border-0 last:pb-0">
|
||||
<span className="text-sm text-muted-foreground">{label}</span>
|
||||
<span
|
||||
className={`text-sm font-medium font-mono ${
|
||||
highlight ? "text-sakura" : "text-foreground"
|
||||
}`}
|
||||
>
|
||||
{value}
|
||||
</span>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
||||
function ScoreBar({
|
||||
language,
|
||||
score,
|
||||
color,
|
||||
}: {
|
||||
language: string
|
||||
score: number
|
||||
color: string
|
||||
}) {
|
||||
return (
|
||||
<div>
|
||||
<div className="mb-1.5 flex items-center justify-between">
|
||||
<span className="text-sm text-foreground">{language}</span>
|
||||
<span className="text-xs font-mono text-muted-foreground">{score}/100</span>
|
||||
</div>
|
||||
<div className="h-2 w-full overflow-hidden rounded-full bg-secondary">
|
||||
<div
|
||||
className={`h-full rounded-full ${color} transition-all duration-1000`}
|
||||
style={{ width: `${score}%` }}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
||||
function ComparisonRow({
|
||||
metric,
|
||||
old,
|
||||
current,
|
||||
}: {
|
||||
metric: string
|
||||
old: string
|
||||
current: string
|
||||
}) {
|
||||
return (
|
||||
<tr className="border-b border-border last:border-0">
|
||||
<td className="px-4 py-2.5 text-muted-foreground">{metric}</td>
|
||||
<td className="px-4 py-2.5 text-right font-mono text-muted-foreground/60">{old}</td>
|
||||
<td className="px-4 py-2.5 text-right font-mono text-sakura font-medium">{current}</td>
|
||||
</tr>
|
||||
)
|
||||
}
|
||||
106
components/yuuki/navbar.tsx
Normal file
106
components/yuuki/navbar.tsx
Normal file
@@ -0,0 +1,106 @@
|
||||
"use client"
|
||||
|
||||
import { useState } from "react"
|
||||
import { Menu, X } from "lucide-react"
|
||||
|
||||
const navLinks = [
|
||||
{ label: "Model", href: "#model" },
|
||||
{ label: "Ecosystem", href: "#ecosystem" },
|
||||
{ label: "Demo", href: "#demo" },
|
||||
{ label: "Stats", href: "#stats" },
|
||||
{ label: "Creator", href: "#creator" },
|
||||
{ label: "Donate", href: "#donate" },
|
||||
]
|
||||
|
||||
export function Navbar() {
|
||||
const [open, setOpen] = useState(false)
|
||||
|
||||
return (
|
||||
<header className="fixed top-0 left-0 right-0 z-50 border-b border-border bg-background/80 backdrop-blur-xl">
|
||||
<nav className="mx-auto flex max-w-7xl items-center justify-between px-6 py-4">
|
||||
<a href="#" className="flex items-center gap-2">
|
||||
<span className="text-xl font-bold text-foreground font-mono tracking-tight">
|
||||
Yuuki
|
||||
</span>
|
||||
<span className="rounded-md bg-sakura-dim px-2 py-0.5 text-xs font-mono text-sakura border border-sakura-border">
|
||||
v0.1
|
||||
</span>
|
||||
</a>
|
||||
|
||||
<div className="hidden items-center gap-8 md:flex">
|
||||
{navLinks.map((link) => (
|
||||
<a
|
||||
key={link.label}
|
||||
href={link.href}
|
||||
className="text-sm text-muted-foreground transition-colors hover:text-foreground"
|
||||
>
|
||||
{link.label}
|
||||
</a>
|
||||
))}
|
||||
</div>
|
||||
|
||||
<div className="hidden md:flex items-center gap-3">
|
||||
<a
|
||||
href="https://github.com/YuuKi-OS"
|
||||
target="_blank"
|
||||
rel="noopener noreferrer"
|
||||
className="rounded-lg border border-border px-4 py-2 text-sm text-foreground transition-colors hover:bg-secondary"
|
||||
>
|
||||
GitHub
|
||||
</a>
|
||||
<a
|
||||
href="https://huggingface.co/OpceanAI/Yuuki-best"
|
||||
target="_blank"
|
||||
rel="noopener noreferrer"
|
||||
className="rounded-lg bg-sakura px-4 py-2 text-sm font-medium text-primary-foreground transition-opacity hover:opacity-90"
|
||||
>
|
||||
Model
|
||||
</a>
|
||||
</div>
|
||||
|
||||
<button
|
||||
onClick={() => setOpen(!open)}
|
||||
className="text-foreground md:hidden"
|
||||
aria-label="Toggle menu"
|
||||
>
|
||||
{open ? <X size={20} /> : <Menu size={20} />}
|
||||
</button>
|
||||
</nav>
|
||||
|
||||
{open && (
|
||||
<div className="border-t border-border bg-background px-6 py-4 md:hidden">
|
||||
<div className="flex flex-col gap-4">
|
||||
{navLinks.map((link) => (
|
||||
<a
|
||||
key={link.label}
|
||||
href={link.href}
|
||||
onClick={() => setOpen(false)}
|
||||
className="text-sm text-muted-foreground transition-colors hover:text-foreground"
|
||||
>
|
||||
{link.label}
|
||||
</a>
|
||||
))}
|
||||
<div className="flex gap-3 pt-2">
|
||||
<a
|
||||
href="https://github.com/YuuKi-OS"
|
||||
target="_blank"
|
||||
rel="noopener noreferrer"
|
||||
className="rounded-lg border border-border px-4 py-2 text-sm text-foreground"
|
||||
>
|
||||
GitHub
|
||||
</a>
|
||||
<a
|
||||
href="https://huggingface.co/OpceanAI/Yuuki-best"
|
||||
target="_blank"
|
||||
rel="noopener noreferrer"
|
||||
className="rounded-lg bg-sakura px-4 py-2 text-sm font-medium text-primary-foreground"
|
||||
>
|
||||
Model
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
</header>
|
||||
)
|
||||
}
|
||||
153
components/yuuki/stats-section.tsx
Normal file
153
components/yuuki/stats-section.tsx
Normal file
@@ -0,0 +1,153 @@
|
||||
export function StatsSection() {
|
||||
const stats = [
|
||||
{ value: "124M", label: "Parameters", sub: "GPT-2 base" },
|
||||
{ value: "988", label: "MB Model Size", sub: "Full precision" },
|
||||
{ value: "37,500", label: "Total Steps", sub: "Target" },
|
||||
{ value: "2,000", label: "Steps Completed", sub: "5.3% done" },
|
||||
{ value: "50+", label: "Hours Training", sub: "On a phone" },
|
||||
{ value: "$0", label: "Total Cost", sub: "Zero cloud" },
|
||||
{ value: "~86s", label: "Per Step", sub: "Snapdragon 685" },
|
||||
{ value: "+146%", label: "Quality Gain", sub: "CP-1400 to CP-2000" },
|
||||
]
|
||||
|
||||
const timeline = [
|
||||
{
|
||||
step: "Phase 1",
|
||||
title: "Foundation",
|
||||
status: "complete",
|
||||
items: [
|
||||
"Training pipeline on mobile",
|
||||
"Custom tokenizer",
|
||||
"Checkpoint system",
|
||||
"Evaluation framework",
|
||||
],
|
||||
},
|
||||
{
|
||||
step: "Phase 2",
|
||||
title: "Current",
|
||||
status: "active",
|
||||
items: [
|
||||
"Continued pre-training",
|
||||
"Language expansion",
|
||||
"YUY CLI tool (Rust)",
|
||||
"YUY-Chat TUI interface",
|
||||
],
|
||||
},
|
||||
{
|
||||
step: "Phase 3",
|
||||
title: "Upcoming",
|
||||
status: "planned",
|
||||
items: [
|
||||
"Yuuki v0.1 full release",
|
||||
"Research paper publication",
|
||||
"Native model (from scratch)",
|
||||
"Community model hub",
|
||||
],
|
||||
},
|
||||
]
|
||||
|
||||
return (
|
||||
<section id="stats" className="relative px-6 py-24">
|
||||
<div className="mx-auto max-w-7xl">
|
||||
<div className="mb-16 text-center">
|
||||
<span className="mb-4 inline-block font-mono text-xs uppercase tracking-widest text-sakura">
|
||||
Numbers
|
||||
</span>
|
||||
<h2 className="mb-4 text-3xl font-bold text-foreground md:text-5xl text-balance">
|
||||
Progress is Real
|
||||
</h2>
|
||||
<p className="mx-auto max-w-2xl text-muted-foreground leading-relaxed">
|
||||
Every metric is measurable and reproducible. Trained at zero cost
|
||||
with consistent improvements across checkpoints.
|
||||
</p>
|
||||
</div>
|
||||
|
||||
{/* Stats grid */}
|
||||
<div className="mb-16 grid grid-cols-2 gap-4 md:grid-cols-4">
|
||||
{stats.map((stat) => (
|
||||
<div
|
||||
key={stat.label}
|
||||
className="rounded-xl border border-border bg-card p-5 text-center"
|
||||
>
|
||||
<div className="mb-1 text-2xl font-bold font-mono text-sakura md:text-3xl">
|
||||
{stat.value}
|
||||
</div>
|
||||
<div className="text-sm font-medium text-foreground">{stat.label}</div>
|
||||
<div className="text-xs text-muted-foreground">{stat.sub}</div>
|
||||
</div>
|
||||
))}
|
||||
</div>
|
||||
|
||||
{/* Roadmap / Timeline */}
|
||||
<div className="grid gap-6 md:grid-cols-3">
|
||||
{timeline.map((phase) => (
|
||||
<div
|
||||
key={phase.step}
|
||||
className={`rounded-xl border p-6 ${
|
||||
phase.status === "active"
|
||||
? "border-sakura-border bg-sakura-dim"
|
||||
: "border-border bg-card"
|
||||
}`}
|
||||
>
|
||||
<div className="mb-4 flex items-center gap-3">
|
||||
<span
|
||||
className={`h-2.5 w-2.5 rounded-full ${
|
||||
phase.status === "complete"
|
||||
? "bg-[#22c55e]"
|
||||
: phase.status === "active"
|
||||
? "bg-sakura animate-pulse"
|
||||
: "bg-muted-foreground/30"
|
||||
}`}
|
||||
/>
|
||||
<div>
|
||||
<span className="text-xs font-mono text-muted-foreground">{phase.step}</span>
|
||||
<h3 className="text-lg font-semibold text-foreground">{phase.title}</h3>
|
||||
</div>
|
||||
</div>
|
||||
<ul className="flex flex-col gap-2">
|
||||
{phase.items.map((item) => (
|
||||
<li key={item} className="flex items-start gap-2 text-sm">
|
||||
<span
|
||||
className={`mt-1.5 h-1 w-1 flex-shrink-0 rounded-full ${
|
||||
phase.status === "complete" ? "bg-[#22c55e]" : "bg-muted-foreground/40"
|
||||
}`}
|
||||
/>
|
||||
<span className="text-secondary-foreground">{item}</span>
|
||||
</li>
|
||||
))}
|
||||
</ul>
|
||||
</div>
|
||||
))}
|
||||
</div>
|
||||
|
||||
{/* Why it matters */}
|
||||
<div className="mt-16 rounded-xl border border-border bg-card p-8 md:p-12">
|
||||
<h3 className="mb-6 text-2xl font-bold text-foreground">Why This Matters</h3>
|
||||
<div className="grid gap-6 md:grid-cols-3">
|
||||
<div>
|
||||
<h4 className="mb-2 text-sm font-semibold text-sakura">Accessibility</h4>
|
||||
<p className="text-sm text-muted-foreground leading-relaxed">
|
||||
Students without GPU access can experiment with ML training.
|
||||
No cloud account, no credit card, no barriers.
|
||||
</p>
|
||||
</div>
|
||||
<div>
|
||||
<h4 className="mb-2 text-sm font-semibold text-sakura">Democratization</h4>
|
||||
<p className="text-sm text-muted-foreground leading-relaxed">
|
||||
Proves that meaningful ML research can happen anywhere in the world,
|
||||
with just a phone and determination.
|
||||
</p>
|
||||
</div>
|
||||
<div>
|
||||
<h4 className="mb-2 text-sm font-semibold text-sakura">Edge ML</h4>
|
||||
<p className="text-sm text-muted-foreground leading-relaxed">
|
||||
Explores the limits of what is possible with mobile hardware,
|
||||
pushing edge ML training into new territory.
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
)
|
||||
}
|
||||
Reference in New Issue
Block a user