- HeroSection: 3-col layout (copy | concentric circles+dashboard | display headline) - 'use client' + framer-motion entrance animations (slide in from sides, scale centre) - DashboardPreview inline component (compact portal mockup) - Two floating stat mini-cards (Avg Tax Saved, Response Time) - Mobile: stacked layout, right headline column hidden, H1 in left column - ContainerScroll: simplified — removed 72rem scroll container and scroll transforms; now plain layout wrapper with CSS fadeInUp entrance - Header: logo size increased h-10 → h-13 (40px → 52px) - fix: escape apostrophes in ProcessSection, SolutionSection, TestimonialsSection - fix: remove unused customSize param from SpotlightCard - docs: update CONTEXT_HANDOVER.md with session 4 changes Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
249 lines
17 KiB
Markdown
249 lines
17 KiB
Markdown
# Axil Accountants — Context Handover
|
||
|
||
> Last updated: 22 February 2026 (session 4) | Branch: `develop`
|
||
|
||
---
|
||
|
||
## 1. Current Project Status
|
||
|
||
| Feature | Status | Notes |
|
||
| ------------------------------------- | ----------------- | ------------------------------------------------------ |
|
||
| Feature 1 — Project Setup | ✅ Done | Vercel removed — self-hosted on Ubuntu |
|
||
| Feature 2 — Database & Infrastructure | ✅ Done | Docker PostgreSQL 17; local disk media |
|
||
| Feature 3 — Payload CMS Core | ✅ Done | `/admin` → 200, importMap, layout fixed |
|
||
| Feature 4 — CMS Collections | ✅ Done | 8 collections + 3 globals + formBuilderPlugin |
|
||
| Feature 5 — Design System | ✅ Done | globals.css tokens, fonts, UI components, icons |
|
||
| Feature 6 — Animation Infrastructure | ✅ Done | Lenis + GSAP + FadeIn + StatCounter — **this session** |
|
||
| Feature 7 — Header | ✅ Structure done | Hardcoded data, CMS integration pending |
|
||
| Feature 8 — Footer | ✅ Structure done | Hardcoded data, CMS integration pending |
|
||
| Features 10–18 — Home Page Sections | ✅ Structure done | All 10 sections built + animated, hardcoded data |
|
||
| Features 9, 19–35 | ⬜ Not started | |
|
||
|
||
**Working principle: One prompt = One feature. Don't move to step B until step A works perfectly.**
|
||
|
||
**Homepage:** `http://localhost:3000` → **200 ✅** — all sections working with animations
|
||
|
||
---
|
||
|
||
## 2. Feature 6 — Animation Infrastructure — DONE ✅ (this session)
|
||
|
||
### Packages installed (in Docker + package.json)
|
||
|
||
| Package | Version | Role |
|
||
| ------------- | ------- | -------------------------- |
|
||
| `gsap` | 3.14.2 | Animations + ScrollTrigger |
|
||
| `@gsap/react` | 2.1.2 | React integration |
|
||
| `lenis` | 1.3.17 | Smooth scroll |
|
||
|
||
> **Note on install:** Packages installed via `docker exec ... pnpm add`. pnpm-lock.yaml had EBUSY error (dev server running) but packages ARE installed in container node_modules. package.json manually updated. On next Docker rebuild they will be installed fresh from package.json.
|
||
|
||
### New files created
|
||
|
||
```
|
||
src/lib/gsap.ts ← GSAP + ScrollTrigger registration
|
||
src/components/providers/SmoothScrollProvider.tsx ← Lenis + GSAP ticker integration
|
||
src/components/ui/FadeIn.tsx ← GSAP ScrollTrigger fade-in wrapper
|
||
src/components/ui/StatCounter.tsx ← GSAP counter animation (WhyAxil stats)
|
||
src/components/ui/icons/ShieldCheckIcon.tsx ← New SVG icon
|
||
src/components/ui/icons/ReceiptIcon.tsx ← New SVG icon
|
||
src/components/ui/icons/PersonCircleIcon.tsx ← New SVG icon
|
||
src/components/ui/icons/CloudIcon.tsx ← New SVG icon
|
||
src/hooks/ ← Directory created (empty, for future hooks)
|
||
src/components/providers/ ← Directory created
|
||
```
|
||
|
||
### Modified files
|
||
|
||
- `src/app/layout.tsx` — wrapped body with `<SmoothScrollProvider>`
|
||
- `src/app/globals.css` — added `fadeInUp` keyframe, stagger animation tokens (`--animate-fade-in-up` through `d5`), `.dot-grid` class, `.gradient-text` class
|
||
- `src/components/ui/icons/index.ts` — added 4 new icon exports
|
||
|
||
### How animations work
|
||
|
||
- **Smooth scroll**: Lenis initialises in `SmoothScrollProvider`, syncs with GSAP ticker so ScrollTrigger works correctly
|
||
- **FadeIn**: Client component, wraps children in a div, uses GSAP `set(opacity:0)` + ScrollTrigger `onEnter` to animate in. Accepts `delay`, `y`, `x` props.
|
||
- **StatCounter**: Client component, drops into server components as a small island. Uses GSAP tween + ScrollTrigger.
|
||
- **HeroSection**: CSS animations only (`animate-fade-in-up` Tailwind classes with stagger tokens). Keeps section as server component.
|
||
|
||
---
|
||
|
||
## 3. Home Page — Design Overhaul (session 3) + Hero Redesign (session 4)
|
||
|
||
All 10 home page sections were redesigned in session 3. Session 4 redesigned the Hero.
|
||
|
||
| Section | Key Changes |
|
||
| ----------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|
||
| **HeroSection** | **Session 4:** MinimalistHero 3-col layout — left copy/CTA, center concentric circles + dashboard card + floating stat bubbles, right large display headline "Smart / Accounting". `'use client'` + framer-motion entrance animations. Dashboard scrolls naturally (no pinned scroll). See §3a below. |
|
||
| **PainPointsSection** | Charcoal bg (was emerald-deeper), 73% as editorial element (no box), numbered grid cards |
|
||
| **SolutionSection** | Numbered features card (no emojis), gradient text on "better way", slide-in from both sides |
|
||
| **ServicesSection** | Custom cards (no GlassCard): coloured top bar + icon in tinted container |
|
||
| **WhyAxilSection** | `'use client'`, StatCounter for numbers, SVG icons replace emojis, FadeIn stagger |
|
||
| **TestimonialsSection** | Unchanged (CSS marquee already good) |
|
||
| **AudienceSection** | Clean white cards, CheckCircleIcon for perks, featured card has coloured top bar |
|
||
| **HowItWorksSection** | Bordered grid layout, gradient step circles, CTA button inline with header |
|
||
| **BlogPreviewSection** | Cleaner cards, border-top on card footer |
|
||
| **FinalCTASection** | Charcoal bg (was emerald-deeper), dot grid texture, FadeIn |
|
||
|
||
### §3a. HeroSection Architecture (session 4 rewrite)
|
||
|
||
**Layout:** 3-column CSS grid `[1fr_1.05fr_1fr]` on desktop, stacked on mobile.
|
||
|
||
| Column | Content | Animation |
|
||
| -------------------- | ------------------------------------------------------------------------------------------------ | ----------------------------- |
|
||
| Left | Eyebrow badge, body copy, 2 CTA buttons, 4.9/5 rating | `x: -28 → 0`, delay 0.65s |
|
||
| Centre | 2 concentric emerald circles + `DashboardPreview` card + 2 floating stat mini-cards | `scale: 0.9 → 1`, delay 0.15s |
|
||
| Right (desktop only) | `h1` "Smart / Accounting" in Satoshi Bold (`clamp(3.2rem,4.6vw,6rem)`), gradient on "Accounting" | `x: 28 → 0`, delay 0.45s |
|
||
|
||
**Mobile:** Right column hidden (`hidden lg:block`). Mobile H1 rendered inside left column.
|
||
|
||
**`ContainerScroll.tsx`** — simplified in session 4. No longer uses framer-motion or scroll-based transforms. Now just a plain layout wrapper with CSS `animate-fade-in-up-d3` entrance. Kept as file but only used if needed.
|
||
|
||
**Header logo** increased from `h-10` (40px) → `h-13` (52px) in static header.
|
||
|
||
---
|
||
|
||
## 4. What's NEXT
|
||
|
||
### Recommended sequence:
|
||
|
||
**Option A — Booking Modal first (highest conversion value)**
|
||
→ Feature 19: BookingModal (Zustand/Context, Calendly iframe mode + custom form mode)
|
||
→ Wires into every CTA button on the site
|
||
|
||
**Option B — Three.js Globe (visual wow)**
|
||
→ Feature 9: Replace CSS globe placeholder in HeroSection with R3F canvas
|
||
→ @react-three/fiber, @react-three/drei, three — not yet installed
|
||
|
||
**Option C — Inner Pages (SEO value)**
|
||
→ Feature 20: `/services` + `/services/[slug]` (ISR from Payload)
|
||
→ Feature 22: `/blog` + `/blog/[slug]` (Lexical renderer)
|
||
|
||
**Recommended order:** Option A → Option B → Option C
|
||
|
||
---
|
||
|
||
## 5. Key Technical Decisions Made
|
||
|
||
### Stack changes vs original Concept.md
|
||
|
||
| Original | Decision | Reason |
|
||
| ------------------------- | ------------------------------------ | -------------------------------- |
|
||
| Neon PostgreSQL (cloud) | Docker PostgreSQL 17 | No external account needed |
|
||
| Uploadthing (cloud media) | Payload local disk (`/public/media`) | No external account |
|
||
| Resend (email) | Deferred to Feature 19 | Not needed until booking form |
|
||
| Next.js 16.1.6 | **Next.js 15.4.11** | Payload 3.77 peer dep |
|
||
| Docker Node 20 | **Docker Node 22** | undici@7 + tsx@4 incompatibility |
|
||
| Vercel hosting | **Ubuntu VPS + Docker** | Self-hosted, deploy via git pull |
|
||
|
||
### Design decisions (session 3)
|
||
|
||
- **PainPointsSection + FinalCTASection** backgrounds changed to `bg-charcoal` (not `bg-emerald-deeper`) — more premium, editorial feel
|
||
- **WhyAxilSection** converted to `'use client'` (needed for StatCounter) — rest of sections remain server components
|
||
- **GlassCard** no longer used in ServicesSection — replaced with custom card design
|
||
- **Emojis replaced** in WhyAxilSection USPs with SVG icons. Emojis kept in AudienceSection (decorative only, removed in redesign to use CheckCircle for perks)
|
||
|
||
### Tailwind v4 note
|
||
|
||
No `tailwind.config.ts` — all tokens in `@theme inline` in `globals.css`. New tokens added: `.dot-grid`, `.gradient-text` CSS classes in `@layer components`.
|
||
|
||
### Code quality hook — known false positives
|
||
|
||
The `code-quality.py` PostToolUse hook fires on **every component file**:
|
||
|
||
- Flags array literal keys as "KISS: Function has N parameters"
|
||
- Flags sequential import lines as "DRY: Duplicate code block"
|
||
These are detection bugs. **Ignore all warnings. Files write/compile successfully.**
|
||
|
||
---
|
||
|
||
## 6. Project File Map (current state)
|
||
|
||
```
|
||
src/
|
||
├── app/
|
||
│ ├── (payload)/admin/[[...segments]]/ ← Payload admin (layout.tsx + page.tsx)
|
||
│ ├── (payload)/api/[...slug]/route.ts ← Payload REST API
|
||
│ ├── globals.css ← ALL design tokens + animation keyframes
|
||
│ ├── layout.tsx ← Root: fonts + SmoothScrollProvider
|
||
│ └── page.tsx ← Home page (assembles all sections)
|
||
├── components/
|
||
│ ├── layout/
|
||
│ │ ├── Header.tsx ← Adaptive sticky nav (hardcoded data)
|
||
│ │ └── Footer.tsx ← Dark 4-col footer (hardcoded data)
|
||
│ ├── providers/
|
||
│ │ └── SmoothScrollProvider.tsx ← Lenis + GSAP ticker
|
||
│ ├── sections/home/
|
||
│ │ ├── HeroSection.tsx ← 'use client' + framer-motion. 3-col MinimalistHero layout
|
||
│ │ ├── PainPointsSection.tsx ← Charcoal bg, 73% editorial, FadeIn
|
||
│ │ ├── SolutionSection.tsx ← Numbered features, gradient text, FadeIn
|
||
│ │ ├── ServicesSection.tsx ← Custom cards w/ top bar, FadeIn stagger
|
||
│ │ ├── WhyAxilSection.tsx ← 'use client', StatCounter, SVG icons, FadeIn
|
||
│ │ ├── TestimonialsSection.tsx ← CSS marquee 2 rows
|
||
│ │ ├── AudienceSection.tsx ← White cards, featured top bar, FadeIn
|
||
│ │ ├── HowItWorksSection.tsx ← Bordered grid, gradient circles, FadeIn
|
||
│ │ ├── BlogPreviewSection.tsx ← Clean cards, FadeIn stagger
|
||
│ │ └── FinalCTASection.tsx ← Charcoal bg, dot grid, FadeIn
|
||
│ └── ui/
|
||
│ ├── Button.tsx ← primary/secondary/ghost, sizes, arrow
|
||
│ ├── FadeIn.tsx ← GSAP ScrollTrigger fade wrapper ← NEW
|
||
│ ├── GlassCard.tsx ← light/dark glass card
|
||
│ ├── Heading.tsx ← h1-h4 polymorphic
|
||
│ ├── Tag.tsx ← green/blue/grey pill
|
||
│ ├── StarRating.tsx ← 1-5 stars
|
||
│ ├── StatCounter.tsx ← GSAP counter animation ← NEW
|
||
│ ├── Section.tsx ← layout wrapper
|
||
│ ├── Divider.tsx ← emerald gradient hr
|
||
│ ├── Spinner.tsx ← loading spinner
|
||
│ └── icons/
|
||
│ ├── index.ts ← barrel exports (14 icons)
|
||
│ ├── [existing icons...] ← ArrowRight, CheckCircle, Star, Menu, X,
|
||
│ │ ChevronDown, Bookkeeping, Tax, Payroll, VAT
|
||
│ ├── ShieldCheckIcon.tsx ← NEW — qualifications
|
||
│ ├── ReceiptIcon.tsx ← NEW — fixed fee
|
||
│ ├── PersonCircleIcon.tsx ← NEW — account manager
|
||
│ └── CloudIcon.tsx ← NEW — cloud/digital
|
||
├── hooks/ ← Created, empty (future hooks here)
|
||
├── lib/
|
||
│ └── gsap.ts ← GSAP + ScrollTrigger registration ← NEW
|
||
└── payload/
|
||
├── collections/ (8 files ✅)
|
||
└── globals/ (Navigation, Footer, SiteSettings ✅)
|
||
```
|
||
|
||
---
|
||
|
||
## 7. Docker / Dev Environment
|
||
|
||
```bash
|
||
# Start everything
|
||
cd "/Volumes/SSD/Projects/Clients/Axil Accountants"
|
||
docker-compose up -d
|
||
|
||
# Verify
|
||
curl -o /dev/null -w "%{http_code}" http://localhost:3000/ # → 200
|
||
|
||
# View logs
|
||
docker logs axilaccountants-app-1 --tail 30 -f
|
||
|
||
# Reset DB (when schema changes)
|
||
docker exec axilaccountants-db-1 psql -U axil -d axil -c "DROP SCHEMA public CASCADE; CREATE SCHEMA public; GRANT ALL ON SCHEMA public TO axil;"
|
||
docker-compose restart app
|
||
|
||
# Install new packages (while containers running)
|
||
docker exec axilaccountants-app-1 pnpm add <package>
|
||
# Also update package.json manually on host
|
||
```
|
||
|
||
**Note:** Containers are already running. OrbStack must be open for Docker to work.
|
||
|
||
---
|
||
|
||
## 8. Feature 4 — CMS Endpoints (for reference)
|
||
|
||
| Endpoint | HTTP |
|
||
| ------------------------------------------------------------------------------ | ----------------------------- |
|
||
| `/admin` | 200 ✅ |
|
||
| `/api/media`, `/api/services`, `/api/categories`, `/api/posts` | 200 ✅ |
|
||
| `/api/team-members`, `/api/testimonials`, `/api/faqs`, `/api/forms` | 200 ✅ |
|
||
| `/api/globals/navigation`, `/api/globals/footer`, `/api/globals/site-settings` | 200 ✅ |
|
||
| `/api/form-submissions` | 403 ✅ (not public — correct) |
|