### Install tw-classed and Radix UI Source: https://tw-classed.vercel.app/docs/guide/using-radix-ui Installs the necessary packages for using tw-classed with Radix UI's progress primitive. ```bash npminstall@radix-ui/react-progress@tw-classed/react ``` -------------------------------- ### Install TW CLASSED React Source: https://tw-classed.vercel.app/docs/installation Installs the @tw-classed/react package using pnpm. This is the first step to using TW CLASSED in your React project. ```bash pnpm add @tw-classed/react ``` -------------------------------- ### Install TW Classed for React Source: https://tw-classed.vercel.app/docs/index Install the TW Classed React package using npm. This is the first step to integrating TW Classed into your React project. ```bash npm install @tw-classed/react ``` -------------------------------- ### Create a Button Component with TW Classed Source: https://tw-classed.vercel.app/docs/api Demonstrates how to use the `classed` function to create a reusable 'Button' component. It includes defining base classes and color variants, and shows examples of how to use the component with and without variant props. ```javascript const Button = classed("button", { base: "", // base classes, variants: { color: { // color variants } } }); // Use it () => // // ``` -------------------------------- ### React: Manual Strict Mode for Specific Variants Source: https://tw-classed.vercel.app/docs/strict-components Allows explicit designation of required variants. This example makes the 'loading' and 'size' variants mandatory for a Button component, while 'color' remains optional. ```javascript import { makeStrict, classed } from"@tw-classed/react"; const Button = classed.button({ base: "px-4 py-2 rounded-md", variants: { color: { primary: "bg-blue-500 text-white", secondary: "bg-gray-500 text-white", }, size: { sm: "text-sm", lg: "text-lg", }, loading: { true: "opacity-50 cursor-progress", }, }, }); export default makeStrict(Button, "loading", "size"); // In your app: // () => ``` -------------------------------- ### Use Default Variants for Button (React) Source: https://tw-classed.vercel.app/docs/guide/writing-clean-classed Explains how to use `defaultVariants` in `tw-classed` to set a default variant for a component, preventing duplicate classes and simplifying usage. The example demonstrates setting a default color for the button. ```TypeScript const Button = classed.button("px-4 py-2", { variants: { color: { primary: "bg-blue-500 text-white", secondary: "bg-black text-white", }, }, defaultVariants: { color: "primary", // Default to primary }, }); // Usage: // () => ; // () => ; ``` -------------------------------- ### Create Responsive Grid Component (React) Source: https://tw-classed.vercel.app/docs/guide/writing-clean-classed Demonstrates how to create a responsive Grid component using `tw-classed` by composing Tailwind CSS classes across multiple arguments. This allows for different grid layouts based on screen size (mobile, tablet, desktop). ```TypeScript const Grid = classed.div( "grid gap-4", // Mobile first "md:grid-cols-2 md:gap-6", // Tablet "lg:grid-cols-3 lg:gap-8", // Desktop "xl:grid-cols-4" // Large desktop ); ``` -------------------------------- ### TW CLASSED React Component Usage Source: https://tw-classed.vercel.app/docs/faq Illustrates how to use TW CLASSED within a React project. The `@tw-classed/react` package provides React components that integrate seamlessly with the library's features. ```JavaScript import React from 'react'; import { classed } from "@tw-classed/react"; const StyledButton = classed('button', { variants: { intent: { primary: 'bg-blue-500 text-white hover:bg-blue-700', danger: 'bg-red-500 text-white hover:bg-red-700', }, size: { medium: 'h-10 px-4', large: 'h-12 px-6', }, }, defaultVariants: { intent: 'primary', size: 'medium', }, }); function MyComponent() { return ( <> Large Primary Button Danger Button ); } export default MyComponent; ``` -------------------------------- ### React: Automatic Strict Mode with Default Variants Source: https://tw-classed.vercel.app/docs/strict-components Enforces required variants based on defaultVariants. If a variant lacks a default, it becomes mandatory. This example shows a Button component where 'size' is required because it has no default, while 'color' is optional due to its default value. ```javascript import { makeStrict, classed } from"@tw-classed/react"; const Button = classed.button({ base: "px-4 py-2 rounded-md", variants: { color: { primary: "bg-blue-500 text-white", secondary: "bg-gray-500 text-white", }, size: { sm: "text-sm", lg: "text-lg", }, }, defaultVariants: { color: "primary", }, }); export default makeStrict(Button); // In your app: // () => // TypeScript will provide auto-completion for 'color' and 'size' props. ``` -------------------------------- ### Create Basic Button Component (React) Source: https://tw-classed.vercel.app/docs/guide/writing-clean-classed Demonstrates two equivalent ways to create a basic button component using `tw-classed` in React. The first method uses a direct string of classes, while the second uses the `classed.button()` shorthand. ```TypeScript import { classed } from"@tw-classed/react"; const Button = classed("button", "px-4 py-2 bg-blue-500 text-white rounded-md"); const Button = classed.button("px-4 py-2 bg-blue-500 text-white rounded-md"); ``` -------------------------------- ### Fix As Prop Usage in Derived Components Source: https://tw-classed.vercel.app/docs/changelog Illustrates how to fix the `As` prop usage within a derived component's render method using `deriveClassed`. This example shows how to explicitly require the `As` generic when manually setting `as` in the render method. If the `As` generic is not manually set, the compiler can infer it. ```typescript deriveClassed((props, ref) => ( )); ``` -------------------------------- ### Rendered Button with Tailwind Merge (React) Source: https://tw-classed.vercel.app/docs/guide/configuring-classed Illustrates the resulting HTML and applied classes for a 'Button' component when using 'tailwind-merge' for class management, highlighting how variants override base styles. ```HTML ``` -------------------------------- ### Nested Components Reacting to Parent Variants via Data Attributes Source: https://tw-classed.vercel.app/docs/data-variants This example illustrates how nested components can react to parent component variants using data attributes. The `LoadingSpinner` component's styling is conditionally applied based on the parent `Button`'s `color` variant using `group-data-[color=dark]:text-white`. ```javascript const Button = classed.button("p-4 group", { variants: { color: { light: "bg-white text-slate-900", dark: "bg-slate-900 text-white", }, dataAttributes: ["color"], }, }); const LoadingSpinner = classed( FiSpinner, "animate-spin rounded-full h-8 w-8 text-slate-900", "group-data-[color=dark]:text-white" // Matches when button is dark variant ); () => { return ( ); }; ``` -------------------------------- ### Import classed from TW CLASSED React Source: https://tw-classed.vercel.app/docs/installation Demonstrates how to import the 'classed' function from the @tw-classed/react package. This function is essential for creating styled components. ```javascript import { classed } from"@tw-classed/react"; ``` -------------------------------- ### Import tw-classed Types in React Source: https://tw-classed.vercel.app/docs/typescript Demonstrates how to import all necessary types from the '@tw-classed/react' library at once for use in your React components. ```TypeScript importtype*as Classed from"@tw-classed/react"; ``` -------------------------------- ### Create CardGrid with Background Color Variant Source: https://tw-classed.vercel.app/docs/guide/writing-clean-classed Shows how to create a CardGrid component that inherits classes and variants from a base Grid component, and adds its own configurable background color variant. This allows for easy customization of the grid's appearance. ```javascript constCardGrid=classed.div( "bg-gray-100 p-4 rounded-md", Grid // Add the Grid component as a child ); () => (
1
2
); ``` -------------------------------- ### Define Button Component with Variants Source: https://tw-classed.vercel.app/docs/index Demonstrates how to create a reusable 'Button' component using TW Classed. It defines size and color variants, compound variants for specific combinations, and default variants for convenience. ```javascript const Button = classed("button", { variants: { size: { sm: "text-sm", md: "text-md", lg: "text-lg", }, color: { primary: "bg-blue-500", secondary: "bg-red-500", }, }, compoundVariants: [ { size: "sm", color: "secondary", class: "px-2 py-1", }, { size: "md", color: "secondary", class: "px-4 py-2", }, ], defaultVariants: { size: "md", color: "primary", }, }); ``` -------------------------------- ### Configure TW Classed with a Custom Merger Source: https://tw-classed.vercel.app/docs/api Shows how to use the `createClassed` function to create a custom classed component with a specific configuration, such as providing a custom merger function for combining class strings. ```typescript type Merger = (...args: string[]) => string; createClassed({ merger: Merger, // The merger function to use when computing all the classes. }); ``` -------------------------------- ### Button Benchmark: React vs tw-classed vs cva vs Stitches Source: https://tw-classed.vercel.app/docs/benchmark Compares the performance of mounting and unmounting a button with variant props across different libraries: native React, tw-classed, class-variance-authority (cva), and stitches.js. The benchmark measures render time in milliseconds, with lower values indicating better performance. Stitches.js, a CSS-in-JS library, is included for comparison despite not being a direct competitor. ```JavaScript Mount button with variants stitches.jstw-classedcvareact00.010.010.010.02render ms. (lower is better) ``` -------------------------------- ### Compose with Non-Classed Components using `as` Prop Source: https://tw-classed.vercel.app/docs/composing-components Demonstrates composing a Classed component (`BaseButton`) with a non-classed component (`react-router-dom`'s `Link`) using the `as` prop. ```javascript import { Link } from"react-router-dom"; import { classed } from"@tw-classed/react"; const BaseButton=classed("button","bg-blue-500 text-white"); () => ( Checkout ); ``` -------------------------------- ### Create Classed Progress Component Source: https://tw-classed.vercel.app/docs/guide/using-radix-ui Binds Radix UI progress primitives with SCSS Module styles using tw-classed to create reusable React components. ```jsx // Progress.jsx import*as ProgressPrimitive from"@radix-ui/react-progress"; import classes from"./Progress.module.scss"; import { classed } from"@tw-classed/react"; constClassedRoot=classed(ProgressPrimitive.Root,classes.root); constClassedIndicator=classed( ProgressPrimitive.Indicator, classes.indicator ); // exports exportconstProgress= ({ value =0 }) => ( ); ``` -------------------------------- ### Create Button without tw-classed using classnames Source: https://tw-classed.vercel.app/docs/guide/with-css-modules Demonstrates creating a Button component using only CSS Modules and the 'classnames' package, highlighting the verbosity compared to tw-classed. It manually toggles classes and lacks an 'as' prop for element remapping. ```TypeScript import classes from"./Button.module.scss"; import cn from"classnames"; import { forwardRef } from "react"; export interface ButtonProps { color?: "primary" | "secondary" | "danger"; } const Button = forwardRef( ({ color, ...props }, ref) => { return ( ``` -------------------------------- ### Core Lib: class/className Support Source: https://tw-classed.vercel.app/docs/changelog Demonstrates how to use the 'class' and 'className' props with a class producer function in the core library. This allows for dynamic class application. ```javascript const button = classed("bg-blue-500"); // LitHTML html``; ``` -------------------------------- ### Organize Button Classes with Multiple Arguments (React) Source: https://tw-classed.vercel.app/docs/guide/writing-clean-classed Illustrates a method for organizing class strings in `tw-classed` by using multiple arguments. This approach separates default styles, responsive adjustments, and interactive states (hover, focus) for better readability and maintainability. ```TypeScript const CardButton = classed.a( "p-4 w-[200px] text-center text-white bg-blue-500 rounded-md", // Defaults "md:p-6 lg:p-8 md:w-[300px] lg:w-[400px]", // Media queries "hover:bg-blue-600 focus:bg-blue-700" // Hover & focus ); ``` -------------------------------- ### Create Derived Components with DerivedComponentType Source: https://tw-classed.vercel.app/docs/typescript Illustrates how to create a derived component by extending a base classed component, overriding its type with `DerivedComponentType` for correct TypeScript `as` prop handling. ```TypeScript import { DerivedComponentType } from"@tw-classed/react"; import { forwardRef } from"react"; import { classed } from"@tw-classed/react"; constBaseButton=classed("button","px-2 py-4", { variants: { color: { blue:"bg-blue-500", red:"bg-red-500", }, }, }); typeBaseButtonProps=React.ComponentProps & { icon?:React.ReactNode; // Add an icon prop }; constButton=forwardRef( ({ icon,...props }, ref) => { return ( {icon && {icon}} {props.children} ); } ) asDerivedComponentType; () => ( Click me ); ``` -------------------------------- ### Create Button Component with Variants and Compound Variants Source: https://tw-classed.vercel.app/docs/changelog Demonstrates how to create a reusable Button component using `classed.button`. It defines base styles, size and color variants, and a compound variant that applies a special class when specific size and color combinations are met. It also shows how to create a new component `GreenButton` that inherits from `Button` and sets a default variant. ```javascript const Button = classed.button({ base: "bg-blue-500 text-white", variants: { size: { sm: "px-2 py-1 text-sm", md: "px-4 py-2 text-base", }, color: { red: "bg-red-500", green: "bg-green-500", }, }, compoundVariants: [ { size: "sm", color: "green", class: "super-special-class-modifyer" }, ], }); const GreenButton = classed(Button, { defaultVariants: { color: "green", // This now triggers the compoundVariant }, }); ``` -------------------------------- ### Create Classed with Tailwind Merge (React) Source: https://tw-classed.vercel.app/docs/guide/configuring-classed Shows how to integrate 'classed' with the 'tailwind-merge' library to enable intelligent merging of Tailwind CSS classes. This is useful for managing class overrides, especially with variants. ```TypeScript // classed.config.ts import { twMerge } from"tailwind-merge"; import { createClassed } from"@tw-classed/react"; exportconst { classed } =createClassed({ merger: twMerge }); ``` -------------------------------- ### TypeScript Configuration Compatibility Source: https://tw-classed.vercel.app/docs/changelog Ensures compatibility with `exactOptionalPropertyTypes: true` in TypeScript configurations. This fix addresses potential type-checking issues for projects with strict TypeScript settings. ```typescript // This change ensures that the library's types are compatible with // TypeScript projects that have exactOptionalPropertyTypes enabled. // No direct code snippet is shown as it's a type-level compatibility fix. ``` -------------------------------- ### TypeScript Interoperability: Core and React Source: https://tw-classed.vercel.app/docs/changelog Shows how to achieve TypeScript interoperability between @tw-classed/core and @tw-classed/react. This enables using a framework-agnostic design system with React applications. ```typescript // Design system import { classed } from "@tw-classed/core"; export const button = classed({ base: "bg-blue-500 text-white", variants: { size: { sm: "px-2 py-1 text-sm", md: "px-3 py-2 text-base", lg: "px-4 py-3 text-lg", }, }, }); // React application import { button } from "design-system"; import { classed } from "@tw-classed/react"; export const Button = classed.button(button); // Variants are automatically inferred ``` -------------------------------- ### Utilize Proxy API for classed Source: https://tw-classed.vercel.app/docs/changelog Adds support for the Proxy API, allowing `classed.button(...args)` syntax. The existing `classed` API remains unchanged and utilizes the proxy internally. This enables more flexible component styling. ```JavaScript import { classed } from "@tw-classed/core"; // Using the new Proxy API const Button = classed.button('px-4 py-2 rounded', { variants: { color: { primary: 'bg-blue-500 text-white', secondary: 'bg-gray-200 text-black' } } }); // Regular classed API usage remains the same const Card = classed('div', { base: 'p-4 border rounded', variants: { shadow: { true: 'shadow-md' } } }); ``` -------------------------------- ### Render Grid Component within Classed Function Source: https://tw-classed.vercel.app/docs/guide/writing-clean-classed Illustrates how to render a Grid component directly within a classed function definition. This approach allows the Grid component's classes and variants to be applied, and the component itself to be rendered, by placing it at the beginning of the classed function arguments. ```javascript constCardGrid=classed( Grid,// Render the Grid component "p-4 rounded-md", { variants: { color: { gray:"bg-gray-500", blue:"bg-blue-500", red:"bg-red-500", }, }, }, ); () => (
1
2
); ``` -------------------------------- ### createClassed API: Extending Functionality Source: https://tw-classed.vercel.app/docs/changelog Introduces the createClassed API, which allows extending the 'classed' function with additional capabilities. Currently, it supports the 'merger' prop. ```javascript // Example usage of createClassed API would go here, but is not provided in the input. ``` -------------------------------- ### Remap Button styles to an 'a' element with tw-classed Source: https://tw-classed.vercel.app/docs/guide/with-css-modules Shows how to create a new component (Link) that inherits the styles of the Button component but renders as an 'a' element using tw-classed. This promotes style reuse and flexibility. ```TypeScript // Link.tsx // ... import { Button } from"./Button"; export const Link = classed("a", Button); ``` ```React Primary ``` -------------------------------- ### Core: Support deriveClassed and makeStrict Source: https://tw-classed.vercel.app/docs/changelog Adds support for two new functionalities: `deriveClassed` and `makeStrict`. This update also includes internal core typing updates to ensure compatibility with these new features. ```javascript // Adds support for `deriveClassed` & `makeStrict`. // Updated core internal typing for compatibility. ``` -------------------------------- ### Extend Progress Component with Variants Source: https://tw-classed.vercel.app/docs/guide/using-radix-ui Enhances the classed progress bar by adding variants for the indicator color, controlled by tw-classed. ```jsx // Progress.jsx // ... constClassedIndicator=classed( ProgressPrimitive.Indicator, classes.indicator, { variants: { color: { blue:"!bg-blue-500", purple:"!bg-purple-500", }, }, defaultVariants: { color:"blue", }, } ); // exports exportconstProgress= ({ value =0, color }) => ( ); ``` -------------------------------- ### Add Configurable Color Variants to CardGrid Source: https://tw-classed.vercel.app/docs/guide/writing-clean-classed Extends the CardGrid component to include configurable color variants. This allows developers to easily change the background color of the grid by passing a color prop, such as 'red', 'blue', or 'gray'. ```javascript constCardGrid=classed.div( "p-4 rounded-md", Grid,// Inherit the Grid's classes and variants { variants: { color: { gray:"bg-gray-500" blue: "bg-blue-500", red:"bg-red-500", }, }, } ); () => (
1
2
); ``` -------------------------------- ### Rendered Button without Tailwind Merge (React) Source: https://tw-classed.vercel.app/docs/guide/configuring-classed Shows the potential HTML output for a 'Button' component without 'tailwind-merge', where class order might lead to unexpected style application or duplication. ```HTML ``` -------------------------------- ### Retrieve Variant Configuration from a Component Source: https://tw-classed.vercel.app/docs/api Illustrates how to use the `getVariantConfig` function to extract the variant configuration from a component previously created with `classed`. This allows programmatic access to variant definitions. ```javascript const Button = classed("button", { variants: { color: { blue: "bg-blue-500", }, }, }); const { variants } = getVariantConfig(Button); variants.color.blue; // "bg-blue-500" ``` -------------------------------- ### Experimental: Manually support 'as' prop with deriveClassed Source: https://tw-classed.vercel.app/docs/derived-components This snippet shows an experimental feature of `deriveClassed` that allows manual control over the `as` prop within the render function. It requires specifying the `as` prop type as a generic argument to `deriveClassed` for correct type inference. ```typescript import { classed, deriveClassed, ComponentProps } from "@tw-classed/react"; // Assuming ButtonBase is defined as in the previous example // const ButtonBase = classed.button({...}); // export type ButtonProps = ComponentProps & { icon?: React.ReactNode }; export const Anchor = deriveClassed( ({ children, icon, ...rest }, ref) => { return ( {icon && {icon}} {children} ); } ); // Usage: // }> // Go to Home // ``` -------------------------------- ### Create Compound Variants Source: https://tw-classed.vercel.app/docs/variants Demonstrates how to define compound variants, which apply styles based on combinations of other variants. This is achieved using an array of variant conditions and associated class names. ```javascript constButton=classed("button", { variants: { color: { primary:"text-white bg-blue-500", secondary:"text-white bg-gray-700", }, size: { small:"py-2 px-4", medium:"py-3 px-6", large:"py-4 px-8", }, }, compoundVariants: [ { size:"small", color:"primary", class:"rounded",// Classes when both size and color are small and primary will be applied className:"",// This is also supported if you prefer to use className }, ], }); () => ( Button ); ``` -------------------------------- ### Support compoundVariants and base property Source: https://tw-classed.vercel.app/docs/changelog Enhances the configuration object with full support for `compoundVariants` and the `base` property. This allows for more complex styling rules and defining default styles. ```JavaScript import { classed } from "@tw-classed/core"; const Alert = classed('div', { base: 'p-4 rounded', variants: { status: { info: 'bg-blue-100 text-blue-800', warning: 'bg-yellow-100 text-yellow-800' }, variant: { solid: 'font-bold', outline: 'border-2' } }, compoundVariants: [ { status: 'info', variant: 'outline', class: 'border-blue-300' }, { status: 'warning', variant: 'solid', class: 'bg-yellow-500 text-white' } ] }); ``` -------------------------------- ### Create Classed with Custom Merger (React) Source: https://tw-classed.vercel.app/docs/guide/configuring-classed Demonstrates how to create a custom merger function for 'classed' that removes duplicate class names using a JavaScript Set. This configuration is applied via the `createClassed` method. ```TypeScript // classed.config.ts import { createClassed } from"@tw-classed/react"; // custom merger that removes duplicates using Set const customMerger= (...classes:string[]) => Array.from(newSet(classes)).join(" "); exportconst { classed } =createClassed({ merger: customMerger }); ``` -------------------------------- ### Remap Button element using 'as' prop with tw-classed Source: https://tw-classed.vercel.app/docs/guide/with-css-modules Illustrates using the 'as' prop with tw-classed to dynamically change the rendered element of a component (e.g., Button) to an 'a' tag while retaining its styles and props. ```React import { Button } from"./Button"; () => ( ); ``` -------------------------------- ### Compose BaseButton with Variants and DefaultVariants Source: https://tw-classed.vercel.app/docs/composing-components Demonstrates composing a `BaseButton` component into a `CheckoutButton`. The `CheckoutButton` inherits all properties from `BaseButton` and adds its own styling, variants for size, and default variants for disabled state. ```javascript import { classed } from"@tw-classed/react"; const BaseButton=classed("button"); const CheckoutButton=classed( BaseButton, "bg-blue-500 text-white font-bold py-2 px-4 rounded", { variants: { size: { sm:"text-sm", lg:"text-lg", }, }, defaultVariants: { disabled:"opacity-50 cursor-not-allowed", }, } ); () => ( <> Base Button Checkout Button ); ```