"use client"; import { useState } from "react"; import RuleCard from "../components/RuleCard"; import Chip from "../components/Chip"; import MultiSelect from "../components/MultiSelect"; import Image from "next/image"; import { getAssetPath } from "../../lib/assetUtils"; interface ChipData { id: string; label: string; state: "Unselected" | "Selected" | "Custom"; palette: "Default" | "Inverse"; size: "S" | "M"; } // MultiSelect example component with state management function MultiSelectExample({ size }: { size: "S" | "M" }) { const [options, setOptions] = useState([ { id: "1", label: "1 member", state: "Unselected" as const }, { id: "2", label: "2-10 members", state: "Unselected" as const }, { id: "3", label: "10-24 members", state: "Unselected" as const }, { id: "4", label: "24-64 members", state: "Unselected" as const }, { id: "5", label: "64-128 members", state: "Unselected" as const }, { id: "6", label: "125-1000 members", state: "Unselected" as const }, { id: "7", label: "1000+ members", state: "Unselected" as const }, ]); const handleChipClick = (chipId: string) => { setOptions((prev) => prev.map((opt) => opt.id === chipId ? { ...opt, state: opt.state === "Selected" ? ("Unselected" as const) : ("Selected" as const), } : opt ) ); }; const handleAddClick = () => { const newId = `custom-${Date.now()}`; setOptions((prev) => [ ...prev, { id: newId, label: "", state: "Custom" as const }, ]); }; const handleCustomConfirm = (chipId: string, value: string) => { setOptions((prev) => prev.map((opt) => opt.id === chipId ? { ...opt, label: value, state: "Selected" as const } : opt ) ); }; const handleCustomClose = (chipId: string) => { setOptions((prev) => prev.filter((opt) => opt.id !== chipId)); }; return (

{size === "S" ? "Small (S)" : "Medium (M)"}

); } export default function ComponentsPreview() { const [expandedCard, setExpandedCard] = useState(null); const [chipStates, setChipStates] = useState>({ "default-s": "Unselected", "default-m": "Unselected", "inverse-s": "Unselected", "inverse-m": "Unselected", }); // Manage custom chips separately const [customChips, setCustomChips] = useState([ { id: "custom-1", label: "", state: "Custom", palette: "Default", size: "S" }, { id: "custom-2", label: "", state: "Custom", palette: "Default", size: "M" }, ]); const sampleCategories = [ { name: "Values", items: ["Consciousness", "Ecology", "Abundance", "Art", "Decisiveness"], createUrl: "/create/value", }, { name: "Communication", items: ["Signal"], createUrl: "/create/communication", }, { name: "Membership", items: ["Open Admission"], createUrl: "/create/membership", }, { name: "Decision-making", items: ["Lazy Consensus", "Modified Consensus"], createUrl: "/create/decision-making", }, { name: "Conflict management", items: ["Code of Conduct", "Restorative Justice"], createUrl: "/create/conflict-management", }, ]; return (

Component Preview

RuleCard and Chip component examples - states, palettes, sizes, and interactions

{/* Chip Component - Controls */}

Chip Component (Controls)

{/* Default palette */}

Default palette

setChipStates((prev) => ({ ...prev, "default-s": prev["default-s"] === "Selected" ? "Unselected" : "Selected", })) } /> setChipStates((prev) => ({ ...prev, "default-m": prev["default-m"] === "Selected" ? "Unselected" : "Selected", })) } /> {customChips .filter((chip) => chip.palette === "Default") .map((chip) => ( { e.stopPropagation(); setCustomChips((prev) => prev.map((c) => c.id === chip.id ? { ...c, label: value, state: "Selected" as const } : c ) ); }} onClose={(e) => { e.stopPropagation(); setCustomChips((prev) => prev.filter((c) => c.id !== chip.id)); }} onClick={(e) => { e.stopPropagation(); // Only toggle if the chip is in Selected or Unselected state (not Custom) if (chip.state === "Selected" || chip.state === "Unselected") { setCustomChips((prev) => prev.map((c) => c.id === chip.id ? { ...c, state: c.state === "Selected" ? ("Unselected" as const) : ("Selected" as const), } : c ) ); } }} /> ))} {/* Add new custom chip button - Ghost button style */}
{/* Inverse palette - on white background */}

Inverse palette (on white background)

setChipStates((prev) => ({ ...prev, "inverse-s": prev["inverse-s"] === "Selected" ? "Unselected" : "Selected", })) } /> setChipStates((prev) => ({ ...prev, "inverse-m": prev["inverse-m"] === "Selected" ? "Unselected" : "Selected", })) } />
{/* Collapsed State - Large */}

Collapsed State - Large (L)

console.log("Card clicked: Mutual Aid Mondays")} />
{/* Collapsed State - Medium */}

Collapsed State - Medium (M)

console.log("Card clicked: Mutual Aid Mondays")} />
{/* Expanded State - Large */}

Expanded State - Large (L)

{ console.log(`Pill clicked: ${category} - ${item}`); }} onCreateClick={(category) => { console.log(`Create clicked: ${category}`); }} onClick={() => console.log("Card clicked: Mutual Aid Mondays")} />
{/* Expanded State - Medium */}

Expanded State - Medium (M)

{ console.log(`Pill clicked: ${category} - ${item}`); }} onCreateClick={(category) => { console.log(`Create clicked: ${category}`); }} onClick={() => console.log("Card clicked: Mutual Aid Mondays")} />
{/* Different Background Colors */}

Different Background Colors

} onClick={() => console.log("Consensus clusters selected")} /> } onClick={() => console.log("Consensus selected")} />
{/* Logo Fallback */}

Logo Fallback (Community Initials)

console.log("Community Example selected")} />
{/* MultiSelect Component */}

MultiSelect Component (Controls)

{/* Small size */} {/* Medium size */}
); }