@mesob/ui 0.1.1 → 0.2.0

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.
Files changed (47) hide show
  1. package/dist/components/app-breadcrumbs.d.ts +34 -0
  2. package/dist/components/app-breadcrumbs.js +177 -0
  3. package/dist/components/app-breadcrumbs.js.map +1 -0
  4. package/dist/components/app-header-actions.d.ts +39 -0
  5. package/dist/components/app-header-actions.js +629 -0
  6. package/dist/components/app-header-actions.js.map +1 -0
  7. package/dist/components/app-sidebar.d.ts +24 -0
  8. package/dist/components/app-sidebar.js +669 -0
  9. package/dist/components/app-sidebar.js.map +1 -0
  10. package/dist/components/data-table/index.d.ts +9 -2
  11. package/dist/components/data-table/index.js +276 -101
  12. package/dist/components/data-table/index.js.map +1 -1
  13. package/dist/components/entity/index.d.ts +85 -9
  14. package/dist/components/entity/index.js +424 -304
  15. package/dist/components/entity/index.js.map +1 -1
  16. package/dist/components/input-group.d.ts +1 -1
  17. package/dist/components/link.d.ts +12 -0
  18. package/dist/components/link.js +51 -0
  19. package/dist/components/link.js.map +1 -0
  20. package/dist/components/mesob-context.d.ts +34 -0
  21. package/dist/components/mesob-context.js +53 -0
  22. package/dist/components/mesob-context.js.map +1 -0
  23. package/dist/components/page/index.d.ts +46 -0
  24. package/dist/components/page/index.js +197 -0
  25. package/dist/components/page/index.js.map +1 -0
  26. package/dist/components/powered-by.d.ts +4 -1
  27. package/dist/components/powered-by.js +28 -12
  28. package/dist/components/powered-by.js.map +1 -1
  29. package/dist/components/shell.d.ts +13 -0
  30. package/dist/components/shell.js +545 -0
  31. package/dist/components/shell.js.map +1 -0
  32. package/dist/components/sidebar.d.ts +4 -0
  33. package/dist/components/sidebar.js +37 -8
  34. package/dist/components/sidebar.js.map +1 -1
  35. package/dist/components/table.js +1 -1
  36. package/dist/components/table.js.map +1 -1
  37. package/dist/components/tooltip.d.ts +1 -1
  38. package/dist/components/tooltip.js +2 -1
  39. package/dist/components/tooltip.js.map +1 -1
  40. package/dist/hooks/use-router.d.ts +7 -0
  41. package/dist/hooks/use-router.js +36 -0
  42. package/dist/hooks/use-router.js.map +1 -0
  43. package/dist/hooks/use-translation.d.ts +5 -0
  44. package/dist/hooks/use-translation.js +41 -0
  45. package/dist/hooks/use-translation.js.map +1 -0
  46. package/package.json +7 -1
  47. package/src/styles/globals.css +4 -0
@@ -30,7 +30,7 @@ function Table({ className, ...props }) {
30
30
  "table",
31
31
  {
32
32
  "data-slot": "table",
33
- className: cn("w-full caption-bottom text-sm", className),
33
+ className: cn("w-full caption-bottom text-sm px-2", className),
34
34
  ...props
35
35
  }
36
36
  )
