# Mobile navigation and Vercel QA for Astro marketing sites

Use this reference when a deployed marketing/company site looks crowded or broken on iPhone/mobile, especially after desktop flyouts were added.

## Durable pattern

1. Treat desktop flyouts and mobile navigation as separate interaction modes.
   - Desktop: hover/focus flyouts may remain appropriate.
   - Mobile/tablet: collapse the primary nav behind a real hamburger button.
2. Add explicit accessibility wiring:
   - `id` on the primary nav.
   - Hamburger `button`, not an anchor/div.
   - `aria-controls` pointing to the nav.
   - `aria-expanded` toggled on open/close.
   - `aria-label` switches between "Menü öffnen" and "Menü schliessen" for German sites.
3. Mobile CSS should hide the nav by default with both visual and interaction guards:
   - `max-height: 0`, `opacity: 0`, `overflow: hidden`, `pointer-events: none`.
   - Open state restores `max-height`, `opacity: 1`, `pointer-events: auto`, and `overflow-y: auto`.
   - Use `max-height: calc(100vh - <header-height>)` and `overscroll-behavior: contain` so long flyout menus remain scrollable on iPhone.
4. Keep submenu behavior inside the hamburger menu:
   - Existing `[data-nav-menu]`/`[data-nav-toggle]` state can be reused.
   - Close submenus when the hamburger closes.
   - Close the whole mobile nav on outside click, Escape, or nav-link click.
5. Prevent header auto-hide while the mobile menu is open.

## Verification recipe

Minimum verification before reporting done:

```bash
npm run build
```

Then run a real mobile-width smoke against local preview or deployed Vercel:

- viewport around `390x844` (iPhone class)
- before click: hamburger visible, nav `max-height: 0`, `opacity: 0`, `pointer-events: none`, `aria-expanded=false`
- after click: nav visible/scrollable, `opacity: 1`, `pointer-events: auto`, `aria-expanded=true`
- open one submenu and confirm it expands inside the mobile menu
- optionally capture a screenshot and visually check that content is readable and not overlapped

For Vercel deployments after pushing to `main`, poll the live page for a deterministic HTML marker introduced by the change before claiming the live site updated. Then repeat the mobile-width smoke against the production URL, not only localhost.

## Pitfalls

- Do not merely stack all desktop nav links on mobile; it becomes visually noisy and touch-hostile.
- Hiding with only `opacity: 0` is insufficient; invisible nav links can still intercept taps unless `pointer-events: none` is also set.
- When measuring computed styles immediately after `click()`, wait briefly for CSS transitions before reading open-state values.
- Do not record package-install quirks from one machine as permanent rules; capture only the verification pattern.
