# ByteLyst UI Anti-Patterns > **Audience:** every engineer and AI agent shipping UI in the ByteLyst > ecosystem. > **Status:** living document — published as part of Wave 9 (cross-cutting > CC.6). Last refresh: 2026-05-27. This file catalogues the **patterns we do not ship**. Each entry has: - **Smell** — how to spot it in a PR diff. - **Why it's wrong** — the trust / a11y / consistency / perf cost. - **Do this instead** — the canonical ByteLyst primitive or pattern. The full roadmap reference is [`UI_ROADMAP_2026_V3_CROSS_REPO.md` §3.8](../UI_ROADMAP_2026_V3_CROSS_REPO.md). This document is enforced by code review and (eventually) a custom ESLint config in `@bytelyst/eslint-config-ui` (planned, see CC.4). --- ## 1. Hard-coded colour / spacing / radius values **Smell.** ```tsx
className="bg-indigo-500 p-3 rounded-lg" ``` **Why it's wrong.** Bypasses the token layer. Themes (dark, hi-contrast, generative branding, per-product accent) cannot affect this surface. Multi-product consistency dies one literal at a time. **Do this instead.** Reference tokens by CSS custom property: ```tsx
``` For Tailwind users, our token-aware utility plugin emits `bg-accent`, `p-3` (mapped to `var(--bl-space-3)`), `rounded-md` etc. Never use a raw `text-indigo-500`. --- ## 2. Bespoke skeleton / spinner / empty-state per surface **Smell.** A `Skeleton.tsx` or `LoadingSpinner.tsx` file inside a product repo's `src/components/`. **Why it's wrong.** Loading affordances are the most-replicated UI in the ecosystem. Every bespoke variant disagrees on size, easing, accessible labels, and dark-mode contrast. Users learn three "loading" languages. **Do this instead.** Import from `@bytelyst/ui`: ```tsx import { Skeleton, SkeletonGroup, LoadingDots, LoadingSpinner, EmptyState } from '@bytelyst/ui'; ``` If a product genuinely needs a custom shape, open an issue on `learning_ai_common_plat` to extend the primitive — never fork it. --- ## 3. Bespoke tag editor / searchable select **Smell.** Custom `TagInput.tsx` with Enter/comma commit logic; custom `Combobox.tsx` with `` + filtered `