@@ -118,9 +118,22 @@ function DataTable({
118
118
  const [internalColumnFilters, setInternalColumnFilters] = React.useState(columnFilters);
119
119
  const [internalColumnVisibility, setInternalColumnVisibility] = React.useState(columnVisibility);
120
120
  const [internalRowSelection, setInternalRowSelection] = React.useState(rowSelection);
121
+ const processedColumns = React.useMemo(() => {
122
+ return columns.map((col) => {
123
+ if ((col.id === "actions" || col.id === "select") && col.size === void 0) {
124
+ return {
125
+ ...col,
126
+ size: 50,
127
+ minSize: col.minSize,
128
+ maxSize: col.maxSize
129
+ };
130
+ }
131
+ return col;
132
+ });
133
+ }, [columns]);
121
134
  const table = useReactTable({
122
135
  data,
123
- columns,
136
+ columns: processedColumns,
124
137
  getRowId: getRowId || ((_, index) => String(index)),
125
138
  state: {
126
139
  sorting: onSortingChange ? sorting : internalSorting,
@@ -174,46 +187,70 @@ function DataTable({
174
187
  getFacetedUniqueValues: getFacetedUniqueValues()
175
188
  });
176
189
  return /* @__PURE__ */ jsx2("div", { className: "rounded-md border", children: /* @__PURE__ */ jsxs(Table, { children: [
177
- /* @__PURE__ */ jsx2(TableHeader, { children: table.getHeaderGroups().map((headerGroup) => /* @__PURE__ */ jsx2(TableRow, { children: headerGroup.headers.map((header) => /* @__PURE__ */ jsx2(TableHead, { colSpan: header.colSpan, children: header.isPlaceholder ? null : flexRender(
178
- header.column.columnDef.header,
179
- header.getContext()
180
- ) }, header.id)) }, headerGroup.id)) }),
190
+ /* @__PURE__ */ jsx2(TableHeader, { children: table.getHeaderGroups().map((headerGroup) => /* @__PURE__ */ jsx2(TableRow, { children: headerGroup.headers.map((header, index) => {
191
+ const isFirst = index === 0;
192
+ const isLast = index === headerGroup.headers.length - 1;
193
+ let className;
194
+ if (isFirst) {
195
+ className = "pl-4";
196
+ } else if (isLast) {
197
+ className = "pr-4";
198
+ }
199
+ return /* @__PURE__ */ jsx2(
200
+ TableHead,
201
+ {
202
+ colSpan: header.colSpan,
203
+ style: { width: header.getSize() },
204
+ className,
205
+ children: header.isPlaceholder ? null : flexRender(
206
+ header.column.columnDef.header,
207
+ header.getContext()
208
+ )
209
+ },
210
+ header.id
211
+ );
212
+ }) }, headerGroup.id)) }),
181
213
  /* @__PURE__ */ jsx2(TableBody, { children: table.getRowModel().rows?.length ? table.getRowModel().rows.map((row) => /* @__PURE__ */ jsx2(
182
214
  TableRow,
183
215
  {
184
216
  "data-state": row.getIsSelected() && "selected",
185
- children: row.getVisibleCells().map((cell) => /* @__PURE__ */ jsx2(TableCell, { children: flexRender(cell.column.columnDef.cell, cell.getContext()) }, cell.id))
217
+ className: "group",
218
+ children: row.getVisibleCells().map((cell, index) => {
219
+ const visibleCells = row.getVisibleCells();
220
+ const isFirst = index === 0;
221
+ const isLast = index === visibleCells.length - 1;
222
+ let className;
223
+ if (isFirst) {
224
+ className = "pl-4";
225
+ } else if (isLast) {
226
+ className = "pr-4";
227
+ }
228
+ return /* @__PURE__ */ jsx2(
229
+ TableCell,
230
+ {
231
+ style: { width: cell.column.getSize() },
232
+ className,
233
+ children: flexRender(
234
+ cell.column.columnDef.cell,
235
+ cell.getContext()
236
+ )
237
+ },
238
+ cell.id
239
+ );
240
+ })
186
241
  },
187
242
  row.id
188
243
  )) : /* @__PURE__ */ jsx2(TableRow, { children: /* @__PURE__ */ jsx2(TableCell, { colSpan: columns.length, className: "h-24 text-center", children: "No results." }) }) })
189
244
  ] }) });
190
245
  }
191
246
 
192
- // src/components/data-table/data-table-column-header.tsx
193
- import { jsx as jsx3 } from "react/jsx-runtime";
194
- function DataTableColumnHeader({
195
- column,
196
- title,
197
- className
198
- }) {
199
- if (!column.getCanSort()) {
200
- return /* @__PURE__ */ jsx3("div", { className: cn(className), children: title });
201
- }
202
- return /* @__PURE__ */ jsx3("div", { className: cn("flex items-center gap-2", className), children: /* @__PURE__ */ jsx3("span", { children: title }) });
203
- }
204
-
205
- // src/components/data-table/data-table-pagination.tsx
206
- import {
207
- IconChevronLeft,
208
- IconChevronRight,
209
- IconChevronsLeft,
210
- IconChevronsRight
211
- } from "@tabler/icons-react";
247
+ // src/components/data-table/data-table-action.tsx
248
+ import { IconChevronRight } from "@tabler/icons-react";
212
249
 
213
250
  // src/components/button.tsx
214
251
  import { Slot } from "@radix-ui/react-slot";
215
252
  import { cva } from "class-variance-authority";
216
- import { jsx as jsx4 } from "react/jsx-runtime";
253
+ import { jsx as jsx3 } from "react/jsx-runtime";
217
254
  var buttonVariants = cva(
218
255
  "inline-flex items-center justify-center gap-2 whitespace-nowrap rounded-md text-sm font-medium transition-all disabled:pointer-events-none disabled:opacity-50 [&_svg]:pointer-events-none [&_svg:not([class*='size-'])]:size-4 shrink-0 [&_svg]:shrink-0 outline-none focus-visible:border-ring focus-visible:ring-ring/50 focus-visible:ring-[3px] aria-invalid:ring-destructive/20 dark:aria-invalid:ring-destructive/40 aria-invalid:border-destructive",
219
256
  {
@@ -249,7 +286,7 @@ function Button({
249
286
  ...props
250
287
  }) {
251
288
  const Comp = asChild ? Slot : "button";
252
- return /* @__PURE__ */ jsx4(
289
+ return /* @__PURE__ */ jsx3(
253
290
  Comp,
254
291
  {
255
292
  "data-slot": "button",
@@ -259,19 +296,94 @@ function Button({
259
296
  );
260
297
  }
261
298
 
299
+ // src/components/data-table/data-table-action.tsx
300
+ import { jsx as jsx4, jsxs as jsxs2 } from "react/jsx-runtime";
301
+ function DataTableAction({
302
+ onClick,
303
+ disabled,
304
+ "aria-label": ariaLabel = "Open menu"
305
+ }) {
306
+ return /* @__PURE__ */ jsx4("div", { className: "flex justify-end align-center", children: /* @__PURE__ */ jsxs2(
307
+ Button,
308
+ {
309
+ variant: "ghost",
310
+ className: "h-8 w-8 p-0 opacity-0 transition-opacity group-hover:opacity-100 cursor-pointer",
311
+ onClick,
312
+ disabled,
313
+ children: [
314
+ /* @__PURE__ */ jsx4("span", { className: "sr-only", children: ariaLabel }),
315
+ /* @__PURE__ */ jsx4(IconChevronRight, { className: "h-4 w-4" })
316
+ ]
317
+ }
318
+ ) });
319
+ }
320
+
321
+ // src/components/data-table/data-table-column-header.tsx
322
+ import { jsx as jsx5 } from "react/jsx-runtime";
323
+ function DataTableColumnHeader({
324
+ column,
325
+ title,
326
+ className
327
+ }) {
328
+ if (!column.getCanSort()) {
329
+ return /* @__PURE__ */ jsx5("div", { className: cn(className), children: title });
330
+ }
331
+ return /* @__PURE__ */ jsx5("div", { className: cn("flex items-center gap-2", className), children: /* @__PURE__ */ jsx5("span", { children: title }) });
332
+ }
333
+
334
+ // src/hooks/use-translation.ts
335
+ import { useTranslations } from "next-intl";
336
+ import { useMemo as useMemo3 } from "react";
337
+
338
+ // src/components/tooltip.tsx
339
+ import * as TooltipPrimitive from "@radix-ui/react-tooltip";
340
+ import { jsx as jsx6, jsxs as jsxs3 } from "react/jsx-runtime";
341
+
342
+ // src/components/mesob-context.tsx
343
+ import {
344
+ createContext,
345
+ useContext,
346
+ useMemo as useMemo2
347
+ } from "react";
348
+ import { jsx as jsx7 } from "react/jsx-runtime";
349
+ var MesobContext = createContext(null);
350
+ function useMesob() {
351
+ return useContext(MesobContext);
352
+ }
353
+
354
+ // src/hooks/use-translation.ts
355
+ function useTranslation(namespace) {
356
+ const mesob = useMesob();
357
+ const nextIntlT = useTranslations(namespace);
358
+ return useMemo3(() => {
359
+ if (mesob?.t) {
360
+ return (key, params) => mesob.t(namespace ? `${namespace}.${key}` : key, params);
361
+ }
362
+ return nextIntlT;
363
+ }, [mesob?.t, namespace, nextIntlT]);
364
+ }
365
+
366
+ // src/components/data-table/data-table-pagination.tsx
367
+ import {
368
+ IconChevronLeft,
369
+ IconChevronRight as IconChevronRight2,
370
+ IconChevronsLeft,
371
+ IconChevronsRight
372
+ } from "@tabler/icons-react";
373
+
262
374
  // src/components/select.tsx
263
375
  import * as SelectPrimitive from "@radix-ui/react-select";
264
376
  import { IconCheck, IconChevronDown, IconChevronUp } from "@tabler/icons-react";
265
- import { jsx as jsx5, jsxs as jsxs2 } from "react/jsx-runtime";
377
+ import { jsx as jsx8, jsxs as jsxs4 } from "react/jsx-runtime";
266
378
  function Select({
267
379
  ...props
268
380
  }) {
269
- return /* @__PURE__ */ jsx5(SelectPrimitive.Root, { "data-slot": "select", ...props });
381
+ return /* @__PURE__ */ jsx8(SelectPrimitive.Root, { "data-slot": "select", ...props });
270
382
  }
271
383
  function SelectValue({
272
384
  ...props
273
385
  }) {
274
- return /* @__PURE__ */ jsx5(SelectPrimitive.Value, { "data-slot": "select-value", ...props });
386
+ return /* @__PURE__ */ jsx8(SelectPrimitive.Value, { "data-slot": "select-value", ...props });
275
387
  }
276
388
  function SelectTrigger({
277
389
  className,
@@ -279,7 +391,7 @@ function SelectTrigger({
279
391
  children,
280
392
  ...props
281
393
  }) {
282
- return /* @__PURE__ */ jsxs2(
394
+ return /* @__PURE__ */ jsxs4(
283
395
  SelectPrimitive.Trigger,
284
396
  {
285
397
  "data-slot": "select-trigger",
@@ -291,7 +403,7 @@ function SelectTrigger({
291
403
  ...props,
292
404
  children: [
293
405
  children,
294
- /* @__PURE__ */ jsx5(SelectPrimitive.Icon, { asChild: true, children: /* @__PURE__ */ jsx5(IconChevronDown, { className: "size-4 opacity-50" }) })
406
+ /* @__PURE__ */ jsx8(SelectPrimitive.Icon, { asChild: true, children: /* @__PURE__ */ jsx8(IconChevronDown, { className: "size-4 opacity-50" }) })
295
407
  ]
296
408
  }
297
409
  );
@@ -303,7 +415,7 @@ function SelectContent({
303
415
  align = "center",
304
416
  ...props
305
417
  }) {
306
- return /* @__PURE__ */ jsx5(SelectPrimitive.Portal, { children: /* @__PURE__ */ jsxs2(
418
+ return /* @__PURE__ */ jsx8(SelectPrimitive.Portal, { children: /* @__PURE__ */ jsxs4(
307
419
  SelectPrimitive.Content,
308
420
  {
309
421
  "data-slot": "select-content",
@@ -316,8 +428,8 @@ function SelectContent({
316
428
  align,
317
429
  ...props,
318
430
  children: [
319
- /* @__PURE__ */ jsx5(SelectScrollUpButton, {}),
320
- /* @__PURE__ */ jsx5(
431
+ /* @__PURE__ */ jsx8(SelectScrollUpButton, {}),
432
+ /* @__PURE__ */ jsx8(
321
433
  SelectPrimitive.Viewport,
322
434
  {
323
435
  className: cn(
@@ -327,7 +439,7 @@ function SelectContent({
327
439
  children
328
440
  }
329
441
  ),
330
- /* @__PURE__ */ jsx5(SelectScrollDownButton, {})
442
+ /* @__PURE__ */ jsx8(SelectScrollDownButton, {})
331
443
  ]
332
444
  }
333
445
  ) });
@@ -337,7 +449,7 @@ function SelectItem({
337
449
  children,
338
450
  ...props
339
451
  }) {
340
- return /* @__PURE__ */ jsxs2(
452
+ return /* @__PURE__ */ jsxs4(
341
453
  SelectPrimitive.Item,
342
454
  {
343
455
  "data-slot": "select-item",
@@ -347,8 +459,8 @@ function SelectItem({
347
459
  ),
348
460
  ...props,
349
461
  children: [
350
- /* @__PURE__ */ jsx5("span", { className: "absolute right-2 flex size-3.5 items-center justify-center", children: /* @__PURE__ */ jsx5(SelectPrimitive.ItemIndicator, { children: /* @__PURE__ */ jsx5(IconCheck, { className: "size-4" }) }) }),
351
- /* @__PURE__ */ jsx5(SelectPrimitive.ItemText, { children })
462
+ /* @__PURE__ */ jsx8("span", { className: "absolute right-2 flex size-3.5 items-center justify-center", children: /* @__PURE__ */ jsx8(SelectPrimitive.ItemIndicator, { children: /* @__PURE__ */ jsx8(IconCheck, { className: "size-4" }) }) }),
463
+ /* @__PURE__ */ jsx8(SelectPrimitive.ItemText, { children })
352
464
  ]
353
465
  }
354
466
  );
@@ -357,7 +469,7 @@ function SelectScrollUpButton({
357
469
  className,
358
470
  ...props
359
471
  }) {
360
- return /* @__PURE__ */ jsx5(
472
+ return /* @__PURE__ */ jsx8(
361
473
  SelectPrimitive.ScrollUpButton,
362
474
  {
363
475
  "data-slot": "select-scroll-up-button",
@@ -366,7 +478,7 @@ function SelectScrollUpButton({
366
478
  className
367
479
  ),
368
480
  ...props,
369
- children: /* @__PURE__ */ jsx5(IconChevronUp, { className: "size-4" })
481
+ children: /* @__PURE__ */ jsx8(IconChevronUp, { className: "size-4" })
370
482
  }
371
483
  );
372
484
  }
@@ -374,7 +486,7 @@ function SelectScrollDownButton({
374
486
  className,
375
487
  ...props
376
488
  }) {
377
- return /* @__PURE__ */ jsx5(
489
+ return /* @__PURE__ */ jsx8(
378
490
  SelectPrimitive.ScrollDownButton,
379
491
  {
380
492
  "data-slot": "select-scroll-down-button",
@@ -383,13 +495,45 @@ function SelectScrollDownButton({
383
495
  className
384
496
  ),
385
497
  ...props,
386
- children: /* @__PURE__ */ jsx5(IconChevronDown, { className: "size-4" })
498
+ children: /* @__PURE__ */ jsx8(IconChevronDown, { className: "size-4" })
387
499
  }
388
500
  );
389
501
  }
390
502
 
391
503
  // src/components/data-table/data-table-pagination.tsx
392
- import { jsx as jsx6, jsxs as jsxs3 } from "react/jsx-runtime";
504
+ import { jsx as jsx9, jsxs as jsxs5 } from "react/jsx-runtime";
505
+ function addRange(pages, start, end) {
506
+ for (let i = start; i <= end; i++) {
507
+ pages.push(i);
508
+ }
509
+ }
510
+ function getPageNumbers(pageIndex, pageCount) {
511
+ const total = pageCount || 1;
512
+ const current = pageIndex + 1;
513
+ const pages = [];
514
+ if (total <= 1) {
515
+ return [1];
516
+ }
517
+ if (total <= 5) {
518
+ addRange(pages, 1, total);
519
+ return pages;
520
+ }
521
+ pages.push(1);
522
+ const isNearStart = current <= 3;
523
+ const isNearEnd = current >= total - 2;
524
+ if (isNearStart) {
525
+ addRange(pages, 2, 4);
526
+ pages.push("ellipsis", total);
527
+ } else if (isNearEnd) {
528
+ pages.push("ellipsis");
529
+ addRange(pages, total - 3, total);
530
+ } else {
531
+ pages.push("ellipsis");
532
+ addRange(pages, current - 1, current + 1);
533
+ pages.push("ellipsis", total);
534
+ }
535
+ return pages;
536
+ }
393
537
  function DataTablePagination({
394
538
  pageIndex,
395
539
  pageSize,
@@ -400,44 +544,40 @@ function DataTablePagination({
400
544
  onPageSizeChange,
401
545
  pageSizeOptions = [10, 20, 30, 50]
402
546
  }) {
547
+ const t = useTranslation("Pagination");
548
+ if (pageCount <= 1) {
549
+ return null;
550
+ }
403
551
  const canPreviousPage = pageIndex > 0;
404
552
  const canNextPage = pageIndex < pageCount - 1;
405
- return /* @__PURE__ */ jsxs3("div", { className: "flex items-center justify-between px-2 py-4", children: [
406
- /* @__PURE__ */ jsxs3("div", { className: "text-muted-foreground flex-1 text-sm", children: [
407
- selectedRows > 0 && /* @__PURE__ */ jsxs3("span", { children: [
408
- selectedRows,
409
- " of ",
410
- totalRows,
411
- " row(s) selected."
412
- ] }),
413
- selectedRows === 0 && /* @__PURE__ */ jsxs3("span", { children: [
414
- totalRows,
415
- " row(s) total."
416
- ] })
417
- ] }),
418
- /* @__PURE__ */ jsxs3("div", { className: "flex items-center space-x-6 lg:space-x-8", children: [
419
- /* @__PURE__ */ jsxs3("div", { className: "flex items-center space-x-2", children: [
420
- /* @__PURE__ */ jsx6("p", { className: "text-sm font-medium", children: "Rows per page" }),
421
- /* @__PURE__ */ jsxs3(
553
+ const pageNumbers = getPageNumbers(pageIndex, pageCount);
554
+ const rowLabel = totalRows === 1 ? t("row") : t("rows");
555
+ const hasSelection = selectedRows > 0;
556
+ const rowText = hasSelection ? `${selectedRows} ${t("of")} ${totalRows} ${rowLabel} ${t("selected")}` : `${totalRows} ${rowLabel} ${t("total")}`;
557
+ const pageText = `${t("page")} ${pageIndex + 1} ${t("of")} ${pageCount || 1}`;
558
+ return /* @__PURE__ */ jsxs5("div", { className: "flex flex-col gap-4 px-2 py-4 sm:flex-row sm:items-center sm:justify-between", children: [
559
+ /* @__PURE__ */ jsx9("div", { className: "text-muted-foreground text-sm", children: /* @__PURE__ */ jsxs5("span", { children: [
560
+ rowText,
561
+ /* @__PURE__ */ jsx9("span", { className: "mx-2", children: "\xB7" }),
562
+ pageText
563
+ ] }) }),
564
+ /* @__PURE__ */ jsxs5("div", { className: "flex flex-wrap items-center gap-4 sm:gap-6 lg:gap-8", children: [
565
+ /* @__PURE__ */ jsxs5("div", { className: "flex items-center gap-2", children: [
566
+ /* @__PURE__ */ jsx9("span", { className: "text-sm font-medium whitespace-nowrap", children: t("rowsPerPage") }),
567
+ /* @__PURE__ */ jsxs5(
422
568
  Select,
423
569
  {
424
570
  value: `${pageSize}`,
425
571
  onValueChange: (value) => onPageSizeChange(Number(value)),
426
572
  children: [
427
- /* @__PURE__ */ jsx6(SelectTrigger, { className: "h-8 w-[70px]", children: /* @__PURE__ */ jsx6(SelectValue, { placeholder: pageSize }) }),
428
- /* @__PURE__ */ jsx6(SelectContent, { side: "top", children: pageSizeOptions.map((size) => /* @__PURE__ */ jsx6(SelectItem, { value: `${size}`, children: size }, size)) })
573
+ /* @__PURE__ */ jsx9(SelectTrigger, { className: "h-8 w-[70px]", children: /* @__PURE__ */ jsx9(SelectValue, { placeholder: pageSize }) }),
574
+ /* @__PURE__ */ jsx9(SelectContent, { side: "top", children: pageSizeOptions.map((size) => /* @__PURE__ */ jsx9(SelectItem, { value: `${size}`, children: size }, size)) })
429
575
  ]
430
576
  }
431
577
  )
432
578
  ] }),
433
- /* @__PURE__ */ jsxs3("div", { className: "flex w-[100px] items-center justify-center text-sm font-medium", children: [
434
- "Page ",
435
- pageIndex + 1,
436
- " of ",
437
- pageCount || 1
438
- ] }),
439
- /* @__PURE__ */ jsxs3("div", { className: "flex items-center space-x-2", children: [
440
- /* @__PURE__ */ jsxs3(
579
+ /* @__PURE__ */ jsxs5("nav", { "aria-label": "Pagination", className: "flex items-center gap-1", children: [
580
+ /* @__PURE__ */ jsxs5(
441
581
  Button,
442
582
  {
443
583
  variant: "outline",
@@ -445,13 +585,14 @@ function DataTablePagination({
445
585
  className: "hidden h-8 w-8 lg:flex",
446
586
  onClick: () => onPageChange(0),
447
587
  disabled: !canPreviousPage,
588
+ "aria-label": t("firstPage"),
448
589
  children: [
449
- /* @__PURE__ */ jsx6("span", { className: "sr-only", children: "Go to first page" }),
450
- /* @__PURE__ */ jsx6(IconChevronsLeft, { className: "h-4 w-4" })
590
+ /* @__PURE__ */ jsx9(IconChevronsLeft, { className: "h-4 w-4" }),
591
+ /* @__PURE__ */ jsx9("span", { className: "sr-only", children: t("firstPage") })
451
592
  ]
452
593
  }
453
594
  ),
454
- /* @__PURE__ */ jsxs3(
595
+ /* @__PURE__ */ jsxs5(
455
596
  Button,
456
597
  {
457
598
  variant: "outline",
@@ -459,13 +600,44 @@ function DataTablePagination({
459
600
  className: "h-8 w-8",
460
601
  onClick: () => onPageChange(pageIndex - 1),
461
602
  disabled: !canPreviousPage,
603
+ "aria-label": t("previousPage"),
462
604
  children: [
463
- /* @__PURE__ */ jsx6("span", { className: "sr-only", children: "Go to previous page" }),
464
- /* @__PURE__ */ jsx6(IconChevronLeft, { className: "h-4 w-4" })
605
+ /* @__PURE__ */ jsx9(IconChevronLeft, { className: "h-4 w-4" }),
606
+ /* @__PURE__ */ jsx9("span", { className: "sr-only", children: t("previousPage") })
465
607
  ]
466
608
  }
467
609
  ),
468
- /* @__PURE__ */ jsxs3(
610
+ pageNumbers.map((page, idx) => {
611
+ if (page === "ellipsis") {
612
+ const prevPage = idx > 0 ? pageNumbers[idx - 1] : null;
613
+ const nextPage = idx < pageNumbers.length - 1 ? pageNumbers[idx + 1] : null;
614
+ return /* @__PURE__ */ jsx9(
615
+ "span",
616
+ {
617
+ className: "flex h-8 w-8 items-center justify-center text-muted-foreground",
618
+ "aria-hidden": "true",
619
+ children: "..."
620
+ },
621
+ `ellipsis-${prevPage}-${nextPage}`
622
+ );
623
+ }
624
+ const pageNum = page;
625
+ const isActive = pageNum === pageIndex + 1;
626
+ return /* @__PURE__ */ jsx9(
627
+ Button,
628
+ {
629
+ variant: isActive ? "default" : "outline",
630
+ size: "icon",
631
+ className: "h-8 w-8",
632
+ onClick: () => onPageChange(pageNum - 1),
633
+ "aria-label": `${t("goToPage")} ${pageNum}`,
634
+ "aria-current": isActive ? "page" : void 0,
635
+ children: pageNum
636
+ },
637
+ pageNum
638
+ );
639
+ }),
640
+ /* @__PURE__ */ jsxs5(
469
641
  Button,
470
642
  {
471
643
  variant: "outline",
@@ -473,13 +645,14 @@ function DataTablePagination({
473
645
  className: "h-8 w-8",
474
646
  onClick: () => onPageChange(pageIndex + 1),
475
647
  disabled: !canNextPage,
648
+ "aria-label": t("nextPage"),
476
649
  children: [
477
- /* @__PURE__ */ jsx6("span", { className: "sr-only", children: "Go to next page" }),
478
- /* @__PURE__ */ jsx6(IconChevronRight, { className: "h-4 w-4" })
650
+ /* @__PURE__ */ jsx9(IconChevronRight2, { className: "h-4 w-4" }),
651
+ /* @__PURE__ */ jsx9("span", { className: "sr-only", children: t("nextPage") })
479
652
  ]
480
653
  }
481
654
  ),
482
- /* @__PURE__ */ jsxs3(
655
+ /* @__PURE__ */ jsxs5(
483
656
  Button,
484
657
  {
485
658
  variant: "outline",
@@ -487,9 +660,10 @@ function DataTablePagination({
487
660
  className: "hidden h-8 w-8 lg:flex",
488
661
  onClick: () => onPageChange(pageCount - 1),
489
662
  disabled: !canNextPage,
663
+ "aria-label": t("lastPage"),
490
664
  children: [
491
- /* @__PURE__ */ jsx6("span", { className: "sr-only", children: "Go to last page" }),
492
- /* @__PURE__ */ jsx6(IconChevronsRight, { className: "h-4 w-4" })
665
+ /* @__PURE__ */ jsx9(IconChevronsRight, { className: "h-4 w-4" }),
666
+ /* @__PURE__ */ jsx9("span", { className: "sr-only", children: t("lastPage") })
493
667
  ]
494
668
  }
495
669
  )
@@ -503,17 +677,17 @@ import { IconSettings } from "@tabler/icons-react";
503
677
 
504
678
  // src/components/dropdown-menu.tsx
505
679
  import * as DropdownMenuPrimitive from "@radix-ui/react-dropdown-menu";
506
- import { IconCheck as IconCheck2, IconChevronRight as IconChevronRight2, IconCircle } from "@tabler/icons-react";
507
- import { jsx as jsx7, jsxs as jsxs4 } from "react/jsx-runtime";
680
+ import { IconCheck as IconCheck2, IconChevronRight as IconChevronRight3, IconCircle } from "@tabler/icons-react";
681
+ import { jsx as jsx10, jsxs as jsxs6 } from "react/jsx-runtime";
508
682
  function DropdownMenu({
509
683
  ...props
510
684
  }) {
511
- return /* @__PURE__ */ jsx7(DropdownMenuPrimitive.Root, { "data-slot": "dropdown-menu", ...props });
685
+ return /* @__PURE__ */ jsx10(DropdownMenuPrimitive.Root, { "data-slot": "dropdown-menu", ...props });
512
686
  }
513
687
  function DropdownMenuTrigger({
514
688
  ...props
515
689
  }) {
516
- return /* @__PURE__ */ jsx7(
690
+ return /* @__PURE__ */ jsx10(
517
691
  DropdownMenuPrimitive.Trigger,
518
692
  {
519
693
  "data-slot": "dropdown-menu-trigger",
@@ -526,7 +700,7 @@ function DropdownMenuContent({
526
700
  sideOffset = 4,
527
701
  ...props
528
702
  }) {
529
- return /* @__PURE__ */ jsx7(DropdownMenuPrimitive.Portal, { children: /* @__PURE__ */ jsx7(
703
+ return /* @__PURE__ */ jsx10(DropdownMenuPrimitive.Portal, { children: /* @__PURE__ */ jsx10(
530
704
  DropdownMenuPrimitive.Content,
531
705
  {
532
706
  "data-slot": "dropdown-menu-content",
@@ -545,7 +719,7 @@ function DropdownMenuCheckboxItem({
545
719
  checked,
546
720
  ...props
547
721
  }) {
548
- return /* @__PURE__ */ jsxs4(
722
+ return /* @__PURE__ */ jsxs6(
549
723
  DropdownMenuPrimitive.CheckboxItem,
550
724
  {
551
725
  "data-slot": "dropdown-menu-checkbox-item",
@@ -556,7 +730,7 @@ function DropdownMenuCheckboxItem({
556
730
  checked,
557
731
  ...props,
558
732
  children: [
559
- /* @__PURE__ */ jsx7("span", { className: "pointer-events-none absolute left-2 flex size-3.5 items-center justify-center", children: /* @__PURE__ */ jsx7(DropdownMenuPrimitive.ItemIndicator, { children: /* @__PURE__ */ jsx7(IconCheck2, { className: "size-4" }) }) }),
733
+ /* @__PURE__ */ jsx10("span", { className: "pointer-events-none absolute left-2 flex size-3.5 items-center justify-center", children: /* @__PURE__ */ jsx10(DropdownMenuPrimitive.ItemIndicator, { children: /* @__PURE__ */ jsx10(IconCheck2, { className: "size-4" }) }) }),
560
734
  children
561
735
  ]
562
736
  }
@@ -567,7 +741,7 @@ function DropdownMenuLabel({
567
741
  inset,
568
742
  ...props
569
743
  }) {
570
- return /* @__PURE__ */ jsx7(
744
+ return /* @__PURE__ */ jsx10(
571
745
  DropdownMenuPrimitive.Label,
572
746
  {
573
747
  "data-slot": "dropdown-menu-label",
@@ -584,7 +758,7 @@ function DropdownMenuSeparator({
584
758
  className,
585
759
  ...props
586
760
  }) {
587
- return /* @__PURE__ */ jsx7(
761
+ return /* @__PURE__ */ jsx10(
588
762
  DropdownMenuPrimitive.Separator,
589
763
  {
590
764
  "data-slot": "dropdown-menu-separator",
@@ -595,29 +769,29 @@ function DropdownMenuSeparator({
595
769
  }
596
770
 
597
771
  // src/components/data-table/data-table-view-options.tsx
598
- import { jsx as jsx8, jsxs as jsxs5 } from "react/jsx-runtime";
772
+ import { jsx as jsx11, jsxs as jsxs7 } from "react/jsx-runtime";
599
773
  function DataTableViewOptions({
600
774
  table
601
775
  }) {
602
- return /* @__PURE__ */ jsxs5(DropdownMenu, { children: [
603
- /* @__PURE__ */ jsx8(DropdownMenuTrigger, { asChild: true, children: /* @__PURE__ */ jsxs5(
776
+ return /* @__PURE__ */ jsxs7(DropdownMenu, { children: [
777
+ /* @__PURE__ */ jsx11(DropdownMenuTrigger, { asChild: true, children: /* @__PURE__ */ jsxs7(
604
778
  Button,
605
779
  {
606
780
  variant: "outline",
607
781
  size: "sm",
608
782
  className: "ml-auto hidden h-8 lg:flex",
609
783
  children: [
610
- /* @__PURE__ */ jsx8(IconSettings, { className: "mr-2 h-4 w-4" }),
784
+ /* @__PURE__ */ jsx11(IconSettings, { className: "mr-2 h-4 w-4" }),
611
785
  "View"
612
786
  ]
613
787
  }
614
788
  ) }),
615
- /* @__PURE__ */ jsxs5(DropdownMenuContent, { align: "end", className: "w-[150px]", children: [
616
- /* @__PURE__ */ jsx8(DropdownMenuLabel, { children: "Toggle columns" }),
617
- /* @__PURE__ */ jsx8(DropdownMenuSeparator, {}),
789
+ /* @__PURE__ */ jsxs7(DropdownMenuContent, { align: "end", className: "w-[150px]", children: [
790
+ /* @__PURE__ */ jsx11(DropdownMenuLabel, { children: "Toggle columns" }),
791
+ /* @__PURE__ */ jsx11(DropdownMenuSeparator, {}),
618
792
  table.getAllColumns().filter(
619
793
  (column) => typeof column.accessorFn !== "undefined" && column.getCanHide()
620
- ).map((column) => /* @__PURE__ */ jsx8(
794
+ ).map((column) => /* @__PURE__ */ jsx11(
621
795
  DropdownMenuCheckboxItem,
622
796
  {
623
797
  className: "capitalize",
@@ -632,6 +806,7 @@ function DataTableViewOptions({
632
806
  }
633
807
  export {
634
808
  DataTable,
809
+ DataTableAction,
635
810
  DataTableColumnHeader,
636
811
  DataTablePagination,
637
812
  DataTableViewOptions