@wix/agent-skills 1.16.2 → 1.17.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (58) hide show
  1. package/package.json +1 -1
  2. package/skills/wix-app/references/EDITOR_REACT_COMPONENT.md +134 -120
  3. package/skills/wix-app/references/EMBEDDED_SCRIPT.md +6 -0
  4. package/skills/wix-app/references/SITE_PLUGIN.md +2 -2
  5. package/skills/wix-app/references/backend-event/COMMON-EVENTS.md +2 -2
  6. package/skills/wix-app/references/editor-react-component/ACCESSIBILITY.md +182 -99
  7. package/skills/wix-app/references/editor-react-component/ANIMATED-COMPONENTS.md +92 -47
  8. package/skills/wix-app/references/editor-react-component/BRANDED-COMPONENTS.md +15 -6
  9. package/skills/wix-app/references/editor-react-component/COMPONENT-CONTRACT.md +275 -0
  10. package/skills/wix-app/references/editor-react-component/COMPONENT-PREVIEW.md +29 -42
  11. package/skills/wix-app/references/editor-react-component/CSS-GUIDELINES.md +153 -449
  12. package/skills/wix-app/references/editor-react-component/DESIGN-STATES.md +66 -19
  13. package/skills/wix-app/references/editor-react-component/DIRECTIONALITY.md +53 -158
  14. package/skills/wix-app/references/editor-react-component/EDITOR-EXTENSION-CONFIGURATION.md +78 -0
  15. package/skills/wix-app/references/editor-react-component/FUNCTION-HANDLERS.md +42 -134
  16. package/skills/wix-app/references/editor-react-component/MANIFEST-ERRORS.md +27 -0
  17. package/skills/wix-app/references/editor-react-component/PARTS.md +45 -24
  18. package/skills/wix-app/references/editor-react-component/PROPS-VS-CSS.md +63 -179
  19. package/skills/wix-app/references/editor-react-component/REACT-GUIDELINES.md +79 -163
  20. package/skills/wix-app/references/editor-react-component/SITE-CONTEXT-HOOKS.md +36 -21
  21. package/skills/wix-app/references/editor-react-component/SSR.md +30 -99
  22. package/skills/wix-base44-connector/SKILL.md +34 -17
  23. package/skills/wix-base44-connector/scripts/utils.js +33 -25
  24. package/skills/wix-headless/entry/bootstrap.mjs +9 -2
  25. package/skills/wix-headless/references/SDK_HANDOFF.md +1 -1
  26. package/skills/wix-headless/references/inline-recipes/how-to-code-a-store.md +42 -23
  27. package/skills/wix-headless/references/inline-recipes/how-to-code-pricing-plans.md +10 -8
  28. package/skills/wix-headless/references/inline-recipes/how-to-code-restaurant-orders.md +27 -24
  29. package/skills/wix-headless/references/managed/AUTHENTICATION.md +5 -0
  30. package/skills/wix-manage/SKILL.md +14 -2
  31. package/skills/wix-manage/references/bookings/booking-system-integration-gaps.md +20 -13
  32. package/skills/wix-manage/references/bookings/create-class-service.md +1 -1
  33. package/skills/wix-manage/references/bookings/end-to-end-booking-flow.md +24 -11
  34. package/skills/wix-manage/references/cms/cms-ecommerce-catalog-integration.md +5 -5
  35. package/skills/wix-manage/references/rich-content/author-ricos-rich-content.md +182 -5
  36. package/skills/wix-manage/references/seo/manage-seo-tags.md +315 -0
  37. package/skills/wix-manage/references/seo/manage-url-redirects.md +250 -0
  38. package/skills/wix-manage/references/sites/query-sites.md +72 -161
  39. package/skills/wix-replatform/resources/rp-mapper/wix-business-solutions-taxonomy.md +5 -6
  40. package/skills/wix-vibe-headless/platforms/base44-ecom-light-seed.md +13 -9
  41. package/skills/wix-vibe-headless/platforms/base44-ecom-light.md +10 -7
  42. package/skills/wix-vibe-headless/platforms/base44.md +13 -10
  43. package/skills/wix-vibe-headless/references/bookings/INSTRUCTIONS.md +2 -0
  44. package/skills/wix-vibe-headless/references/bookings/app/rest/wix-bookings-checkout.js +9 -8
  45. package/skills/wix-vibe-headless/references/restaurants/INSTRUCTIONS.md +4 -1
  46. package/skills/wix-vibe-headless/references/restaurants/app/components/OrderCartDrawer.jsx +23 -11
  47. package/skills/wix-vibe-headless/references/restaurants/app/context/OrderCartContext.jsx +1 -1
  48. package/skills/wix-vibe-headless/references/restaurants/app/rest/wix-restaurants-ordering.js +29 -31
  49. package/skills/wix-vibe-headless/references/storefront/INSTRUCTIONS.md +15 -8
  50. package/skills/wix-vibe-headless/references/storefront/app/components/CartDrawer.jsx +37 -38
  51. package/skills/wix-vibe-headless/references/storefront/app/context/CartContext.jsx +2 -2
  52. package/skills/wix-vibe-headless/references/storefront/app/rest/wix-store-cart.js +35 -35
  53. package/skills/wix-app/references/editor-react-component/A11Y-REVIEW-REFERENCE.md +0 -172
  54. package/skills/wix-app/references/editor-react-component/A11Y-REVIEW.md +0 -143
  55. package/skills/wix-app/references/editor-react-component/COMPONENT-API.md +0 -484
  56. package/skills/wix-app/references/editor-react-component/COMPONENT-CONFIGURATION.md +0 -225
  57. package/skills/wix-app/references/editor-react-component/EDIT-FLOW.md +0 -6
  58. package/skills/wix-app/references/editor-react-component/REACT-PATTERNS.md +0 -95
