528 lines
15 KiB
Vue
528 lines
15 KiB
Vue
<script setup>
|
|
import PatientPrescriptionDetail from '@/layouts/components/PatientPrescriptionDetail.vue';
|
|
import QueueComponent from '@/layouts/components/QueueComponent.vue';
|
|
import { computed } from 'vue';
|
|
import { useRouter } from 'vue-router';
|
|
import { useTheme } from 'vuetify';
|
|
import { useStore } from 'vuex';
|
|
const router = useRouter()
|
|
const store = useStore()
|
|
const isMobile = ref(window.innerWidth <= 768);
|
|
const prescriptionModelForm = ref(false)
|
|
const search = ref('');
|
|
const loading = ref(true);
|
|
const page = ref(1);
|
|
const itemsPerPage = ref(10);
|
|
const pageCount = ref(0);
|
|
const itemsPrescriptions = ref([]);
|
|
const show = ref(false)
|
|
const prescriptionDetail = ref(false);
|
|
const selectedItem = ref(null);
|
|
const PrescriptionData = ref('');
|
|
const isSelected = ref(false);
|
|
const isPrintable = ref(false);
|
|
// Components
|
|
const selectedRows = ref([]);
|
|
|
|
const vuetifyTheme = useTheme()
|
|
const userRole = localStorage.getItem('user_role'); // Fetch user role from local storage
|
|
const isAgent = computed(() => userRole.toLowerCase() === 'agent');
|
|
|
|
const queueComp = ref(null);
|
|
|
|
|
|
const headers = [
|
|
{ key: 'action', title: '', sortable: false },
|
|
{ key: 'name', title: 'Name' },
|
|
{ key: 'brand', title: 'Brand' },
|
|
{ key: 'from', title: 'From' },
|
|
{ key: 'direction_quantity', title: 'Direction Quantity' },
|
|
{ key: 'dosage', title: 'Dosage' },
|
|
{ key: 'quantity', title: 'Quantity' },
|
|
{ key: 'refill_quantity', title: 'Refill Quantity', align: 'center' },
|
|
{ key: 'status', title: 'status' },
|
|
|
|
];
|
|
|
|
onMounted(async () => {
|
|
const navbar = document.querySelector('.layout-navbar');
|
|
const callDiv = document.querySelector('.layout-page-content');
|
|
if (navbar) {
|
|
navbar.style.display = 'block';
|
|
}
|
|
if (callDiv)
|
|
callDiv.style.padding = '1.5rem';
|
|
console.log("router", store.getters.getCurrentPage)
|
|
if (userRole === 'agent') {
|
|
await getprescriptionList()
|
|
}
|
|
window.addEventListener('resize', checkMobile);
|
|
|
|
});
|
|
|
|
const checkMobile = () => {
|
|
isMobile.value = window.innerWidth <= 768;
|
|
};
|
|
const formatDateDate = (date) => {
|
|
const messageDate = new Date(date);
|
|
const options = {
|
|
year: 'numeric',
|
|
month: 'long',
|
|
day: 'numeric',
|
|
hour: '2-digit',
|
|
minute: '2-digit'
|
|
};
|
|
return messageDate.toLocaleDateString('en-US', options).replace(/\//g, '-');
|
|
};
|
|
const getStatusColor = (status) => {
|
|
switch (status) {
|
|
case 'pending':
|
|
return 'warning'; // Use Vuetify's warning color (typically yellow)
|
|
case 'shipped':
|
|
return '#45B8AC'; // Use Vuetify's primary color (typically blue)
|
|
case 'delivered':
|
|
return 'green';
|
|
case 'returned':
|
|
return 'red';
|
|
case 'results':
|
|
return '#34568B';
|
|
default:
|
|
return 'warning'; // Use Vuetify's grey color for any other status
|
|
}
|
|
};
|
|
const getprescriptionList = async () => {
|
|
let Calluser = localStorage.getItem('call_user')
|
|
let patient = JSON.parse(Calluser)
|
|
await store.dispatch('getPrescriptions', {
|
|
patient_id: patient.id,
|
|
appointment_id: patient.appointment.id
|
|
|
|
})
|
|
loading.value = false;
|
|
itemsPrescriptions.value = store.getters.getPrescriptionList
|
|
// await axios.post(`/agent/api/get-patient-prescriptions/${patient.id}/${patient.appointments.id}`, {}, {
|
|
// headers: {
|
|
// 'Authorization': `Bearer ${localStorage.getItem('access_token')}`,
|
|
// }
|
|
// }).then(response => {
|
|
|
|
// console.log('Response prescriptions:', response.data);
|
|
|
|
|
|
// for (let data of response.data) {
|
|
// let dataObject = {}
|
|
// dataObject.name = data.prescription.name
|
|
// dataObject.brand = data.prescription.brand
|
|
// dataObject.from = data.prescription.from
|
|
// dataObject.direction_quantity = data.prescription.direction_quantity
|
|
// dataObject.dosage = data.prescription.dosage
|
|
// dataObject.quantity = data.prescription.quantity
|
|
// dataObject.refill_quantity = data.prescription.refill_quantity
|
|
// dataObject.actions = ''
|
|
// dataObject.id = data.prescription.id
|
|
// dataObject.comments = data.comments
|
|
// dataObject.direction_one = data.direction_one
|
|
// dataObject.direction_two= data.direction_two
|
|
// itemsPrescriptions.value.push(dataObject)
|
|
// }
|
|
|
|
// //itemsPrescriptions.value = response.data
|
|
// //itemsPrescriptions.value.push(dataObject)
|
|
//
|
|
// })
|
|
// .catch(error => {
|
|
// loading.value = false;
|
|
// console.error('Error:', error);
|
|
// });
|
|
|
|
|
|
};
|
|
|
|
const formattedPrescription = computed(() => {
|
|
console.log('>>>>itemsPrescriptions.value<<<', itemsPrescriptions.value)
|
|
return itemsPrescriptions.value;
|
|
});
|
|
|
|
const updateStatus = (status) => {
|
|
console.log('status', status);
|
|
if (status == '' || status == null) {
|
|
return 'Pending';
|
|
}
|
|
}
|
|
const openCallModel = async (type) => {
|
|
console.log('here')
|
|
if (queueComp.value) {
|
|
console.log(queueComp.value)
|
|
let Calluser = localStorage.getItem('call_user')
|
|
console.log('Calluser', Calluser)
|
|
queueComp.value.openDialog(JSON.parse(Calluser), type);
|
|
}
|
|
};
|
|
computed(async () => {
|
|
console.log('computed=====')
|
|
|
|
await getprescriptionList()
|
|
|
|
});
|
|
|
|
const handleFormSubmitted = (updatData) => {
|
|
itemsPrescriptions.value = updatData.getPrescriptionList
|
|
}
|
|
|
|
const openPrint = async (item) => {
|
|
console.log('itemP', item);
|
|
selectedItem.value = item;
|
|
PrescriptionData.value = item;
|
|
prescriptionDetail.value = true;
|
|
// localStorage.setItem('printData', JSON.stringify(item))
|
|
// isSelected.value = true;
|
|
// printReecpt();
|
|
};
|
|
|
|
// const printReecpt = () => {
|
|
// if (isSelected.value == true) {
|
|
// prescriptionDetail.value = true;
|
|
// } else {
|
|
// isPrintable.value = true;
|
|
// }
|
|
|
|
// }
|
|
|
|
// const selectedRows = ref([]);
|
|
|
|
// Watcher to detect changes in selection
|
|
const handleRowSelection = (selectedRos) => {
|
|
console.log('Selected items:', selectedRos, selectedRows.value);
|
|
// Detect rows that were added to the selection
|
|
};
|
|
const options = ref({});
|
|
const handleOptionsUpdate = (newOptions) => {
|
|
options.value = newOptions;
|
|
if (options.value.selectedAll) {
|
|
selectedRows.value = formattedPrescription.value;
|
|
console.log('Selected items:', selectedRows.value)// Set all items as selected
|
|
} else {
|
|
selectedRows.value = []; // Clear selected rows
|
|
}
|
|
};
|
|
|
|
|
|
|
|
</script>
|
|
|
|
<template>
|
|
|
|
<VDialog v-model="store.getters.getIsLoading" width="110" height="150" color="primary">
|
|
<VCardText class="" style="color: white !important;">
|
|
<div class="demo-space-x">
|
|
<VProgressCircular :size="40" color="primary" indeterminate />
|
|
</div>
|
|
</VCardText>
|
|
</VDialog>
|
|
<QueueComponent ref="queueComp" :isVisable="false" @addPrescription="handleFormSubmitted" />
|
|
<v-dialog v-model="prescriptionDetail" max-width="600"
|
|
:class="isMobile ? 'dialog_padding_mobile' : 'dialog_padding'">
|
|
<v-card class="pa-3 printReceipt">
|
|
<v-row>
|
|
<v-col class="text-right cross pb-5 ">
|
|
<v-btn icon color="transparent" small
|
|
@click="[prescriptionDetail = false, isSelected = false, selectedItem = '']">
|
|
<v-icon>mdi-close</v-icon>
|
|
</v-btn>
|
|
|
|
</v-col>
|
|
</v-row>
|
|
<PatientPrescriptionDetail :itemProps="PrescriptionData"></PatientPrescriptionDetail>
|
|
</v-card>
|
|
</v-dialog>
|
|
<v-row class='mb-1'>
|
|
<v-col cols="12" class="text-left" md="6">
|
|
<v-btn color="primary" size="small" class="p-5" @click="openCallModel('Prescription')">
|
|
New Prescriptions
|
|
</v-btn>
|
|
</v-col>
|
|
<v-col cols="12" class="text-right cross mr-5 pr-2">
|
|
<!-- <Img :src="PrintImg" height="60" width="60" ></Img> -->
|
|
<!-- <router-link to="/print" target="_blank">
|
|
|
|
<VIcon icon="tabler-printer" color="primary" class="mr-3"></VIcon>
|
|
</router-link> -->
|
|
</v-col>
|
|
</v-row>
|
|
<template v-if="formattedPrescription">
|
|
<v-row>
|
|
<!-- <VSnackbar v-model="isPrintable" :timeout="5000" location="top end" variant="flat" color="red">
|
|
Please select an item in the list.
|
|
</VSnackbar> -->
|
|
<v-col cols="12" md="12" class="pt-0">
|
|
<v-data-table :item-value="item => item" :headers="headers" :items="formattedPrescription"
|
|
:search="search" :loading="loading" :items-per-page.sync="itemsPerPage"
|
|
@page-count="pageCount = $event">
|
|
<template v-slot:top>
|
|
<v-toolbar flat :height="30">
|
|
<v-toolbar-title>Prescriptions</v-toolbar-title>
|
|
<v-divider class="mx-4" inset vertical></v-divider>
|
|
<v-spacer></v-spacer>
|
|
<v-text-field v-model="search" label="Search" single-line hide-details></v-text-field>
|
|
</v-toolbar>
|
|
</template>
|
|
<template v-slot:item.status="{ item }">
|
|
<v-chip :color="getStatusColor(item.status)" label size="small" variant="text">
|
|
{{ item.status }}
|
|
</v-chip>
|
|
</template>
|
|
<template v-slot:item.action="{ item }">
|
|
<VCheckbox :value="item === selectedItem" @click="openPrint(item)">
|
|
</VCheckbox>
|
|
</template>
|
|
</v-data-table>
|
|
</v-col>
|
|
</v-row>
|
|
<!-- <VExpansionPanels variant="accordion">
|
|
<VExpansionPanel v-for="item in itemsPrescriptions" :key="item">
|
|
<VExpansionPanelTitle collapse-icon="mdi-chevron-down" expand-icon="mdi-chevron-right">
|
|
<div class="order-header d-flex align-center">
|
|
<div class="order-info">
|
|
<span class="status-icon mr-2">
|
|
</span>
|
|
<div>
|
|
<h3 class="flex-grow-1 mb-1">{{ item.name }}</h3>
|
|
<small class="text-grey mt-3 fs-5">by {{ item.doctor.name
|
|
}} </small>
|
|
<br>
|
|
<small class="text-grey mt-3 fs-5">{{ formatDateDate(item.date
|
|
) }} </small>
|
|
|
|
</div>
|
|
</div>
|
|
<div class="order-status">
|
|
<p class="text-end fs-5 mb-0 pb-0 text-grey">
|
|
<v-chip :color="getStatusColor(item.status)" label size="small" variant="text">
|
|
{{ item.status }}
|
|
</v-chip>
|
|
</p>
|
|
</div>
|
|
</div>
|
|
</VExpansionPanelTitle>
|
|
<VExpansionPanelText class="pt-0">
|
|
<v-row class='mt-1'>
|
|
<v-col cols="12" md="4">
|
|
|
|
<p><span class='heading'>Brand:</span>{{ item.brand }}</p>
|
|
</v-col>
|
|
<v-col cols="12" md="4">
|
|
<p><span class='heading'>From:</span> {{ item.from }}</p>
|
|
</v-col>
|
|
<v-col cols="12" md="4">
|
|
<p><span class='heading'>Dosage:</span> {{ item.dosage }}</p>
|
|
</v-col>
|
|
</v-row>
|
|
<v-row class='mt-1'>
|
|
<v-col cols="12" md="4">
|
|
<p><span class='heading'>Quantity:</span> {{ item.quantity }}</p>
|
|
</v-col>
|
|
<v-col cols="12" md="4">
|
|
<p><span class='heading'>Direction Quantity:</span> {{ item.direction_quantity }}</p>
|
|
</v-col>
|
|
<v-col cols="12" md="4">
|
|
<p><span class='heading'>Direction One:</span> {{ item.direction_one }}</p>
|
|
</v-col>
|
|
</v-row>
|
|
<v-row class='mt-1'>
|
|
<v-col cols="12" md="4">
|
|
<p><span class='heading'>Direction Two:</span> {{ item.direction_two }}</p>
|
|
</v-col>
|
|
<v-col cols="12" md="4">
|
|
<p><span class='heading'>Refill Quantity:</span> {{ item.refill_quantity }}</p>
|
|
</v-col>
|
|
|
|
</v-row>
|
|
<v-row class='mt-1'>
|
|
<v-col cols="12" md="12">
|
|
<p><span class='heading'>Comments:</span> {{ item.comments }}</p>
|
|
</v-col>
|
|
|
|
|
|
</v-row>
|
|
|
|
|
|
|
|
|
|
|
|
</VExpansionPanelText>
|
|
</VExpansionPanel>
|
|
|
|
</VExpansionPanels> -->
|
|
|
|
</template>
|
|
<template v-else>
|
|
<v-card>
|
|
<v-card-text>
|
|
|
|
<p class="text-center pt-0 pb-0 mb-0">No data found</p>
|
|
|
|
</v-card-text>
|
|
</v-card>
|
|
</template>
|
|
|
|
|
|
|
|
|
|
</template>
|
|
|
|
<style lang="scss" scoped>
|
|
.printReceipt {
|
|
overflow: hidden !important;
|
|
}
|
|
|
|
.status-color {
|
|
background-color: rgb(228 228 255);
|
|
// color: red;
|
|
padding: 2px 10px;
|
|
border-radius: 5px
|
|
}
|
|
|
|
.success-color {
|
|
background-color: rgb(224 245 219);
|
|
// color: red;
|
|
padding: 2px 10px;
|
|
border-radius: 5px
|
|
}
|
|
|
|
.heading {
|
|
font-size: 13px;
|
|
font-weight: 600;
|
|
}
|
|
|
|
.status-arrow {
|
|
font-weight: bold;
|
|
color: green;
|
|
/* or any other desired color */
|
|
}
|
|
|
|
.order-header {
|
|
width: 100%;
|
|
display: flex;
|
|
justify-content: space-between;
|
|
align-items: center;
|
|
}
|
|
|
|
.order-info {
|
|
display: flex;
|
|
align-items: center;
|
|
}
|
|
|
|
.status-icon {
|
|
margin-right: 10px;
|
|
}
|
|
|
|
h3 {
|
|
margin: 0;
|
|
flex-grow: 1;
|
|
}
|
|
|
|
.order-status {
|
|
text-align: right;
|
|
}
|
|
|
|
.status-text {
|
|
display: flex;
|
|
align-items: center;
|
|
}
|
|
|
|
.status-arrow {
|
|
margin-left: 5px;
|
|
}
|
|
|
|
button.v-expansion-panel-title {
|
|
background-color: rgb(var(--v-theme-yellow)) !important;
|
|
color: #fff;
|
|
}
|
|
|
|
button.v-expansion-panel-title.bg-secondary {
|
|
background-color: rgb(var(--v-theme-yellow)) !important;
|
|
color: #fff;
|
|
}
|
|
|
|
button.v-expansion-panel-title {
|
|
background-color: rgb(var(--v-theme-yellow)) !important;
|
|
color: #fff;
|
|
}
|
|
|
|
.v-expansion-panel {
|
|
background-color: #fff;
|
|
border-radius: 16px;
|
|
box-shadow: 0px 4px 12px rgba(0, 0, 0, 0.1);
|
|
margin-bottom: 10px;
|
|
overflow: hidden;
|
|
transition: box-shadow 0.3s ease;
|
|
}
|
|
|
|
span.v-expansion-panel-title__icon {
|
|
color: #fff
|
|
}
|
|
|
|
.v-expansion-panel-title {
|
|
padding: 15px;
|
|
font-size: 13px;
|
|
font-weight: 600;
|
|
color: #333;
|
|
cursor: pointer;
|
|
display: flex;
|
|
justify-content: space-between;
|
|
align-items: center;
|
|
transition: background-color 0.3s ease, color 0.3s ease;
|
|
}
|
|
|
|
.v-expansion-panel-title.pt-0 {
|
|
padding-top: 0;
|
|
}
|
|
|
|
// .v-expansion-panel-title:hover {
|
|
// background-color: #f9f9f9;
|
|
// color: #222;
|
|
// }
|
|
|
|
.v-expansion-panel-title .mdi {
|
|
font-size: 20px;
|
|
color: #666;
|
|
transition: transform 0.3s ease, color 0.3s ease;
|
|
}
|
|
|
|
.v-expansion-panel-title.v-expansion-panel-title--active .mdi {
|
|
transform: rotate(180deg);
|
|
color: #222;
|
|
}
|
|
|
|
.cross {
|
|
padding: 0;
|
|
}
|
|
|
|
.v-expansion-panel-text {
|
|
padding: 10px 15px;
|
|
font-size: 13px;
|
|
color: #555;
|
|
border-top: 1px solid #eee;
|
|
}
|
|
|
|
.v-expansion-panel-text .d-flex {
|
|
margin-bottom: 24px;
|
|
}
|
|
|
|
.v-expansion-panel-text .d-flex>div {
|
|
flex: 1;
|
|
}
|
|
|
|
.v-expansion-panel-text p {
|
|
margin-bottom: 16px;
|
|
font-size: 14px;
|
|
}
|
|
|
|
.v-expansion-panel-text h3 {
|
|
font-size: 20px;
|
|
font-weight: 600;
|
|
margin-bottom: 16px;
|
|
color: #333;
|
|
}
|
|
</style>
|