Dev branch

This commit is contained in:
Simon Pocrnjič
2025-11-02 12:31:01 +01:00
parent 5f879c9436
commit 63e0958b66
241 changed files with 17686 additions and 7327 deletions
@@ -1,13 +1,15 @@
<script setup>
import { computed, ref, watch } from "vue";
import SkeletonTable from "@/Components/Skeleton/SkeletonTable.vue";
import EmptyState from "@/Components/EmptyState.vue";
import {
FwbTable,
FwbTableHead,
FwbTableHeadCell,
FwbTableBody,
FwbTableRow,
FwbTableCell,
} from "flowbite-vue";
Table,
TableHeader,
TableHead,
TableBody,
TableRow,
TableCell,
} from "@/Components/ui/table";
const props = defineProps({
columns: { type: Array, required: true }, // [{ key, label, sortable?, align?, class?, formatter? }]
@@ -197,42 +199,43 @@ function setPageSize(ps) {
<div
class="relative overflow-x-auto rounded-lg border border-gray-200 bg-white shadow-sm"
>
<FwbTable hoverable striped class="text-sm">
<FwbTableHead
<Table class="text-sm">
<TableHeader
class="sticky top-0 z-10 bg-gray-50/90 backdrop-blur border-b border-gray-200 shadow-sm"
>
<FwbTableHeadCell v-for="col in columns" :key="col.key" :class="col.class">
<button
v-if="col.sortable"
type="button"
class="inline-flex items-center gap-1 hover:text-indigo-600"
@click="toggleSort(col)"
:aria-sort="sort?.key === col.key ? sort.direction || 'none' : 'none'"
>
<span class="uppercase">{{ col.label }}</span>
<span v-if="sort?.key === col.key && sort.direction === 'asc'"></span>
<span v-else-if="sort?.key === col.key && sort.direction === 'desc'"
></span
<TableRow class="border-b">
<TableHead v-for="col in columns" :key="col.key" :class="col.class">
<button
v-if="col.sortable"
type="button"
class="inline-flex items-center gap-1 hover:text-indigo-600"
@click="toggleSort(col)"
:aria-sort="sort?.key === col.key ? sort.direction || 'none' : 'none'"
>
</button>
<span v-else>{{ col.label }}</span>
</FwbTableHeadCell>
<FwbTableHeadCell v-if="$slots.actions" class="w-px">&nbsp;</FwbTableHeadCell>
</FwbTableHead>
<span class="uppercase">{{ col.label }}</span>
<span v-if="sort?.key === col.key && sort.direction === 'asc'"></span>
<span v-else-if="sort?.key === col.key && sort.direction === 'desc'"
></span
>
</button>
<span v-else>{{ col.label }}</span>
</TableHead>
<TableHead v-if="$slots.actions" class="w-px">&nbsp;</TableHead>
</TableRow>
</TableHeader>
<FwbTableBody>
<TableBody>
<template v-if="!loading && pageRows.length">
<FwbTableRow
<TableRow
v-for="(row, idx) in pageRows"
:key="keyOf(row)"
@click="$emit('row:click', row)"
class="cursor-default"
class="cursor-default hover:bg-gray-50/50"
>
<FwbTableCell
<TableCell
v-for="col in columns"
:key="col.key"
:class="col.class"
:align="col.align || 'left'"
>
<template v-if="$slots['cell-' + col.key]">
<slot
@@ -255,33 +258,37 @@ function setPageSize(ps) {
<template v-else>
{{ col.formatter ? col.formatter(row) : row?.[col.key] ?? "" }}
</template>
</FwbTableCell>
<FwbTableCell v-if="$slots.actions" class="w-px text-right">
</TableCell>
<TableCell v-if="$slots.actions" class="w-px text-right">
<slot name="actions" :row="row" :index="idx" />
</FwbTableCell>
</FwbTableRow>
</TableCell>
</TableRow>
</template>
<template v-else-if="loading">
<FwbTableRow>
<FwbTableCell :colspan="columns.length + ($slots.actions ? 1 : 0)">
<div class="p-6 text-center text-gray-500">Nalagam...</div>
</FwbTableCell>
</FwbTableRow>
<TableRow>
<TableCell :colspan="columns.length + ($slots.actions ? 1 : 0)">
<SkeletonTable :rows="5" :cols="columns.length" />
</TableCell>
</TableRow>
</template>
<template v-else>
<FwbTableRow>
<FwbTableCell :colspan="columns.length + ($slots.actions ? 1 : 0)">
<TableRow>
<TableCell :colspan="columns.length + ($slots.actions ? 1 : 0)">
<slot name="empty">
<div class="p-6 text-center text-gray-500">{{ emptyText }}</div>
<EmptyState
:title="emptyText"
size="sm"
/>
</slot>
</FwbTableCell>
</FwbTableRow>
</TableCell>
</TableRow>
</template>
</FwbTableBody>
</FwbTable>
</TableBody>
</Table>
</div>
<nav
v-if="showPagination"
class="mt-3 flex flex-wrap items-center justify-between gap-3 text-sm text-gray-700"
aria-label="Pagination"
>