@@ -0,0 +1,27 @@
1
+ # Manifest Build Errors
2
+
3
+ Use this reference only when `npx wix build` or `npx wix generate manifest`
4
+ exits with an error. Read the error name from the first token before the colon
5
+ (`IoError:`, `ParseError:`, or `NotFoundError:`), then apply the matching fix.
6
+
7
+ | Error | Fix |
8
+ | --- | --- |
9
+ | `IoError: Failed to load compiled bundle` | Re-run `npx wix build`; fix any TypeScript/build errors it reports first |
10
+ | `IoError: Failed to access component "X" from compiled bundle` | Corrupted artifact — delete `dist/`, re-run `npx wix build` from scratch |
11
+ | `IoError: CSS selector matching failed for "X"` | Fix invalid selector syntax in `<componentName>.module.css` |
12
+ | `IoError: Component "X" render produced no root element` | Component returns null or bare text — ensure it always renders a root JSX element |
13
+ | `IoError` (render phase, no other pattern) | SSR crash — remove browser-only APIs (`window`, `document`, `localStorage`) used at render time; ensure props have defaults |
14
+ | `NotFoundError: File not found` | Restore the missing source file or fix its registered/imported path; do not re-scaffold an existing component |
15
+ | `NotFoundError: Component "X" was not found as a named export` | Confirm `component.tsx` has a default export and re-run `npx wix build` |
16
+ | `ParseError: Failed to parse TypeScript config` | Fix `tsconfig.json`; run `npx tsc --noEmit` to surface the error |
17
+ | `ParseError: Failed to extract component types from "X"` | TypeScript error in the component — run `npx tsc --noEmit` and fix |
18
+ | `ParseError: Failed to compile "<file.scss>"` | SCSS syntax error — line/column is in the error message |
19
+ | `ParseError: Failed to parse CSS file for component "X"` | CSS syntax error in `.module.css` — line/column is in the error message |
20
+
21
+ After each fix, re-run `npx wix build && npx wix generate manifest` to confirm.
22
+
23
+ ## Checklist
24
+
25
+ - [ ] The fix matches the reported error name and message.
26
+ - [ ] Build errors are resolved before manifest generation is retried.
27
+ - [ ] Both build and manifest generation pass after the fix.
@@ -1,39 +1,60 @@
1
- # What Qualifies as a Part
1
+ # Named Parts and Root Election
2
2
 
