AI Citations
hextaui/ai-citationsFreeComponent
Display citations and sources with collapsible source previews.
Install it
npx shadcn@latest add https://hextaui.com/r/ai-citations.jsonSource
1"use client";23import {4 ChevronDown,5 ExternalLink,6 FileText,7 Globe,8 Quote,9} from "lucide-react";10import { useCallback, useMemo, useState } from "react";11import { cn } from "@/lib/utils";12import {13 Collapsible,14 CollapsibleContent,15 CollapsibleTrigger,16} from "@/registry/new-york/ui/collapsible";17import {18 Empty,19 EmptyDescription,20 EmptyHeader,21 EmptyMedia,22 EmptyTitle,23} from "@/registry/new-york/ui/empty";2425export interface CitationSource {26 id: string;27 title: string;28 url: string;29 domain?: string;30 snippet?: string;31 author?: string;32 publishedAt?: Date;33 type?: "web" | "document" | "paper" | "other";34}3536export interface Citation {37 id: string;38 number: number;39 sources: CitationSource[];40 text?: string;41}4243export interface AICitationsProps {44 citations: Citation[];45 className?: string;46 defaultExpanded?: boolean;47 showInlineNumbers?: boolean;48 onSourceClick?: (source: CitationSource) => void;49}5051const SOURCE_ICONS: Record<52 NonNullable<CitationSource["type"]>,53 React.ComponentType<{ className?: string }>54> = {55 document: FileText,56 paper: FileText,57 web: Globe,58 other: Globe,59};6061function formatDomain(url: string): string {62 try {63 const urlObj = new URL(url);64 return urlObj.hostname.replace(/^www\./, "");65 } catch {66 return url;67 }68}6970function formatDate(date: Date): string {71 const months = [72 "Jan",73 "Feb",74 "Mar",75 "Apr",76 "May",77 "Jun",78 "Jul",79 "Aug",80 "Sep",81 "Oct",82 "Nov",83 "Dec",84 ];85 const month = months[date.getMonth()];86 const day = date.getDate();87 const year = date.getFullYear();88 return `${month} ${day}, ${year}`;89}9091interface CitationNumberProps {92 number: number;93 onClick?: () => void;94 className?: string;95 asButton?: boolean;96 "aria-label"?: string;97}9899function CitationNumber({100 number,101 onClick,102 className,103 asButton = true,104 "aria-label": ariaLabel,105}: CitationNumberProps) {106 const baseClassName = cn(107 "inline-flex items-center justify-center rounded-full border bg-primary/10 font-mono font-semibold text-primary text-xs transition-colors",108 "size-6 min-h-6 min-w-6 md:size-[24px] md:min-h-[24px] md:min-w-[24px]",109 asButton &&110 onClick &&111 "cursor-pointer [-webkit-tap-highlight-color:transparent] hover:bg-primary/20 focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-primary focus-visible:ring-offset-2 active:bg-primary/30",112 !asButton && "pointer-events-none",113 className114 );115116// … truncated
What it pulls in
Other registry items
Files it writes
More from HextaUI
All 139 items| Component | Registry | Kind | Access | Installs | Command |
|---|---|---|---|---|---|
| Accordionaccordion | HextaUI | Components | Free | 1 dep | |
| AI Chat Historyai-chat-history | HextaUI | Components | Free | no deps | |
| AI Conversationai-conversation | HextaUI | Components | Free | no deps | |
| AI Error Handlerai-error-handler | HextaUI | Components | Free | no deps | |
| AI File Uploadai-file-upload | HextaUI | Components | Free | no deps | |
| AI Messageai-message | HextaUI | Components | Free | 4 deps | |
| AI Model Selectorai-model-selector | HextaUI | Components | Free | no deps | |
| AI Prompt Inputai-prompt-input | HextaUI | Components | Free | no deps |
