improvement: separate Table and Renderer

This commit is contained in:
Kazhnuz 2023-02-13 21:47:02 +01:00
parent f6fcf218d3
commit d62bbceef9
2 changed files with 145 additions and 111 deletions

View file

@ -1,9 +1,9 @@
<script lang="ts" setup>
import { computed, reactive, onMounted } from "vue";
import PaginatedFilteredTable from "@/utils/tables/PaginatedFilteredTable";
import type { TableField } from "@/utils/tables/types";
import { ref, onMounted } from "vue";
import type { TableField, TableItem } from "@/utils/tables/types";
import type { PropType } from "vue";
import axios from "axios";
import TableRenderer from "./TableRenderer.vue";
const props = defineProps({
fields: {
@ -20,21 +20,8 @@ const props = defineProps({
},
});
const DEFAULT_MAX_ITEM_BY_PAGE = 10;
const table = reactive(new PaginatedFilteredTable(DEFAULT_MAX_ITEM_BY_PAGE));
const filtersFieldMap = computed(() => {
return table?.filteredTable?.filtersFieldMap;
});
const displayedFieldKeys = computed(() => {
return table?.filteredTable?.table.displayedFieldKeys;
});
const paginatedList = computed(() => {
return table?.items;
});
const toLoad = ref(1);
const items = ref([] as TableItem[]);
onMounted(() => {
setTimeout(() => {
@ -43,106 +30,21 @@ onMounted(() => {
});
function refresh() {
table.fields = props.fields;
toLoad.value = props.files.length;
for (const file of props.files) {
const listItems = `/jdr/${props.category}/${file}.json`;
axios.get(listItems).then((response) => {
table.addItems(response.data);
table.currentPage = 0;
toLoad.value = toLoad.value - 1;
items.value = items.value.concat(response.data);
});
}
}
function switchFilter(filterSet: string | number, filterName: string | number) {
table.switchFilter(filterSet as string, filterName as string);
}
function removeFilter(filterSet: string | number) {
table.removeAllFilters(filterSet as string);
}
const currentPage = computed(() => {
return table?.currentPage;
});
const getTotalPage = computed(() => {
return table?.pageNumber;
});
function canGo(rel: number) {
return table?.canGo(rel);
}
function go(rel: number) {
table?.go(rel);
}
</script>
<template>
<div class="small-text" v-for="(filter, key) in filtersFieldMap" :key="key">
<strong>{{ filter.title }} : </strong>
<button
v-for="(isTrue, filterName) in filter.filters"
:key="filterName"
class="btn-small mb-0"
:class="{ 'btn-grey': !isTrue, 'btn-primary': isTrue }"
@click="switchFilter(key, filterName)"
>
{{ filterName }}
</button>
<button class="btn-small btn-secondary mb-0" @click="removeFilter(key)">
Vider filtres
</button>
</div>
<table class="pb-0 table-auto">
<thead>
<tr>
<th v-for="field in fields" :key="field.key">
{{ field.label }}
</th>
</tr>
</thead>
<tbody>
<tr v-for="(item, index) of paginatedList" :key="index">
<td v-for="(key, index2) in displayedFieldKeys" :key="index2">
{{ item[key] }}
</td>
</tr>
</tbody>
</table>
<div class="d-flex f-between f-middle nextprevious small-text">
<div>
<strong class="btn m-0 pages pl-0">
Page {{ currentPage + 1 }} / {{ getTotalPage + 1 }}
</strong>
</div>
<div>
<button
class="btn btn-grey m-0 mr-1"
:class="{ 'bg-grey': !canGo(-1), 'btn-secondary': canGo(-1) }"
@click="go(-1)"
>
Page précédante
</button>
<button
class="btn btn-grey m-0"
:class="{ 'bg-grey': !canGo(1), 'btn-secondary': canGo(1) }"
@click="go(1)"
>
Page suivante
</button>
</div>
</div>
<TableRenderer
:fields="fields"
:items="items"
v-if="toLoad === 0"
></TableRenderer>
</template>
<style lang="scss" scoped>
.small-text {
font-size: 0.8rem;
padding-bottom: 0.5rem;
}
.pages {
font-weight: 600;
}
</style>

View file

@ -0,0 +1,132 @@
<script lang="ts" setup>
import { computed, reactive, onMounted } from "vue";
import PaginatedFilteredTable from "@/utils/tables/PaginatedFilteredTable";
import type { TableField, TableItem } from "@/utils/tables/types";
import type { PropType } from "vue";
const props = defineProps({
fields: {
type: Array as PropType<TableField[]>,
default: () => [],
},
items: {
type: Array as PropType<TableItem[]>,
default: () => [],
},
});
const DEFAULT_MAX_ITEM_BY_PAGE = 10;
const table = reactive(new PaginatedFilteredTable(DEFAULT_MAX_ITEM_BY_PAGE));
const filtersFieldMap = computed(() => {
return table?.filteredTable?.filtersFieldMap;
});
const displayedFieldKeys = computed(() => {
return table?.filteredTable?.table.displayedFieldKeys;
});
const paginatedList = computed(() => {
return table?.items;
});
onMounted(() => {
table.fields = props.fields;
table.addItems(props.items);
table.currentPage = 0;
});
function switchFilter(filterSet: string | number, filterName: string | number) {
table.switchFilter(filterSet as string, filterName as string);
}
function removeFilter(filterSet: string | number) {
table.removeAllFilters(filterSet as string);
}
const currentPage = computed(() => {
return table?.currentPage;
});
const getTotalPage = computed(() => {
return table?.pageNumber;
});
function canGo(rel: number) {
return table?.canGo(rel);
}
function go(rel: number) {
table?.go(rel);
}
</script>
<template>
<div class="small-text" v-for="(filter, key) in filtersFieldMap" :key="key">
<strong>{{ filter.title }} : </strong>
<button
v-for="(isTrue, filterName) in filter.filters"
:key="filterName"
class="btn-small mb-0"
:class="{ 'btn-grey': !isTrue, 'btn-primary': isTrue }"
@click="switchFilter(key, filterName)"
>
{{ filterName }}
</button>
<button class="btn-small btn-secondary mb-0" @click="removeFilter(key)">
Vider filtres
</button>
</div>
<table class="pb-0 table-auto">
<thead>
<tr>
<th v-for="field in fields" :key="field.key">
{{ field.label }}
</th>
</tr>
</thead>
<tbody>
<tr v-for="(item, index) of paginatedList" :key="index">
<td v-for="(key, index2) in displayedFieldKeys" :key="index2">
{{ item[key] }}
</td>
</tr>
</tbody>
</table>
<div class="d-flex f-between f-middle nextprevious small-text">
<div>
<strong class="btn m-0 pages pl-0">
Page {{ currentPage + 1 }} / {{ getTotalPage + 1 }}
</strong>
</div>
<div>
<button
class="btn btn-grey m-0 mr-1"
:class="{ 'bg-grey': !canGo(-1), 'btn-secondary': canGo(-1) }"
@click="go(-1)"
>
Page précédante
</button>
<button
class="btn btn-grey m-0"
:class="{ 'bg-grey': !canGo(1), 'btn-secondary': canGo(1) }"
@click="go(1)"
>
Page suivante
</button>
</div>
</div>
</template>
<style lang="scss" scoped>
.small-text {
font-size: 0.8rem;
padding-bottom: 0.5rem;
}
.pages {
font-weight: 600;
}
</style>