Todos os componentes

Checkbox

Checkbox é um componente de formulário para React e Tailwind CSS, da biblioteca SmoothUI, com licença MIT. Copia e cola no teu projeto.

SmoothUI MIT forms

O que é

Checkbox é um componente de formulário para React e Tailwind CSS, da biblioteca SmoothUI, com licença MIT. Copia e cola no teu projeto.

Como usar

Abre o componente no catálogo, carrega em copiar, e cola no teu projeto. O prompt copiado leva o código e as regras para o teu agente o reproduzir sem alterar nada.

Abrir no catálogo

Cinco cópias grátis por mês. Sem cartão.

Precisa de

npm i motion radix-ui

Licença

Este componente vem de SmoothUI e é redistribuído sob a licença MIT, que permite uso comercial. O aviso de copyright viaja com o código.

Checkbox

index.tsx
"use client";

import { cn } from "@/lib/utils";
import { AnimatePresence, motion, useReducedMotion } from "motion/react";
import { Checkbox as CheckboxPrimitive } from "radix-ui";
import { SPRING_DEFAULT } from "@/components/smoothui/lib/animation";

export interface CheckboxProps {
  /** Whether the checkbox is checked */
  checked?: boolean;
  /** Optional CSS class */
  className?: string;
  /** Whether the checkbox is disabled */
  disabled?: boolean;
  /** ID for label association */
  id?: string;
  /** Whether the checkbox is in an indeterminate state */
  indeterminate?: boolean;
  /** Accessible name for the checkbox */
  name?: string;
  /** Callback when the checked state changes */
  onCheckedChange?: (checked: boolean) => void;
  /** Whether the checkbox is required */
  required?: boolean;
  /** Value attribute for form submission */
  value?: string;
}

const CheckmarkPath = motion.path;
const MotionSvg = motion.svg;

export default function Checkbox({
  checked = false,
  indeterminate = false,
  onCheckedChange,
  disabled = false,
  className,
  name,
  value,
  id,
  required,
}: CheckboxProps) {
  const shouldReduceMotion = useReducedMotion();

  const derivedState = indeterminate
    ? "indeterminate"
    : checked
      ? "checked"
      : "unchecked";

  const handleChange = (state: boolean | "indeterminate") => {
    if (state === "indeterminate") {
      return;
    }
    onCheckedChange?.(state);
  };

  return (
    <CheckboxPrimitive.Root
      aria-checked={indeterminate ? "mixed" : checked}
      checked={indeterminate ? "indeterminate" : checked}
      className={cn(
        "peer size-4 shrink-0 rounded-[4px] border border-input shadow-xs outline-none transition-shadow focus-visible:border-ring focus-visible:ring-[3px] focus-visible:ring-ring/50 disabled:cursor-not-allowed disabled:opacity-50 aria-invalid:border-destructive aria-invalid:ring-destructive/20 data-[state=checked]:border-foreground data-[state=indeterminate]:border-foreground data-[state=checked]:bg-foreground data-[state=indeterminate]:bg-foreground data-[state=unchecked]:bg-background data-[state=checked]:text-background data-[state=indeterminate]:text-background dark:data-[state=unchecked]:bg-input/30 dark:aria-invalid:ring-destructive/40",
        className
      )}
      data-slot="checkbox"
      disabled={disabled}
      id={id}
      name={name}
      onCheckedChange={handleChange}
      required={required}
      value={value}
    >
      <CheckboxPrimitive.Indicator
        className="grid place-content-center text-current"
        data-slot="checkbox-indicator"
        forceMount
      >
        <AnimatePresence mode="wait">
          {derivedState === "checked" && (
            <MotionSvg
              animate={
                shouldReduceMotion ? { opacity: 1 } : { opacity: 1, scale: 1 }
              }
              className="size-3.5"
              exit={
                shouldReduceMotion
                  ? { opacity: 0, transition: { duration: 0 } }
                  : { opacity: 0, scale: 0.8 }
              }
              fill="none"
              initial={
                shouldReduceMotion ? { opacity: 1 } : { opacity: 0, scale: 0.8 }
              }
              key="check"
              stroke="currentColor"
              strokeLinecap="round"
              strokeLinejoin="round"
              strokeWidth={3}
              transition={shouldReduceMotion ? { duration: 0 } : SPRING_DEFAULT}
              viewBox="0 0 24 24"
            >
              <title>Checked</title>
              <CheckmarkPath
                animate={shouldReduceMotion ? {} : { pathLength: 1 }}
                d="M20 6L9 17l-5-5"
                initial={shouldReduceMotion ? {} : { pathLength: 0 }}
                transition={
                  shouldReduceMotion
                    ? { duration: 0 }
                    : { ...SPRING_DEFAULT, delay: 0.05 }
                }
              />
            </MotionSvg>
          )}
          {derivedState === "indeterminate" && (
            <MotionSvg
              animate={
                shouldReduceMotion ? { opacity: 1 } : { opacity: 1, scale: 1 }
              }
              className="size-3.5"
              exit={
                shouldReduceMotion
                  ? { opacity: 0, transition: { duration: 0 } }
                  : { opacity: 0, scale: 0.8 }
              }
              fill="none"
              initial={
                shouldReduceMotion ? { opacity: 1 } : { opacity: 0, scale: 0.8 }
              }
              key="indeterminate"
              stroke="currentColor"
              strokeLinecap="round"
              strokeLinejoin="round"
              strokeWidth={3}
              transition={shouldReduceMotion ? { duration: 0 } : SPRING_DEFAULT}
              viewBox="0 0 24 24"
            >
              <title>Indeterminate</title>
              <CheckmarkPath
                animate={shouldReduceMotion ? {} : { pathLength: 1 }}
                d="M5 12h14"
                initial={shouldReduceMotion ? {} : { pathLength: 0 }}
                transition={
                  shouldReduceMotion
                    ? { duration: 0 }
                    : { ...SPRING_DEFAULT, delay: 0.05 }
                }
              />
            </MotionSvg>
          )}
        </AnimatePresence>
      </CheckboxPrimitive.Indicator>
    </CheckboxPrimitive.Root>
  );
}

Componentes parecidos