3
- ## Step 0 — Elect the root element
3
+ Use this reference to choose the component root and decide which inner elements
4
+ receive independent editor controls.
4
5
 
5
- The root always becomes the component's editor element: it carries the `'<component-name>'` global class and gets a name and design capabilities either way. So elect a root that deserves them, before enumerating inner parts.
6
+ ## Elect the Root First
6
7
 
7
- - ✅ **The component reduces to one meaningful element** (a single control, link, media surface, or list) — that element **is** the root. It takes `id`, `dir`, the `fallbackDirection` class, the merged `className`, the `a11y` spread, `'<component-name>'`, and the root CSS rule. All of these are attributes and classes, so they sit on a `<button>` or `<a>` exactly as on a `<div>` — needing them is never a reason to add a wrapper.
8
- - ✅ **The elected root is the root, not an inner part** — it carries the **unprefixed** `'<component-name>'` class and gets no `elementProps` entry. A single-control component therefore has exactly one named part: its root.
9
- - ❌ **Wrapper `<div>` holding only root plumbing** — the editor element is then a transparent box and the real element is demoted to a nested part. A root wrapper is justified only when it lays out two or more sibling parts, is the sizing/scroll/clipping container, or hosts a root-level prop-triggered state ([`DESIGN-STATES.md`](DESIGN-STATES.md) §5). Anchoring absolutely positioned decoration is not a justification — `position: relative` works on any element.
10
- - **Stutter test** — a part class repeating the component's own noun (`confetti-button-button`) means the wrapper took the root's name. Collapse it and promote the real element.
8
+ The root is always the component's editor element. It carries the unprefixed
9
+ `'<component-name>'` global class and receives top-level `id`, `className`,
10
+ `direction`, and `a11y`. It never has an `elementProps` entry.
11
11
 
12
- ## Inner parts
12
+ - If the component reduces to one meaningful control, link, media surface, or
13
+ list, make that semantic element the root.
14
+ - Add a wrapper root only when it lays out multiple sibling parts, owns
15
+ sizing/scrolling/clipping, or hosts a root-level prop-triggered state.
16
+ - Do not add a wrapper solely to hold root props or position decoration.
17
+ - If an inner part name stutters (`confetti-button-button`), the real semantic
18
+ element probably should have been the root.
13
19
 
14
- A **named part** is an element that a site owner would plausibly want to control independently in the editor. Zero config scans global class names and creates an editor element for each one. Each editor element can surface:
20
+ ## Identify Named Inner Parts
15
21
 
16
- - **CSS properties** — styling controls (fill, typography, border, etc.)
17
- - **Data** — content bindings (text, image, link, etc.)
22
+ A named inner part is an element whose styling or data/content a site owner
23
+ would plausibly control independently in the editor. It receives:
18
24
 
19
- An element deserves its own named part if a site owner would plausibly need to independently control either its styling **or** its data/content through the editor. Every named part gets exactly one global plain string class in JSX and one corresponding CSS rule. Elements that do not qualify should not get a global class.
25
+ - one prefixed global class: `'<component-name>-<part-name>'`
26
+ - one CSS Module class
27
+ - one matching `elementProps` entry, spread onto the element
20
28
 
21
- ## Mandatory filter — apply to every candidate element
29
+ Apply this filter to every candidate:
22
30
 
