Installation

pnpm dlx shadcn@latest add @cortexcn/toggle-groupUsage
import { ToggleGroup, ToggleGroupItem } from "@/components/toggle-group";Examples
Basic
import { ToggleGroup, ToggleGroupItem } from "@/components/toggle-group"import { BoldIcon, ItalicIcon, UnderlineIcon } from "lucide-react"export function ToggleGroupBasic() { return ( <div className="flex flex-col gap-6"> <ToggleGroup type="multiple" spacing={1}> <ToggleGroupItem value="bold" aria-label="Toggle bold"> <BoldIcon /> </ToggleGroupItem> <ToggleGroupItem value="italic" aria-label="Toggle italic"> <ItalicIcon /> </ToggleGroupItem> <ToggleGroupItem value="underline" aria-label="Toggle underline"> <UnderlineIcon /> </ToggleGroupItem> </ToggleGroup> </div> )}Outline
import { ToggleGroup, ToggleGroupItem } from "@/components/toggle-group"export function ToggleGroupOutline() { return ( <div className="flex flex-col gap-6"> <ToggleGroup variant="outline" type="single" defaultValue="all"> <ToggleGroupItem value="all" aria-label="Toggle all"> All </ToggleGroupItem> <ToggleGroupItem value="missed" aria-label="Toggle missed"> Missed </ToggleGroupItem> </ToggleGroup> </div> )}Outline with icons
import { ToggleGroup, ToggleGroupItem } from "@/components/toggle-group"import { BoldIcon, ItalicIcon, UnderlineIcon } from "lucide-react"export function ToggleGroupOutlineWithIcons() { return ( <div className="flex flex-col gap-6"> <ToggleGroup variant="outline" type="multiple" size="sm"> <ToggleGroupItem value="bold" aria-label="Toggle bold"> <BoldIcon /> </ToggleGroupItem> <ToggleGroupItem value="italic" aria-label="Toggle italic"> <ItalicIcon /> </ToggleGroupItem> <ToggleGroupItem value="underline" aria-label="Toggle underline"> <UnderlineIcon /> </ToggleGroupItem> </ToggleGroup> </div> )}Sizes
import { ToggleGroup, ToggleGroupItem } from "@/components/toggle-group"export function ToggleGroupSizes() { return ( <div className="flex flex-col gap-6"> <div className="flex flex-col gap-4"> <ToggleGroup type="single" size="sm" defaultValue="top" variant="outline" > <ToggleGroupItem value="top" aria-label="Toggle top"> Top </ToggleGroupItem> <ToggleGroupItem value="bottom" aria-label="Toggle bottom"> Bottom </ToggleGroupItem> <ToggleGroupItem value="left" aria-label="Toggle left"> Left </ToggleGroupItem> <ToggleGroupItem value="right" aria-label="Toggle right"> Right </ToggleGroupItem> </ToggleGroup> <ToggleGroup type="single" defaultValue="top" variant="outline"> <ToggleGroupItem value="top" aria-label="Toggle top"> Top </ToggleGroupItem> <ToggleGroupItem value="bottom" aria-label="Toggle bottom"> Bottom </ToggleGroupItem> <ToggleGroupItem value="left" aria-label="Toggle left"> Left </ToggleGroupItem> <ToggleGroupItem value="right" aria-label="Toggle right"> Right </ToggleGroupItem> </ToggleGroup> </div> </div> )}With spacing
import { ToggleGroup, ToggleGroupItem } from "@/components/toggle-group"export function ToggleGroupSpacing() { return ( <div className="flex flex-col gap-6"> <ToggleGroup type="single" size="sm" defaultValue="top" spacing={2}> <ToggleGroupItem value="top" aria-label="Toggle top"> Top </ToggleGroupItem> <ToggleGroupItem value="bottom" aria-label="Toggle bottom"> Bottom </ToggleGroupItem> <ToggleGroupItem value="left" aria-label="Toggle left"> Left </ToggleGroupItem> <ToggleGroupItem value="right" aria-label="Toggle right"> Right </ToggleGroupItem> </ToggleGroup> </div> )}With icons
import { ToggleGroup, ToggleGroupItem } from "@/components/toggle-group"import { BookmarkIcon, HeartIcon, StarIcon } from "lucide-react"export function ToggleGroupWithIcons() { return ( <div className="flex flex-col gap-6"> <ToggleGroup type="multiple" variant="outline" spacing={1} size="sm"> <ToggleGroupItem value="star" aria-label="Toggle star" className="aria-pressed:*:[svg]:stroke-foregfill-foreground aria-pressed:bg-transparent aria-pressed:*:[svg]:fill-foreground" > <StarIcon data-icon="inline-start" /> Star </ToggleGroupItem> <ToggleGroupItem value="heart" aria-label="Toggle heart" className="aria-pressed:bg-transparent aria-pressed:*:[svg]:fill-foreground aria-pressed:*:[svg]:stroke-foreground" > <HeartIcon data-icon="inline-start" /> Heart </ToggleGroupItem> <ToggleGroupItem value="bookmark" aria-label="Toggle bookmark" className="aria-pressed:bg-transparent aria-pressed:*:[svg]:fill-foreground aria-pressed:*:[svg]:stroke-foreground" > <BookmarkIcon data-icon="inline-start" /> Bookmark </ToggleGroupItem> </ToggleGroup> </div> )}Filter
import { ToggleGroup, ToggleGroupItem } from "@/components/toggle-group"export function ToggleGroupFilter() { return ( <div className="flex flex-col gap-6"> <ToggleGroup type="single" defaultValue="all" variant="outline" size="sm"> <ToggleGroupItem value="all" aria-label="All"> All </ToggleGroupItem> <ToggleGroupItem value="active" aria-label="Active"> Active </ToggleGroupItem> <ToggleGroupItem value="completed" aria-label="Completed"> Completed </ToggleGroupItem> <ToggleGroupItem value="archived" aria-label="Archived"> Archived </ToggleGroupItem> </ToggleGroup> </div> )}Date range
import { ToggleGroup, ToggleGroupItem } from "@/components/toggle-group"export function ToggleGroupDateRange() { return ( <div className="flex flex-col gap-6"> <ToggleGroup type="single" defaultValue="today" variant="outline" size="sm" spacing={2} > <ToggleGroupItem value="today" aria-label="Today"> Today </ToggleGroupItem> <ToggleGroupItem value="week" aria-label="This Week"> This Week </ToggleGroupItem> <ToggleGroupItem value="month" aria-label="This Month"> This Month </ToggleGroupItem> <ToggleGroupItem value="year" aria-label="This Year"> This Year </ToggleGroupItem> </ToggleGroup> </div> )}Sort
import { ToggleGroup, ToggleGroupItem } from "@/components/toggle-group"import { ArrowDownIcon, ArrowUpIcon, TrendingUpIcon } from "lucide-react"export function ToggleGroupSort() { return ( <div className="flex flex-col gap-6"> <ToggleGroup type="single" defaultValue="newest" variant="outline" size="sm" > <ToggleGroupItem value="newest" aria-label="Newest"> <ArrowDownIcon data-icon="inline-start" /> Newest </ToggleGroupItem> <ToggleGroupItem value="oldest" aria-label="Oldest"> <ArrowUpIcon data-icon="inline-start" /> Oldest </ToggleGroupItem> <ToggleGroupItem value="popular" aria-label="Popular"> <TrendingUpIcon data-icon="inline-start" /> Popular </ToggleGroupItem> </ToggleGroup> </div> )}With input and select
import { Input } from "@/components/input"import { Select, SelectContent, SelectGroup, SelectItem, SelectTrigger, SelectValue } from "@/components/select"import { ToggleGroup, ToggleGroupItem } from "@/components/toggle-group"export function ToggleGroupWithInputAndSelect() { return ( <div className="flex flex-col gap-6"> <div className="flex items-center gap-2"> <Input type="search" placeholder="Search..." className="flex-1" /> <Select defaultValue="all"> <SelectTrigger className="w-32"> <SelectValue /> </SelectTrigger> <SelectContent> <SelectGroup> <SelectItem value="all">All</SelectItem> <SelectItem value="active">Active</SelectItem> <SelectItem value="archived">Archived</SelectItem> </SelectGroup> </SelectContent> </Select> <ToggleGroup type="single" defaultValue="grid" variant="outline"> <ToggleGroupItem value="grid" aria-label="Grid view"> Grid </ToggleGroupItem> <ToggleGroupItem value="list" aria-label="List view"> List </ToggleGroupItem> </ToggleGroup> </div> </div> )}Vertical
import { ToggleGroup, ToggleGroupItem } from "@/components/toggle-group"import { BoldIcon, ItalicIcon, UnderlineIcon } from "lucide-react"export function ToggleGroupVertical() { return ( <div className="flex flex-col gap-6"> <ToggleGroup type="multiple" orientation="vertical" spacing={2}> <ToggleGroupItem value="bold" aria-label="Toggle bold"> <BoldIcon /> </ToggleGroupItem> <ToggleGroupItem value="italic" aria-label="Toggle italic"> <ItalicIcon /> </ToggleGroupItem> <ToggleGroupItem value="underline" aria-label="Toggle underline"> <UnderlineIcon /> </ToggleGroupItem> </ToggleGroup> </div> )}Vertical outline
import { ToggleGroup, ToggleGroupItem } from "@/components/toggle-group"export function ToggleGroupVerticalOutline() { return ( <div className="flex flex-col gap-6"> <ToggleGroup variant="outline" type="single" defaultValue="all" orientation="vertical" size="sm" > <ToggleGroupItem value="all" aria-label="Toggle all"> All </ToggleGroupItem> <ToggleGroupItem value="active" aria-label="Toggle active"> Active </ToggleGroupItem> <ToggleGroupItem value="completed" aria-label="Toggle completed"> Completed </ToggleGroupItem> <ToggleGroupItem value="archived" aria-label="Toggle archived"> Archived </ToggleGroupItem> </ToggleGroup> </div> )}Vertical outline with icons
import { ToggleGroup, ToggleGroupItem } from "@/components/toggle-group"import { BoldIcon, ItalicIcon, UnderlineIcon } from "lucide-react"export function ToggleGroupVerticalOutlineWithIcons() { return ( <div className="flex flex-col gap-6"> <ToggleGroup variant="outline" type="multiple" orientation="vertical" size="sm" > <ToggleGroupItem value="bold" aria-label="Toggle bold"> <BoldIcon /> </ToggleGroupItem> <ToggleGroupItem value="italic" aria-label="Toggle italic"> <ItalicIcon /> </ToggleGroupItem> <ToggleGroupItem value="underline" aria-label="Toggle underline"> <UnderlineIcon /> </ToggleGroupItem> </ToggleGroup> </div> )}Vertical with spacing
import { ToggleGroup, ToggleGroupItem } from "@/components/toggle-group"export function ToggleGroupVerticalWithSpacing() { return ( <div className="flex flex-col gap-6"> <ToggleGroup type="single" size="sm" defaultValue="top" orientation="vertical" spacing={2} > <ToggleGroupItem value="top" aria-label="Toggle top"> Top </ToggleGroupItem> <ToggleGroupItem value="bottom" aria-label="Toggle bottom"> Bottom </ToggleGroupItem> <ToggleGroupItem value="left" aria-label="Toggle left"> Left </ToggleGroupItem> <ToggleGroupItem value="right" aria-label="Toggle right"> Right </ToggleGroupItem> </ToggleGroup> </div> )}Font weight selector
Use font-normal to set the font weight.
import * as React from "react"import { Field, FieldDescription, FieldLabel } from "@/components/field"import { ToggleGroup, ToggleGroupItem } from "@/components/toggle-group"export function ToggleGroupFontWeightSelector() { const [fontWeight, setFontWeight] = React.useState("normal") return ( <div className="flex flex-col gap-6"> <Field> <FieldLabel>Font Weight</FieldLabel> <ToggleGroup type="single" value={fontWeight} onValueChange={(value) => setFontWeight(value)} variant="outline" spacing={2} size="lg" > <ToggleGroupItem value="light" aria-label="Light" className="flex size-16 flex-col items-center justify-center rounded-xl" > <span className="text-2xl leading-none font-light">Aa</span> <span className="text-xs text-muted-foreground">Light</span> </ToggleGroupItem> <ToggleGroupItem value="normal" aria-label="Normal" className="flex size-16 flex-col items-center justify-center rounded-xl" > <span className="text-2xl leading-none font-normal">Aa</span> <span className="text-xs text-muted-foreground">Normal</span> </ToggleGroupItem> <ToggleGroupItem value="medium" aria-label="Medium" className="flex size-16 flex-col items-center justify-center rounded-xl" > <span className="text-2xl leading-none font-medium">Aa</span> <span className="text-xs text-muted-foreground">Medium</span> </ToggleGroupItem> <ToggleGroupItem value="bold" aria-label="Bold" className="flex size-16 flex-col items-center justify-center rounded-xl" > <span className="text-2xl leading-none font-bold">Aa</span> <span className="text-xs text-muted-foreground">Bold</span> </ToggleGroupItem> </ToggleGroup> <FieldDescription> Use{" "} <code className="rounded-md bg-muted px-1 py-0.5 font-mono"> font-{fontWeight} </code>{" "} to set the font weight. </FieldDescription> </Field> </div> )}Adapted from the shadcn/ui Toggle Group (MIT).
