veza/apps/web/docs/UI_QUALITY_LOG.md

125 lines
8.2 KiB
Markdown
Raw Normal View History

# UI Quality Log
Suivi des leviers traités pour atteindre le niveau premium Discord/Spotify-like.
Chaque entrée documente : levier, fichiers impactés, impact visuel, risques évités.
---
## 2025-02-08 — Session 1
### Levier 1 : Contraste `muted-foreground` (WCAG AA+)
- **Fichiers** : `src/index.css` (3 variables)
- **Changement** : dark mode oklch(0.65 → 0.70), light mode oklch(0.45 → 0.42), sidebar-foreground synchronisé
- **Impact** : texte secondaire plus lisible sur toutes les surfaces (labels, timestamps, placeholders, sidebar nav items). Rapproche du ratio Spotify (~0.70) et Discord (~0.76).
- **Risques évités** : pas de régression de hiérarchie (delta foreground/muted reste 0.28, suffisant pour distinction visuelle)
### Levier 2 : Migration `text-[10px]` → `text-xs` (23 composants)
- **Fichiers** : 23 composants (admin, marketplace, player, settings, chat, upload, etc.)
- **Changement** : remplacement de toutes les tailles arbitraires `text-[10px]` par `text-xs`. Exceptions documentées : avatar xs, badge JSDoc.
- **Impact** : typographie cohérente et conforme au design system sur toute l'app
- **Risques évités** : vérification que text-xs (0.75rem = 12px vs 10px) ne casse pas la densité des composants compacts
### Levier 3 : Migration `max-h-[XXvh]` → tokens layout (15 composants)
- **Fichiers** : 15 composants (modales, panels, player, hero)
- **Changement** : toutes les hauteurs arbitraires viewport remplacées par `max-h-layout-modal*`, `max-h-layout-list`, `max-h-layout-drawer`, `h-layout-lyrics`
- **Impact** : système de hauteurs cohérent, modales qui respectent un contrat visuel
- **Risques évités** : tokens déjà définis et testés dans index.css avant usage
### Levier 4 : Shell DashboardLayout + Header transparence
- **Fichiers** : `DashboardLayout.tsx`, `Header.tsx`
- **Changement** : `min-w-0` (fix overflow), `max-lg:ml-0` (responsive), `bg-transparent backdrop-blur-md` header
- **Impact** : header seamless type Spotify, meilleur scroll
- **Risques évités** : pas de modification des tokens — changements locaux aux composants
### Levier 5 : Player sidebar-aware + synced lyrics
- **Fichiers** : `GlobalPlayer.tsx`, `PlayerExpanded.tsx`, `PlayerQueue.tsx`, `types.ts`
- **Changement** : positionnement player aligné sur sidebar, vue étendue avec lyrics synchronisées, queue repositionnée
- **Impact** : player qui ne chevauche plus la sidebar sur desktop, expérience lyrics type Spotify
- **Risques évités** : z-index vérifié, reduced-motion respecté
### Levier 6 : Focus-visible rings (16 composants)
- **Fichiers** : 16 composants (TrackCard, ConversationItem, SelectOptionItem, etc.)
- **Changement** : ajout `focus-visible:ring-2 focus-visible:ring-ring` sur éléments interactifs sans indicateur focus
- **Impact** : navigation clavier fonctionnelle sur les contrôles manquants
- **Risques évités** : pattern cohérent avec les composants déjà couverts (Button, Sidebar)
### Levier 7 : Arbitrary min-w → Tailwind scale (5 composants)
- **Fichiers** : AdminModerationView, PasswordStrengthIndicator, PlaylistFollowButton, FollowButton, collapsible
- **Changement** : `min-w-[Xpx]``min-w-N` Tailwind, exception documentée pour collapsible
- **Impact** : cohérence du spacing system
- **Risques évités** : valeurs Tailwind les plus proches vérifées (140px → 36 = 144px, 100px → 24 = 96px, 80px → 20 = 80px)
### Levier 8 : Unification scrollbar
- **Fichiers** : `global-effects.css`, `fixDisplayIssues.ts`
- **Changement** : suppression des définitions scrollbar dupliquées, index.css comme source unique
- **Impact** : scrollbar cohérente dans toute l'app (dev et prod)
- **Risques évités** : pas de conflit d'ordre de chargement CSS
### Levier 9 : Nettoyage `fixDisplayIssues.ts` (719 → 70 lignes)
- **Fichiers** : `fixDisplayIssues.ts`, `aggressiveVisualFix.ts`
- **Changement** : suppression de l'injection CSS nucléaire, MutationObserver, setInterval. Conservation des outils diagnostic opt-in.
- **Impact** : dev mode fidèle à la prod (borders, backgrounds, éléments étroits visibles)
- **Risques évités** : vérification que le problème original (lignes verticales) est toujours corrigé à la source CSS
### Levier 10 : PlaylistCard hover transition fix + focus-visible
- **Fichiers** : `PlaylistCard.tsx`
- **Changement** : suppression de `transition-opacity` qui écrasait les transitions du Card (shadow, bg-color). Ajout focus-visible ring. `ring-blue-500``ring-primary`.
- **Impact** : hover shadow animation fonctionne maintenant, navigation clavier accessible
- **Risques évités** : pas de changement de layout, seulement des transitions et ring
### Levier 11 : Switch, Toast, LoadingSpinner → design system
- **Fichiers** : `switch.tsx`, `Toast.tsx`, `loading-spinner.tsx`
- **Changement** : dimensions arbitraires → Tailwind scale (`w-[44px]` → `w-11`), couleurs hardcodées → tokens (`bg-kodo-cyan` → `bg-primary`, `border-t-blue-600``border-t-primary`)
- **Impact** : composants alignés sur le design system, cohérence visuelle
- **Risques évités** : dimensions Tailwind exactement identiques aux px arbitraires
### Levier 12 : Skeleton shimmer animation (premium loading)
- **Fichiers** : `skeleton.tsx`, `index.css`
- **Changement** : remplacement `animate-pulse` (opacité simple) par overlay shimmer (gradient balayant). `bg-kodo-steel/50``bg-muted/50`. Respecte `prefers-reduced-motion`.
- **Impact** : loading states perçus comme premium (pattern Spotify/Discord). Visible sur chaque page load et transition.
- **Risques évités** : shimmer via enfant overlay, pas de conflit avec les classes animate-pulse inline existantes
---
## 2026-02-08 — Session 2
### Levier 13 : Migration inline skeletons → `<Skeleton>` shimmer (43 fichiers)
- **Fichiers** : 43 skeleton files across all major views (TrackDetailPage, LibraryPage, PlaylistDetailPage, DiscoverView, PlaybackDashboard, StudioView, MonitoringDashboard, UserProfilePage, SearchPage, ChatMessages, AudioPlayer, etc.)
- **Changement** : remplacement de tous les `<div className="... bg-muted animate-pulse">` par `<Skeleton>` component avec shimmer premium
- **Impact** : chaque état de chargement dans l'app utilise maintenant le shimmer premium au lieu du pulse basique. Perception de fluidité uniforme.
- **Risques évités** : layout identique (seules les classes bg-muted/animate-pulse retirées), props/structure inchangées
### Levier 14 : Inline empty states → `<EmptyState>` component (6 composants)
- **Fichiers** : MarketplaceHome, MarketplaceViewGrid, ProfileViewTracksTab, ProfileViewPlaylistsTab, PurchasesViewList, SessionManagement, empty-state.tsx
- **Changement** : remplacement des "No X found" nus par EmptyState (icône + titre + description + action optionnelle). Tokens du composant EmptyState migrés : `text-white``text-foreground`, `text-kodo-content-dim``text-muted-foreground`
- **Impact** : les états vides sont maintenant des moments UX designés, pas des fallback bruts
- **Risques évités** : migration conservatrice — même texte, ajout d'icône contextuelle
### Levier 15 : `text-red-500` → `text-destructive` (11 composants)
- **Fichiers** : PlayerExpanded, PlayerQueue, WebhooksView, RolesPage, ChatPage, AdminDashboardStatCard, NotificationsViewItem/Header, AnalyticsViewTopTracks, AdminDashboardTabs, AdminDashboardHeader
- **Changement** : migration systématique de `text-red-500`, `bg-red-500/10`, `border-red-500/20` etc. vers les équivalents `destructive` du design system
- **Impact** : les états d'erreur et destructifs s'adapteront au thème, cohérence du langage visuel
- **Risques évités** : tokens `destructive` déjà définis dans index.css, couleur visuellement identique
### Levier 16 : Focus-visible + a11y SearchPageResults & UserCard
- **Fichiers** : SearchPageResults.tsx, UserCard.tsx
- **Changement** : ajout tabIndex/role/onKeyDown/focus-visible ring sur toutes les Cards interactives de SearchPageResults. Conversion des div/h3 cliquables de UserCard en `<button>` sémantiques. Migration tokens couleur legacy.
- **Impact** : navigation clavier complète dans la recherche, conformité a11y UserCard
- **Risques évités** : pas de changement de layout visuel, focus ring visible uniquement au clavier (focus-visible)