@kinetixui/ui 0.6.2 → 0.6.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.d.ts CHANGED
@@ -27,13 +27,10 @@ import * as ToggleGroupPrimitive from '@radix-ui/react-toggle-group';
27
27
  import * as TooltipPrimitive from '@radix-ui/react-tooltip';
28
28
  import { DayPicker } from 'react-day-picker';
29
29
  import useEmblaCarousel, { UseEmblaCarouselType } from 'embla-carousel-react';
30
- import * as recharts_types_util_payload_getUniqPayload from 'recharts/types/util/payload/getUniqPayload';
31
- import * as recharts_types_component_Tooltip from 'recharts/types/component/Tooltip';
32
- import * as recharts_types_util_types from 'recharts/types/util/types';
33
- import * as recharts_types_component_DefaultTooltipContent from 'recharts/types/component/DefaultTooltipContent';
34
30
  import * as RechartsPrimitive from 'recharts';
35
31
  import * as ContextMenuPrimitive from '@radix-ui/react-context-menu';
36
- import { ColumnDef } from '@tanstack/react-table';
32
+ import * as _tanstack_react_table from '@tanstack/react-table';
33
+ import { RowData, ColumnDef } from '@tanstack/react-table';
37
34
  import * as vaul from 'vaul';
38
35
  import { Drawer as Drawer$1 } from 'vaul';
39
36
  import * as react_hook_form from 'react-hook-form';
@@ -502,37 +499,17 @@ declare const ChartStyle: ({ id, config }: {
502
499
  config: ChartConfig;
503
500
  }) => React$1.JSX.Element | null;
504
501
  declare const ChartTooltip: typeof RechartsPrimitive.Tooltip;
