Skip to main content

react

React patterns with destructured props, compiler optimization, Effects, and Tailwind v4 syntax. ALWAYS use when using React.

Informations de source

Dépôt
udecode/plate
Dernière activité de la source
1 juin 2026 à 17:16
Langue détectée de SKILL.md
anglais
Étoiles
16 651
Forks
993

Options d'installation

Le prompt qui vérifie d'abord la source est sélectionné par défaut. Vous pouvez passer à une commande directe ou télécharger une copie locale.

Vérifiez les fichiers source

Lisez SKILL.md et les fichiers associés affichés par SkillsMP avant de décider de l'installer.

Affichage de SKILL.md

SKILL.md
Instructions source · Aperçu en lecture seule
description
React patterns with destructured props, compiler optimization, Effects, and Tailwind v4 syntax. ALWAYS use when using React.
name
react
metadata
{"skiller":{"source":".agents/rules/react.mdc"}}
## Requirements - Always use destructured props in function parameters - Define TypeScript types inline with the destructured props - Avoid creating separate interfaces for component props - Avoid non-destructured props that require additional destructuring inside the component - Use available UI components from the component library - Use CSS variables from globals.css for consistent theming - Use Tailwind v4 syntax (see [Tailwind v4 Syntax](#tailwind-v4-syntax)) - DO NOT add icon margin in Button, DropdownMenuItem: use gap-2 instead - Use `useEffectEvent` to extract non-reactive logic from Effects (see [Separating Events from Effects](#separating-events-from-effects)) - NEVER suppress the dependency linter with `eslint-disable` - use `useEffectEvent` instead - Use custom breakpoint syntax for responsive design (see [App-Specific Rules](#app-specific-rules)) ## Tailwind v4 Syntax - **Inline opacity**: Use `/` for opacity (`bg-black/50 text-white/80`) - v3: `bg-black bg-opacity-50 text-white text-opacity-80` - Removed: `bg-opacity-*`, `text-opacity-*`, `border-opacity-*` - **Renamed utilities**: `shadow-sm` → `shadow-xs`, `rounded-sm` → `rounded-xs`, `blur-sm` → `blur-xs` - **CSS variables**: Use parentheses `bg-(--brand-color)` instead of brackets `bg-[--brand-color]` - **Important modifier**: Exclamation mark at the end (`size-5!`) instead of beginning (`!size-5`) - **Descendant selectors**: Use `**:` for all descendants (replaces `[&_*]:`) and `*:` for direct children (replaces `[&>*]:`) - All descendants: `**:px-4` instead of `[&_*]:px-4` - Direct children: `*:px-4` instead of `[&>*]:px-4` - Element filtering: `*:[a]:underline` instead of `[&>a]:underline`, `**:[a]:underline` instead of `[&_a]:underline` - Data attributes: `*:data-[slot=field-label]:flex-auto` instead of `*:[[data-slot=field-label]]:flex-auto`. Keep `[[data-...]]` if there are other selectors. - Context-aware (in-): `in-data-[slot=tooltip-content]:text-background` instead of `[[data-slot=tooltip-content]_&]:text-background` - **Composable variants**: Chain variants together (`group-has-data-selected:opacity-100`, `data-highlighted:ring-2`) - **Canonical classes**: Always prefer built-in utilities over arbitrary values (e.g., `w-full` instead of `w-[100%]`, `translate-x-full` instead of `translate-x-[100%]`) - **Default changes**: Border color now `currentColor` (was `gray-200`), ring width now 1px (was 3px) # Component Patterns ## Design Tokens Design tokens are semantic CSS variables that separate theme, context, and usage. Rather than hardcoding colors, use a semantic naming convention that creates layers of abstraction. ### Variable Architecture ```css @theme inline { --color-background: var(--background); --color-foreground: var(--foreground); --color-primary: var(--primary); --color-primary-foreground: var(--primary-foreground); } :root { --background: oklch(1 0 0); --foreground: oklch(0.145 0 0); --primary: oklch(0.205 0 0); --primary-foreground: oklch(0.985 0 0); } .dark { --background: oklch(0.145 0 0); --foreground: oklch(0.985 0 0); --primary: oklch(0.922 0 0); --primary-foreground: oklch(0.205 0 0); } ``` Common tokens: - `--background` - Page background color - `--foreground` - General text color - `--primary` - Main brand color - `--primary-foreground` - Text color against primary This creates a maintainable, flexible system that scales across applications. ## Data Attribute Styling Patterns Shadcn/ui and Radix UI components use data attributes (`data-state`, `data-slot`) to enable flexible styling without prop explosion. Use these patterns when working with components that expose data attributes. ### Styling with data-state Components expose their state through `data-state` attributes. Use Tailwind's arbitrary variant syntax to style based on component state: ```tsx <Dialog className={cn( // Base styles "rounded-lg border p-4", // State-based styles "data-[state=open]:animate-in data-[state=open]:fade-in", "data-[state=closed]:animate-out data-[state=closed]:fade-out", // Multiple attributes "data-[state=open][data-side=top]:slide-in-from-top-2", )} /> ``` For commonly-used states, extend Tailwind's configuration: ```js title="tailwind.config.js" module.exports = { theme: { extend: { data: { open: 'state="open"', closed: 'state="closed"', active: 'state="active"', }, }, }, }; ``` Then use shorthand: ```tsx <Dialog className="data-open:opacity-100 data-closed:opacity-0" /> ``` ### Radix UI Data Attributes Radix UI automatically applies data attributes to its primitives: ```tsx import * as Dialog from "@radix-ui/react-dialog"; <Dialog.Root> <Dialog.Trigger /> <Dialog.Portal> {/* Radix automatically adds data-state="open" | "closed" */} <Dialog.Overlay className="data-[state=open]:animate-in data-[state=closed]:animate-out" /> <Dialog.Content className="data-[state=open]:fade-in data-[state=closed]:fade-out" /> </Dialog.Portal> </Dialog.Root>; ``` Common Radix data attributes: - `data-state` - open/closed, active/inactive, on/off - `data-side` - top/right/bottom/left (for positioned elements) - `data-align` - start/center/end (for positioned elements) - `data-orientation` - horizontal/vertical - `data-disabled` - present when disabled - `data-placeholder` - present when showing placeholder ### Common State Patterns Use data attributes for all kinds of component state: ```tsx // Open/closed state <Accordion data-state={isOpen ? 'open' : 'closed'} /> // Selected state <Tab data-state={isSelected ? 'active' : 'inactive'} /> // Disabled state (in addition to disabled attribute) <Button data-disabled={isDisabled} disabled={isDisabled} /> // Loading state <Button data-loading={isLoading} /> // Orientation <Slider data-orientation="horizontal" /> // Side/position <Tooltip data-side="top" /> ``` ### Using data-slot for Component Targeting Components use `data-slot` attributes for stable identifiers that can be targeted by parents. **Using `has-[]` for parent-aware styling:** ```tsx <form data-slot="form" className={cn( "space-y-4", // Adjust spacing when specific slots are present "has-[>[data-slot=form-section]]:space-y-6", "has-[>[data-slot=inline-fields]]:space-y-2", // Style based on slot states "has-[[data-slot=submit-button][data-loading=true]]:opacity-50", )} > {children} </form> ``` **Using `[&_]` for descendant targeting:** ```tsx <div data-slot="card" className={cn( "rounded-lg border p-4", // Target any descendant with data-slot "[&_[data-slot=card-header]]:mb-4", "[&_[data-slot=card-title]]:text-lg [&_[data-slot=card-title]]:font-semibold", "[&_[data-slot=card-description]]:text-muted-foreground [&_[data-slot=card-description]]:text-sm", "[&_[data-slot=card-footer]]:mt-4 [&_[data-slot=card-footer]]:border-t [&_[data-slot=card-footer]]:pt-4", )} > {children} </div> ``` ### Global CSS with data-slot Use global CSS for theme-wide component styling: ```css title="globals.css" /* Style all buttons within forms */ [data-slot="form"] [data-slot="button"] { @apply w-full @xl:w-auto; } /* Style submit buttons specifically */ [data-slot="form"] [data-slot="submit-button"] { @apply bg-primary text-primary-foreground; } /* Adjust inputs within inline layouts */ [data-slot="inline-fields"] [data-slot="input"] { @apply flex-1; } /* Style based on state combinations */ [data-slot="dialog"][data-state="open"] [data-slot="dialog-content"] { @apply animate-in fade-in; } ``` ### data-slot Naming Conventions Follow these conventions for consistent `data-slot` naming: 1. **Use kebab-case** - `data-slot="form-field"` not `data-slot="formField"` 2. **Be specific** - `data-slot="submit-button"` not `data-slot="button"` 3. **Match component purpose** - Name reflects what it does, not how it looks 4. **Avoid implementation details** - `data-slot="user-avatar"` not `data-slot="rounded-image"` ```tsx // ✅ Good examples data-slot="search-input" data-slot="navigation-menu" data-slot="error-message" data-slot="submit-button" data-slot="card-header" // ❌ Avoid data-slot="input" // Too generic data-slot="blueButton" // Includes styling data-slot="div-wrapper" // Implementation detail data-slot="mainContent" // Use kebab-case ``` ### When to Use Data Attributes vs Props **Use `data-state` for:** - Visual states (open/closed, active/inactive, loading) - Layout states (orientation, side, alignment) - Interaction states (hover, focus, disabled when styling children) **Use `data-slot` for:** - Component identification with stable identifiers - Parent-child composition patterns - Theme-wide component styling - Variant-independent targeting **Use props for:** - Variants (primary, secondary, destructive) - Sizes (sm, md, lg) - Behavioral configuration (controlled/uncontrolled, defaults) - Event handlers (onClick, onChange) **Combined example:** ```tsx const Button = ({ variant = 'primary', size = 'md', loading, disabled, className, ...props }) => ( <button data-slot="button" data-loading={loading} data-disabled={disabled} className={cn(buttonVariants({ variant, size }), className)} disabled={disabled} {...props} /> ); // Usage <Button variant="primary" size="lg">Submit</Button> <form className="[&_[data-slot=button]]:w-full"><Button>Submit</Button></form> <Button loading={isLoading} className="data-[loading=true]:opacity-50">Submit</Button> ``` # React Compiler ## Context This project uses React Compiler, which automatically optimizes your React code through automatic memoization at build time. Manual memoization with `useMemo`, `useCallback`, and `React.memo` is rarely needed and often introduces unnecessary complexity. ## Core Principle **Write clean, idiomatic React code. Let the compiler optimize it.** React Compiler automatically applies optimal memoization based on data flow analysis. It can even optimize cases that manual memoization cannot handle, such as memoizing values after conditional returns or within complex control flow. ## Requirements ### DO NOT Use Manual Memoization - **NEVER** wrap components with `React.memo` unless you have a specific, documented reason - **NEVER** use `useMemo` for performance optimization - the compiler handles this - **NEVER** use `useCallback` for performance optimization - the compiler handles this
Voir sur GitHub
Ce SKILL.md est tres volumineux, SkillsMP affiche donc ici seulement la premiere section. Voir sur GitHub