first commit

This commit is contained in:
Inshal
2024-05-29 22:34:28 +05:00
commit e63fc41a20
1470 changed files with 174828 additions and 0 deletions

View File

@@ -0,0 +1,126 @@
<script setup>
import { PerfectScrollbar } from 'vue3-perfect-scrollbar'
const props = defineProps({
isDrawerOpen: {
type: Boolean,
required: true,
},
})
const emit = defineEmits([
'update:isDrawerOpen',
'submit',
])
const invoiceBalance = ref()
const paymentAmount = ref()
const paymentDate = ref('')
const paymentMethod = ref()
const paymentNote = ref('')
const onSubmit = () => {
emit('update:isDrawerOpen', false)
emit('submit', {
invoiceBalance: invoiceBalance.value,
paymentAmount: paymentAmount.value,
paymentDate: paymentDate.value,
paymentMethod: paymentMethod.value,
paymentNote: paymentNote.value,
})
}
const handleDrawerModelValueUpdate = val => {
emit('update:isDrawerOpen', val)
}
</script>
<template>
<VNavigationDrawer
temporary
location="end"
:width="400"
:model-value="props.isDrawerOpen"
class="scrollable-content"
@update:model-value="handleDrawerModelValueUpdate"
>
<!-- 👉 Header -->
<AppDrawerHeaderSection
title="Add Payment"
@cancel="$emit('update:isDrawerOpen', false)"
/>
<VDivider />
<PerfectScrollbar :options="{ wheelPropagation: false }">
<VCard flat>
<VCardText>
<VForm @submit.prevent="onSubmit">
<VRow>
<VCol cols="12">
<VTextField
v-model="invoiceBalance"
label="Invoice Balance"
type="number"
placeholder="$99"
/>
</VCol>
<VCol cols="12">
<VTextField
v-model="paymentAmount"
label="Payment Amount"
type="number"
placeholder="$99"
/>
</VCol>
<VCol cols="12">
<AppDateTimePicker
v-model="paymentDate"
label="Payment Date"
placeholder="Select Date"
/>
</VCol>
<VCol cols="12">
<VSelect
v-model="paymentMethod"
label="Select Payment Method"
placeholder="Select Payment Method"
:items="['Cash', 'Bank Transfer', 'Debit', 'Credit', 'PayPal']"
/>
</VCol>
<VCol cols="12">
<VTextarea
v-model="paymentNote"
label="Internal Payment Note"
placeholder="Internal Payment Note"
/>
</VCol>
<VCol cols="12">
<VBtn
type="submit"
class="me-3"
>
Send
</VBtn>
<VBtn
type="reset"
color="secondary"
variant="outlined"
@click="$emit('update:isDrawerOpen', false)"
>
Cancel
</VBtn>
</VCol>
</VRow>
</VForm>
</VCardText>
</VCard>
</PerfectScrollbar>
</VNavigationDrawer>
</template>

View File