505
- declare const ChartTooltipContent: React$1.ForwardRefExoticComponent<Omit<RechartsPrimitive.DefaultTooltipContentProps<recharts_types_component_DefaultTooltipContent.ValueType, recharts_types_component_DefaultTooltipContent.NameType> & {
506
- accessibilityLayer?: boolean;
507
- active?: boolean | undefined;
508
- includeHidden?: boolean | undefined;
509
- allowEscapeViewBox?: recharts_types_util_types.AllowInDimension;
510
- animationDuration?: recharts_types_util_types.AnimationDuration;
511
- animationEasing?: recharts_types_util_types.AnimationTiming;
512
- content?: recharts_types_component_Tooltip.ContentType<recharts_types_component_DefaultTooltipContent.ValueType, recharts_types_component_DefaultTooltipContent.NameType> | undefined;
513
- coordinate?: Partial<recharts_types_util_types.Coordinate>;
514
- cursor?: boolean | React$1.ReactElement | React$1.SVGProps<SVGElement>;
515
- filterNull?: boolean;
516
- defaultIndex?: number;
517
- isAnimationActive?: boolean;
518
- offset?: number;
519
- payloadUniqBy?: recharts_types_util_payload_getUniqPayload.UniqueOption<recharts_types_component_DefaultTooltipContent.Payload<recharts_types_component_DefaultTooltipContent.ValueType, recharts_types_component_DefaultTooltipContent.NameType>> | undefined;
520
- position?: Partial<recharts_types_util_types.Coordinate>;
521
- reverseDirection?: recharts_types_util_types.AllowInDimension;
522
- shared?: boolean;
523
- trigger?: "hover" | "click";
524
- useTranslate3d?: boolean;
525
- viewBox?: recharts_types_util_types.CartesianViewBox;
526
- wrapperStyle?: React$1.CSSProperties;
527
- } & React$1.ClassAttributes<HTMLDivElement> & React$1.HTMLAttributes<HTMLDivElement> & {
502
+ declare const ChartTooltipContent: React$1.ForwardRefExoticComponent<Omit<Partial<RechartsPrimitive.TooltipContentProps> & Omit<React$1.DetailedHTMLProps<React$1.HTMLAttributes<HTMLDivElement>, HTMLDivElement>, "content"> & {
528
503
  hideLabel?: boolean;
529
504
  hideIndicator?: boolean;
530
505
  indicator?: "line" | "dot" | "dashed";
531
506
  nameKey?: string;
532
507
  labelKey?: string;
533
508
  }, "ref"> & React$1.RefAttributes<HTMLDivElement>>;
534
- declare const ChartLegend: typeof RechartsPrimitive.Legend;
535
- declare const ChartLegendContent: React$1.ForwardRefExoticComponent<Omit<React$1.ClassAttributes<HTMLDivElement> & React$1.HTMLAttributes<HTMLDivElement> & Pick<RechartsPrimitive.LegendProps, "payload" | "verticalAlign"> & {
509
+ declare const ChartLegend: React$1.MemoExoticComponent<(outsideProps: RechartsPrimitive.LegendProps) => React$1.ReactPortal | null>;
510
+ declare const ChartLegendContent: React$1.ForwardRefExoticComponent<Omit<React$1.ClassAttributes<HTMLDivElement> & React$1.HTMLAttributes<HTMLDivElement> & {
511
+ payload?: ReadonlyArray<RechartsPrimitive.LegendPayload>;
512
+ verticalAlign?: RechartsPrimitive.LegendProps["verticalAlign"];
536
513
  hideIcon?: boolean;
537
514
  nameKey?: string;
538
515
  }, "ref"> & React$1.RefAttributes<HTMLDivElement>>;
@@ -640,13 +617,27 @@ declare const ContextMenuShortcut: {
640
617
  displayName: string;
641
618
  };
642
619
 
620
+ declare const features: {
621
+ rowSortingFeature: _tanstack_react_table.TableFeature;
622
+ rowPaginationFeature: _tanstack_react_table.TableFeature;
623
+ sortedRowModel: (table: _tanstack_react_table.Table<any, any>) => () => _tanstack_react_table.RowModel<any, any>;
624
+ paginatedRowModel: (table: _tanstack_react_table.Table<any, any>) => () => _tanstack_react_table.RowModel<any, any>;
625
+ sortFns: {
626
+ alphanumeric: _tanstack_react_table.CreatedSortFn<any, any>;
627
+ alphanumericCaseSensitive: _tanstack_react_table.CreatedSortFn<any, any>;
628
+ basic: _tanstack_react_table.CreatedSortFn<any, any>;
629
+ datetime: _tanstack_react_table.CreatedSortFn<any, any>;
630
+ text: _tanstack_react_table.CreatedSortFn<any, any>;
631
+ textCaseSensitive: _tanstack_react_table.CreatedSortFn<any, any>;
632
+ };
633
+ };
643
634
  /**
644
635
  * DataTable — a thin wrapper over @tanstack/react-table + the KinetixUI Table.
645
636
  * Pass `columns` and `data`; sorting + pagination are on by default. For full
646
- * control, drop down to `useReactTable` directly.
637
+ * control, drop down to `useTable` directly.
647
638
  */
648
- declare function DataTable<TData, TValue>({ columns, data, className, pageSize, }: {
649
- columns: ColumnDef<TData, TValue>[];
639
+ declare function DataTable<TData extends RowData>({ columns, data, className, pageSize, }: {
640
+ columns: ColumnDef<typeof features, TData>[];
650
641
  data: TData[];
651
642
  className?: string;
652
643
  pageSize?: number;
@@ -809,25 +800,12 @@ declare const NavigationMenuLink: React$1.ForwardRefExoticComponent<NavigationMe
809
800
  declare const NavigationMenuViewport: React$1.ForwardRefExoticComponent<Omit<NavigationMenuPrimitive.NavigationMenuViewportProps & React$1.RefAttributes<HTMLDivElement>, "ref"> & React$1.RefAttributes<HTMLDivElement>>;
810
801
  declare const NavigationMenuIndicator: React$1.ForwardRefExoticComponent<Omit<NavigationMenuPrimitive.NavigationMenuIndicatorProps & React$1.RefAttributes<HTMLDivElement>, "ref"> & React$1.RefAttributes<HTMLDivElement>>;
811
802
 
812
- declare const ResizablePanelGroup: ({ className, ...props }: React$1.ComponentProps<typeof ResizablePrimitive.PanelGroup>) => React$1.JSX.Element;
813
- declare const ResizablePanel: React$1.ForwardRefExoticComponent<Omit<React$1.HTMLAttributes<HTMLButtonElement | HTMLElement | HTMLObjectElement | HTMLFormElement | HTMLSlotElement | HTMLStyleElement | HTMLTitleElement | HTMLAnchorElement | HTMLAreaElement | HTMLAudioElement | HTMLBaseElement | HTMLQuoteElement | HTMLBodyElement | HTMLBRElement | HTMLCanvasElement | HTMLTableColElement | HTMLDataElement | HTMLDataListElement | HTMLModElement | HTMLDetailsElement | HTMLDialogElement | HTMLDivElement | HTMLDListElement | HTMLEmbedElement | HTMLFieldSetElement | HTMLHeadingElement | HTMLHeadElement | HTMLHRElement | HTMLHtmlElement | HTMLIFrameElement | HTMLImageElement | HTMLInputElement | HTMLLabelElement | HTMLLegendElement | HTMLLIElement | HTMLLinkElement | HTMLMapElement | HTMLMetaElement | HTMLMeterElement | HTMLOListElement | HTMLOptGroupElement | HTMLOptionElement | HTMLOutputElement | HTMLParagraphElement | HTMLPreElement | HTMLProgressElement | HTMLScriptElement | HTMLSelectElement | HTMLSourceElement | HTMLSpanElement | HTMLTableElement | HTMLTemplateElement | HTMLTableSectionElement | HTMLTableCellElement | HTMLTextAreaElement | HTMLTimeElement | HTMLTableRowElement | HTMLTrackElement | HTMLUListElement | HTMLVideoElement | HTMLTableCaptionElement | HTMLMenuElement | HTMLPictureElement>, "id" | "onResize"> & {
814
- className?: string | undefined;
815
- collapsedSize?: number | undefined;
816
- collapsible?: boolean | undefined;
817
- defaultSize?: number | undefined;
818
- id?: string | undefined;
819
- maxSize?: number | undefined;
820
- minSize?: number | undefined;
821
- onCollapse?: ResizablePrimitive.PanelOnCollapse | undefined;
822
- onExpand?: ResizablePrimitive.PanelOnExpand | undefined;
823
- onResize?: ResizablePrimitive.PanelOnResize | undefined;
824
- order?: number | undefined;
825
- style?: object | undefined;
826
- tagName?: keyof HTMLElementTagNameMap | undefined;
827
- } & {
828
- children?: React$1.ReactNode;
829
- } & React$1.RefAttributes<ResizablePrimitive.ImperativePanelHandle>>;
830
- declare const ResizableHandle: ({ withHandle, className, ...props }: React$1.ComponentProps<typeof ResizablePrimitive.PanelResizeHandle> & {
803
+ type ResizablePanelGroupProps = Omit<React$1.ComponentProps<typeof ResizablePrimitive.Group>, "orientation"> & {
804
+ direction?: "horizontal" | "vertical";
805
+ };
806
+ declare const ResizablePanelGroup: ({ className, direction, ...props }: ResizablePanelGroupProps) => React$1.JSX.Element;
807
+ declare const ResizablePanel: ({ defaultSize, minSize, maxSize, ...props }: React$1.ComponentProps<typeof ResizablePrimitive.Panel>) => React$1.JSX.Element;
808
+ declare const ResizableHandle: ({ withHandle, className, ...props }: React$1.ComponentProps<typeof ResizablePrimitive.Separator> & {
831
809
  withHandle?: boolean;
832
810
  }) => React$1.JSX.Element;
833
811
 
@@ -930,7 +908,7 @@ declare const Image: React$1.ForwardRefExoticComponent<ImageProps & React$1.RefA
930
908
  * and can carry a CTA.
931
909
  */
932
910
  declare const informVariants: (props?: ({
933
- variant?: "action" | "success" | "warning" | "error" | "information" | null | undefined;
911
+ variant?: "success" | "warning" | "error" | "information" | "action" | null | undefined;
934
912
  } & class_variance_authority_types.ClassProp) | undefined) => string;
935
913
  interface InformProps extends React$1.HTMLAttributes<HTMLDivElement>, VariantProps<typeof informVariants> {
936
914
  hideIcon?: boolean;
package/dist/index.js CHANGED
@@ -1348,37 +1348,44 @@ function Calendar({ className, classNames, showOutsideDays = true, ...props }) {
1348
1348
  classNames: {
1349
1349
  months: "flex flex-col sm:flex-row gap-2",
1350
1350
  month: "flex flex-col gap-4",
1351
- caption: "flex justify-center pt-1 relative items-center w-full",
1351
+ month_caption: "flex justify-center pt-1 relative items-center w-full",
1352
1352
  caption_label: "text-sm font-medium",
1353
1353
  nav: "flex items-center gap-1",
1354
- nav_button: cn(
1354
+ button_previous: cn(
1355
1355
  buttonVariants({ variant: "Outline", size: "icon" }),
1356
- "size-7 bg-transparent p-0 opacity-50 hover:opacity-100"
1356
+ "absolute left-1 size-7 bg-transparent p-0 opacity-50 hover:opacity-100"
1357
1357
  ),
1358
- nav_button_previous: "absolute left-1",
1359
- nav_button_next: "absolute right-1",
1360
- table: "w-full border-collapse space-x-1",
1361
- head_row: "flex",
1362
- head_cell: "text-muted-foreground rounded-md w-8 font-normal text-[0.8rem]",
1363
- row: "flex w-full mt-2",
1364
- cell: cn(
1365
- "relative p-0 text-center text-sm focus-within:relative focus-within:z-20 [&:has([aria-selected])]:bg-accent [&:has([aria-selected].day-range-end)]:rounded-r-md",
1366
- props.mode === "range" ? "[&:has(>.day-range-end)]:rounded-r-md [&:has(>.day-range-start)]:rounded-l-md first:[&:has([aria-selected])]:rounded-l-md last:[&:has([aria-selected])]:rounded-r-md" : "[&:has([aria-selected])]:rounded-md"
1358
+ button_next: cn(
1359
+ buttonVariants({ variant: "Outline", size: "icon" }),
1360
+ "absolute right-1 size-7 bg-transparent p-0 opacity-50 hover:opacity-100"
1361
+ ),
1362
+ month_grid: "w-full border-collapse space-x-1",
1363
+ weekdays: "flex",
1364
+ weekday: "text-muted-foreground rounded-md w-8 font-normal text-[0.8rem]",
1365
+ week: "flex w-full mt-2",
1366
+ // Selection state (aria-selected/data-selected) lands on the day cell
1367
+ // itself in v10 (not a nested button), so the cell owns the
1368
+ // accent background + corner rounding and hands the primary-colored
1369
+ // "selected" circle down to `day_button` via a `group` class.
1370
+ day: cn(
1371
+ "group relative p-0 text-center text-sm focus-within:relative focus-within:z-20 aria-selected:bg-accent",
1372
+ props.mode === "range" ? "" : "aria-selected:rounded-md"
1373
+ ),
1374
+ day_button: cn(
1375
+ buttonVariants({ variant: "Ghost", size: "icon" }),
1376
+ "size-8 p-0 font-normal group-aria-selected:opacity-100 group-data-[selected=true]:bg-primary group-data-[selected=true]:text-primary-foreground group-data-[selected=true]:hover:bg-primary group-data-[selected=true]:hover:text-primary-foreground group-data-[selected=true]:focus:bg-primary group-data-[selected=true]:focus:text-primary-foreground"
1367
1377
  ),
1368
- day: cn(buttonVariants({ variant: "Ghost", size: "icon" }), "size-8 p-0 font-normal aria-selected:opacity-100"),
1369
- day_range_start: "day-range-start",
1370
- day_range_end: "day-range-end",
1371
- day_selected: "bg-primary text-primary-foreground hover:bg-primary hover:text-primary-foreground focus:bg-primary focus:text-primary-foreground",
1372
- day_today: "bg-accent text-accent-foreground",
1373
- day_outside: "day-outside text-muted-foreground aria-selected:text-muted-foreground",
1374
- day_disabled: "text-muted-foreground opacity-50",
1375
- day_range_middle: "aria-selected:bg-accent aria-selected:text-accent-foreground",
1376
- day_hidden: "invisible",
1378
+ range_start: "day-range-start rounded-l-md",
1379
+ range_end: "day-range-end rounded-r-md",
1380
+ range_middle: "aria-selected:bg-accent aria-selected:text-accent-foreground",
1381
+ today: "bg-accent text-accent-foreground",
1382
+ outside: "day-outside text-muted-foreground aria-selected:text-muted-foreground",
1383
+ disabled: "text-muted-foreground opacity-50",
1384
+ hidden: "invisible",
1377
1385
  ...classNames
1378
1386
  },
1379
1387
  components: {
1380
- IconLeft: () => /* @__PURE__ */ jsx35(ChevronLeft2, { className: "size-4" }),
1381
- IconRight: () => /* @__PURE__ */ jsx35(ChevronRight4, { className: "size-4" })
1388
+ Chevron: ({ orientation, className: chevronClassName }) => orientation === "right" ? /* @__PURE__ */ jsx35(ChevronRight4, { className: cn("size-4", chevronClassName) }) : /* @__PURE__ */ jsx35(ChevronLeft2, { className: cn("size-4", chevronClassName) })
1382
1389
  },
1383
1390
  ...props
1384
1391
  }
@@ -1670,7 +1677,7 @@ ${colorConfig.map(([key, itemConfig]) => {
1670
1677
  };
1671
1678
  var ChartTooltip = RechartsPrimitive.Tooltip;
1672
1679
  var ChartTooltipContent = React32.forwardRef(
1673
- ({ active, payload, className, indicator = "dot", hideLabel = false, hideIndicator = false, label, labelFormatter, formatter, color }, ref) => {
1680
+ ({ active, payload, className, indicator = "dot", hideLabel = false, hideIndicator = false, label, labelFormatter, formatter }, ref) => {
1674
1681
  const { config } = useChart();
1675
1682
  if (!active || !payload?.length) return null;
1676
1683
  return /* @__PURE__ */ jsxs15(
@@ -1686,7 +1693,7 @@ var ChartTooltipContent = React32.forwardRef(
1686
1693
  /* @__PURE__ */ jsx37("div", { className: "grid gap-1.5", children: payload.map((item, i) => {
1687
1694
  const key = `${item.name || item.dataKey || "value"}`;
1688
1695
  const itemConfig = config[key];
1689
- const indicatorColor = color || item.payload?.fill || item.color;
1696
+ const indicatorColor = item.payload?.fill || item.color;
1690
1697
  return /* @__PURE__ */ jsxs15("div", { className: "flex w-full items-center gap-2", children: [
1691
1698
  !hideIndicator && /* @__PURE__ */ jsx37(
1692
1699
  "div",
@@ -1865,13 +1872,23 @@ ContextMenuShortcut.displayName = "ContextMenuShortcut";
1865
1872
  // src/components/data-table.tsx
1866
1873
  import * as React35 from "react";
1867
1874
  import {
1875
+ createPaginatedRowModel,
1876
+ createSortedRowModel,
1868
1877
  flexRender,
1869
- getCoreRowModel,
1870
- getPaginationRowModel,
1871
- getSortedRowModel,
1872
- useReactTable
1878
+ rowPaginationFeature,
1879
+ rowSortingFeature,
1880
+ sortFns,
1881
+ tableFeatures,
1882
+ useTable
1873
1883
  } from "@tanstack/react-table";
1874
1884
  import { jsx as jsx40, jsxs as jsxs18 } from "react/jsx-runtime";
1885
+ var features = tableFeatures({
1886
+ rowSortingFeature,
1887
+ rowPaginationFeature,
1888
+ sortedRowModel: createSortedRowModel(),
1889
+ paginatedRowModel: createPaginatedRowModel(),
1890
+ sortFns
1891
+ });
1875
1892
  function DataTable({
1876
1893
  columns,
1877
1894
  data,
@@ -1879,20 +1896,18 @@ function DataTable({
1879
1896
  pageSize = 10
1880
1897
  }) {
1881
1898
  const [sorting, setSorting] = React35.useState([]);
1882
- const table = useReactTable({
1899
+ const table = useTable({
1900
+ features,
1883
1901
  data,
1884
1902
  columns,
1885
1903
  state: { sorting },
1886
1904
  onSortingChange: setSorting,
1887
- getCoreRowModel: getCoreRowModel(),
1888
- getSortedRowModel: getSortedRowModel(),
1889
- getPaginationRowModel: getPaginationRowModel(),
1890
- initialState: { pagination: { pageSize } }
1905
+ initialState: { pagination: { pageIndex: 0, pageSize } }
1891
1906
  });
1892
1907
  return /* @__PURE__ */ jsxs18("div", { className: cn("space-y-3", className), children: [
1893
1908
  /* @__PURE__ */ jsx40("div", { className: "rounded-md border", children: /* @__PURE__ */ jsxs18(Table, { children: [
1894
1909
  /* @__PURE__ */ jsx40(TableHeader, { children: table.getHeaderGroups().map((hg) => /* @__PURE__ */ jsx40(TableRow, { children: hg.headers.map((header) => /* @__PURE__ */ jsx40(TableHead, { children: header.isPlaceholder ? null : flexRender(header.column.columnDef.header, header.getContext()) }, header.id)) }, hg.id)) }),
1895
- /* @__PURE__ */ jsx40(TableBody, { children: table.getRowModel().rows.length ? table.getRowModel().rows.map((row) => /* @__PURE__ */ jsx40(TableRow, { "data-state": row.getIsSelected() && "selected", children: row.getVisibleCells().map((cell) => /* @__PURE__ */ jsx40(TableCell, { children: flexRender(cell.column.columnDef.cell, cell.getContext()) }, cell.id)) }, row.id)) : /* @__PURE__ */ jsx40(TableRow, { children: /* @__PURE__ */ jsx40(TableCell, { colSpan: columns.length, className: "h-24 text-center", children: "No results." }) }) })
1910
+ /* @__PURE__ */ jsx40(TableBody, { children: table.getRowModel().rows.length ? table.getRowModel().rows.map((row) => /* @__PURE__ */ jsx40(TableRow, { children: row.getAllCells().map((cell) => /* @__PURE__ */ jsx40(TableCell, { children: flexRender(cell.column.columnDef.cell, cell.getContext()) }, cell.id)) }, row.id)) : /* @__PURE__ */ jsx40(TableRow, { children: /* @__PURE__ */ jsx40(TableCell, { colSpan: columns.length, className: "h-24 text-center", children: "No results." }) }) })
1896
1911
  ] }) }),
1897
1912
  /* @__PURE__ */ jsxs18("div", { className: "flex items-center justify-end gap-2", children: [
1898
1913
  /* @__PURE__ */ jsx40(Button, { variant: "Outline", size: "sm", onClick: () => table.previousPage(), disabled: !table.getCanPreviousPage(), children: "Previous" }),
@@ -2393,26 +2408,31 @@ NavigationMenuIndicator.displayName = NavigationMenuPrimitive.Indicator.displayN
2393
2408
  import { GripVertical } from "lucide-react";
2394
2409
  import * as ResizablePrimitive from "react-resizable-panels";
2395
2410
  import { jsx as jsx49 } from "react/jsx-runtime";
2396
- var ResizablePanelGroup = ({
2397
- className,
2411
+ var ResizablePanelGroup = ({ className, direction = "horizontal", ...props }) => /* @__PURE__ */ jsx49(ResizablePrimitive.Group, { className: cn("flex h-full w-full", className), orientation: direction, ...props });
2412
+ var asPercent = (value) => typeof value === "number" ? `${value}%` : value;
2413
+ var ResizablePanel = ({
2414
+ defaultSize,
2415
+ minSize,
2416
+ maxSize,
2398
2417
  ...props
2399
2418
  }) => /* @__PURE__ */ jsx49(
2400
- ResizablePrimitive.PanelGroup,
2419
+ ResizablePrimitive.Panel,
2401
2420
  {
2402
- className: cn("flex h-full w-full data-[panel-group-direction=vertical]:flex-col", className),
2421
+ defaultSize: asPercent(defaultSize),
2422
+ minSize: asPercent(minSize),
2423
+ maxSize: asPercent(maxSize),
2403
2424
  ...props
2404
2425
  }
2405
2426
  );
2406
- var ResizablePanel = ResizablePrimitive.Panel;
2407
2427
  var ResizableHandle = ({
2408
2428
  withHandle,
2409
2429
  className,
2410
2430
  ...props
2411
2431
  }) => /* @__PURE__ */ jsx49(
2412
- ResizablePrimitive.PanelResizeHandle,
2432
+ ResizablePrimitive.Separator,
2413
2433
  {
2414
2434
  className: cn(
2415
- "relative flex w-px items-center justify-center bg-border after:absolute after:inset-y-0 after:left-1/2 after:w-1 after:-translate-x-1/2 focus-visible:outline-none focus-visible:ring-1 focus-visible:ring-ring focus-visible:ring-offset-1 data-[panel-group-direction=vertical]:h-px data-[panel-group-direction=vertical]:w-full data-[panel-group-direction=vertical]:after:left-0 data-[panel-group-direction=vertical]:after:h-1 data-[panel-group-direction=vertical]:after:w-full data-[panel-group-direction=vertical]:after:-translate-y-1/2 data-[panel-group-direction=vertical]:after:translate-x-0 [&[data-panel-group-direction=vertical]>div]:rotate-90",
2435
+ "relative flex w-px items-center justify-center bg-border after:absolute after:inset-y-0 after:left-1/2 after:w-1 after:-translate-x-1/2 focus-visible:outline-none focus-visible:ring-1 focus-visible:ring-ring focus-visible:ring-offset-1 aria-[orientation=horizontal]:h-px aria-[orientation=horizontal]:w-full aria-[orientation=horizontal]:after:left-0 aria-[orientation=horizontal]:after:h-1 aria-[orientation=horizontal]:after:w-full aria-[orientation=horizontal]:after:-translate-y-1/2 aria-[orientation=horizontal]:after:translate-x-0 [&[aria-orientation=horizontal]>div]:rotate-90",
2416
2436
  className
2417
2437
  ),
2418
2438
  ...props,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@kinetixui/ui",
3
- "version": "0.6.2",
3
+ "version": "0.6.4",
4
4
  "private": false,
5
5
  "description": "KinetixUI React components — CVA + Radix + Tailwind on the KinetixUI token contract. Also distributed via the kinetixui CLI as a component registry.",
6
6
  "keywords": [
@@ -40,70 +40,70 @@
40
40
  "tailwind.config.ts"
41
41
  ],
42
42
  "dependencies": {
43
- "@hookform/resolvers": "^3.9.1",
44
- "@radix-ui/react-accordion": "^1.2.2",
45
- "@radix-ui/react-alert-dialog": "^1.1.4",
46
- "@radix-ui/react-aspect-ratio": "^1.1.1",
47
- "@radix-ui/react-avatar": "^1.1.2",
48
- "@radix-ui/react-checkbox": "^1.1.3",
49
- "@radix-ui/react-collapsible": "^1.1.2",
50
- "@radix-ui/react-context-menu": "^2.2.4",
51
- "@radix-ui/react-dialog": "^1.1.4",
52
- "@radix-ui/react-dropdown-menu": "^2.1.4",
53
- "@radix-ui/react-hover-card": "^1.1.4",
54
- "@radix-ui/react-label": "^2.1.1",
55
- "@radix-ui/react-menubar": "^1.1.4",
56
- "@radix-ui/react-navigation-menu": "^1.2.3",
57
- "@radix-ui/react-popover": "^1.1.4",
58
- "@radix-ui/react-progress": "^1.1.1",
59
- "@radix-ui/react-radio-group": "^1.2.2",
60
- "@radix-ui/react-scroll-area": "^1.2.2",
61
- "@radix-ui/react-select": "^2.1.4",
62
- "@radix-ui/react-separator": "^1.1.1",
63
- "@radix-ui/react-slider": "^1.2.2",
64
- "@radix-ui/react-slot": "^1.1.1",
65
- "@radix-ui/react-switch": "^1.1.2",
66
- "@radix-ui/react-tabs": "^1.1.2",
67
- "@radix-ui/react-toggle": "^1.1.1",
68
- "@radix-ui/react-toggle-group": "^1.1.1",
69
- "@radix-ui/react-tooltip": "^1.1.6",
70
- "@tanstack/react-table": "^8.20.6",
43
+ "@hookform/resolvers": "^5.9.1",
44
+ "@radix-ui/react-accordion": "^1.2.20",
45
+ "@radix-ui/react-alert-dialog": "^1.1.23",
46
+ "@radix-ui/react-aspect-ratio": "^1.1.15",
47
+ "@radix-ui/react-avatar": "^1.2.6",
48
+ "@radix-ui/react-checkbox": "^1.3.11",
49
+ "@radix-ui/react-collapsible": "^1.1.20",
50
+ "@radix-ui/react-context-menu": "^2.3.7",
51
+ "@radix-ui/react-dialog": "^1.1.23",
52
+ "@radix-ui/react-dropdown-menu": "^2.1.24",
53
+ "@radix-ui/react-hover-card": "^1.1.23",
54
+ "@radix-ui/react-label": "^2.1.15",
55
+ "@radix-ui/react-menubar": "^1.1.24",
56
+ "@radix-ui/react-navigation-menu": "^1.2.22",
57
+ "@radix-ui/react-popover": "^1.1.23",
58
+ "@radix-ui/react-progress": "^1.1.16",
59
+ "@radix-ui/react-radio-group": "^1.4.7",
60
+ "@radix-ui/react-scroll-area": "^1.2.18",
61
+ "@radix-ui/react-select": "^2.3.7",
62
+ "@radix-ui/react-separator": "^1.1.15",
63
+ "@radix-ui/react-slider": "^1.4.7",
64
+ "@radix-ui/react-slot": "^1.3.3",
65
+ "@radix-ui/react-switch": "^1.3.7",
66
+ "@radix-ui/react-tabs": "^1.1.21",
67
+ "@radix-ui/react-toggle": "^1.1.18",
68
+ "@radix-ui/react-toggle-group": "^1.1.19",
69
+ "@radix-ui/react-tooltip": "^1.2.16",
70
+ "@tanstack/react-table": "^9.2.4",
71
71
  "class-variance-authority": "^0.7.1",
72
72
  "clsx": "^2.1.1",
73
- "cmdk": "^1.0.4",
74
- "date-fns": "^3.6.0",
75
- "embla-carousel-react": "^8.5.1",
76
- "input-otp": "^1.4.1",
77
- "lucide-react": "^0.468.0",
78
- "react-day-picker": "8.10.1",
79
- "react-hook-form": "^7.54.1",
80
- "react-resizable-panels": "^2.1.7",
81
- "recharts": "^2.15.0",
82
- "sonner": "^1.7.1",
83
- "tailwind-merge": "^2.6.0",
73
+ "cmdk": "^1.1.1",
74
+ "date-fns": "^4.4.0",
75
+ "embla-carousel-react": "^8.6.0",
76
+ "input-otp": "^1.5.0",
77
+ "lucide-react": "^1.46.0",
78
+ "react-day-picker": "^10.0.1",
79
+ "react-hook-form": "^7.88.0",
80
+ "react-resizable-panels": "^4.12.4",
81
+ "recharts": "^3.10.1",
82
+ "sonner": "^2.0.8",
83
+ "tailwind-merge": "^3.7.0",
84
84
  "tailwindcss-animate": "^1.0.7",
85
85
  "vaul": "^1.1.2",
86
- "zod": "^3.24.1"
86
+ "zod": "^4.6.5"
87
87
  },
88
88
  "peerDependencies": {
89
89
  "react": ">=18",
90
90
  "react-dom": ">=18"
91
91
  },
92
92
  "devDependencies": {
93
- "@kinetixui/tokens": "0.6.2",
94
- "@testing-library/jest-dom": "^6.6.3",
95
- "@testing-library/react": "^16.1.0",
96
- "@testing-library/user-event": "^14.5.2",
97
- "@types/react": "^18.3.17",
98
- "@types/react-dom": "^18.3.5",
99
- "@vitejs/plugin-react": "^5.2.0",
100
- "jsdom": "^25.0.1",
101
- "react": "^18.3.1",
102
- "react-dom": "^18.3.1",
103
- "tailwindcss": "^3.4.17",
104
- "tsup": "^8.3.5",
105
- "typescript": "^5.7.2",
106
- "vitest": "^5.0.0"
93
+ "@kinetixui/tokens": "0.6.4",
94
+ "@testing-library/jest-dom": "^7.0.1",
95
+ "@testing-library/react": "^16.3.3",
96
+ "@testing-library/user-event": "^14.6.7",
97
+ "@types/react": "^19.3.0",
98
+ "@types/react-dom": "^19.3.0",
99
+ "@vitejs/plugin-react": "^6.1.1",
100
+ "jsdom": "^30.0.1",
101
+ "react": "^19.3.0",
102
+ "react-dom": "^19.3.0",
103
+ "tailwindcss": "^3.4.19",
104
+ "tsup": "^8.5.1",
105
+ "typescript": "^5.9.3",
106
+ "vitest": "^5.0.1"
107
107
  },
108
108
  "scripts": {
109
109
  "build": "tsup src/index.ts --format esm --dts --external react --external react-dom",
@@ -16,40 +16,49 @@ function Calendar({ className, classNames, showOutsideDays = true, ...props }: C
16
16
  classNames={{
17
17
  months: "flex flex-col sm:flex-row gap-2",
18
18
  month: "flex flex-col gap-4",
19
- caption: "flex justify-center pt-1 relative items-center w-full",
19
+ month_caption: "flex justify-center pt-1 relative items-center w-full",
20
20
  caption_label: "text-sm font-medium",
21
21
  nav: "flex items-center gap-1",
22
- nav_button: cn(
22
+ button_previous: cn(
23
23
  buttonVariants({ variant: "Outline", size: "icon" }),
24
- "size-7 bg-transparent p-0 opacity-50 hover:opacity-100",
24
+ "absolute left-1 size-7 bg-transparent p-0 opacity-50 hover:opacity-100",
25
25
  ),
26
- nav_button_previous: "absolute left-1",
27
- nav_button_next: "absolute right-1",
28
- table: "w-full border-collapse space-x-1",
29
- head_row: "flex",
30
- head_cell: "text-muted-foreground rounded-md w-8 font-normal text-[0.8rem]",
31
- row: "flex w-full mt-2",
32
- cell: cn(
33
- "relative p-0 text-center text-sm focus-within:relative focus-within:z-20 [&:has([aria-selected])]:bg-accent [&:has([aria-selected].day-range-end)]:rounded-r-md",
34
- props.mode === "range"
35
- ? "[&:has(>.day-range-end)]:rounded-r-md [&:has(>.day-range-start)]:rounded-l-md first:[&:has([aria-selected])]:rounded-l-md last:[&:has([aria-selected])]:rounded-r-md"
36
- : "[&:has([aria-selected])]:rounded-md",
26
+ button_next: cn(
27
+ buttonVariants({ variant: "Outline", size: "icon" }),
28
+ "absolute right-1 size-7 bg-transparent p-0 opacity-50 hover:opacity-100",
29
+ ),
30
+ month_grid: "w-full border-collapse space-x-1",
31
+ weekdays: "flex",
32
+ weekday: "text-muted-foreground rounded-md w-8 font-normal text-[0.8rem]",
33
+ week: "flex w-full mt-2",
34
+ // Selection state (aria-selected/data-selected) lands on the day cell
35
+ // itself in v10 (not a nested button), so the cell owns the
36
+ // accent background + corner rounding and hands the primary-colored
37
+ // "selected" circle down to `day_button` via a `group` class.
38
+ day: cn(
39
+ "group relative p-0 text-center text-sm focus-within:relative focus-within:z-20 aria-selected:bg-accent",
40
+ props.mode === "range" ? "" : "aria-selected:rounded-md",
41
+ ),
42
+ day_button: cn(
43
+ buttonVariants({ variant: "Ghost", size: "icon" }),
44
+ "size-8 p-0 font-normal group-aria-selected:opacity-100 group-data-[selected=true]:bg-primary group-data-[selected=true]:text-primary-foreground group-data-[selected=true]:hover:bg-primary group-data-[selected=true]:hover:text-primary-foreground group-data-[selected=true]:focus:bg-primary group-data-[selected=true]:focus:text-primary-foreground",
37
45
  ),
38
- day: cn(buttonVariants({ variant: "Ghost", size: "icon" }), "size-8 p-0 font-normal aria-selected:opacity-100"),
39
- day_range_start: "day-range-start",
40
- day_range_end: "day-range-end",
41
- day_selected:
42
- "bg-primary text-primary-foreground hover:bg-primary hover:text-primary-foreground focus:bg-primary focus:text-primary-foreground",
43
- day_today: "bg-accent text-accent-foreground",
44
- day_outside: "day-outside text-muted-foreground aria-selected:text-muted-foreground",
45
- day_disabled: "text-muted-foreground opacity-50",
46
- day_range_middle: "aria-selected:bg-accent aria-selected:text-accent-foreground",
47
- day_hidden: "invisible",
46
+ range_start: "day-range-start rounded-l-md",
47
+ range_end: "day-range-end rounded-r-md",
48
+ range_middle: "aria-selected:bg-accent aria-selected:text-accent-foreground",
49
+ today: "bg-accent text-accent-foreground",
50
+ outside: "day-outside text-muted-foreground aria-selected:text-muted-foreground",
51
+ disabled: "text-muted-foreground opacity-50",
52
+ hidden: "invisible",
48
53
  ...classNames,
49
54
  }}
50
55
  components={{
51
- IconLeft: () => <ChevronLeft className="size-4" />,
52
- IconRight: () => <ChevronRight className="size-4" />,
56
+ Chevron: ({ orientation, className: chevronClassName }) =>
57
+ orientation === "right" ? (
58
+ <ChevronRight className={cn("size-4", chevronClassName)} />
59
+ ) : (
60
+ <ChevronLeft className={cn("size-4", chevronClassName)} />
61
+ ),
53
62
  }}
54
63
  {...props}
55
64
  />
@@ -236,8 +236,14 @@ const ChartTooltip = RechartsPrimitive.Tooltip;
236
236
 
237
237
  const ChartTooltipContent = React.forwardRef<
238
238
  HTMLDivElement,
239
- React.ComponentProps<typeof RechartsPrimitive.Tooltip> &
240
- React.ComponentProps<"div"> & {
239
+ // Recharts v3 moved active/payload/label/coordinate to context-only props
240
+ // (`PropertiesReadFromContext`, omitted from `TooltipProps`) — the custom
241
+ // `content` render prop receives them back via `TooltipContentProps`.
242
+ // Partial because `<ChartTooltip content={<ChartTooltipContent />} />`
243
+ // constructs the element with no props — Recharts clones it with the real
244
+ // values at render time.
245
+ Partial<RechartsPrimitive.TooltipContentProps> &
246
+ Omit<React.ComponentProps<"div">, "content"> & {
241
247
  hideLabel?: boolean;
242
248
  hideIndicator?: boolean;
243
249
  indicator?: "line" | "dot" | "dashed";
@@ -246,7 +252,7 @@ const ChartTooltipContent = React.forwardRef<
246
252
  }
247
253
  >(
248
254
  (
249
- { active, payload, className, indicator = "dot", hideLabel = false, hideIndicator = false, label, labelFormatter, formatter, color },
255
+ { active, payload, className, indicator = "dot", hideLabel = false, hideIndicator = false, label, labelFormatter, formatter },
250
256
  ref,
251
257
  ) => {
252
258
  const { config } = useChart();
@@ -268,7 +274,7 @@ const ChartTooltipContent = React.forwardRef<
268
274
  {payload.map((item, i) => {
269
275
  const key = `${item.name || item.dataKey || "value"}`;
270
276
  const itemConfig = config[key];
271
- const indicatorColor = color || (item.payload as Record<string, string>)?.fill || item.color;
277
+ const indicatorColor = (item.payload as Record<string, string>)?.fill || item.color;
272
278
  return (
273
279
  <div key={key + i} className="flex w-full items-center gap-2">
274
280
  {!hideIndicator && (
@@ -303,8 +309,14 @@ const ChartLegend = RechartsPrimitive.Legend;
303
309
 
304
310
  const ChartLegendContent = React.forwardRef<
305
311
  HTMLDivElement,
306
- React.ComponentProps<"div"> &
307
- Pick<RechartsPrimitive.LegendProps, "payload" | "verticalAlign"> & { hideIcon?: boolean; nameKey?: string }
312
+ // Recharts v3 dropped `payload` from the exported `LegendProps` (also
313
+ // context-only now, like Tooltip's) — type it from `LegendPayload` directly.
314
+ React.ComponentProps<"div"> & {
315
+ payload?: ReadonlyArray<RechartsPrimitive.LegendPayload>;
316
+ verticalAlign?: RechartsPrimitive.LegendProps["verticalAlign"];
317
+ hideIcon?: boolean;
318
+ nameKey?: string;
319
+ }
308
320
  >(({ className, payload, verticalAlign = "bottom" }, ref) => {
309
321
  const { config } = useChart();
310
322
  if (!payload?.length) return null;
@@ -2,45 +2,59 @@
2
2
 
3
3
  import * as React from "react";
4
4
  import {
5
+ createPaginatedRowModel,
6
+ createSortedRowModel,
5
7
  flexRender,
6
- getCoreRowModel,
7
- getPaginationRowModel,
8
- getSortedRowModel,
9
- useReactTable,
8
+ rowPaginationFeature,
9
+ rowSortingFeature,
10
+ sortFns,
11
+ tableFeatures,
12
+ useTable,
10
13
  type ColumnDef,
14
+ type RowData,
11
15
  type SortingState,
12
16
  } from "@tanstack/react-table";
13
17
  import { cn } from "../lib/utils";
14
18
  import { Button } from "./button";
15
19
  import { Table, TableBody, TableCell, TableHead, TableHeader, TableRow } from "./table";
16
20
 
21
+ // @tanstack/react-table v9 replaced the bundled-everything `useReactTable`
22
+ // with tree-shakeable `features` passed into `useTable` — sorting and
23
+ // pagination are opt-in plugins now instead of default row models. Declared
24
+ // once at module scope since it's static config, not per-render state.
25
+ const features = tableFeatures({
26
+ rowSortingFeature,
27
+ rowPaginationFeature,
28
+ sortedRowModel: createSortedRowModel(),
29
+ paginatedRowModel: createPaginatedRowModel(),
30
+ sortFns,
31
+ });
32
+
17
33
  /**
18
34
  * DataTable — a thin wrapper over @tanstack/react-table + the KinetixUI Table.
19
35
  * Pass `columns` and `data`; sorting + pagination are on by default. For full
20
- * control, drop down to `useReactTable` directly.
36
+ * control, drop down to `useTable` directly.
21
37
  */
22
- export function DataTable<TData, TValue>({
38
+ export function DataTable<TData extends RowData>({
23
39
  columns,
24
40
  data,
25
41
  className,
26
42
  pageSize = 10,
27
43
  }: {
28
- columns: ColumnDef<TData, TValue>[];
44
+ columns: ColumnDef<typeof features, TData>[];
29
45
  data: TData[];
30
46
  className?: string;
31
47
  pageSize?: number;
32
48
  }) {
33
49
  const [sorting, setSorting] = React.useState<SortingState>([]);
34
50
 
35
- const table = useReactTable({
51
+ const table = useTable({
52
+ features,
36
53
  data,
37
54
  columns,
38
55
  state: { sorting },
39
56
  onSortingChange: setSorting,
40
- getCoreRowModel: getCoreRowModel(),
41
- getSortedRowModel: getSortedRowModel(),
42
- getPaginationRowModel: getPaginationRowModel(),
43
- initialState: { pagination: { pageSize } },
57
+ initialState: { pagination: { pageIndex: 0, pageSize } },
44
58
  });
45
59
 
46
60
  return (
@@ -63,8 +77,8 @@ export function DataTable<TData, TValue>({
63
77
  <TableBody>
64
78
  {table.getRowModel().rows.length ? (
65
79
  table.getRowModel().rows.map((row) => (
66
- <TableRow key={row.id} data-state={row.getIsSelected() && "selected"}>
67
- {row.getVisibleCells().map((cell) => (
80
+ <TableRow key={row.id}>
81
+ {row.getAllCells().map((cell) => (
68
82
  <TableCell key={cell.id}>{flexRender(cell.column.columnDef.cell, cell.getContext())}</TableCell>
69
83
  ))}
70
84
  </TableRow>
@@ -5,26 +5,47 @@ import { GripVertical } from "lucide-react";
5
5
  import * as ResizablePrimitive from "react-resizable-panels";
6
6
  import { cn } from "../lib/utils";
7
7
 
8
- const ResizablePanelGroup = ({
9
- className,
8
+ // react-resizable-panels v4 renamed PanelGroup/PanelResizeHandle to
9
+ // Group/Separator and dropped the old `direction`/`data-panel-group-direction`
10
+ // API in favor of `orientation` + `aria-orientation` (set on the Separator
11
+ // itself, opposite of the group's own orientation). `direction` is kept as
12
+ // this wrapper's public prop name — every call site (demos, stories, the CLI
13
+ // registry) still passes it — and mapped to `orientation` underneath.
14
+ type ResizablePanelGroupProps = Omit<React.ComponentProps<typeof ResizablePrimitive.Group>, "orientation"> & {
15
+ direction?: "horizontal" | "vertical";
16
+ };
17
+
18
+ const ResizablePanelGroup = ({ className, direction = "horizontal", ...props }: ResizablePanelGroupProps) => (
19
+ <ResizablePrimitive.Group className={cn("flex h-full w-full", className)} orientation={direction} {...props} />
20
+ );
21
+
22
+ // v4 also changed bare numeric `defaultSize`/`minSize`/`maxSize` to mean
23
+ // pixels instead of percent — coerce plain numbers to a percentage string so
24
+ // existing call sites (`defaultSize={50}`) keep their v2 percentage meaning.
25
+ const asPercent = (value: number | string | undefined) => (typeof value === "number" ? `${value}%` : value);
26
+
27
+ const ResizablePanel = ({
28
+ defaultSize,
29
+ minSize,
30
+ maxSize,
10
31
  ...props
11
- }: React.ComponentProps<typeof ResizablePrimitive.PanelGroup>) => (
12
- <ResizablePrimitive.PanelGroup
13
- className={cn("flex h-full w-full data-[panel-group-direction=vertical]:flex-col", className)}
32
+ }: React.ComponentProps<typeof ResizablePrimitive.Panel>) => (
33
+ <ResizablePrimitive.Panel
34
+ defaultSize={asPercent(defaultSize)}
35
+ minSize={asPercent(minSize)}
36
+ maxSize={asPercent(maxSize)}
14
37
  {...props}
15
38
  />
16
39
  );
17
40
 
18
- const ResizablePanel = ResizablePrimitive.Panel;
19
-
20
41
  const ResizableHandle = ({
21
42
  withHandle,
22
43
  className,
23
44
  ...props
24
- }: React.ComponentProps<typeof ResizablePrimitive.PanelResizeHandle> & { withHandle?: boolean }) => (
25
- <ResizablePrimitive.PanelResizeHandle
45
+ }: React.ComponentProps<typeof ResizablePrimitive.Separator> & { withHandle?: boolean }) => (
46
+ <ResizablePrimitive.Separator
26
47
  className={cn(
27
- "relative flex w-px items-center justify-center bg-border after:absolute after:inset-y-0 after:left-1/2 after:w-1 after:-translate-x-1/2 focus-visible:outline-none focus-visible:ring-1 focus-visible:ring-ring focus-visible:ring-offset-1 data-[panel-group-direction=vertical]:h-px data-[panel-group-direction=vertical]:w-full data-[panel-group-direction=vertical]:after:left-0 data-[panel-group-direction=vertical]:after:h-1 data-[panel-group-direction=vertical]:after:w-full data-[panel-group-direction=vertical]:after:-translate-y-1/2 data-[panel-group-direction=vertical]:after:translate-x-0 [&[data-panel-group-direction=vertical]>div]:rotate-90",
48
+ "relative flex w-px items-center justify-center bg-border after:absolute after:inset-y-0 after:left-1/2 after:w-1 after:-translate-x-1/2 focus-visible:outline-none focus-visible:ring-1 focus-visible:ring-ring focus-visible:ring-offset-1 aria-[orientation=horizontal]:h-px aria-[orientation=horizontal]:w-full aria-[orientation=horizontal]:after:left-0 aria-[orientation=horizontal]:after:h-1 aria-[orientation=horizontal]:after:w-full aria-[orientation=horizontal]:after:-translate-y-1/2 aria-[orientation=horizontal]:after:translate-x-0 [&[aria-orientation=horizontal]>div]:rotate-90",
28
49
  className,
29
50
  )}
30
51
  {...props}
@@ -34,7 +55,7 @@ const ResizableHandle = ({
34
55
  <GripVertical className="size-2.5" />
35
56
  </div>
36
57
  )}
37
- </ResizablePrimitive.PanelResizeHandle>
58
+ </ResizablePrimitive.Separator>
38
59
  );
39
60
 
40
61
  export { ResizablePanelGroup, ResizablePanel, ResizableHandle };