Paginator for DataTable

pull/12/head
cagataycivici 2019-06-29 14:29:19 +03:00
parent 793b2276af
commit 6f20655a74
5 changed files with 368 additions and 175 deletions

View File

@ -2,9 +2,18 @@
<div class="p-datatable p-component"> <div class="p-datatable p-component">
<slot></slot> <slot></slot>
<div class="p-datatable-wrapper"> <div class="p-datatable-wrapper">
<div class="p-datatable-header" v-if="$scopedSlots.header"> <div class="p-datatable-header" v-if="$slots.header">
<slot name="header"></slot> <slot name="header"></slot>
</div> </div>
<DTPaginator v-if="paginatorTop" :rows="rows" :first="first" :totalRecords="totalRecordsLength" :pageLinkSize="pageLinkSize" :template="paginatorTemplate" :rowsPerPageOptions="rowsPerPageOptions"
:currentPageReportTemplate="currentPageReportTemplate" :class="{'p-paginator-top': paginatorTop}" @page="onPage($event)">
<template #left v-if="$scopedSlots.paginatorLeft">
<slot name="paginatorLeft"></slot>
</template>
<template #right v-if="$scopedSlots.paginatorRight">
<slot name="paginatorRight"></slot>
</template>
</DTPaginator>
<table> <table>
<thead class="p-datatable-thead"> <thead class="p-datatable-thead">
<tr> <tr>
@ -14,7 +23,7 @@
</tr> </tr>
</thead> </thead>
<tbody class="p-datatable-tbody"> <tbody class="p-datatable-tbody">
<tr class="p-datatable-row" v-for="(rowData, index) of value" :key="getRowKey(rowData, index)"> <tr class="p-datatable-row" v-for="(rowData, index) of data" :key="getRowKey(rowData, index)">
<td v-for="(col,i) of columns" :key="col.columnKey||col.field||i" :style="col.bodyStyle" :class="col.bodyClass"> <td v-for="(col,i) of columns" :key="col.columnKey||col.field||i" :style="col.bodyStyle" :class="col.bodyClass">
<ColumnSlot :data="rowData" :column="col" type="body" v-if="col.$scopedSlots.body" /> <ColumnSlot :data="rowData" :column="col" type="body" v-if="col.$scopedSlots.body" />
<template v-else>{{resolveFieldData(rowData, col.field)}}</template> <template v-else>{{resolveFieldData(rowData, col.field)}}</template>
@ -22,12 +31,25 @@
</tr> </tr>
</tbody> </tbody>
</table> </table>
<DTPaginator v-if="paginatorBottom" :rows="rows" :first="first" :totalRecords="totalRecordsLength" :pageLinkSize="pageLinkSize" :template="paginatorTemplate" :rowsPerPageOptions="rowsPerPageOptions"
:currentPageReportTemplate="currentPageReportTemplate" :class="{'p-paginator-bottom': paginatorBottom}" @page="onPage($event)">
<template #left v-if="$scopedSlots.paginatorLeft">
<slot name="paginatorLeft"></slot>
</template>
<template #right v-if="$scopedSlots.paginatorRight">
<slot name="paginatorRight"></slot>
</template>
</DTPaginator>
<div class="p-datatable-footer" v-if="$slots.footer">
<slot name="footer"></slot>
</div>
</div> </div>
</div> </div>
</template> </template>
<script> <script>
import ObjectUtils from '../utils/ObjectUtils'; import ObjectUtils from '../utils/ObjectUtils';
import Paginator from '../paginator/Paginator';
const ColumnSlot = { const ColumnSlot = {
functional: true, functional: true,
@ -63,13 +85,67 @@ export default {
dataKey: { dataKey: {
type: String, type: String,
default: null default: null
},
rows: {
type: Number,
default: 0
},
first: {
type: Number,
default: 0
},
totalRecords: {
type: Number,
default: 0
},
paginator: {
type: Boolean,
default: false
},
paginatorPosition: {
type: String,
default: 'bottom'
},
alwaysShowPaginator: {
type: Boolean,
default: true
},
paginatorTemplate: {
type: String,
default: 'FirstPageLink PrevPageLink PageLinks NextPageLink LastPageLink RowsPerPageDropdown'
},
pageLinkSize: {
type: Number,
default: 5
},
rowsPerPageOptions: {
type: Array,
default: null
},
currentPageReportTemplate: {
type: String,
default: '({currentPage} of {totalPages})'
},
lazy: {
type: Boolean,
default: false
} }
}, },
data() { data() {
return { return {
columns: [] columns: [],
d_first: this.first,
d_rows: this.rows
}; };
}, },
watch: {
first(newValue) {
this.d_first = newValue;
},
rows(newValue) {
this.d_rows = newValue;
}
},
mounted() { mounted() {
this.columns = [...this.$children]; this.columns = [...this.$children];
}, },
@ -79,10 +155,65 @@ export default {
}, },
resolveFieldData(rowData, field) { resolveFieldData(rowData, field) {
return ObjectUtils.resolveFieldData(rowData, field); return ObjectUtils.resolveFieldData(rowData, field);
},
onPage(event) {
this.d_first = event.first;
this.d_rows = event.rows;
this.$emit('update:first', this.d_first);
this.$emit('update:rows', this.d_rows);
this.$emit('page', event);
} }
}, },
computed: {
data() {
if (this.value && this.value.length) {
let data = this.value;
/*if (data && data.length && this.sortField) {
data = this.sort();
}*/
if (this.paginator) {
const first = this.lazy ? 0 : this.d_first;
return data.slice(first, first + this.d_rows);
}
else {
return data;
}
}
else {
return null;
}
},
totalRecordsLength() {
if (this.totalRecords)
return this.totalRecords;
else
return this.value ? this.value.length : 0;
},
empty() {
return (!this.value || this.value.length === 0);
},
paginatorTop() {
if (this.paginatorPosition && (this.paginatorPosition !== 'bottom' || this.paginatorPosition === 'both')) {
return true
}
else
return null;
},
paginatorBottom() {
if (this.paginatorPosition && (this.paginatorPosition !== 'top' || this.paginatorPosition === 'both')) {
return true
}
else
return null;
},
},
components: { components: {
'ColumnSlot': ColumnSlot 'ColumnSlot': ColumnSlot,
'DTPaginator': Paginator
} }
} }
</script> </script>

