HNU-TimeLetter (与她的海大时光笺) is an interactive visual narrative website that weaves galgame-style anime characters together with real campus locations at Hainan University (HNU). Visitors move through a scrapbook-meets-private-letter aesthetic — a warm grey paper backdrop, wax-seal red accents, and hand-picked typography — to discover the decisive moments and hidden stories embedded in campus landmarks. Content is authored entirely inside Feishu (Lark) Bitable and delivered to the frontend through a synchronisation pipeline that writes typed JSON artifacts, so editorial teams never touch a line of code.Documentation Index
Fetch the complete documentation index at: https://mintlify.com/HNU-himematsu/HNU-TimeLetter/llms.txt
Use this file to discover all available pages before exploring further.
What Is HNU-TimeLetter?
The project combines three ideas into one cohesive experience:- Galgame visual language — illustrated characters, cinematic scene compositions, and deliberate motion design borrowed from Japanese visual-novel games.
- Campus documentary — real Hainan University locations serve as the stage. Every story is anchored to a map pin, a photograph, and a prose narrative recorded in Feishu Bitable.
- Community creativity — a public Creation Board lets community members (群友) share their own galgame-inspired ideas in a sticky-note waterfall layout.
Application Routes
The site is composed of four routes, each delivering a distinct interaction mode:| Route | Purpose |
|---|---|
/ | Envelope ritual — the opening screen animates an envelope unsealing, then scrolls through About the Project, About Us, Credits, and the Footer as a sequence of full-viewport sections driven by Lenis smooth scroll. |
/map | Interactive campus map — on desktop, an SVG map hosts clickable pins that open story cards; on mobile, the same content renders as a vertically scrolling stamp-collection waterfall. |
/creation | Community creation board — a sticky-note masonry grid of ideas submitted by community members, sourced from a dedicated Feishu table. |
/admin | Admin panel — a password-protected back-office for triggering manual Feishu syncs, inspecting sync logs, and configuring scheduled tasks. |
Technology Stack
Every layer of the stack was chosen to support fluid motion, type safety, and a zero-friction CMS workflow.| Layer | Technology | Version |
|---|---|---|
| Framework | Next.js App Router + Turbopack | 16.2.4 |
| Language | TypeScript (Strict Mode) | 5+ |
| Styling | Tailwind CSS v4 + Radix UI / Shadcn-style components | v4 |
| Animation | Framer Motion — opening screen, transitions, card effects, magnetic buttons, sticky cursor | v12 |
| Smooth Scroll | Lenis — desktop scroll sections with built-in footer snap | 1.3.x |
| Scroll Animation | @waaark/luge — scroll-driven progressive effects (smooth scroll plugin disabled to decouple from Lenis) | 0.6.x |
| State Management | Zustand | v5 |
| CMS | Feishu Bitable (飞书多维表格) | — |
| Object Storage | Aliyun OSS | — |
| Scheduled Tasks | node-schedule — auto-sync from /admin | 2.1.x |
| E2E Testing | Playwright | — |
| React | React 19 | 19.2.3 |
Key Features
Envelope Opening Ritual
The homepage opens with a full-screen envelope animation powered by Framer Motion. After the seal breaks, Lenis smooth-scroll drives users through a curated sequence of full-viewport story sections — About the Project, About Us, Credits, and Footer — each snapping cleanly into place.
Interactive Campus Map
The
/map route renders an interactive campus map on desktop with clickable location pins linked to illustrated story cards. On mobile the identical data renders as a vertical stamp-collection waterfall, ensuring the full story catalogue is accessible on any device without a separate codebase.Community Creation Board
The
/creation route surfaces community-submitted galgame ideas from Feishu as a masonry sticky-note layout. A dedicated Bitable table (FEISHU_CREATION_TABLE_ID) and optional header table (FEISHU_CREATION_HEADER_TABLE_ID) power the board, and content refreshes automatically without a redeploy.Feishu CMS Integration
Feishu Bitable is the single source of truth for all content. The
npm run sync command (which wraps src/scripts/sync-feishu.ts) pulls records, uploads image attachments to Aliyun OSS, and writes three typed JSON files into src/data/. The admin panel exposes a manual sync trigger and a scheduled-task configurator for production environments.Zero-Config Content API
Runtime API routes under
src/app/api/ serve the pre-written JSON files with no-store cache headers, giving the frontend live data without a database query. The client polls these endpoints on a configurable interval, so new content from a Feishu sync appears on-screen without a page reload.Dual Deployment Model
The project supports Vercel Preview deployments (using committed JSON as build-time fallback data) and self-hosted production environments where GitHub Actions executes the full quality gate → sync → build → deploy pipeline on the
release branch. Both models share the same codebase and content API surface.Data Flow Overview
Content travels from Feishu to the browser in three clearly separated stages:The sync step is mandatory. The repository does not ship mock data, so
src/data/*.json files will be absent (or empty) until npm run sync succeeds. See Quickstart for step-by-step instructions./admin) exposes two additional sync mechanisms: a one-click manual sync button (backed by src/app/api/admin/) and a node-schedule cron job that can be configured from the admin UI and persisted in src/config/admin.json.
Architecture Overview
Thesrc/ directory is divided into five top-level concerns:
The root-level
agents/, .opencode/agents/, and .trae/skills/ directories hold collaboration assets for the development workflow. They are excluded from the TypeScript compilation scope in tsconfig.json and play no part in the runtime application.Visual Design Language
The site’s aesthetic is intentionally restrained and paper-like:- Background:
#ece9e4— warm grey, evoking aged paper - Accent:
#c23643— wax-seal red, used for interactive highlights - Heading font:
ChillDINGothic_SemiBold(locally hosted OTF) - Body font:
ZouLDFXKAJ(locally hosted TTF) - Viewport frame: 5 px white border + 16 px border radius wrapping the entire viewport, reinforcing the “private photograph” metaphor