23
- - ❌ **State or variant** (`active`, `selected`, `current`, `disabled`, `open`, `checked`) — not a part, it's a **design state** of a part. Implement it per [`DESIGN-STATES.md`](DESIGN-STATES.md): native states from interactive markup; custom states as a flat global modifier on the element's own (component-name-prefixed) class (e.g. `carousel-slide--active`, toggled in JSX) plus a `:global(.carousel-slide--active)` CSS rule. The modifier is a state, not a named part.
24
- - ❌ **Hidden/shown state of an existing part** — the hidden and shown states of a part are not separate parts. The element itself should be a named part (so the editor can control its visibility per breakpoint); creating an additional part to represent its hidden or shown variant is wrong.
25
- - ❌ **Pure grouping wrapper** — not a part. A `<div>` whose only role is to hold already-named siblings has no independent editor surface; let layout live in the parent's CSS.
26
- - ❌ **Child with no independent editor surface** — not a part if its styling and data are already fully owned by the parent. This applies regardless of how many siblings it has. Two ways a child's editor surface can already be covered by the parent: (1) its CSS properties are inherited or set via the parent's rule; (2) its data is defined on the parent. **Canonical example:** an `<img>` inside a carousel slide whose `src` and `alt` come from the parent slide's data, and whose visual properties (object-fit, border-radius) could equally be set on the slide's own CSS rule — the slide already owns both data and styling, so the `<img>` is not a named part. Use a CSS module class for any structural CSS it needs. **Exception — interactive HTML elements (`<button>`, `<a>`, `<input>`) are never excluded by this criterion.** They always carry an independent styling surface: background, border, border-radius, hover/focus states, color, and typography are all meaningfully tunable per element in the editor. Apply this exclusion only to purely static structural elements (layout wrappers, grouping containers, decorative dividers). This makes an interactive element a named part **when it is an inner element** — if it is the elected root (Step 0), it is already named by `'<component-name>'` and must not be given a prefixed inner-part class as well.
27
- - ❌ **Positional duplicate** — not separate parts. Elements that are semantically identical and differ only in position (e.g. prev/next buttons) are one part; differentiate position with CSS (`:first-of-type` / `:last-of-type`, `data-` attribute, or `:nth-child`).
28
- - ✅ **Passes all checks** — a named part. Classify as **Semantic** (needs `elementProps`: data, behavior, direction, event handlers) or **Styling-only** (CSS class is sufficient).
31
+ - A state or variant (`selected`, `active`, `open`, `disabled`) is not a part.
32
+ Implement it as a prefixed design-state modifier on the affected part.
33
+ - A hidden and shown version of the same element is one part, not two.
34
+ - A grouping or layout-only wrapper is not a part.
35
+ - A static child whose styling and data are fully owned by its parent is not a
36
+ part. For example, an image whose source and appearance both belong to its
37
+ carousel slide can remain module-class-only.
38
+ - An inner interactive element (`button`, `a`, `input`, and equivalent semantic
39
+ controls) is a named part because it has an independent interaction and
40
+ styling surface.
41
+ - Positional duplicates such as previous/next buttons are one part when they
42
+ share the same semantic editor surface. Distinguish position with data or a
43
+ module-only helper class, not separate part names.
29
44
 
30
- ## Sanity check — apply after producing the parts list
45
+ ## Sanity Check
31
46
 
32
- Before finalising, verify each proposed part against its parent:
47
+ For each candidate, ask:
33
48
 
34
- > Would the editor controls generated for this part be a strict subset of its parent's controls?
49
+ > Would the controls for this element be a strict subset of its parent's controls?
35
50
 
36
- If yes — the part adds no independent editor surface and should be removed. This catches rationalisation after-the-fact ("the parent *could* expose this CSS property too, but so could the child separately"). When in doubt, fewer parts is usually better.
51
+ If yes, remove the part. Then check the root in reverse: if it has one child part
52
+ and no independent surface, remove the wrapper and promote the child.
37
53
 
38
- Then run the same question in reverse, on the root: if the root has exactly one child part and no editor surface of its own, it is a plumbing wrapper — delete it and promote the child per Step 0.
54
+ ## Checklist
39
55
 
