-
-
+
+
+
+
+
-
-
-
-
-
-
-
-
-
+
+
-
-
-
-
+
+
+
-
-
+
+
+
+
+
+
+
-
-
-
+
+
+
+
Nastavitve pogleda
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
-
-
-
-
-
- {{ selectedCount }} izbran{{ selectedCount === 1 ? 'o' : 'ih' }}
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- Možnosti tabele
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- Izvozi
-
-
- CSV
-
-
-
- Excel
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- Izvozi
-
-
-
-
-
- CSV
-
-
- Excel
-
-
-
-
-
-
-
-
-
-
-
-
-
-
diff --git a/resources/js/Components/DataTable/DataTableToolbarExample.vue b/resources/js/Components/DataTable/DataTableToolbarExample.vue
new file mode 100644
index 0000000..0de48b8
--- /dev/null
+++ b/resources/js/Components/DataTable/DataTableToolbarExample.vue
@@ -0,0 +1,86 @@
+
+
+
+
+
+
+
+
+
+ Dodaj novo
+
+
+
+
+
+
+ Opcija 1
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ Akcija
+
+
+
+
+
+
+
Search: {{ search }}
+
Page Size: {{ pageSize }}
+
Selected: {{ selectedCount }}
+
+
+
diff --git a/resources/js/Components/DataTable/DataTableViewOptions.vue b/resources/js/Components/DataTable/DataTableViewOptions.vue
new file mode 100644
index 0000000..4e7a8a9
--- /dev/null
+++ b/resources/js/Components/DataTable/DataTableViewOptions.vue
@@ -0,0 +1,50 @@
+
+
+
+
+
+
+
+ Pogled
+
+
+
+ Toggle columns
+
+ column.toggleVisibility(!!value)"
+ >
+ {{ column.id }}
+
+
+
+
diff --git a/resources/js/Components/DataTable/MIGRATION.md b/resources/js/Components/DataTable/MIGRATION.md
new file mode 100644
index 0000000..22bccb0
--- /dev/null
+++ b/resources/js/Components/DataTable/MIGRATION.md
@@ -0,0 +1,291 @@
+# DataTable Migration Guide
+
+## Summary of Changes
+
+The DataTable component has been updated to follow **shadcn-vue** architecture patterns using **TanStack Table v8**. This provides better flexibility, more features, and follows industry-standard patterns.
+
+## What's New
+
+### ✅ Components Created/Updated
+
+1. **`DataTableNew2.vue`** - New main component with shadcn-vue architecture
+2. **`DataTableColumnHeader.vue`** - Already good, uses lucide-vue-next icons
+3. **`DataTablePagination.vue`** - Already follows shadcn-vue patterns
+4. **`DataTableViewOptions.vue`** - Already follows shadcn-vue patterns
+5. **`DataTableToolbar.vue`** - Already exists with advanced features
+6. **`columns-example.js`** - Column definition examples
+7. **`README.md`** - Comprehensive documentation
+8. **`DataTableExample.vue`** - Working example page
+
+### ✅ Utilities Added
+
+- **`valueUpdater()`** in `lib/utils.js` - Helper for TanStack Table state management
+
+## Key Improvements
+
+### 1. **FlexRender Integration**
+Now properly uses TanStack Table's FlexRender for column headers and cells:
+```vue
+
+```
+
+### 2. **Better Column Definitions**
+Supports both simple and advanced formats:
+
+**Simple:**
+```javascript
+{ key: 'name', label: 'Name', sortable: true }
+```
+
+**Advanced:**
+```javascript
+{
+ accessorKey: 'name',
+ header: ({ column }) => h(DataTableColumnHeader, { column, title: 'Name' }),
+ cell: ({ row }) => h('div', {}, row.getValue('name')),
+}
+```
+
+### 3. **Enhanced Features**
+- ✅ Row selection with checkboxes
+- ✅ Column visibility toggle
+- ✅ Advanced filtering
+- ✅ Better loading/empty states
+- ✅ Custom cell slots
+- ✅ Flexible toolbar
+
+### 4. **Better State Management**
+Uses `valueUpdater()` helper for proper Vue reactivity with TanStack Table:
+```javascript
+onSortingChange: (updater) => valueUpdater(updater, sorting)
+```
+
+## Migration Steps
+
+### Step 1: Update Imports
+
+**Before:**
+```vue
+import DataTable from '@/Components/DataTable/DataTable.vue';
+```
+
+**After:**
+```vue
+import DataTable from '@/Components/DataTable/DataTableNew2.vue';
+```
+
+### Step 2: Update Props
+
+**Before:**
+```vue
+
+```
+
+**After:**
+```vue
+
+```
+
+Main prop changes:
+- `rows` → `data`
+- Add `route-name` for server-side pagination
+
+### Step 3: Column Definitions
+
+Your existing simple column format still works:
+```javascript
+const columns = [
+ { key: 'id', label: 'ID', sortable: true },
+ { key: 'name', label: 'Name', sortable: true },
+];
+```
+
+But you can now use advanced format for more control:
+```javascript
+import { h } from 'vue';
+import DataTableColumnHeader from '@/Components/DataTable/DataTableColumnHeader.vue';
+
+const columns = [
+ {
+ accessorKey: 'name',
+ header: ({ column }) => h(DataTableColumnHeader, { column, title: 'Name' }),
+ cell: ({ row }) => h('div', { class: 'font-medium' }, row.getValue('name')),
+ },
+];
+```
+
+### Step 4: Custom Cell Rendering
+
+**Before:** Required editing component
+**After:** Use slots!
+
+```vue
+
+
+
+ {{ value }}
+
+
+
+```
+
+## Backward Compatibility
+
+The **old DataTable components are still available**:
+- `DataTable.vue` - Your current enhanced version
+- `DataTableServer.vue` - Your server-side version
+- `DataTableOld.vue` - Original version
+
+You can migrate pages gradually. Both old and new can coexist.
+
+## Example Migration
+
+### Before (Client/Index.vue)
+
+```vue
+
+
+
+
+
+```
+
+### After (Using DataTableNew2)
+
+```vue
+
+
+
+
+
+
+
+ {{ value }}
+
+
+
+
+```
+
+## Testing Your Migration
+
+1. **Check the example page:**
+ ```
+ Visit: /examples/datatable
+ ```
+ (You'll need to add a route for this)
+
+2. **Test features:**
+ - ✅ Sorting (click column headers)
+ - ✅ Filtering (use search input)
+ - ✅ Pagination (navigate pages)
+ - ✅ Row selection (if enabled)
+ - ✅ Column visibility (View button)
+
+3. **Check browser console:**
+ - No errors
+ - Events firing correctly
+
+## Common Issues
+
+### Issue: "FlexRender is not defined"
+**Solution:** Make sure you imported it:
+```javascript
+import { FlexRender } from '@tanstack/vue-table';
+```
+
+### Issue: Column not sorting
+**Solution:** Make sure `sortable: true` is set:
+```javascript
+{ key: 'name', label: 'Name', sortable: true }
+```
+
+### Issue: Server-side not working
+**Solution:** Provide both `meta` and `route-name`:
+```vue
+
+```
+
+### Issue: Custom cells not rendering
+**Solution:** Use the correct slot name format:
+```vue
+
+
+
+```
+
+## Need Help?
+
+1. Check `README.md` for detailed documentation
+2. Look at `columns-example.js` for column patterns
+3. Review `DataTableExample.vue` for working examples
+4. Check TanStack Table docs: https://tanstack.com/table/v8
+
+## Rollback Plan
+
+If you encounter issues, you can always use the old components:
+```vue
+import DataTable from '@/Components/DataTable/DataTable.vue';
+// or
+import DataTableServer from '@/Components/DataTable/DataTableServer.vue';
+```
+
+Nothing breaks your existing code!
diff --git a/resources/js/Components/DataTable/README.md b/resources/js/Components/DataTable/README.md
new file mode 100644
index 0000000..3234a96
--- /dev/null
+++ b/resources/js/Components/DataTable/README.md
@@ -0,0 +1,390 @@
+# DataTable Component - Usage Guide
+
+This DataTable component follows the shadcn-vue architecture and uses TanStack Table v8 for powerful table functionality.
+
+## Features
+
+- ✅ Client-side and server-side pagination
+- ✅ Sorting (single column)
+- ✅ Filtering/Search
+- ✅ Row selection
+- ✅ Column visibility toggle
+- ✅ Customizable column definitions
+- ✅ Loading states
+- ✅ Empty states
+- ✅ Flexible toolbar
+- ✅ Cell-level customization via slots
+- ✅ Responsive design
+- ✅ Laravel Inertia integration
+
+## Basic Usage
+
+### Simple Format (Recommended for basic tables)
+
+```vue
+
+
+
+
+
+```
+
+### Advanced Format (Full TanStack Table power)
+
+```vue
+
+
+
+
+
+```
+
+See `columns-example.js` for comprehensive column definition examples.
+
+## Props
+
+### Data Props
+- `columns` (Array, required) - Column definitions (simple or TanStack format)
+- `data` (Array, default: []) - Array of data objects
+- `meta` (Object, default: null) - Laravel pagination meta for server-side
+- `loading` (Boolean, default: false) - Loading state
+
+### Server-side Props
+- `routeName` (String) - Laravel route name for server-side requests
+- `routeParams` (Object) - Additional route parameters
+- `pageParamName` (String, default: 'page') - Custom page parameter name
+- `onlyProps` (Array) - Inertia.js only props
+- `preserveState` (Boolean, default: true)
+- `preserveScroll` (Boolean, default: true)
+
+### Sorting & Filtering
+- `sort` (Object, default: {key: null, direction: null})
+- `search` (String, default: '')
+- `filterColumn` (String) - Column to filter on
+- `filterPlaceholder` (String, default: 'Filter...')
+
+### Pagination
+- `showPagination` (Boolean, default: true)
+- `pageSize` (Number, default: 10)
+- `pageSizeOptions` (Array, default: [10, 25, 50, 100])
+
+### Features
+- `enableRowSelection` (Boolean, default: false)
+- `showToolbar` (Boolean, default: true)
+- `striped` (Boolean, default: false)
+- `hoverable` (Boolean, default: true)
+- `rowKey` (String|Function, default: 'id')
+
+### Empty State
+- `emptyText` (String, default: 'No results.')
+- `emptyIcon` (String|Object|Array)
+- `emptyDescription` (String)
+
+## Events
+
+- `@update:search` - Emitted when search changes
+- `@update:sort` - Emitted when sort changes
+- `@update:page` - Emitted when page changes
+- `@update:pageSize` - Emitted when page size changes
+- `@row:click` - Emitted when row is clicked
+- `@selection:change` - Emitted when selection changes
+
+## Client-side Example
+
+```vue
+
+
+
+
+
+```
+
+## Server-side Example (Laravel Inertia)
+
+### Controller
+```php
+public function index(Request $request)
+{
+ $query = Client::query();
+
+ // Search
+ if ($request->search) {
+ $query->where('name', 'like', "%{$request->search}%")
+ ->orWhere('email', 'like', "%{$request->search}%");
+ }
+
+ // Sort
+ if ($request->sort && $request->direction) {
+ $query->orderBy($request->sort, $request->direction);
+ }
+
+ $clients = $query->paginate($request->per_page ?? 10);
+
+ return Inertia::render('Clients/Index', [
+ 'clients' => $clients,
+ 'filters' => $request->only(['search', 'sort', 'direction']),
+ ]);
+}
+```
+
+### Vue Component
+```vue
+
+
+
+
+
+```
+
+## Custom Cell Rendering
+
+### Using Slots
+```vue
+
+
+
+
+
+ {{ value }}
+
+
+
+
+
+ Edit
+
+
+
+```
+
+### Using Column Definitions
+```javascript
+import { h } from 'vue';
+import { Badge } from '@/Components/ui/badge';
+
+export const columns = [
+ {
+ accessorKey: 'status',
+ header: 'Status',
+ cell: ({ row }) => {
+ const status = row.getValue('status');
+ return h(Badge, {
+ variant: status === 'active' ? 'default' : 'secondary'
+ }, () => status);
+ },
+ },
+];
+```
+
+## Custom Toolbar
+
+The new toolbar is simplified and follows shadcn-vue patterns:
+
+```vue
+
+
+
+
+
+
+
+
+
+ Export
+ Add New
+
+
+
+```
+
+Or completely replace the toolbar:
+
+```vue
+
+
+
+
+
+
+
+```
+
+## Row Selection
+
+```vue
+
+
+
+
+
+
+ Selected {{ selectedRows.length }} row(s)
+
+
+```
+
+## Row Click Handler
+
+```vue
+
+
+
+
+
+```
+
+## Tips
+
+1. **Column Keys**: Always use consistent keys/accessorKeys across your data
+2. **Server-side**: Always provide `meta` and `routeName` props together
+3. **Performance**: For large datasets, use server-side pagination
+4. **Styling**: Use column `class` property for custom styling
+5. **Slots**: Prefer slots for complex cell rendering over h() functions
+
+## Migration from Old DataTable
+
+### Before (Old API)
+```vue
+
+```
+
+### After (New API)
+```vue
+
+```
+
+Main changes:
+- `rows` → `data`
+- Added `route-name` prop for server-side
+- More consistent prop naming
+- Better TypeScript support
+- More flexible column definitions
+
+## Component Files
+
+- `DataTableNew2.vue` - Main table component
+- `DataTableColumnHeader.vue` - Sortable column header
+- `DataTablePagination.vue` - Pagination controls
+- `DataTableViewOptions.vue` - Column visibility toggle
+- `DataTableToolbar.vue` - Toolbar component
+- `columns-example.js` - Column definition examples
diff --git a/resources/js/Components/DataTable/TableActions.vue b/resources/js/Components/DataTable/TableActions.vue
index 5a8dc2f..f5c0254 100644
--- a/resources/js/Components/DataTable/TableActions.vue
+++ b/resources/js/Components/DataTable/TableActions.vue
@@ -1,31 +1,36 @@
-
-
-
+
+
+
-
-
-
+
+
+
-
-
+
+
-
-
diff --git a/resources/js/Components/DataTable/columns-example.js b/resources/js/Components/DataTable/columns-example.js
new file mode 100644
index 0000000..7fe26c6
--- /dev/null
+++ b/resources/js/Components/DataTable/columns-example.js
@@ -0,0 +1,267 @@
+import { h } from 'vue';
+import { Badge } from '@/Components/ui/badge';
+import { Button } from '@/Components/ui/button';
+import { Checkbox } from '@/Components/ui/checkbox';
+import {
+ DropdownMenu,
+ DropdownMenuContent,
+ DropdownMenuItem,
+ DropdownMenuLabel,
+ DropdownMenuSeparator,
+ DropdownMenuTrigger,
+} from '@/Components/ui/dropdown-menu';
+import { MoreHorizontal, ArrowUpDown } from 'lucide-vue-next';
+
+/**
+ * Example columns definition following shadcn-vue DataTable patterns
+ *
+ * Usage:
+ * import { columns } from './columns'
+ *
+ *
+ * This is a TypeScript-like example for JavaScript.
+ * The columns follow TanStack Table's ColumnDef format.
+ */
+
+/**
+ * Simple format - automatically converted to ColumnDef
+ * Use this for basic tables
+ */
+export const simpleColumns = [
+ { key: 'id', label: 'ID', sortable: true },
+ { key: 'name', label: 'Name', sortable: true },
+ { key: 'email', label: 'Email', sortable: true },
+ { key: 'status', label: 'Status', sortable: false },
+];
+
+/**
+ * Advanced format - full TanStack Table ColumnDef
+ * Use this for custom rendering, formatting, etc.
+ */
+export const advancedColumns = [
+ // Selection column (added automatically if enableRowSelection prop is true)
+ // {
+ // id: 'select',
+ // header: ({ table }) => {
+ // return h(Checkbox, {
+ // modelValue: table.getIsAllPageRowsSelected(),
+ // indeterminate: table.getIsSomePageRowsSelected(),
+ // 'onUpdate:modelValue': (value) => table.toggleAllPageRowsSelected(!!value),
+ // 'aria-label': 'Select all',
+ // });
+ // },
+ // cell: ({ row }) => {
+ // return h(Checkbox, {
+ // modelValue: row.getIsSelected(),
+ // 'onUpdate:modelValue': (value) => row.toggleSelected(!!value),
+ // 'aria-label': 'Select row',
+ // });
+ // },
+ // enableSorting: false,
+ // enableHiding: false,
+ // },
+
+ // ID column
+ {
+ accessorKey: 'id',
+ header: ({ column }) => {
+ return h(
+ Button,
+ {
+ variant: 'ghost',
+ onClick: () => column.toggleSorting(column.getIsSorted() === 'asc'),
+ },
+ () => ['ID', h(ArrowUpDown, { class: 'ml-2 h-4 w-4' })]
+ );
+ },
+ cell: ({ row }) => {
+ return h('div', { class: 'w-20 font-medium' }, row.getValue('id'));
+ },
+ },
+
+ // Name column
+ {
+ accessorKey: 'name',
+ header: 'Name',
+ cell: ({ row }) => {
+ return h('div', { class: 'font-medium' }, row.getValue('name'));
+ },
+ },
+
+ // Email column with custom rendering
+ {
+ accessorKey: 'email',
+ header: ({ column }) => {
+ return h(
+ Button,
+ {
+ variant: 'ghost',
+ onClick: () => column.toggleSorting(column.getIsSorted() === 'asc'),
+ },
+ () => ['Email', h(ArrowUpDown, { class: 'ml-2 h-4 w-4' })]
+ );
+ },
+ cell: ({ row }) => {
+ return h('div', { class: 'lowercase' }, row.getValue('email'));
+ },
+ },
+
+ // Amount column with formatting
+ {
+ accessorKey: 'amount',
+ header: () => h('div', { class: 'text-right' }, 'Amount'),
+ cell: ({ row }) => {
+ const amount = parseFloat(row.getValue('amount'));
+ const formatted = new Intl.NumberFormat('sl-SI', {
+ style: 'currency',
+ currency: 'EUR',
+ }).format(amount);
+
+ return h('div', { class: 'text-right font-medium' }, formatted);
+ },
+ },
+
+ // Status column with badge
+ {
+ accessorKey: 'status',
+ header: 'Status',
+ cell: ({ row }) => {
+ const status = row.getValue('status');
+ const variants = {
+ success: 'default',
+ pending: 'secondary',
+ failed: 'destructive',
+ };
+
+ return h(
+ Badge,
+ {
+ variant: variants[status] || 'outline',
+ },
+ () => status
+ );
+ },
+ },
+
+ // Actions column
+ {
+ id: 'actions',
+ enableHiding: false,
+ cell: ({ row }) => {
+ const item = row.original;
+
+ return h(
+ 'div',
+ { class: 'text-right' },
+ h(
+ DropdownMenu,
+ {},
+ {
+ default: () => [
+ h(
+ DropdownMenuTrigger,
+ { asChild: true },
+ {
+ default: () =>
+ h(
+ Button,
+ {
+ variant: 'ghost',
+ class: 'h-8 w-8 p-0',
+ },
+ {
+ default: () => [
+ h('span', { class: 'sr-only' }, 'Open menu'),
+ h(MoreHorizontal, { class: 'h-4 w-4' }),
+ ],
+ }
+ ),
+ }
+ ),
+ h(
+ DropdownMenuContent,
+ { align: 'end' },
+ {
+ default: () => [
+ h(DropdownMenuLabel, {}, () => 'Actions'),
+ h(
+ DropdownMenuItem,
+ {
+ onClick: () => navigator.clipboard.writeText(item.id),
+ },
+ () => 'Copy ID'
+ ),
+ h(DropdownMenuSeparator),
+ h(DropdownMenuItem, {}, () => 'View details'),
+ h(DropdownMenuItem, {}, () => 'Edit'),
+ ],
+ }
+ ),
+ ],
+ }
+ )
+ );
+ },
+ },
+];
+
+/**
+ * Payments example from shadcn-vue docs
+ */
+export const paymentColumns = [
+ {
+ accessorKey: 'status',
+ header: 'Status',
+ cell: ({ row }) => {
+ const status = row.getValue('status');
+ return h('div', { class: 'capitalize' }, status);
+ },
+ },
+ {
+ accessorKey: 'email',
+ header: ({ column }) => {
+ return h(
+ Button,
+ {
+ variant: 'ghost',
+ onClick: () => column.toggleSorting(column.getIsSorted() === 'asc'),
+ },
+ () => ['Email', h(ArrowUpDown, { class: 'ml-2 h-4 w-4' })]
+ );
+ },
+ cell: ({ row }) => h('div', { class: 'lowercase' }, row.getValue('email')),
+ },
+ {
+ accessorKey: 'amount',
+ header: () => h('div', { class: 'text-right' }, 'Amount'),
+ cell: ({ row }) => {
+ const amount = parseFloat(row.getValue('amount'));
+ const formatted = new Intl.NumberFormat('en-US', {
+ style: 'currency',
+ currency: 'USD',
+ }).format(amount);
+ return h('div', { class: 'text-right font-medium' }, formatted);
+ },
+ },
+];
+
+/**
+ * Example with custom cell slots
+ * Use template slots in your component:
+ *
+ *
+ *
+ *
+ * {{ value }}
+ *
+ *
+ *
+ */
+export const columnsWithSlots = [
+ { key: 'id', label: 'ID', sortable: true },
+ { key: 'name', label: 'Name', sortable: true },
+ { key: 'status', label: 'Status', sortable: false }, // Will use #cell-status slot
+ { key: 'email', label: 'Email', sortable: true },
+];
+
+export default advancedColumns;
diff --git a/resources/js/Components/DocumentsTable/DocumentsTable.vue b/resources/js/Components/DocumentsTable/DocumentsTable.vue
index 43ab17c..54dfc86 100644
--- a/resources/js/Components/DocumentsTable/DocumentsTable.vue
+++ b/resources/js/Components/DocumentsTable/DocumentsTable.vue
@@ -13,32 +13,47 @@ import {
faTrash,
faFileAlt,
} from "@fortawesome/free-solid-svg-icons";
-import { ref } from "vue";
+import { ref, computed } from "vue";
import { router } from "@inertiajs/vue3";
-import DataTable from "../DataTable/DataTable.vue";
+import DataTable from "../DataTable/DataTableNew2.vue";
import Dropdown from "@/Components/Dropdown.vue";
import DeleteDialog from "../Dialogs/DeleteDialog.vue";
import { Badge } from "@/Components/ui/badge";
+import TableActions from "@/Components/DataTable/TableActions.vue";
+import ActionMenuItem from "@/Components/DataTable/ActionMenuItem.vue";
+import { fmtDateTime } from "@/Utilities/functions";
const props = defineProps({
- documents: { type: Array, default: () => [] },
+ documents: { type: [Array, Object], default: () => [] },
viewUrlBuilder: { type: Function, default: null },
// Optional: direct download URL builder; if absent we emit 'download'
downloadUrlBuilder: { type: Function, default: null },
// Optional: direct delete URL builder; if absent we emit 'delete'
deleteUrlBuilder: { type: Function, default: null },
edit: { type: Boolean, default: false },
+ pageSize: {
+ type: Number,
+ default: 15,
+ },
+ pageSizeOptions: {
+ type: Array,
+ default: () => [10, 15, 25, 50, 100],
+ },
+ // Server-side pagination support
+ clientCase: { type: Object, default: null },
});
// Define columns for DataTable
const columns = [
- { key: 'name', label: 'Naziv' },
- { key: 'type', label: 'Vrsta' },
- { key: 'size', label: 'Velikost', align: 'right' },
- { key: 'created_at', label: 'Dodano' },
- { key: 'source', label: 'Vir' },
- { key: 'description', label: 'Opis', align: 'center' },
+ { key: "name", label: "Naziv", sortable: false },
+ { key: "type", label: "Vrsta", sortable: false },
+ { key: "size", label: "Velikost", align: "right", sortable: false },
+ { key: "created_at", label: "Dodano", sortable: false },
+ { key: "source", label: "Vir", sortable: false },
+ { key: "description", label: "Opis", align: "center", sortable: false },
+ { key: "actions", label: "", sortable: false, hideable: false, align: "center" },
];
+
// Derive a human-friendly source for a document: Case or Contract reference
const sourceLabel = (doc) => {
// Server can include optional documentable meta; fall back to type
@@ -50,6 +65,19 @@ const sourceLabel = (doc) => {
const emit = defineEmits(["view", "download", "delete", "edit"]);
+// Support both array and Resource Collection (object with data property)
+const documentsData = computed(() => {
+ if (Array.isArray(props.documents)) {
+ return props.documents;
+ }
+ return props.documents?.data || [];
+});
+
+// Check if using server-side pagination
+const isServerSide = computed(() => {
+ return !!(props.documents?.links && props.clientCase);
+});
+
const formatSize = (bytes) => {
if (bytes == null) return "-";
const thresh = 1024;
@@ -243,19 +271,27 @@ function closeActions() {
-
+
+
+
+
@@ -267,7 +303,12 @@ function closeActions() {
>
{{ row.name }}
- Public
+ Public
- {{ new Date(row.created_at).toLocaleString() }}
+
+ {{ row.created_by }}
+
+
+
+ {{ fmtDateTime(row.created_at) }}
+
+
- {{ sourceLabel(row) }}
+ {{ sourceLabel(row) }}
@@ -321,53 +375,29 @@ function closeActions() {
-
-
-
-
-
-
-
-
-
-
-
-
- Uredi
-
-
-
- Prenos
-
-
-
- Izbriši
-
-
-
-
-
+
+
+
+
+
+
+
+
diff --git a/resources/js/Components/Pagination.vue b/resources/js/Components/Pagination.vue
index 9dd9053..5a2dbb4 100644
--- a/resources/js/Components/Pagination.vue
+++ b/resources/js/Components/Pagination.vue
@@ -1,14 +1,40 @@