Apply Quali — override legacy SCSS
Authority: This skill overrides any project habit that keeps or extends
legacy button/input/select/tooltip SCSS when a Quali primitive exists.
Companion: Always load and follow naf-quali first (Storybook MCP, imports,
tokens, DSProvider). This skill adds the migration / override rules.
Storybook: https://qa-nafdesignsystem.naftech.io/
Non-negotiables
- Quali owns chrome. Border, padding, height, font-size, focus ring, colors
on fields/buttons/tooltips/modals → Quali component + tokens. Not app SCSS.
- Do not restyle Quali. No wrapping class that resets
input/button /
[class*="Input"] padding, border, or font to match old rem chrome.
- Gut legacy field SCSS. When adapting a control to Quali, delete (or empty
to layout-only) the old
*.scss rules for that chrome. Leaving both = Quali
loses to later/unlayered hub CSS.
- Tokens only in remaining custom CSS:
var(--color-*), var(--spacing-*),
var(--font-*), var(--border-radius-*), var(--radius-*). No new hex.
- Default size
md unless Storybook docs say otherwise for that control.
- Never invent props —
get_docs via Storybook MCP before coding.
Mandatory workflow
Copy and track:
Apply Quali:
- [ ] 1. Load naf-quali; connect Storybook MCP
- [ ] 2. Map UI need → Quali primitive (decision tree in naf-quali)
- [ ] 3. get_docs for that component
- [ ] 4. Replace or wrap legacy component with Quali
- [ ] 5. Gut competing SCSS (chrome out; layout-only in)
- [ ] 6. Fix cascade (layer order + kill universal resets)
- [ ] 7. Verify checklist below
Step 4 — replace vs adapter
| Situation |
Do |
| New screen / new control |
Import Quali directly (@naf/react-ui/ui or /forms) |
Wide legacy API (components/ui/Button) |
Adapter: keep export, render Quali inside; map props via size/variant maps |
One-off page still on raw <input> / .btn |
Replace with Quali in that file; do not add more legacy SCSS |
Step 5 — gut SCSS (hard rule)
Delete or stop shipping rules that set any of these on Quali-owned elements:
padding, height / min-height, border, border-radius (field chrome)
font-size, line-height, font-family on inputs/buttons (use Quali / tokens)
- Rem-based “52px field” /
5.2rem control chrome
- Absolute yellow tooltip bubbles when Quali
Tooltip exists
appearance hacks that fight native Quali controls
Keep only layout in app SCSS (prefer tokens):
- Flex/grid,
gap, width / max-width, margin between sections
- Positioning for page shells (sidebar offset, page padding) using tokens
Comment at top of gutted files:
/* Layout only — Quali owns field/button chrome. */
Step 6 — cascade wins Quali
Legacy unlayered CSS beats Quali @layer styles. Fix foundation once per app:
- Import order (entry):
import '@naf/design-tokens/css/light';
// optional: layer-order CSS that declares @layer before Quali
import '@naf/react-ui/styles.css';
- Declare layers before Quali CSS (example):
@layer naf-hub-reset, naf-design-system;
- Remove or narrow universal resets that zero Quali padding, e.g.
* { padding: 0; margin: 0; } — especially unlayered and loaded after Quali.
- Prefer
html { font-size: 100%; } (16px rem root) so Quali rem sizing is correct.
Do not keep html { font-size: 62.5%; } while relying on Quali defaults.
Details: scss-override.md
Component override map (legacy → Quali)
Use this when ripping SCSS off old wrappers:
| Legacy pattern |
Quali |
.btn / custom Button SCSS |
Button (variant, size) |
text <input> + label SCSS |
FormField + Input |
| password field |
FormField + PasswordInput (+ PasswordHint) |
| select / dropdown SCSS |
FormField + Select |
| checkbox / radio SCSS |
Checkbox / RadioGroup |
| textarea SCSS |
FormField + Textarea |
| currency / masked money |
MaskedInput / NumberInput as documented |
| date picker chrome |
Quali DatePicker (or documented date input) |
| toast / banner SCSS |
useToaster / AlertCard |
| modal / popup SCSS |
Modal |
| spinner overlay SCSS |
Loader |
| tooltip yellow bubble SCSS |
Tooltip (size sm|md|lg, default md) |
| badge / chip SCSS |
Badge / Chip |
If not listed → Storybook search, then get_docs. Do not invent a third CSS kit.
Anti-patterns (forbidden under this skill)
| Forbidden |
Required |
| “Match old rem look” with SCSS on Quali nodes |
Accept Quali sm/md/lg |
!important to beat Quali |
Gut hub rule or fix layer order |
Duplicate chrome: Quali + legacy .scss both active |
Gut legacy chrome |
| New hex / magic rem for fields |
Tokens + Quali sizes |
| Skip Storybook because “only CSS tweak” |
Still get_docs if touching a Quali control |
Extend components/ui/*.scss for new features |
Quali component or layout-only tokens |
Verify before done
Additional resources
- Cascade / rem / gut recipes: scss-override.md
- Full Quali build skill: personal
naf-quali (SKILL.md, components.md, reference.md)
1---2name: apply-quali3description: Forces Quali (@naf/react-ui, @naf/design-tokens) over legacy SCSS/CSS and bespoke UI chrome on any project. Use when the user says apply quali, override old SCSS, kill legacy styles, migrate components off rem/hex chrome, fix Quali padding lost to hub resets, or when legacy .scss fights Quali components.4---56# Apply Quali — override legacy SCSS78**Authority:** This skill **overrides** any project habit that keeps or extends9legacy button/input/select/tooltip SCSS when a Quali primitive exists.1011**Companion:** Always load and follow `naf-quali` first (Storybook MCP, imports,12tokens, `DSProvider`). This skill adds the **migration / override** rules.1314**Storybook:** https://qa-nafdesignsystem.naftech.io/1516## Non-negotiables17181. **Quali owns chrome.** Border, padding, height, font-size, focus ring, colors19 on fields/buttons/tooltips/modals → Quali component + tokens. Not app SCSS.202. **Do not restyle Quali.** No wrapping class that resets `input`/`button` /21 `[class*="Input"]` padding, border, or font to match old rem chrome.223. **Gut legacy field SCSS.** When adapting a control to Quali, delete (or empty23 to layout-only) the old `*.scss` rules for that chrome. Leaving both = Quali24 loses to later/unlayered hub CSS.254. **Tokens only** in remaining custom CSS: `var(--color-*)`, `var(--spacing-*)`,26 `var(--font-*)`, `var(--border-radius-*)`, `var(--radius-*)`. No new hex.275. **Default size `md`** unless Storybook docs say otherwise for that control.286. **Never invent props** — `get_docs` via Storybook MCP before coding.2930## Mandatory workflow3132Copy and track:3334```35Apply Quali:36- [ ] 1. Load naf-quali; connect Storybook MCP37- [ ] 2. Map UI need → Quali primitive (decision tree in naf-quali)38- [ ] 3. get_docs for that component39- [ ] 4. Replace or wrap legacy component with Quali40- [ ] 5. Gut competing SCSS (chrome out; layout-only in)41- [ ] 6. Fix cascade (layer order + kill universal resets)42- [ ] 7. Verify checklist below43```4445### Step 4 — replace vs adapter4647| Situation | Do |48|-----------|----|49| New screen / new control | Import Quali directly (`@naf/react-ui/ui` or `/forms`) |50| Wide legacy API (`components/ui/Button`) | Adapter: keep export, render Quali inside; map props via size/variant maps |51| One-off page still on raw `<input>` / `.btn` | Replace with Quali in that file; do not add more legacy SCSS |5253### Step 5 — gut SCSS (hard rule)5455**Delete or stop shipping** rules that set any of these on Quali-owned elements:5657- `padding`, `height` / `min-height`, `border`, `border-radius` (field chrome)58- `font-size`, `line-height`, `font-family` on inputs/buttons (use Quali / tokens)59- Rem-based “52px field” / `5.2rem` control chrome60- Absolute yellow tooltip bubbles when Quali `Tooltip` exists61- `appearance` hacks that fight native Quali controls6263**Keep only layout** in app SCSS (prefer tokens):6465- Flex/grid, `gap`, `width` / `max-width`, margin between sections66- Positioning for page shells (sidebar offset, page padding) using tokens6768Comment at top of gutted files:6970```scss71/* Layout only — Quali owns field/button chrome. */72```7374### Step 6 — cascade wins Quali7576Legacy unlayered CSS beats Quali `@layer` styles. Fix foundation once per app:77781. **Import order** (entry):79 ```ts80 import '@naf/design-tokens/css/light';81 // optional: layer-order CSS that declares @layer before Quali82 import '@naf/react-ui/styles.css';83 ```842. **Declare layers before Quali CSS** (example):85 ```css86 @layer naf-hub-reset, naf-design-system;87 ```883. **Remove or narrow** universal resets that zero Quali padding, e.g.89 `* { padding: 0; margin: 0; }` — especially unlayered and loaded after Quali.904. Prefer `html { font-size: 100%; }` (16px rem root) so Quali rem sizing is correct.91 Do not keep `html { font-size: 62.5%; }` while relying on Quali defaults.9293Details: [scss-override.md](scss-override.md)9495## Component override map (legacy → Quali)9697Use this when ripping SCSS off old wrappers:9899| Legacy pattern | Quali |100|----------------|-------|101| `.btn` / custom Button SCSS | `Button` (`variant`, `size`) |102| text `<input>` + label SCSS | `FormField` + `Input` |103| password field | `FormField` + `PasswordInput` (+ `PasswordHint`) |104| select / dropdown SCSS | `FormField` + `Select` |105| checkbox / radio SCSS | `Checkbox` / `RadioGroup` |106| textarea SCSS | `FormField` + `Textarea` |107| currency / masked money | `MaskedInput` / `NumberInput` as documented |108| date picker chrome | Quali `DatePicker` (or documented date input) |109| toast / banner SCSS | `useToaster` / `AlertCard` |110| modal / popup SCSS | `Modal` |111| spinner overlay SCSS | `Loader` |112| tooltip yellow bubble SCSS | `Tooltip` (`size` sm\|md\|lg, default `md`) |113| badge / chip SCSS | `Badge` / `Chip` |114115If not listed → Storybook `search`, then `get_docs`. Do not invent a third CSS kit.116117## Anti-patterns (forbidden under this skill)118119| Forbidden | Required |120|-----------|----------|121| “Match old rem look” with SCSS on Quali nodes | Accept Quali `sm`/`md`/`lg` |122| `!important` to beat Quali | Gut hub rule or fix layer order |123| Duplicate chrome: Quali + legacy `.scss` both active | Gut legacy chrome |124| New hex / magic rem for fields | Tokens + Quali sizes |125| Skip Storybook because “only CSS tweak” | Still `get_docs` if touching a Quali control |126| Extend `components/ui/*.scss` for new features | Quali component or layout-only tokens |127128## Verify before done129130- [ ] `naf-quali` workflow done (Storybook docs for every Quali component touched)131- [ ] Token CSS before `@naf/react-ui/styles.css`; `DSProvider theme="light"` present132- [ ] Legacy chrome SCSS removed or layout-only for migrated controls133- [ ] No universal padding reset killing Quali134- [ ] Layer order declared if hub uses `@layer` / Quali still loses specificity wars135- [ ] Visual check: field padding/height matches Storybook `md` (or chosen size), not old 5.2rem136137## Additional resources138139- Cascade / rem / gut recipes: [scss-override.md](scss-override.md)140- Full Quali build skill: personal `naf-quali` (`SKILL.md`, `components.md`, `reference.md`)