56
+ - [ ] The root is the component's best semantic element.
57
+ - [ ] The root has no `elementProps` entry or duplicate prefixed part class.
58
+ - [ ] Each inner part offers independent data or styling control.
59
+ - [ ] Every named inner part has global/module classes and `elementProps` wiring.
60
+ - [ ] States, wrappers, decorations, and positional variants are not extra parts.
@@ -1,203 +1,87 @@
1
1
  # Props vs CSS
2
2
 
3
- Rules and patterns for handling visual/layout properties that vary by breakpoint.
3
+ Use this reference to decide whether a value belongs in the public React
4
+ contract, component logic, or editable CSS.
4
5
 
5
- ---
6
+ ## Decision Table
6
7
 
7
- ## Should This Be a React Prop or CSS?
8
+ | Value controls | Put it in | Examples |
9
+ | --- | --- | --- |
10
+ | User-authored content or data | React prop | `label`, `items`, `image`, `link` |
11
+ | Stable runtime behavior | React prop | `disabled`, `required`, `autoPlay`, `loop` |
12
+ | Value derived from props or state | Component logic | subtotal, active count, formatted label |
13
+ | Appearance or layout | CSS | spacing, alignment, orientation, icon position |
14
+ | Breakpoint-specific visibility | CSS/editor controls | show label, compact layout, mobile visibility |
15
+ | Direction | React prop plus logical CSS | `direction?: Direction` |
8
16
 
9
- ```
10
- Is this a content/data property?
11
- │
12
- ├─ YES → Can it be derived from other props / internal state?
13
- │ │
14
- │ ├─ YES (subtotal = price × qty, fullName = first + last, etc.)
15
- │ │ └─ ❌ NOT a prop → compute internally
16
- │ │
17
- │ └─ NO (label, items, imageSrc, link, title, etc.)
18
- │ └─ ✅ React prop
19
- │
20
- └─ NO → Would a user want this to vary per breakpoint?
21
- │
22
- ├─ YES (showLabel, orientation, displayMode, iconPosition)
23
- │ └─ ❌ NOT a prop → CSS only
24
- │
25
- └─ NO → Is it direction (RTL/LTR)?
26
- │
27
- ├─ YES
28
- │ └─ ✅ React prop (internationalization)
29
- │
30
- └─ NO → Is it behavior (disabled, required)?
31
- │
32
- ├─ YES
33
- │ └─ ✅ React prop
34
- │
35
- └─ NO
36
- └─ ❌ NOT a prop → CSS only
37
- ```
38
-
39
- ---
40
-
41
- ## Rules
42
-
43
- Components must distinguish between content/data and visual/layout properties:
44
-
45
- - **Content/Data** (same across all breakpoints) → React props ✅
46
- - **Visual/Layout** (vary by breakpoint) → CSS only, NOT props ❌
47
-
48
- ### What CAN be props
49
-
50
- - Content data that stays the same: `label`, `items`, `imageSrc`, `link`, `title`
51
- - Behavior that's consistent: `disabled`, `required`, `searchable`, `multiple`
52
-
53
- ### What CANNOT be props (must be CSS)
54
-
55
- - Visual display decisions: `showLabel`, `showIcon`, `displayMode`, `iconOnly`
56
- - Layout decisions: `orientation`, `alignment`, `compact`
57
- - Visibility toggles: `hideOnMobile`, `showOnDesktop`, `mobileView`
17
+ Ask in this order:
58
18
 
59
- ### Critical: ALL Show/Hide Toggles Are Visual/Layout Properties
19
+ 1. Can the value be derived? Compute it internally.
20
+ 2. Does it select content or stable behavior? Use a prop.
21
+ 3. Could a site owner reasonably vary it by breakpoint? Use CSS/editor controls.
22
+ 4. Otherwise, keep visual and layout choices in CSS.
60
23
 
61
- Props like `showProgressBar`, `showVolumeControls`, `showTimeDisplay`, `showNavigation`, `showControls` are visual display decisions that CANNOT be props.
24
+ ## Visibility Rules
62
25
 
