Global: Standardize collapsible controls with neutral chevrons #48

Closed
opened 2026-06-27 15:41:16 +02:00 by bullitt · 1 comment
Owner

Problem

Collapsible sections use two different UI patterns:

Pattern A — ChevronDown icon rotating (Dashboard: Delivered/Archived sections, Parsers: field map):

<ChevronDown className={cn("h-4 w-4 transition-transform", open && "rotate-180")} />

Pattern B — Plain text toggle (ShipmentDetail: Scrape Log):

<span className="text-xs text-muted-foreground">{scrapeLogOpen ? "Hide" : "Show"}</span>

Pattern B appears in ShipmentDetail.tsx line ~566 for the Scrape Log card header. It looks like a text link and is visually inconsistent with every other collapsible in the app.

Implementation

File: frontend/src/pages/ShipmentDetail.tsx — Scrape Log card header around line 565.

Change:

<button
  onClick={() => setScrapeLogOpen(!scrapeLogOpen)}
  className="flex items-center justify-between w-full text-left"
>
  <CardTitle className="text-sm text-muted-foreground font-medium">Scrape Log</CardTitle>
  <span className="text-xs text-muted-foreground">{scrapeLogOpen ? "Hide" : "Show"}</span>
</button>

To:

<button
  onClick={() => setScrapeLogOpen(!scrapeLogOpen)}
  className="flex items-center gap-2 text-sm font-medium text-muted-foreground hover:text-foreground transition-colors"
>
  <ChevronDown className={cn("h-4 w-4 transition-transform", scrapeLogOpen && "rotate-180")} />
  Scrape Log
</button>

Import ChevronDown (already imported in ShipmentDetail.tsx line ~8).

After fix for issue #9 (merging scraper cards), apply the same pattern to the inline scrape log toggle within the merged card.

Acceptance criteria

  • All collapsible toggles in the app use the ChevronDown rotating pattern
  • No collapsible uses "Show"/"Hide" text as the sole toggle affordance

Brand identity alignment

Expandable technical details are common in Trackbox: raw events, field maps, scrape logs, and source/debug metadata. Collapsible controls should be predictable, quiet, and consistent.

Brand-compliant implementation notes

  • Use a left-aligned ChevronDown line icon with rotation for disclosure.
  • Keep label text factual: Field map, Raw events, Scrape log, Source details.
  • Avoid Show/Hide as the only affordance; it reads like generic admin copy.
  • Use subtle motion only for chevron rotation and content expansion.

Additional acceptance criteria

  • Collapsible controls follow one shared visual pattern.
  • Expanded technical content remains secondary and does not overwhelm primary shipment state.
  • Keyboard focus and aria-expanded state are preserved.

Migrated from GitHub issue #27: https://github.com/bullitt186/trackbox/issues/27
Original author: @bullitt186
Original created: 2026-06-27T13:26:22Z
Original labels: ux

## Problem Collapsible sections use two different UI patterns: **Pattern A — ChevronDown icon rotating** (Dashboard: Delivered/Archived sections, Parsers: field map): ```tsx <ChevronDown className={cn("h-4 w-4 transition-transform", open && "rotate-180")} /> ``` **Pattern B — Plain text toggle** (ShipmentDetail: Scrape Log): ```tsx <span className="text-xs text-muted-foreground">{scrapeLogOpen ? "Hide" : "Show"}</span> ``` Pattern B appears in `ShipmentDetail.tsx` line ~566 for the Scrape Log card header. It looks like a text link and is visually inconsistent with every other collapsible in the app. ## Implementation File: `frontend/src/pages/ShipmentDetail.tsx` — Scrape Log card header around line 565. Change: ```tsx <button onClick={() => setScrapeLogOpen(!scrapeLogOpen)} className="flex items-center justify-between w-full text-left" > <CardTitle className="text-sm text-muted-foreground font-medium">Scrape Log</CardTitle> <span className="text-xs text-muted-foreground">{scrapeLogOpen ? "Hide" : "Show"}</span> </button> ``` To: ```tsx <button onClick={() => setScrapeLogOpen(!scrapeLogOpen)} className="flex items-center gap-2 text-sm font-medium text-muted-foreground hover:text-foreground transition-colors" > <ChevronDown className={cn("h-4 w-4 transition-transform", scrapeLogOpen && "rotate-180")} /> Scrape Log </button> ``` Import `ChevronDown` (already imported in `ShipmentDetail.tsx` line ~8). After fix for issue #9 (merging scraper cards), apply the same pattern to the inline scrape log toggle within the merged card. ## Acceptance criteria - All collapsible toggles in the app use the ChevronDown rotating pattern - No collapsible uses "Show"/"Hide" text as the sole toggle affordance ## Brand identity alignment Expandable technical details are common in Trackbox: raw events, field maps, scrape logs, and source/debug metadata. Collapsible controls should be predictable, quiet, and consistent. ## Brand-compliant implementation notes - Use a left-aligned `ChevronDown` line icon with rotation for disclosure. - Keep label text factual: `Field map`, `Raw events`, `Scrape log`, `Source details`. - Avoid `Show/Hide` as the only affordance; it reads like generic admin copy. - Use subtle motion only for chevron rotation and content expansion. ## Additional acceptance criteria - Collapsible controls follow one shared visual pattern. - Expanded technical content remains secondary and does not overwhelm primary shipment state. - Keyboard focus and aria-expanded state are preserved. --- Migrated from GitHub issue #27: https://github.com/bullitt186/trackbox/issues/27 Original author: @bullitt186 Original created: 2026-06-27T13:26:22Z Original labels: ux
bullitt changed title from Global: Standardize collapsible toggle pattern — some use ChevronDown, some use 'Show/Hide' text to Global: Standardize collapsible controls with neutral chevrons 2026-06-27 15:46:22 +02:00
Author
Owner

Implemented in commit bd6b0e7 as part of the Source & sync card merge (also resolves #30 and #49). The 'Show'/'Hide' text toggle in the Scrape Log section has been replaced with a rotating ChevronDown button matching the pattern used in Dashboard and Parsers. The chevron rotates 180° when expanded, with aria-expanded set. The scrape log is now collapsible within the unified Source & sync card.

Implemented in commit bd6b0e7 as part of the Source & sync card merge (also resolves #30 and #49). The 'Show'/'Hide' text toggle in the Scrape Log section has been replaced with a rotating ChevronDown button matching the pattern used in Dashboard and Parsers. The chevron rotates 180° when expanded, with `aria-expanded` set. The scrape log is now collapsible within the unified Source & sync card.
Sign in to join this conversation.
No labels
arch
harness
security
ux
No milestone
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set.

Reference
bullitt/trackbox#48
No description provided.