The Guide

How This Site Was Built

This page documents the actual decisions behind HALCYON, the dark editorial direction of the Nomadic Owls site. No marketing language — just what was chosen, why, and what a reader would need to reproduce it.

Concept & Inspiration

The brief for this direction was “quiet-money, high-fashion editorial” — the idea that a studio confident in its work doesn’t need to shout. The reference point isn’t a typical SaaS landing page; it’s a design annual or a photography monograph: near-black stock, generous margins, one disciplined accent colour, and work presented as numbered “plates” rather than portfolio cards. That last idea became the structural gimmick of the Selected Work section — each client project is Plate I, II, or III, with a duotone image, a roman numeral, and a caption, styled the way a fashion or architecture book would present a spread.

Restraint was treated as a design constraint, not an afterthought: the gold accent (#b08d57) is never used as a fill or a button background — only as 1px hairlines and 0.72rem letter-spaced small-caps labels. If gold shows up anywhere else, that’s a bug, not a variation.

Typography & Colour

Display type is Fraunces, used at its italic and optical-size variants for pull-quotes (the manifesto line and the four belief statements) — Fraunces was built for exactly this: it has a soft, wet-ink italic that reads as considered rather than decorative. Body copy is Work Sans at a light weight (300–400), chosen for its neutrality: it needed to disappear next to Fraunces, not compete with it. Both are self-hosted via @fontsource/fraunces and @fontsource/work-sans rather than loaded from Google Fonts at runtime — one less third-party request, no render blocking on an external origin, and it works if a build ever needs to run somewhere offline.

Colour is three values on purpose: background #0b0b0a, ink #f2ede4, accent #b08d57. Cream on near-black measures at roughly 16.9:1 contrast — comfortably past WCAG AA (4.5:1) and AAA (7:1) for body text, which matters more here than usual because the whole design leans on long-form reading (the manifesto, the beliefs, this page).

The Reveal Technique

Two distinct mechanisms are in play, deliberately not unified into one library-driven system:

Every section (pillars, disciplines, plates, beliefs, contact) uses a plain IntersectionObserver. Elements start with opacity: 0 and translateY(12px) in CSS; when an element crosses 15% into the viewport, JS adds .is-visible, which triggers a CSS transition back to rest. Stagger comes from an inline --i custom property read by a CSS transition-delay: calc(var(--i) * 0.09s) rule — no animation library needed for the vast majority of the page.

The hero gets special treatment because the brief called for two specific hero-only beats: the headline splits into one <span> per letter and animates in with GSAP (opacity, a few pixels of Y, and letter-spacing easing from 0.06em to 0) on load, and the hero image drifts via GSAP ScrollTrigger (yPercent: 14, scrubbed against hero scroll progress) for the parallax. GSAP is imported dynamically (await import('gsap')) only inside that hero-init function, so the ~30kb of GSAP core plus ScrollTrigger never loads on a reduced-motion visit or blocks anything else on the page. Everything motion-related checks prefers-reduced-motion first and short-circuits to the final, settled state if it's set.

The Imagery

Three images were generated with gpt_image_2 (via the Higgsfield CLI), all in the same photographic language so they'd read consistently once treated:

  1. Hero portrait (3:4) — “a majestic owl portrait, dramatic single-source studio lighting, deep shadow, high contrast black and white photography, sharp focus on eyes, minimal background”. Used full-bleed behind the hero headline and again, cropped, as Plate I.
  2. Feather macro (16:9) — “extreme macro close-up of owl feather texture, soft directional light, monochrome, fine detail”. Used as the full-bleed section divider between the pillars and the disciplines grid, and again as Plate III.
  3. Wing in flight (3:4) — “owl wing extended mid-flight, motion blur at wingtip, dramatic side lighting, monochrome high contrast photography, dark background”. Used as Plate II.

All three run through Astro's built-in <Image /> component (astro:assets, sharp-backed) at build time, which emits responsive .webp variants at the specific widths each placement needs rather than shipping one oversized source file everywhere. The duotone look (near-black shadows, warm-gold midtones) is a CSS treatment — grayscale(1) contrast(1.15) brightness(0.92) on the <img>, plus a mix-blend-mode: color gradient overlay — rather than being baked into the source PNG. That keeps the three source images reusable and means the exact tone can still be tuned in one place (global.css) without regenerating anything.

Two Honest Tradeoffs

1. The plates aren't literal project screenshots. The three real client projects (Rentsy, a rental aggregator; Bali Destination Wedding, a wedding reseller platform; Non La Vietnam Tours, a tour operator site) don't have production screenshots available as content assets for this brief. Rather than fabricate fake interface mockups, the Selected Work plates reuse the same three owl photographs as a consistent editorial motif — a legitimate convention in photography-book design, but it does mean the three plates aren't visually distinct from one another beyond the crop. A production version of this site would swap in real project photography per plate.

2. GSAP is a real dependency for a small amount of the page. It's dynamically imported and scoped to the hero only, but it's still a second animation system alongside the IntersectionObserver path used everywhere else. The alternative — doing the letter stagger and scroll-scrubbed parallax in hand-rolled JS or pure CSS scroll-timelines — was considered and rejected: CSS scroll-timelines aren't reliably supported across browsers yet, and hand-rolling scrub-linked transforms duplicates what ScrollTrigger already does correctly. The cost is accepted as worth it for the two moments the brief specifically called for, not used as a general-purpose animation crutch.