@@ -0,0 +1,334 @@
<script setup>
import InvoiceProductEdit from './InvoiceProductEdit.vue'
import { VNodeRenderer } from '@layouts/components/VNodeRenderer'
import { themeConfig } from '@themeConfig'
const props = defineProps({
data: {
type: null,
required: true,
},
})
const emit = defineEmits([
'push',
'remove',
])
const invoice = ref(props.data.invoice)
const salesperson = ref(props.data.salesperson)
const thanksNote = ref(props.data.thanksNote)
const note = ref(props.data.note)
// 👉 Clients
const clients = ref([])
// 👉 fetchClients
const fetchClients = async () => {
const { data, error } = await useApi('/apps/invoice/clients')
if (error.value)
console.log(error.value)
else
clients.value = data.value
}
fetchClients()
// 👉 Add item function
const addItem = () => {
emit('push', {
title: 'App Design',
cost: 24,
hours: 1,
description: 'Designed UI kit & app pages.',
})
}
const removeProduct = id => {
emit('remove', id)
}
</script>
<template>
<VCard class="pa-12">
<!-- SECTION Header -->
<div class="d-flex flex-wrap justify-space-between flex-column rounded bg-var-theme-background flex-sm-row gap-6 pa-6 mb-6">
<!-- 👉 Left Content -->
<div>
<div class="d-flex align-center mb-6">
<!-- 👉 Logo -->
<VNodeRenderer
:nodes="themeConfig.app.logo"
class="me-3"
/>
<!-- 👉 Title -->
<h6 class="font-weight-medium text-xl text-uppercase">
{{ themeConfig.app.title }}
</h6>
</div>
<!-- 👉 Address -->
<p class="text-high-emphasis mb-0">
Office 149, 450 South Brand Brooklyn
</p>
<p class="text-high-emphasis mb-0">
San Diego County, CA 91905, USA
</p>
<p class="text-high-emphasis mb-0">
+1 (123) 456 7891, +44 (876) 543 2198
</p>
</div>
<!-- 👉 Right Content -->
<div>
<!-- 👉 Invoice Id -->
<div class="d-flex align-start font-weight-medium justify-sm-end flex-column flex-sm-row text-lg mb-3">
<span
class="text-high-emphasis me-4"
style="inline-size: 5.625rem ;"
>Invoice:</span>
<span>
<VTextField
v-model="invoice.id"
disabled
density="compact"
prefix="#"
style="inline-size: 9.5rem;"
/>
</span>
</div>
<!-- 👉 Issue Date -->
<div class="d-flex align-start justify-sm-end flex-column flex-sm-row mb-3">
<span
class="text-high-emphasis me-4"
style="inline-size: 5.625rem;"
>Date Issued:</span>
<span style="inline-size: 9.5rem;">
<AppDateTimePicker
v-model="invoice.issuedDate"
density="compact"
placeholder="YYYY-MM-DD"
:config="{ position: 'auto right' }"
/>
</span>
</div>
<!-- 👉 Due Date -->
<div class="d-flex align-start justify-sm-end flex-column flex-sm-row mb-0">
<span
class="text-high-emphasis me-4"
style="inline-size: 5.625rem;"
>Due Date:</span>
<span style="min-inline-size: 9.5rem;">
<AppDateTimePicker
v-model="invoice.dueDate"
density="compact"
placeholder="YYYY-MM-DD"
:config="{ position: 'auto right' }"
/>
</span>
</div>
</div>
</div>
<!-- !SECTION -->
<VRow>
<VCol class="text-no-wrap">
<h6 class="text-h6 mb-4">
Invoice To:
</h6>
<VSelect
v-model="invoice.client"
:items="clients"
item-title="name"
item-value="name"
placeholder="Select Client"
return-object
class="mb-4"
style="inline-size: 11.875rem;"
/>
<p class="mb-0">
{{ invoice.client.name }}
</p>
<p class="mb-0">
{{ invoice.client.company }}
</p>
<p
v-if="invoice.client.address"
class="mb-0"
>
{{ invoice.client.address }}, {{ invoice.client.country }}
</p>
<p class="mb-0">
{{ invoice.client.contact }}
</p>
<p class="mb-0">
{{ invoice.client.companyEmail }}
</p>
</VCol>
<VCol class="text-no-wrap">
<h6 class="text-h6 mb-4">
Bill To:
</h6>
<table>
<tbody>
<tr>
<td class="pe-6">
Total Due:
</td>
<td>{{ props.data.paymentDetails.totalDue }}</td>
</tr>
<tr>
<td class="pe-6">
Bank Name:
</td>
<td>{{ props.data.paymentDetails.bankName }}</td>
</tr>
<tr>
<td class="pe-6">
Country:
</td>
<td>{{ props.data.paymentDetails.country }}</td>
</tr>
<tr>
<td class="pe-6">
IBAN:
</td>
<td>
<p class="text-wrap me-4">
{{ props.data.paymentDetails.iban }}
</p>
</td>
</tr>
<tr>
<td class="pe-6">
SWIFT Code:
</td>
<td>{{ props.data.paymentDetails.swiftCode }}</td>
</tr>
</tbody>
</table>
</VCol>
</VRow>
<VDivider class="my-6 border-dashed" />
<!-- 👉 Add purchased products -->
<div class="add-products-form">
<div
v-for="(product, index) in props.data.purchasedProducts"
:key="product.title"
class="mb-4"
>
<InvoiceProductEdit
:id="index"
:data="product"
@remove-product="removeProduct"
/>
</div>
<VBtn
size="small"
prepend-icon="ri-add-line"
@click="addItem"
>
Add Item
</VBtn>
</div>
<VDivider class="my-6 border-dashed" />
<!-- 👉 Total Amount -->
<div class="d-flex justify-space-between flex-wrap flex-column flex-sm-row">
<div class="mb-6 mb-sm-0">
<div class="d-flex align-center mb-4">
<h6 class="text-h6 me-2">
Salesperson:
</h6>
<VTextField
v-model="salesperson"
style="inline-size: 8rem;"
placeholder="John Doe"
/>
</div>
<VTextField
v-model="thanksNote"
placeholder="Thanks for your business"
/>
</div>
<div>
<table class="w-100">
<tbody>
<tr>
<td class="pe-16">
Subtotal:
</td>
<td :class="$vuetify.locale.isRtl ? 'text-start' : 'text-end'">
<h6 class="text-h6">
$1800
</h6>
</td>
</tr>
<tr>
<td class="pe-16">
Discount:
</td>
<td :class="$vuetify.locale.isRtl ? 'text-start' : 'text-end'">
<h6 class="text-h6">
$28
</h6>
</td>
</tr>
<tr>
<td class="pe-16">
Tax:
</td>
<td :class="$vuetify.locale.isRtl ? 'text-start' : 'text-end'">
<h6 class="text-h6">
21%
</h6>
</td>
</tr>
</tbody>
</table>
<VDivider class="mt-4 mb-3" />
<table class="w-100">
<tbody>
<tr>
<td class="pe-16">
Total:
</td>
<td :class="$vuetify.locale.isRtl ? 'text-start' : 'text-end'">
<h6 class="text-h6">
$1690
</h6>
</td>
</tr>
</tbody>
</table>
</div>
</div>
<VDivider class="my-6 border-dashed" />
<div>
<h6 class="text-h6 mb-2">
Note:
</h6>
<VTextarea
v-model="note"
placeholder="Write note here..."
:rows="2"
/>
</div>
</VCard>
</template>

