=
<template>
<div>
<p>five</p>
<!-- Table Container Card -->
<b-card no-body class="mb-0">
<div class="m-2">
<!-- Table Top -->
<b-row>
<!-- Per Page -->
<b-col cols="12" md="6" class="d-flex align-items-center justify-content-start mb-1 mb-md-0">
<label>Show</label>
<b-form-select
v-model="queryBody.per_page"
:options="pageOptions"
:clearable="false"
@change="changePageCount"
class="per-page-selector d-inline-block mx-50"
/>
<label>entries</label>
</b-col>
<!-- Per Page -->
<!-- Search -->
<b-col cols="12" md="6">
<div class="d-flex align-items-center justify-content-end">
<b-input-group size="md" class="mr-2">
<b-form-input
v-model="filter"
type="search"
placeholder="Type here to Search ..."
v-on:keyup="findData"
@search="clearSearch"
></b-form-input>
<b-input-group-append>
<b-button
:disabled="!filter"
@click="findData"
variant="primary"
>Search</b-button>
</b-input-group-append>
</b-input-group>
<b-button variant="primary">
<span class="text-nowrap">Add</span>
</b-button>
</div>
</b-col>
</b-row>
</div>
<b-table
:busy="isTableLoading"
class="position-relative"
:items="itemsData"
responsive
:fields="fields"
primary-key="id"
no-local-sorting
@sort-changed="customSorting"
show-empty
empty-text="No matching records found"
>
<template v-slot:table-busy>
<div class="text-center text-primary my-2">
<b-spinner class="align-middle"></b-spinner>
</div>
</template>
<template v-slot:cell(actions)="row">
<b-dropdown variant="link" no-caret v-if="row.item.id !== -1">
<template #button-content>
<font-awesome-icon
:icon="['fas', 'ellipsis-vertical']"
class="align-middle text-body"
/>
</template>
<b-dropdown-item @click="viewTeam(row.item.name, row.item.id)">
<font-awesome-icon :icon="['fas', 'file-lines']" />
<span class="align-middle ml-50">Details</span>
</b-dropdown-item>
<b-dropdown-item @click="callEditTeam(row.item.name, row.item.id)">
<font-awesome-icon :icon="['fas', 'pen']" />
<span class="align-middle ml-50">Edit</span>
</b-dropdown-item>
<b-dropdown-item @click="openModal(row.item)">
<font-awesome-icon :icon="['fas', 'trash']" />
<span class="align-middle ml-50">Delete</span>
</b-dropdown-item>
</b-dropdown>
</template>
</b-table>
<div class="mx-2 mb-2">
<b-row>
<b-col cols="12" sm="6" class="d-flex align-items-center justify-content-center justify-content-sm-start">
<span class="text-muted">
Showing {{ pageMeta.from }} to {{ pageMeta.to }} of {{ totalRows }} entries
<span v-if="filter">(filtered from {{ rowsCount }} total entries)</span>
</span>
</b-col>
<!-- Pagination -->
<b-col cols="12" sm="6" class="d-flex align-items-center justify-content-center justify-content-sm-end">
<b-pagination
v-model="queryBody.page"
:total-rows="totalRows"
:per-page="queryBody.per_page"
@page-change="pagination"
first-number
last-number
class="mb-0 mt-1 mt-sm-0"
prev-class="prev-item"
next-class="next-item"
>
<template #prev-text>
<font-awesome-icon :icon="['fas', 'chevron-left']" />
</template>
<template #next-text>
<font-awesome-icon :icon="['fas', 'chevron-right']" />
</template>
</b-pagination>
</b-col>
</b-row>
</div>
</b-card>
<div></div>
</div>
</template>
<script>
import { ref, reactive, computed, watchEffect } from 'vue';
import axios from 'axios';
export default {
setup() {
const queryBody = reactive({
sort_by: '',
order: '',
page: 1,
per_page: 5,
role: '',
team: '',
});
const fields = reactive([
{ key: 'id', label: 'ID' },
{ key: 'name', label: 'Name' },
{ key: 'description', label: 'Description' },
{ key: 'actions', label: 'Actions' },
]);
const isTableLoading = ref(false);
const pageOptions = [5, 10, 25, 50, 100];
const totalRows = ref(1);
const filter = ref('');
const itemsData = ref([]);
const lastPage = ref(1);
const rowsCount = ref(0);
const refetchData = () => {
getData(queryBody);
};
const pageMeta = computed(() => {
const from = (queryBody.page - 1) * queryBody.per_page + 1;
const to =
queryBody.page * queryBody.per_page > totalRows.value
? totalRows.value
: queryBody.page * queryBody.per_page;
return { from, to };
});
const changePageCount = (per_page) => {
queryBody.page = 1;
queryBody.per_page = per_page;
getData(queryBody);
};
const findData = () => {
queryBody.query = filter.value;
getData(queryBody);
};
const customSorting = (ctx) => {
if (ctx.sortBy == '' || ctx.sortBy == null) {
return;
}
queryBody.order = ctx.sortDesc ? 'asc' : 'desc';
queryBody.sort_by = ctx.sortBy;
queryBody.page = 1;
getData(queryBody);
};
const clearSearch = (event) => {
if (event.target.value === '') {
if (!filter.value) {
queryBody.page = 1;
queryBody.per_page = 10;
delete queryBody.query;
getData(queryBody);
}
}
};
const formateResponse = (result) => {
let si_no = (queryBody.page - 1) * queryBody.per_page + 1;
itemsData.value = result.data.map((item, index) => ({
...item,
si_no: si_no + index + 1,
}));
let pagination = result;
queryBody.page = parseInt(pagination.current_page);
queryBody.per_page = parseInt(pagination.per_page, 10);
lastPage.value = pagination.last_page;
totalRows.value = pagination.total;
rowsCount.value = pagination.rows_count;
// if (itemsData.value.length === 1) {
// itemsData.value.push({
// id: -1,
// name: '',
// });
// }
};
const deleteEmptyKeys = (data) => {
let query = {};
for (let key in data) {
data[key] !== '' ? (query[key] = data[key]) : '';
}
return query;
};
const pagination =(pageNumber)=> {
console.log('vamsi',pageNumber);
this.queryBody.page=pageNumber;
this.getData(this.queryBody);
};
const getData = (params) => {
const queryParams = {
params: deleteEmptyKeys(params),
};
isTableLoading.value = true;
axios
.get('cards', queryParams)
.then((response) => {
formateResponse(response.data.data);
})
.catch((error) => {
console.error('Error fetching user data:', error);
})
.finally(() => {
isTableLoading.value = false;
});
};
watchEffect(() => {
getData(queryBody);
});
return {
queryBody,
pageOptions,
totalRows,
filter,
itemsData,
lastPage,
rowsCount,
refetchData,
changePageCount,
findData,
customSorting,
fields,
clearSearch,
deleteEmptyKeys,
getData,
formateResponse,
pageMeta,
pagination,
isTableLoading,
};
},
};
</script>
<style>
.per-page-selector {
width: 90px;
}
.custom-table {
overflow-x: auto;
white-space: nowrap !important;
}
.loader-container {
display: flex;
justify-content: center;
align-items: center;
height: 100px; /* Adjust the height as needed */
}
</style>
=
No comments:
Post a Comment