63
- **Why:** Show/hide decisions affect layout and users need breakpoint control:
26
+ Do not add `showLabel`, `showIcon`, `hideOnMobile`, `displayMode`, or similar
27
+ props for purely presentational visibility. Render the named part and let the
28
+ editor control that part per breakpoint.
64
29
 
65
- - Show progress bar on desktop, hide on mobile
66
- - Show cover art on desktop, hide on tablet
67
- - Show full controls on large screens, minimal on small screens
68
-
69
- **Pattern:** These look like "feature toggles" but they're actually "layout modes".
70
-
71
- **Exception:** `direction` (RTL/LTR) is a mandatory prop for internationalization, not a breakpoint-responsive property.
72
-
73
- **Critical Rule:** If a property should be customizable per breakpoint, it CANNOT be a React prop.
74
-
75
- ### How to Implement
76
-
77
- Visibility/display properties can be overridden per breakpoint by the user via the editor — but, just like background colors, the component still authors the resting defaults in CSS:
78
-
79
- 1. **Always render all elements** — No conditional rendering with props
80
- 2. **Do NOT hardcode visibility-toggling display in CSS** (e.g. `display: none` to hide an element by default) — visibility is user-controlled per breakpoint. Layout `display` (`flex`, `grid`, etc.) on layout containers is fine and expected. Resting visual properties (background, color, border-radius, padding, font) DO belong in CSS — see `CSS-GUIDELINES.md`.
81
- 3. **Visibility is user-controlled** — Users control what shows/hides per breakpoint via the editor
30
+ Use this pattern:
82
31
 
83
32
  ```tsx
84
- // ✅ CORRECT: Always render
85
- <div className={styles.progressBar}>...</div>
86
- <div className={styles.volumeControls}>...</div>
87
- <div className={styles.trackInfo}>...</div>
88
-
89
- // SCSS: no `display: none` default — visibility is user-controlled per breakpoint
90
- .progressBar {
91
- position: relative;
92
- }
33
+ <div
34
+ {...elementProps?.progressBar}
35
+ className={classNames(
36
+ 'audio-player-progress-bar',
37
+ styles.progressBar,
38
+ elementProps?.progressBar?.className,
39
+ )}
40
+ >
41
+ {/* progress UI */}
42
+ </div>
93
43
  ```
94
44
 
95
- ### How to Identify
96
-
97
- Ask these questions in order:
98
-
99
- 1. **"Would a user want this to vary per breakpoint?"** (mobile vs desktop vs tablet)
100
- - If YES → CSS only, NOT a prop
101
-
102
- 2. **"Does this control WHAT is displayed vs WHICH content to display?"**
103
- - `showProgressBar` → Controls WHAT (layout decision) → CSS only
104
- - `audioUrl` → Specifies WHICH audio file (content) → Prop is OK
105
-
106
- 3. **"Does it change the visual appearance or layout?"**
107
- - `showControls`, `orientation`, `alignment` → Visual/layout → CSS only
108
- - `disabled`, `required`, `autoPlay` → Behavior (not visual) → Props are OK
45
+ Do not interpret this rule as "never conditionally render." Conditional output
46
+ is valid when data, semantics, or runtime behavior requires it—for example an
47
+ empty-state message, a loading branch, or content that does not exist.
109
48
 
110
- **Rule of thumb:** If the prop name starts with `show*`, `hide*`, `display*` → It's CSS-only.
49
+ Behavior-critical visibility may also be a prop when visibility itself changes
50
+ the interaction contract. `pauseButtonVisibility` in an autoplaying component
51
+ is the canonical exception: the editor preview must be able to force the
52
+ play/pause control visible.
111
53
 
112
- **Examples:**
54
+ ## Examples
113
55
 
114
- - ✅ **Visual properties:** Show/hide elements, display modes → CSS only
115
- - ✅ **Layout properties:** Orientation, alignment, spacing variations, flex/grid directions → CSS only
116
- - ❌ **Content properties:** Text, media URLs, links, data → Props are OK
117
- - ❌ **Internationalization:** RTL/LTR (`direction` prop) → Props are OK (not breakpoint-responsive)
56
+ ### Content and Behavior Props
118
57
 