View File

@@ -0,0 +1,207 @@
<!-- eslint-disable vue/no-mutating-props -->
<script setup>
const props = defineProps({
id: {
type: Number,
required: true,
},
data: {
type: Object,
required: true,
default: () => ({
title: 'App Design',
cost: 24,
hours: 1,
description: 'Designed UI kit & app pages.',
}),
},
})
const emit = defineEmits([
'removeProduct',
'totalAmount',
])
const itemsOptions = [
{
title: 'App Design',
cost: 24,
hours: 1,
description: 'Designed UI kit & app pages.',
},
{
title: 'App Customization',
cost: 26,
hours: 1,
description: 'Customization & Bug Fixes.',
},
{
title: 'ABC Template',
cost: 28,
hours: 1,
description: 'Vuetify admin template.',
},
{
title: 'App Development',
cost: 32,
hours: 1,
description: 'Native App Development.',
},
]
const selectedItem = ref('App Customization')
const localProductData = ref(structuredClone(toRaw(props.data)))
watch(selectedItem, () => {
const item = itemsOptions.filter(obj => {
return obj.title === selectedItem.value
})
localProductData.value = item[0]
})
const removeProduct = () => {
emit('removeProduct', props.id)
}
const totalPrice = computed(() => Number(localProductData.value.cost) * Number(localProductData.value.hours))
watch(totalPrice, () => {
emit('totalAmount', totalPrice.value)
}, { immediate: true })
</script>
<template>
<!-- eslint-disable vue/no-mutating-props -->
<div class="add-products-header mb-2 d-none d-md-flex mb-4">
<VRow class="me-10">
<VCol
cols="12"
md="6"
>
<h6 class="text-h6">
Item
</h6>
</VCol>
<VCol
cols="12"
md="2"
>
<h6 class="text-h6 ps-2">
Cost
</h6>
</VCol>
<VCol
cols="12"
md="2"
>
<h6 class="text-h6 ps-2">
Hours
</h6>
</VCol>
<VCol
cols="12"
md="2"
>
<h6 class="text-h6">
Price
</h6>
</VCol>
</VRow>
</div>
<VCard
flat
border
class="d-flex flex-sm-row flex-column-reverse"
>
<!-- 👉 Left Form -->
<div class="pa-5 flex-grow-1">
<VRow>
<VCol
cols="12"
md="6"
>
<VSelect
v-model="selectedItem"
:items="itemsOptions"
item-title="title"
item-value="title"
label="Select Item"
placeholder="Select Item"
class="mb-5"
/>
<VTextarea
v-model="localProductData.description"
rows="2"
label="Description"
placeholder="Item description"
/>
</VCol>
<VCol
cols="12"
md="2"
sm="4"
>
<VTextField
v-model="localProductData.cost"
type="number"
label="Cost"
placeholder="100"
/>
<div class="text-high-emphasis mt-4">
<p class="mb-1">
Discount
</p>
<span>0%</span>
<span class="mx-2">
0%
<VTooltip activator="parent">Tax 1</VTooltip>
</span>
<span>
0%
<VTooltip activator="parent">Tax 2</VTooltip>
</span>
</div>
</VCol>
<VCol
cols="12"
md="2"
sm="4"
>
<VTextField
v-model="localProductData.hours"
type="number"
label="Hours"
placeholder="5"
/>
</VCol>
<VCol
cols="12"
md="2"
sm="4"
>
<p class="my-2">
<span class="d-inline d-md-none">Price: </span>
<span class="text-high-emphasis">${{ totalPrice }}</span>
</p>
</VCol>
</VRow>
</div>
<!-- 👉 Item Actions -->
<div
class="d-flex flex-column align-end item-actions"
:class="$vuetify.display.smAndUp ? 'border-s' : 'border-b' "
>
<IconBtn @click="removeProduct">
<VIcon
:size="20"
icon="ri-close-line"
/>
</IconBtn>
</div>
</VCard>
</template>