View File

@ -3,7 +3,7 @@
<div class="p-dataview-header" v-if="$scopedSlots.header"> <div class="p-dataview-header" v-if="$scopedSlots.header">
<slot name="header"></slot> <slot name="header"></slot>
</div> </div>
<Paginator v-if="paginatorTop" :rows="rows" :first="first" :totalRecords="getTotalRecords" :pageLinkSize="pageLinkSize" :template="paginatorTemplate" :rowsPerPageOptions="rowsPerPageOptions" <DVPaginator v-if="paginatorTop" :rows="rows" :first="first" :totalRecords="getTotalRecords" :pageLinkSize="pageLinkSize" :template="paginatorTemplate" :rowsPerPageOptions="rowsPerPageOptions"
:currentPageReportTemplate="currentPageReportTemplate" :class="{'p-paginator-top': paginatorTop}" @page="onPage($event)"> :currentPageReportTemplate="currentPageReportTemplate" :class="{'p-paginator-top': paginatorTop}" @page="onPage($event)">
<template #left v-if="$scopedSlots.paginatorLeft"> <template #left v-if="$scopedSlots.paginatorLeft">
<slot name="paginatorLeft"></slot> <slot name="paginatorLeft"></slot>
@ -11,7 +11,7 @@
<template #right v-if="$scopedSlots.paginatorRight"> <template #right v-if="$scopedSlots.paginatorRight">
<slot name="paginatorRight"></slot> <slot name="paginatorRight"></slot>
</template> </template>
</Paginator> </DVPaginator>
<div class="p-dataview-content"> <div class="p-dataview-content">
<div class="p-grid"> <div class="p-grid">
<template v-for="(item,index) of items"> <template v-for="(item,index) of items">
@ -21,7 +21,7 @@
<div v-if="isEmpty" class="p-col-12">{{emptyMessage}}</div> <div v-if="isEmpty" class="p-col-12">{{emptyMessage}}</div>
</div> </div>
</div> </div>
<Paginator v-if="paginatorBottom" :rows="rows" :first="first" :totalRecords="getTotalRecords" :pageLinkSize="pageLinkSize" :template="paginatorTemplate" :rowsPerPageOptions="rowsPerPageOptions" <DVPaginator v-if="paginatorBottom" :rows="rows" :first="first" :totalRecords="getTotalRecords" :pageLinkSize="pageLinkSize" :template="paginatorTemplate" :rowsPerPageOptions="rowsPerPageOptions"
:currentPageReportTemplate="currentPageReportTemplate" :class="{'p-paginator-bottom': paginatorBottom}" @page="onPage($event)"> :currentPageReportTemplate="currentPageReportTemplate" :class="{'p-paginator-bottom': paginatorBottom}" @page="onPage($event)">
<template #left v-if="$scopedSlots.paginatorLeft"> <template #left v-if="$scopedSlots.paginatorLeft">
<slot name="paginatorLeft"></slot> <slot name="paginatorLeft"></slot>
@ -29,7 +29,7 @@
<template #right v-if="$scopedSlots.paginatorRight"> <template #right v-if="$scopedSlots.paginatorRight">
<slot name="paginatorRight"></slot> <slot name="paginatorRight"></slot>
</template> </template>
</Paginator> </DVPaginator>
<div class="p-dataview-footer" v-if="$scopedSlots.footer"> <div class="p-dataview-footer" v-if="$scopedSlots.footer">
<slot name="footer"></slot> <slot name="footer"></slot>
</div> </div>
@ -37,6 +37,8 @@
</template> </template>
<script> <script>
import ObjectUtils from '../utils/ObjectUtils'; import ObjectUtils from '../utils/ObjectUtils';
import Paginator from '../paginator/Paginator';
export default { export default {
props: { props: {
value: { value: {
@ -209,6 +211,9 @@
return null; return null;
} }
} }
},
components: {
'DVPaginator': Paginator
} }
} }
</script> </script>

