Files
KArtSell.Aegis/frontend/src/shared/ui/adapter/primevue/AgGridAdapter.vue
T

85 lines
2.1 KiB
Vue

<script setup lang="ts">
import { computed } from 'vue'
import { AgGridVue } from 'ag-grid-vue3'
import {
ClientSideRowModelModule,
ColumnAutoSizeModule,
CellStyleModule,
ValidationModule,
TextFilterModule,
themeQuartz,
ModuleRegistry,
RowSelectionModule,
type ColDef,
type RowClickedEvent
} from 'ag-grid-community'
import type { UiGridColumn } from '../contracts'
ModuleRegistry.registerModules([
ClientSideRowModelModule,
ColumnAutoSizeModule,
CellStyleModule,
ValidationModule,
TextFilterModule,
RowSelectionModule
])
const props = withDefaults(defineProps<{
rows: unknown[]
columns: UiGridColumn[]
loading?: boolean
height?: string
rowSelection?: 'single' | 'multiple' | 'none'
}>(), { loading: false, height: '32rem', rowSelection: 'single' })
const emit = defineEmits<{ rowSelected: [row: unknown] }>()
const columnDefs = computed<ColDef[]>(() => props.columns.map(column => ({
field: column.field,
headerName: column.header,
width: column.width,
minWidth: column.minWidth ?? 120,
sortable: column.sortable ?? true,
filter: column.filterable ?? true,
valueFormatter: column.formatter
? params => column.formatter?.(params.value, params.data) ?? ''
: undefined
})))
const rowSelectionOptions = computed(() => {
if (props.rowSelection === 'none') return undefined
return props.rowSelection === 'multiple'
? ({ mode: 'multiRow' } as const)
: ({ mode: 'singleRow' } as const)
})
function onRowClicked(event: RowClickedEvent): void {
if (event.data) emit('rowSelected', event.data)
}
</script>
<template>
<div class="ks-grid" :style="{ height }" :aria-busy="loading">
<AgGridVue
style="height: 100%; width: 100%"
:theme="themeQuartz"
:row-data="rows"
:column-defs="columnDefs"
:row-selection="rowSelectionOptions"
:loading="loading"
:suppress-no-rows-overlay="rows.length > 0"
@row-clicked="onRowClicked"
/>
</div>
</template>
<style scoped>
.ks-grid {
min-height: 12rem;
border: 1px solid var(--ks-color-neutral-200);
border-radius: var(--ks-radius-md);
overflow: hidden;
background: #fff;
}
</style>