View File

@@ -0,0 +1,133 @@
<script setup>
import { PerfectScrollbar } from 'vue3-perfect-scrollbar'
const props = defineProps({
isDrawerOpen: {
type: Boolean,
required: true,
},
})
const emit = defineEmits([
'update:isDrawerOpen',
'submit',
])
const emailFrom = ref('shelbyComapny@email.com')
const emailTo = ref('qConsolidated@email.com')
const invoiceSubject = ref('Invoice of purchased Admin Templates')
const paymentMessage = ref(`Dear Queen Consolidated,
Thank you for your business, always a pleasure to work with you!
We have generated a new invoice in the amount of $95.59
We would appreciate payment of this invoice by 05/11/2019`)
const onSubmit = () => {
emit('update:isDrawerOpen', false)
emit('submit', {
emailFrom: emailFrom.value,
emailTo: emailTo.value,
invoiceSubject: invoiceSubject.value,
paymentMessage: paymentMessage.value,
})
}
const handleDrawerModelValueUpdate = val => {
emit('update:isDrawerOpen', val)
}
</script>
<template>
<VNavigationDrawer
temporary
location="end"
:width="400"
:model-value="props.isDrawerOpen"
class="scrollable-content"
@update:model-value="handleDrawerModelValueUpdate"
>
<!-- 👉 Header -->
<AppDrawerHeaderSection
title="Send Invoice"
@cancel="$emit('update:isDrawerOpen', false)"
/>
<VDivider />
<PerfectScrollbar :options="{ wheelPropagation: false }">
<VCard flat>
<VCardText>
<VForm @submit.prevent="onSubmit">
<VRow>
<VCol cols="12">
<VTextField
v-model="emailFrom"
label="From"
placeholder="sender@email.com"
/>
</VCol>
<VCol cols="12">
<VTextField
v-model="emailTo"
label="To"
placeholder="receiver@email.com"
/>
</VCol>
<VCol cols="12">
<VTextField
v-model="invoiceSubject"
label="Subject"
placeholder="Invoice of purchased Admin Templates"
/>
</VCol>
<VCol cols="12">
<VTextarea
v-model="paymentMessage"
rows="10"
label="Message"
placeholder="Thank you for your business, always a pleasure to work with you!"
/>
</VCol>
<VCol cols="12">
<div class="mb-6">
<VChip
label
color="primary"
size="small"
>
<VIcon
start
icon="ri-links-line"
/>
Invoice Attached
</VChip>
</div>
<VBtn
type="submit"
class="me-3"
>
Send
</VBtn>
<VBtn
color="secondary"
variant="outlined"
@click="$emit('update:isDrawerOpen', false)"
>
Cancel
</VBtn>
</VCol>
</VRow>
</VForm>
</VCardText>
</VCard>
</PerfectScrollbar>
</VNavigationDrawer>
</template>

View File

@@ -0,0 +1 @@
export {}