Closer/ClaudeBrandingReview.md

336 lines
28 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# Closer — Branding & Artwork Review (Pass H)
Living status document for Closer's brand artwork pass. It records which illustrations/glyphs are live, which surfaces
should reuse existing assets, and which brand issues belong in implementation or QA rather than image generation.
**Asset ownership:** Codex is responsible for making all needed images, dark variants, and custom glyphs. Do not leave
image work as user-generated prompt handoff; backlog items here are Codex-owned assets to generate, add to the repo, and
verify.
**Current state (2026-06-28 re-audit against the code/resources — supersedes the 2026-06-27 audit):**
- **Backlog 1 (dark illustration variants) — essentially DONE.** `drawable-night-nodpi/` now holds a dark variant for
**every** non-transparent surface: all 22 `illustration_*` (incl. all `illustration_couple_*` heroes, `daily_question`,
`partner_activation`, `tonight_partner_prompt`, `together_empty`) **and all 10 `pack_art_*` banners**. Only **3**
transparent celebration assets have no dark variant — `illustration_premium_unlock`, `illustration_spin_wheel`,
`illustration_streak_milestone` — which rule 1 exempts *if* they read on both themes (verify, don't assume). Decoupled
in-app-Dark + system-Light now renders the dark art correctly app-wide after the **C-DARKART-002** fix (see below), so
the "light/pink art on a dark screen" defect class is closed for these surfaces.
- **Backlog 2 (custom glyphs) — ✅ DONE (2026-06-28).** Every generic Material icon has been replaced with a Closer
glyph: **0 `Icons.*` call sites and 0 `androidx.compose.material.icons` imports remain** (was 187 across ~49 distinct
icons). Wiring goes through a central `ui/components/CloserGlyphs.kt` accessor object (`@Composable` getter vals →
`ImageVector.vectorResource(R.drawable.glyph_*)`), used by 53 files; `CategoryGlyph.kt` resolves category glyphs the
same way. Build + 205 unit tests green; verified live both themes (back, check, close, lock, chat, heart, photo,
camera, mic, category badges all render with correct tint). **BRAND-ICON-CUSTOM is resolved.**
- **C-DARKART-002 (theming mechanism, fixed 2026-06-28):** `MainActivity` now drives `AppCompatDelegate.setDefaultNightMode`
from the in-app `ThemeMode`, so the real Configuration `uiMode` follows the app theme and **all** art resolution —
`painterResource` AND `BrandIllustration`, `drawable-night*` included — follows the in-app theme. This supersedes the
old "only `BrandIllustration` follows the theme" caveat.
- Done earlier: This-or-That redesign (C-DARK-UI-001) + Premium-unlock modal (A13).
> Branding **defects** (off-brand color, clipped/low-contrast art, a **light image on a dark screen**, a **generic
> Material icon**) → `ClaudeReport.md`. Pure "could be warmer / feature" ideas → `Future.md` `## QA`. **New art/glyphs to
> create** (dark variants, custom glyphs) → logged HERE as Codex-owned assets to make and verify.
---
## Brand standards — MUST hold every QA round (Pass C visual + Pass H branding own these)
Two non-negotiable brand rules. A violation of either is a **bug** (`ClaudeReport.md`) **and** the asset to create is
logged here as Codex-owned image/glyph work:
1. **Every image has a LIGHT and a DARK variant that matches the IN-APP theme.** No light/pink art on a dark screen, no
dark art on a light screen. `drawable-nodpi/` = light, `drawable-night-nodpi/` = dark. Since **C-DARKART-002**
(2026-06-28) the dark variant is auto-selected by the real Configuration `uiMode`, which `MainActivity` syncs to the
in-app `ThemeMode` via `AppCompatDelegate.setDefaultNightMode` — so **both** `painterResource` and `BrandIllustration`
resolve `-night` correctly even in the decoupled in-app-Dark + system-Light state. Transparent/celebration art that
genuinely reads on **both** themes is the only exemption — **verify it, don't assume.** A surface missing its variant = bug.
2. **Every icon/glyph is a custom Closer glyph — NO generic Material icons, no generic hearts.** Material `Icons.*`
(ArrowBack, Favorite, Person, Lock, Star, PlayArrow, …) are placeholders, not brand. Each in use is replaced by a
bespoke glyph in the Closer house style, logged in the icon backlog below for Codex to make + add (`glyph_*`).
**Image style lock:** all generated imagery must match the existing shipped flat 2D vector assets, especially
`illustration_couple_paywall`, `illustration_couple_subscription`, `illustration_couple_onboarding`,
`illustration_daily_question`, and the `pack_art_*` banners. Keep shapes simple and graphic, with pastel fills, minimal
facial/detail rendering, clean vector-like edges, and gentle gradients only. **Reject** painterly/storybook rendering,
3D-ish lighting, realistic texture, detailed hair/skin shading, dramatic cinematic glow, hard rectangular backdrops, or
anything that looks materially richer than the existing asset family. For any new batch, generate and review **one sample
first** against the existing contact sheet before saving more assets.
## Image theme-variant coverage (light + dark per surface) — ✅ essentially COMPLETE
> Re-verified against `res/` on 2026-06-28. Every non-transparent surface now has BOTH a light (`drawable-nodpi/`) and a
> dark (`drawable-night-nodpi/`) asset with the identical filename.
| Illustration | Light | Dark | Status |
|---|---|---|---|
| **All 22 `illustration_*`** — account_deletion_goodbye · answer_history_empty · bucket_list_empty · connection_challenges_header · couple_history · couple_invite · couple_onboarding · couple_paywall · couple_subscription · daily_question · date_match_empty · date_match_success · memory_lane_capsule · messages_empty · pairing_success · partner_activation · privacy_recovery · quiet_hours · reveal_celebration · together_empty · tonight_partner_prompt | ✅ | ✅ | **both exist** — dark variants added since the 2026-06-27 audit |
| **All 10 `pack_art_*`** (communication, deep_reflection, desire, family_commitment, fun_date, future_goals, home_life, intimacy, money_values, trust_repair) | ✅ | ✅ | **both exist**; pack banners verified live dark (C-DARKART-002 round) |
| illustration_premium_unlock · illustration_spin_wheel · illustration_streak_milestone | ✅ (transparent) | — | transparent/celebration — **exempt per rule 1 IF they read on both themes; verify** (only remaining "no dark" assets) |
**Remaining (small):** spot-check the freshly-added dark variants in Pass C (light + dark) for contrast/clipping — they
exist + resolve correctly via the C-DARKART-002 uiMode-sync (pack art + Today hero verified live across all 4 theme/art
states); the rest resolve by the same mechanism but haven't each been eyeballed. Then verify the 3 transparent celebration
assets read on dark; add a dark variant only if one doesn't. **Orphan:** `illustration_couple_history` has both
light+dark variants but **no code reference at all** (superseded by `illustration_answer_history_empty`) — dead asset,
removal candidate. **Debug-only now:** `illustration_quiet_hours` was removed from the Notification-settings UI
(2026-06-28, unprofessional mid-list art) and is now referenced **only** in the debug `ArtPreviewScreen` gallery.
> **⛔ CLAUDE — decoupled-theme art now works app-wide** (C-DARKART-002): raw `painterResource(R.drawable.illustration_*`/
> `pack_art_*)` follows the in-app theme via the Configuration `uiMode` sync, so it no longer *needs* `BrandIllustration`
> to get the right `-night` variant. `scripts/painter-xml-scan.sh` (crash guard) + Pass C's decoupled check (system-light +
> in-app-Dark) remain the per-round guards.
## Icon/glyph audit — ✅ COMPLETE (every Material icon is now a Closer glyph)
> Done 2026-06-28: all 187 `Icons.*` call sites (~49 distinct icons) were swapped to `glyph_*` via the central
> `CloserGlyphs` accessor; **0 `Icons.*` and 0 `androidx.compose.material.icons` imports remain.** The table below is kept
> for the historical mapping (Material icon → glyph) and as the reference for any *new* icon added later: never introduce a
> raw `Icons.*` — add a `CloserGlyphs` accessor + `glyph_*.xml` instead. A `scripts/` guard that fails on any `Icons.`
> call site would keep this at zero (recommended).
| Generic icon (≈remaining uses) | Used for | Wire to `glyph_*` (✅ asset exists) |
|---|---|---|
| `ArrowBack` (31) | every top-bar back | `glyph_back` (brand chevron) |
| `Favorite` / `FavoriteBorder` (17/5) | **generic hearts** — likes, love, daily | `glyph_heart` (the Closer two-equal-halves heart, filled + outline) |
| `Lock` / `LockOpen` (18/2) | premium-locked, security | `glyph_lock` / `glyph_lock_open` (keyhole motif from the mark) |
| `Person` / `People` (16/1) | avatars/partner fallback | `glyph_person` / `glyph_couple` |
| `Check` / `Done` / `CheckCircle` (11/1/1) | confirm/selected/sent | `glyph_check` |
| `ArrowForward` / `ArrowForwardIos` (10/4) | row chevrons, next | `glyph_forward` |
| `PlayArrow` (8) | Play tab / start | `glyph_play` |
| `Close` (7) | dismiss/close | `glyph_close` |
| `Star` (6) | premium/★ ideas | `glyph_star` (brand sparkle) |
| `Visibility` / `VisibilityOff` (5/2) | password reveal | `glyph_eye` / `glyph_eye_off` |
| `ContentCopy` (4) | copy invite code | `glyph_copy` |
| `Sync` (3) · `Image`/`PhotoLibrary`/`PhotoCamera`/`AddAPhoto` (3/2/2/2) · `Send` (3) · `Chat` (3) · `Delete` (3) | retry · media pickers · send · messages · delete | `glyph_sync` · `glyph_photo`/`glyph_camera` · `glyph_send` · `glyph_chat` · `glyph_trash` |
| `Home` (2) · `Settings` (1) · `Notifications`/`NotificationsNone` (2) | bottom nav + settings | `glyph_home` · `glyph_settings` · `glyph_bell` |
| `LocalFireDepartment` (2) | **streak flame** (generic) | `glyph_streak` (brand flame/spark) |
| `Mic`/`Pause` · `Timeline`/`TrendingUp`/`Psychology` · `Fingerprint`/`Key`/`Shield` · `Edit`/`Add`/`Share`/`Refresh`/`Warning`/`CalendarToday`/`Cake`/`CardGiftcard`/`AttachMoney`/`HourglassEmpty`/`QuestionAnswer`/`Palette`/`OpenInNew` (1 each) | voice · progress · security · misc | one bespoke `glyph_*` each, in house style |
Replace each `Icons.*` call site with `ImageVector.vectorResource(R.drawable.glyph_*)` + `Icon(tint=…)` (the existing
wiring pattern — see any wired glyph for the idiom). The glyphs now all exist, so a remaining `Icons.*` call site is an
**unfinished wiring = a logged brand defect**, not acceptable for ship. A `scripts/` scanner that greps `Icons\.` call
sites (excluding files that already wire the matching glyph) would make this measurable per round — currently ~196 remain.
---
## R10 brand walk (2026-06-26) — existing art integration clean, 0 defects
R10 visual sweep doubled as the Pass-H existing-art integration check: Today (paired-books daily-question art),
Paywall (couple illustration), Security (padlock), Memory Lane / Date / Bucket-List empties, Home cards — **all render
on-brand, in-context, both themes, no clipping/placeholder/off-brand issues** (any defect would be a `ClaudeReport.md`
bug; none found). The new game-alert surfaces (`GamePromptBanner`, `GameWaitingHeroCard`) use the brand purple gradient
+ PlayArrow glyph and read as intentional action banners, so no illustration is warranted there.
## This or That gameplay brand plan (Codex QA, 2026-06-27) — ✅ IMPLEMENTED + verified live R13 (2026-06-27)
> **Done (R13, working tree).** `ThisOrThatScreen.kt` `ChoicePromptBackdrop` replaced: the two-circle + diagonal-line
> "diagram" is gone — now a soft theme-aware glow + two faint paired-card silhouettes low in the frame, never crossing
> the prompt. `OptionCard` A/B map to `colorScheme.primary`/`secondary` with high-contrast `onSurface` body text, visible
> accent borders, and a rich filled selected state (`onPrimary`/`onSecondary`). `VersusBadge`, progress bar, the
> `N/total` + "This or That" pills, the mood number-circle, and `TotLengthChips` are all theme-aware (no fixed
> `CloserPalette` darks). Light/dark previews added. Verified live both themes (5554 dark / 5556 light), 0 FATAL — closes
> C-DARK-UI-001. Results screen left as-is (verified clean in R12 dark). The plan below is retained for history.
Live review used a dedicated QA launcher/device (`CloserCodexQA`) with a fresh admin-created test couple
(`codex-this-or-that-*` / `codex-partner-*`). Screenshots checked the mood picker and active gameplay in light and dark
mode. The visual issue is real: light-mode option buttons are directionally good, but dark mode makes the current prompt
backdrop feel like an accidental placeholder.
**Verdict:** The current `ChoicePromptBackdrop` two-circle + diagonal-line drawing should be treated as a branding defect
for active gameplay. In dark mode the diagonal line cuts through the question, the circles turn muddy, and the whole
motif reads like a technical diagram instead of a warm private ritual for two.
**Plan**
- Replace the two circles + line with a Closer-native "private choice" motif: two soft sealed answer cards, paired-card
silhouettes, or a subtle C-heart/keyhole accent. Keep it decorative and low-contrast behind the prompt; no line should
cross the question text.
- Keep the light-mode option card shape, spacing, and button feel. Make the colors theme-aware rather than reusing fixed
purple/pink values in both themes.
- Dark-mode option cards need stronger contrast: readable body text, visible borders, and selected states that feel rich
instead of dim. Disabled/other-selected states should still be legible.
- Keep `closerBackgroundBrush()` as the foundation, but consider one very subtle game-local glow or paired-card vignette
in brand colors. The background should support focus, not compete with the question or options.
- Re-check the mood picker after gameplay is fixed. The numbered mood circles are acceptable, but paired-card glyphs or
warmer step badges would feel more branded than plain numbered bubbles.
- Results can reuse `illustration_reveal_celebration` and existing heart/petal particles for high-match moments; the game
surface itself should stay code-native rather than needing a full raster illustration.
**Implementation map**
- Update `app/src/main/java/app/closer/ui/thisorthat/ThisOrThatScreen.kt`, especially `ChoicePromptBackdrop`,
`OptionCard`, and `VersusBadge`.
- Add local theme-aware helpers for This-or-That option A/B colors, selected colors, disabled colors, border colors, and
prompt-backdrop alphas. Validate against both `MaterialTheme.colorScheme.background` and `surface`.
- Prefer Compose `Canvas`/shape drawing for the prompt motif. Generate raster art only if the code-native motif cannot
carry the brand; if generated, use transparent PNG art with no readable text.
- Add or update light/dark Compose previews for mood selection, active prompt, selected answer, waiting/disabled, and
results.
**Acceptance checks**
- Light and dark screenshots show no decorative element crossing or competing with the prompt text.
- Long prompts, long options, selected, unselected, and disabled states stay readable.
- The light-mode cards retain the current friendly button feel.
- Dark mode feels intentionally Closer-branded: aubergine/lavender/pink, soft and private, not a placeholder diagram.
- Logs are checked after opening a game from notification/deep link before assuming the route worked.
## Generated Art Live
The generated art (source in gitignored `docs/brand/generated-art/`, copied full-res to
`app/src/main/res/drawable-nodpi/`) is now wired into the app via the shared `EmptyState`
(rounded-tile, theme-safe) and a new `ui/components/BrandIllustration.kt` helper:
| Art | Screen wired | Verified |
|---|---|---|
| A1 `pairing_success` (transparent) | PairingSuccessScreen hero (replaced the keyhole chip; pulse/spring kept) | gallery (transparent floats) |
| A2 `answer_history_empty` | AnswerHistoryScreen empty (replaced generic couple_history) | shared EmptyState (Run-2 both-theme) |
| A3 `connection_challenges_header` (banner) | ConnectionChallengesScreen series-list header | gallery (16:9 banner) |
| A4 `memory_lane_capsule` | MemoryLaneScreen empty (replaced 📦 emoji) | shared tile |
| A5 `date_match_empty` / `date_match_success` | DateMatchesScreen empty / "It is a match!" modal | shared tile / gallery |
| A6 `bucket_list_empty` | BucketListScreen empty | **live dark + light** |
| A8 `messages_empty` | MessagesInboxScreen (new empty state added) | shared EmptyState |
| A9 `quiet_hours` | ~~NotificationSettings quiet-hours section~~ **REMOVED 2026-06-28** (out-of-place mid-list illustration → cleaner standalone toggle); asset now in debug Art-preview gallery only | n/a |
| A10 `past_games_empty` | WheelHistoryScreen ("Past Games") empty | shared tile |
| A11 `privacy_recovery` | SecurityScreen header | **live dark** |
| A12 `account_deletion_goodbye` | DeleteAccountScreen header | **live dark** |
| A13 `premium_unlock` (transparent) | **✅ Wired R13** — one-time Premium unlock modal (`PremiumUnlockOverlay`) | **live both themes** |
All 12 also live in the debug **Art preview** gallery (Settings → Art preview) for both-theme verification. A7 pack art is
**N/A** because all 10 question packs already have `pack_art_*`.
A1-A12 prompts are complete and should not be regenerated. Empty/match/pairing states that need empty-or-new data were
not all reachable on the baseline couple, but their render path is proven through the shared tile + gallery.
**Premium unlock modal — ✅ IMPLEMENTED + verified live R13 (2026-06-27).** `ui/components/PremiumUnlockOverlay.kt`
(`PremiumUnlockViewModel` + `PremiumUnlockOverlay`), hosted at the `AppNavigation` root next to `MessageBubbleOverlay`,
so it surfaces over any screen. It's driven off `CouplePremiumChecker.isPremium()` (which already OR-combines both
partners) — so it fires for **both** the purchaser (own entitlement active) **and** the partner (couple-shared Premium
turns on), without depending on the push route. One-time per activation via a new persisted `premiumUnlockCelebrated`
flag on `SettingsRepository`/`SettingsDataStore` (set on dismiss; auto-reset when Premium lapses so a re-activation
celebrates again — mirrors `lastCelebratedStreakMilestone`). The modal shows `illustration_premium_unlock` (transparent,
floats via `BrandIllustration(tile=false)`) + "Premium unlocked ✨" + "Start exploring". **Verified live:** admin toggle
QA premium ON → modal on BOTH 5554 (dark) and 5556 (light); dismiss → relaunch → no re-show (gate holds); 0 FATAL.
## Glyph Status
**~63 `glyph_*.xml` now exist** in `app/src/main/res/drawable-nodpi/` — the original G/G2 set PLUS the full Material-icon
replacement set (back, heart, heart_outline, lock, lock_open, person, couple, check, forward, play, close, star, eye,
eye_off, copy, sync, photo, camera, send, chat, trash, home, settings, bell, streak, mic, pause, timeline, trending_up,
psychology, fingerprint, key, shield, edit, add, share, refresh, warning, calendar, cake, card_giftcard, attach_money,
hourglass, question_answer, palette, open_in_new, …). Source SVGs: `docs/brand/generated-art/glyphs/source-svg/`;
Android vectors: `docs/brand/generated-art/glyphs/android-vector/`.
**Wired in code (23 distinct, verified 2026-06-28):** `paired_cards`, `how_well`, `sealed_answer`,
`connection_challenge`, `memory_capsule`, `date_card_heart`, `question_packs`, `bucket_list`, `past_games`, `spin_wheel`
(Play-hub cards + WaitingForPartner); `couple_premium`, `privacy_lock`, `delete_account`, `settings` (Settings); plus
`couple`, `daily_card`, `forward`, `home`, `lock`, `play`, `streak`, `chat`, `closer_heart_keyhole`.
**Created but NOT yet wired (~40):** every glyph in the icon-audit table whose Material equivalent still appears in code —
`back` (vs ArrowBack ×31), `heart`/`heart_outline` (vs Favorite ×12/×5), `person` (vs Person ×16), `check` (×11),
`close` (×7), `star` (×6), `eye`/`eye_off` (×5/×2), `copy` (×4), `send` (×3), `sync` (×3), `photo`/`camera`, `trash` (×3),
`bell`, `mic`, `pause`, `timeline`, `trending_up`, `psychology`, `fingerprint`, `key`, `shield`, `edit`, `add`, `share`,
`refresh`, `warning`, `calendar`, `cake`, `card_giftcard`, `attach_money`, `hourglass`, `question_answer`, `palette`,
`open_in_new`, `quiet_hours_moon`, `export_data`, `closer_mark`. **This is the open work** — see the icon-audit table.
White monochrome vectors are re-tinted by `Icon(tint = ...)` and loaded via `ImageVector.vectorResource(...)`.
---
## Prompt Style Reference
Use this only when a future pass creates a new prompt. Existing completed art should not be regenerated.
> Flat 2D pastel vector **illustration** in the "Closer" couples-app style: soft rounded shapes, **no harsh outlines**,
> gentle smooth gradients, calm and intimate. **Palette only:** aubergine `#24122F`, deep purple `#56306F`, lavender
> `#B98AF4`, soft pink `#F7C8E4`, soft lavender `#D9B8FF`, blush white `#FFF8FC`. Mood: **warm, quiet, equal,
> intentional — a private ritual for two.** Recurring motifs available: paired/sealed cards, floating hearts and
> petals, a small wooden table with mugs + a lit candle + a lavender sprig, moon/window for quiet hours, a
> calendar/date-card, a sealed capsule/box. If people appear: **two balanced, inclusive figures, simple friendly
> faces, no dominant partner.** Soft abstract floral/heart shapes in the background.
> **Do NOT include:** any readable text, answer/prompt/message content, invite codes, emails, app UI/buttons, generic
> dating-app clichés, stock-photo realism, other brands' logos/wordmarks/app-store badges,
> alarm/urgency/surveillance/fire imagery.
> **The Closer brand mark** (use ONLY where a prompt explicitly calls for it — otherwise keep art mark-free): a
> pink-to-lavender **"C"** whose upper arc is soft pink and lower sweep is lavender, curving around a **heart-shaped
> negative space** with a small **dark aubergine keyhole** at its center (the keyhole = trust/privacy; the heart =
> the couple). Keep it faithful — do not redraw it as a plain `C`, turn the keyhole into a heart, add a key/lock
> shackle, add faces or text. On dark/aubergine surfaces use a white keyhole; on light/blush use the aubergine keyhole.
**Aspect/format conventions**
- Hero/onboarding/paywall: portrait **4:5** (matches `illustration_couple_*`).
- Empty states: roughly **square 1:1**, generous padding, sits centered above text.
- Celebration: **1:1**, transparent or blush-white background.
- Glyphs: **single-color** simple vector, square, legible at 2032 dp.
- Pack/category art: **landscape ~16:9** banner, object-led (no people), like `pack_art_*`.
- Always readable on **both** blush-white (light) and aubergine (dark) surfaces — keep a soft self-contained vignette
rather than a hard rectangular background; export PNG with transparency where noted.
**Existing assets (reuse before generating):** the generated A1-A12 illustration set above, `illustration_couple_*`,
`illustration_daily_question`, `illustration_tonight_partner_prompt`, `illustration_partner_activation`,
`illustration_reveal_celebration`, `illustration_streak_milestone`, `illustration_together_empty`,
`illustration_premium_unlock`, all 10 `pack_art_*` assets, `particle_heart`, and `particle_petal`. These are Android
assets now; only generate new art when a future QA pass finds a specific missing surface or replacement-worthy defect.
---
## Screen-By-Screen Audit
Legend: ✅ on-brand / no art needed · reuse/wire existing art · 🔤 brand-copy/color/code touch
| Screen / surface | Current brand state | Opportunity |
|---|---|---|
| Onboarding carousel | ✅ couple art + warm copy | ✅ strong already |
| Welcome (Create / I have account) | heart mark + privacy line | ✅ on-brand; could rotate privacy messages 🔤 |
| Sign up / Login / Forgot password | plain form | 🔤 add small heart mark + one privacy line above the form (no big art — keep forms clean) |
| Create profile — name / sex / photo | plain steps | 🔤 light: small step glyphs; ✅ otherwise (forms stay clean) |
| Pair: invite (create code) | `illustration_couple_invite` wired | ✅ |
| Pair: accept code / pairing success | `illustration_pairing_success` wired | ✅ |
| Home (paired) | cards, warm copy | ✅ good |
| Home (unpaired "bring your person in") | couple art present | ✅ on-brand |
| Today / daily question | clean card | ✅; reveal moment is the place for art (below) |
| Answer reveal (mutual) | `illustration_reveal_celebration` wired | ✅ |
| Answer history | `illustration_answer_history_empty` wired | ✅ |
| Play hub | game glyphs wired | ✅ |
| This or That (setup/play) | light buttons good; dark prompt backdrop off-brand | 🔤 replace two-circle/line motif + theme option colors |
| This or That / How Well / Desire Sync **results** | score + rows | reuse `reveal_celebration`; particles on high match |
| How Well / Desire Sync intro | icon + copy | ✅ |
| Spin the Wheel | nice wheel art | ✅ wheel is on-brand |
| Wheel complete / results | text reveal | celebration header (reuse particles) |
| Connection Challenges (series list) | `illustration_connection_challenges_header` wired | ✅ |
| Connection Challenges (active day) | clean | 🔤 small streak/heart glyph; ✅ otherwise |
| Memory Lane (list) | `illustration_memory_lane_capsule` empty state wired | ✅ |
| Memory Lane (sealed capsule) | lock + date | optional: reuse capsule art on sealed-card detail, no new art |
| Date Match (deck) | clean cards | ✅ |
| Date Match (your matches / empty) | empty + success art wired | ✅ |
| Plan Date / Date Builder | form | 🔤 small date-card glyph; ✅ otherwise |
| Bucket List (empty) | `illustration_bucket_list_empty` wired | ✅ |
| Question Packs (library) | all 10 `pack_art_*` assets present | ✅ |
| Messages (inbox empty) | `illustration_messages_empty` wired | ✅ |
| Conversation | chat | ✅ keep clean; quiet-hours art is in settings |
| Past Games (empty/list) | `illustration_past_games_empty` wired | ✅ |
| Your Progress / Activity | stats | 🔤 brand-colored charts; reuse `streak_milestone` for milestones |
| Paywall / Subscription | couple art present | ✅ strong (couple illustration + “one subscription for both”) |
| Premium unlock modal | `illustration_premium_unlock` wired in `PremiumUnlockOverlay` (R13) | ✅ one-time modal for purchaser + partner; verified live both themes |
| WaitingForPartner | per-game glyphs + copy | ✅ |
| Settings + sub-pages | dense lists | ✅ keep clean — **no illustrations**; brand via section headers/color only 🔤 |
| Security / Recovery phrase | `illustration_privacy_recovery` wired | ✅ |
| Privacy & Terms | settings row uses `glyph_privacy_lock` | ✅; page can stay text-first |
| Delete account | `illustration_account_deletion_goodbye` wired | ✅ |
| Quiet hours (settings) | illustration REMOVED 2026-06-28 (looked unprofessional mid-list) — now a clean standalone toggle | ✅ matches "Settings stays clean — no illustrations" |
| Notifications (system) | `ic_notification_closer` used | ✅ no glyph swap needed |
---
## Generation Backlog
**Status (2026-06-28 re-audit) — the asset-generation backlogs are essentially DONE; the remaining work is CODE:**
1. **Dark illustration variants — ✅ DONE.** `drawable-night-nodpi/` has a dark variant for every non-transparent
surface (all 22 `illustration_*` + all 10 `pack_art_*`). Remaining: verify the 3 transparent celebration assets
(`premium_unlock`, `spin_wheel`, `streak_milestone`) read on dark, and Pass-C spot-check the new variants.
2. **Custom glyphs — ✅ DONE.** Assets created AND wired: all 187 `Icons.*` call sites swapped to `glyph_*` via the
central `CloserGlyphs` accessor; 0 Material icons / 0 material-icon imports remain. BRAND-ICON-CUSTOM resolved.
Do not regenerate **completed** illustration/glyph art unless a QA pass logs a specific defect.
---
## Notes for the asset hand-off
- Match filenames to the existing scheme: `illustration_<name>.png` (nodpi), `pack_art_<pack>.png`, `glyph_<name>.xml`,
`particle_<name>.png`. Provide @1x in `drawable-nodpi/` (illustrations) or density buckets where the existing asset has them.
- For the generated G-set, use the source SVGs in `docs/brand/generated-art/glyphs/source-svg/` for review and the
Android-ready vectors in `docs/brand/generated-art/glyphs/android-vector/` for app wiring.
- After adding art, re-run Pass C (visual, light + dark) on those screens to confirm contrast + no clipping, and
re-export store graphics per `docs/brand/visual-identity.md` if the palette/mark changed.