View File

@ -116,6 +116,11 @@ export default new Router({
name: 'datatabletemplating', name: 'datatabletemplating',
component: () => import('./views/datatable/DataTableTemplatingDemo.vue') component: () => import('./views/datatable/DataTableTemplatingDemo.vue')
}, },
{
path: '/datatable/paginator',
name: 'datatablepaginator',
component: () => import('./views/datatable/DataTablePaginatorDemo.vue')
},
{ {
path: '/dataview', path: '/dataview',
name: 'dataview', name: 'dataview',

View File

@ -0,0 +1,44 @@
<template>
<div>
<DataTableSubMenu />
<div class="content-section introduction">
<div class="feature-intro">
<h1>DataTable - Paginator</h1>
<p>Pagination is enabled by setting paginator property to true and defining the rows attribute as the number of rows per page.</p>
</div>
</div>
<div class="content-section implementation">
<DataTable :value="cars" :paginator="true" :rows="10">
<Column field="vin" header="Vin"></Column>
<Column field="year" header="Year"></Column>
<Column field="brand" header="Brand"></Column>
<Column field="color" header="Color"></Column>
</DataTable>
</div>
</div>
</template>
<script>
import CarService from '../../service/CarService';
import DataTableSubMenu from './DataTableSubMenu';
export default {
data() {
return {
cars: null
}
},
carService: null,
created() {
this.carService = new CarService();
},
mounted() {
this.carService.getCarsLarge().then(data => this.cars = data);
},
components: {
'DataTableSubMenu': DataTableSubMenu
}
}
</script>

View File

@ -11,6 +11,12 @@
<div class="content-section implementation"> <div class="content-section implementation">
<DataTable :value="cars"> <DataTable :value="cars">
<template #header>
<div style="line-height:1.87em" class="clearfix">
<Button icon="pi pi-refresh" style="float: right"/>
List of Cars
</div>
</template>
<Column field="vin" header="Vin"></Column> <Column field="vin" header="Vin"></Column>
<Column field="year" header="Year"></Column> <Column field="year" header="Year"></Column>
<Column field="brand" header="Brand"> <Column field="brand" header="Brand">
@ -25,6 +31,9 @@
<Button type="button" icon="pi pi-pencil" class="p-button-warning"></Button> <Button type="button" icon="pi pi-pencil" class="p-button-warning"></Button>
</template> </template>
</Column> </Column>
<template #footer>
In total there are {{cars.length}} cars.
</template>
</DataTable> </DataTable>
</div> </div>
</div> </div>
@ -37,7 +46,6 @@ import DataTableSubMenu from './DataTableSubMenu';
export default { export default {
data() { data() {
return { return {
columns: null,
cars: null cars: null
} }
}, },