mtversemtverseui
Main homepage

MENU

UI ElementsFormsTablesChartsAdvanced UIExtended UI
EcommerceAnalyticsMarketingCRMStocksSaaSLogisticsAINEWSalesNEWFinanceNEW
Text GeneratorImage GeneratorCode Generator
ProductsOrdersCustomersInvoicesTransactionsCoupons
CalendarChatEmailTasksFile ManagerSupport
World MapRoute MapDensity Map
ProfileSettingsPricingFAQAPI KeysIntegrationsActivity LogNotificationsTeamSuccessBlank Page404 Error500 Error503 ErrorComing SoonMaintenance
Sign InSign UpForgot Password
Arun Pandian

Arun Pandian

arun@mtverse.io

⌘K
UI Elements/Popovers

Popovers

Source Free

Popover components for displaying rich content panels triggered by click or hover.

src/components/mtverse/ui-elements/index.tsx
tsx
1'use client';
2import { useState, useEffect, type ReactNode } from 'react';
3import Link from 'next/link';
4import { Trash2, Code2 } from 'lucide-react';
5
6function SectionCard({ title, sourceSlug, children }: { title: string; sourceSlug?: string; children: ReactNode }) {
7  return (
8    <div>
9      <div className="mb-3 flex flex-wrap items-center justify-between gap-2">
10        <h3 className="text-theme-xl font-semibold text-gray-800 dark:text-white/90">{title}</h3>
11        {sourceSlug && (
12          <Link
13            href={sourceSlug}
14            className="inline-flex items-center gap-1.5 rounded-lg px-3 py-1.5 text-xs font-medium text-brand-500 transition-colors hover:bg-brand-50 dark:text-brand-400 dark:hover:bg-brand-500/10"
15          >
16            <Code2 className="size-3.5" />
17            View Source
18          </Link>
19        )}
20      </div>
21      <div className="rounded-xl border border-gray-200 bg-white p-6 dark:border-white/5 dark:bg-gray-dark">
22        {children}
23      </div>
24    </div>
25  );
26}
27
28export function PopoversSection() {
29  const [popoverOpen, setPopoverOpen] = useState<string | null>(null);
30  const togglePopover = (id: string) => setPopoverOpen((p) => (p === id ? null : id));
31
32  useEffect(() => {
33    const handler = () => setPopoverOpen(null);
34    if (popoverOpen) document.addEventListener('click', handler);
35    return () => document.removeEventListener('click', handler);
36  }, [popoverOpen]);
37
38  return (
39    <SectionCard title="Popovers" sourceSlug="/ui/source/ui-elements/popovers">
40      <div className="flex flex-wrap gap-6">
41        {/* Click Popover */}
42        <div className="relative">
43          <button onClick={(e) => { e.stopPropagation(); togglePopover('click'); }} className="rounded-xl bg-brand-500 px-5 py-2.5 text-sm font-medium text-white hover:bg-brand-600 transition-colors">
44            Click Popover
45          </button>
46          {popoverOpen === 'click' && (
47            <div className="absolute left-0 top-full z-50 mt-3 w-64 rounded-xl border border-gray-200 bg-white p-4 shadow-theme-lg dark:border-white/5 dark:bg-gray-800">
48              <div className="absolute -top-1.5 left-6 size-3 rotate-45 border-l border-t border-gray-200 bg-white dark:border-white/5 dark:bg-gray-800" />
49              <p className="text-sm font-semibold text-gray-800 dark:text-white/90">Popover Title</p>
50              <p className="mt-1 text-xs text-gray-500 dark:text-gray-400">This popover appears on click. It can contain any content including forms and actions.</p>
51              <div className="mt-3 flex gap-2">
52                <button className="rounded-lg bg-brand-500 px-3 py-1.5 text-xs font-medium text-white hover:bg-brand-600 transition-colors">Action</button>
53                <button className="rounded-lg border border-gray-300 px-3 py-1.5 text-xs font-medium text-gray-600 hover:bg-gray-50 dark:border-white/10 dark:text-gray-400 dark:hover:bg-white/5 transition-colors">Cancel</button>
54              </div>
55            </div>
56          )}
57        </div>
58
59        {/* Info Popover */}
60        <div className="relative">
61          <button onClick={(e) => { e.stopPropagation(); togglePopover('info'); }} className="inline-flex items-center gap-2 rounded-xl border border-gray-300 bg-white px-4 py-2.5 text-sm font-medium text-gray-700 hover:bg-gray-50 dark:bg-gray-800 dark:border-white/10 dark:text-gray-300 dark:hover:bg-gray-700 transition-colors">
62            <Info className="size-4 text-blue-light-500" /> Info Popover
63          </button>
64          {popoverOpen === 'info' && (
65            <div className="absolute left-0 top-full z-50 mt-3 w-56 rounded-xl border border-gray-200 bg-white p-4 shadow-theme-lg dark:border-white/5 dark:bg-gray-800">
66              <div className="absolute -top-1.5 left-6 size-3 rotate-45 border-l border-t border-gray-200 bg-white dark:border-white/5 dark:bg-gray-800" />
67              <div className="flex items-center gap-2 text-sm font-semibold text-blue-light-500">
68                <Info className="size-4" /> Information
69              </div>
70              <p className="mt-1.5 text-xs text-gray-500 dark:text-gray-400">This is an informational popover with helpful context about the feature.</p>
71            </div>
72          )}
73        </div>
74
75        {/* Confirmation Popover */}
76        <div className="relative">
77          <button onClick={(e) => { e.stopPropagation(); togglePopover('confirm'); }} className="inline-flex items-center gap-2 rounded-xl bg-error-500 px-4 py-2.5 text-sm font-medium text-white hover:bg-error-600 transition-colors">
78            <Trash2 className="size-4" /> Delete
79          </button>
80          {popoverOpen === 'confirm' && (
81            <div className="absolute right-0 top-full z-50 mt-3 w-64 rounded-xl border border-gray-200 bg-white p-4 shadow-theme-lg dark:border-white/5 dark:bg-gray-800">
82              <div className="absolute -top-1.5 right-6 size-3 rotate-45 border-l border-t border-gray-200 bg-white dark:border-white/5 dark:bg-gray-800" />
83              <p className="text-sm font-semibold text-gray-800 dark:text-white/90">Confirm Deletion</p>
84              <p className="mt-1 text-xs text-gray-500 dark:text-gray-400">Are you sure you want to delete this item? This action cannot be undone.</p>
85              <div className="mt-3 flex gap-2">
86                <button onClick={() => setPopoverOpen(null)} className="rounded-lg bg-error-500 px-3 py-1.5 text-xs font-medium text-white hover:bg-error-600 transition-colors">Delete</button>
87                <button onClick={() => setPopoverOpen(null)} className="rounded-lg border border-gray-300 px-3 py-1.5 text-xs font-medium text-gray-600 dark:border-white/10 dark:text-gray-400 transition-colors">Cancel</button>
88              </div>
89            </div>
90          )}
91        </div>
92      </div>
93    </SectionCard>
94  );
95}

More ui elements Components

ButtonsAlertsBadgesCardsDropdownsModalsTabsAccordionsTooltipsProgressSpinnersSkeletonsAvatarsPaginationPopoversToastsTimelinesTypographyBreadcrumbEmpty StatesTag InputCode BlockDividersChipsSwitchesRadio GroupsCheckboxesText InputsTextareasSelect MenusRange SlidersFile UploadColor SwatchesIcon ShowcaseData TagsNotification BadgeStatus IndicatorCountdown TimerGradient TextAnimated UnderlineKeyboard KeysMetric CardsComparison ToggleScroll IndicatorResizable PanelCollapsible SectionsDrag Handle ListTabs with IconsVertical NavBreadcrumb with Dropdown