119
- ---
120
-
121
- ## Patterns
122
-
123
- ### Correct: Only Data as Props
124
-
125
- **❌ Wrong — visual properties as props:**
126
-
127
- ```typescript
128
- interface ButtonProps {
129
- showLabel?: boolean; // ❌ Breakpoint-customizable
130
- showIcon?: boolean; // ❌ Breakpoint-customizable
131
- displayMode?: 'icon-only' | 'label-only' | 'both'; // ❌
132
- iconPosition?: 'left' | 'right'; // ❌ Layout
133
- orientation?: 'horizontal' | 'vertical'; // ❌ Layout
134
- }
135
- ```
136
-
137
- **✅ Correct — only data as props:**
138
-
139
- ```typescript
140
- interface ButtonProps {
141
- label: string; // ✅ Content data
142
- icon: VectorArt; // ✅ Content data
143
- }
58
+ ```ts
59
+ export type AudioPlayerProps = {
60
+ title?: string;
61
+ audioUrl?: string;
62
+ disabled?: boolean;
63
+ autoPlay?: boolean;
64
+ };
144
65
  ```
145
66
 
146
- ### Correct: Always Render, Users Control Visibility
147
-
148
- **❌ Wrong — show/hide as props:**
67
+ ### Visual Decisions Kept Out of Props
149
68
 
150
- ```typescript
151
- interface AudioPlayerProps {
152
- showProgressBar?: boolean; // ❌ Layout decision
153
- showVolumeControls?: boolean; // ❌ Layout decision
154
- showTimeDisplay?: boolean; // ❌ Layout decision
155
- showTrackInfo?: boolean; // ❌ Layout decision
156
- }
157
-
158
- // Conditional rendering
159
- {showProgressBar && <div className={styles.progressBar}>...</div>}
69
+ ```ts
70
+ // Do not add these to the public contract:
71
+ // showIcon?: boolean
72
+ // orientation?: 'horizontal' | 'vertical'
73
+ // compact?: boolean
74
+ // hideOnMobile?: boolean
160
75
  ```
161
76
 
162
- **✅ Correct — always render, users control visibility:**
163
-
164
- ```typescript
165
- interface AudioPlayerProps {
166
- audioUrl: string; // ✅ Content data only
167
- title?: string; // ✅ Content data
168
- artist?: string; // ✅ Content data
169
- }
77
+ Define their resting appearance in the CSS Module and expose independently
78
+ editable elements as named parts with global/module classes and `elementProps`
79
+ wiring.
170
80
 
171
- // Always render all elements
172
- <div className={styles.progressBar}>...</div>
173
- <div className={styles.volumeControls}>...</div>
174
- <div className={styles.trackInfo}>...</div>
81
+ ## Checklist
175
82
 
176
- // SCSS: no `display: none` default — visibility is user-controlled per breakpoint
177
- .progressBar {
178
- position: relative;
179
- }
180
- ```
181
-
182
- ---
183
-
184
- ## Common Mistake: Adding Visual Toggle Props
185
-
186
- **❌ Wrong:**
187
-
188
- ```typescript
189
- export interface ButtonProps {
190
- showIcon?: boolean; // ❌ Breakpoint-customizable
191
- iconPosition?: 'left' | 'right'; // ❌ Layout
192
- }
193
- ```
194
-
195
- **✅ Correct:**
196
-
197
- ```typescript
198
- export interface ButtonProps {
199
- label: string;
200
- icon: VectorArt;
201
- // Visual variations via CSS
202
- }
203
- ```
83
+ - [ ] Props represent authored data or stable behavior.
84
+ - [ ] Derived values are computed internally.
85
+ - [ ] Visual and layout choices live in CSS.
86
+ - [ ] Breakpoint visibility uses a named part, not a show/hide prop.
87
+ - [ ] Conditional rendering is used only for real data, semantic, or behavioral branches.