2
0
mirror of https://github.com/frappe/books.git synced 2025-04-02 08:11:52 +00:00

feat: split item list and grid views for ClassicPOS and ModernPOS

This commit is contained in:
AbleKSaju 2024-10-30 15:54:33 +05:30
parent d223d49f4f
commit a4de661a42
6 changed files with 604 additions and 253 deletions

View File

@ -3,18 +3,28 @@
class="
flex flex-col
gap-4
p-4
p-2
items-center
mt-4
px-2
rounded-t-md
text-black
w-full
overflow-y-auto
custom-scroll custom-scroll-thumb2
"
style="height: 80vh"
style="height: 83vh"
>
<!-- Items Grid -->
<div class="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-2 w-full">
<div
class="
grid grid-cols-1
md:grid-cols-2
lg:grid-cols-3
xl:grid-cols-4
gap-2
w-full
"
>
<div
class="
border border-gray-300
@ -27,20 +37,21 @@
v-for="item in items as POSItem[]"
:key="item.name"
>
<div class="self-center w-32 h-32 rounded-lg mb-1">
<div class="relative">
<div class="self-center w-32 h-32 p-1 rounded-lg">
<div class="relative w-full h-full p-2">
<img
v-if="item.image"
:src="item.image"
alt=""
class="rounded-lg w-32 h-32 object-cover"
class="rounded-lg w-full h-full object-cover"
/>
<div
v-else
class="
rounded-lg
w-32
h-32
w-full
h-full
flex
bg-gray-100
dark:bg-gray-850
@ -53,7 +64,17 @@
</p>
</div>
<p
class="absolute top-1 right-1 rounded-full p-1"
class="
absolute
top-1
right-1
rounded-full
w-6
h-6
flex
justify-center
items-center
"
:class="
item.availableQty > 0
? 'bg-green-100 text-green-900'
@ -80,7 +101,7 @@
<script lang="ts">
import { defineComponent } from 'vue';
import { fyo } from 'src/initFyo';
import { POSItem } from './types';
import { POSItem } from '../types';
export default defineComponent({
name: 'ItemsGrid',

View File

@ -29,7 +29,10 @@
</div>
</Row>
<div class="overflow-y-auto" style="height: 80vh">
<div
class="overflow-y-auto custom-scroll custom-scroll-thumb2"
style="height: calc(70vh)"
>
<Row
v-if="items"
v-for="row in items as any"
@ -64,12 +67,12 @@
</template>
<script lang="ts">
import FormControl from '../Controls/FormControl.vue';
import FormControl from 'src/components/Controls/FormControl.vue';
import Row from 'src/components/Row.vue';
import { isNumeric } from 'src/utils';
import { defineComponent } from 'vue';
import { Field } from 'schemas/types';
import { POSItem } from './types';
import { POSItem } from '../types';
export default defineComponent({
name: 'ItemsTable',

View File

@ -0,0 +1,132 @@
<template>
<div
class="
flex flex-col
gap-4
p-2
my-3
items-center
px-2
rounded-t-md
text-black
w-full
overflow-y-auto
custom-scroll custom-scroll-thumb2
"
style="height: 80vh"
>
<!-- Items Grid -->
<div
class="
grid grid-cols-1
gap-2
w-full
sm:grid-cols-2
md:grid-cols-4
lg:grid-cols-6
xl:grid-cols-7'
"
>
<div
class="
border border-gray-300
dark:border-gray-800
p-1
flex flex-col
text-sm text-center
"
@click="handleChange(item as POSItem)"
v-for="item in items as POSItem[]"
:key="item.name"
>
<div class="self-center w-32 h-32 p-1 rounded-lg">
<div class="relative w-full h-full p-2">
<img
v-if="item.image"
:src="item.image"
alt=""
class="rounded-lg w-full h-full object-cover"
/>
<div
v-else
class="
rounded-lg
w-full
h-full
flex
bg-gray-100
dark:bg-gray-850
justify-center
items-center
"
>
<p class="text-4xl font-semibold text-gray-400 select-none">
{{ getExtractedWords(item.name) }}
</p>
</div>
<p
class="
absolute
top-1
right-1
rounded-full
w-6
h-6
flex
justify-center
items-center
"
:class="
item.availableQty > 0
? 'bg-green-100 text-green-900'
: 'bg-red-100 text-red-900'
"
>
{{ item.availableQty }}
</p>
</div>
</div>
<h3 class="text-lg font-medium dark:text-white">{{ item.name }}</h3>
<p class="text-lg font-medium dark:text-white">
{{
item.rate ? fyo.currencySymbols[item.rate.getCurrency()] : undefined
}}
{{ item.rate }}
</p>
</div>
</div>
</div>
</template>
<script lang="ts">
import { defineComponent } from 'vue';
import { fyo } from 'src/initFyo';
import { POSItem } from '../types';
export default defineComponent({
name: 'ModernPOSItemsGrid',
emits: ['addItem', 'updateValues'],
props: {
items: {
type: Array,
},
itemQtyMap: {
type: Object,
},
},
methods: {
getExtractedWords(item: string) {
const initials = item.split(' ').map((word) => {
return word[0].toUpperCase();
});
return initials.join('');
},
handleChange(value: POSItem) {
this.$emit('addItem', value);
this.$emit('updateValues');
},
},
});
</script>

View File

@ -0,0 +1,202 @@
<template>
<div class="flex gap-2">
<div
class="w-1/2 overflow-y-auto custom-scroll custom-scroll-thumb2"
style="height: calc(81vh)"
>
<Row
:ratio="ratio"
class="
border
dark:border-gray-800
flex
items-center
mt-2
px-2
rounded-t-md
text-gray-600
dark:text-gray-400
w-full
"
>
<div
v-for="df in tableFields"
:key="df.fieldname"
class="flex items-center px-2 py-2 text-lg"
:class="{
'ms-auto': isNumeric(df as Field),
}"
:style="{
height: ``,
}"
>
{{ df.label }}
</div>
</Row>
<Row
v-for="row in firstColumnItems as POSItem[]"
:key="row.id"
:ratio="ratio"
:border="true"
class="
border-b border-l border-r
dark:border-gray-800
flex
group
h-row-mid
hover:bg-gray-25
dark:bg-gray-890
items-center
justify-center
px-2
w-full
"
@click="handleChange(row)"
>
<FormControl
v-for="df in tableFields"
:key="df.fieldname"
size="large"
:df="df"
:value="row[df.fieldname]"
:readOnly="true"
/>
</Row>
</div>
<div
class="w-1/2 overflow-y-auto custom-scroll custom-scroll-thumb2"
style="height: calc(80vh - 20rem)"
>
<Row
:ratio="ratio"
class="
border
dark:border-gray-800
flex
items-center
mt-2
px-2
rounded-t-md
text-gray-600
dark:text-gray-400
w-full
"
>
<div
v-for="df in tableFields"
:key="df.fieldname"
class="flex items-center px-2 py-2 text-lg"
:class="{
'ms-auto': isNumeric(df as Field),
}"
:style="{
height: ``,
}"
>
{{ df.label }}
</div>
</Row>
<Row
v-for="row in secondColumnItems as POSItem[]"
:key="row.id"
:ratio="ratio"
:border="true"
class="
border-b border-l border-r
dark:border-gray-800
flex
group
h-row-mid
hover:bg-gray-25
dark:bg-gray-890
items-center
justify-center
px-2
w-full
"
@click="handleChange(row)"
>
<FormControl
v-for="df in tableFields"
:key="df.fieldname"
size="large"
:df="df"
:value="row[df.fieldname]"
:readOnly="true"
/>
</Row>
</div>
</div>
</template>
<script lang="ts">
import FormControl from 'src/components/Controls/FormControl.vue';
import Row from 'src/components/Row.vue';
import { isNumeric } from 'src/utils';
import { defineComponent } from 'vue';
import { Field } from 'schemas/types';
import { POSItem } from '../types';
export default defineComponent({
name: 'ModernPOSItemsTable',
components: { FormControl, Row },
emits: ['addItem', 'updateValues'],
props: {
items: Array,
itemQtyMap: Object,
},
computed: {
ratio() {
return [1, 1, 0.6, 0.7];
},
tableFields() {
return [
{
fieldname: 'name',
fieldtype: 'Data',
label: 'Item',
placeholder: 'Item',
readOnly: true,
},
{
fieldname: 'rate',
label: 'Rate',
placeholder: 'Rate',
fieldtype: 'Currency',
readOnly: true,
},
{
fieldname: 'availableQty',
label: 'Qty',
placeholder: 'Available Qty',
fieldtype: 'Float',
readOnly: true,
},
{
fieldname: 'unit',
label: 'Unit',
placeholder: 'Unit',
fieldtype: 'Data',
target: 'UOM',
readOnly: true,
},
] as Field[];
},
firstColumnItems() {
return this.items?.slice(0, Math.ceil(this.items.length / 2));
},
secondColumnItems() {
return this.items?.slice(Math.ceil(this.items.length / 2));
},
},
methods: {
handleChange(value: POSItem) {
this.$emit('addItem', value);
this.$emit('updateValues');
},
isNumeric,
},
});
</script>

View File

@ -514,7 +514,6 @@ import FloatingLabelFloatInput from 'src/components/POS/FloatingLabelFloatInput.
import ItemsTable from 'src/components/POS/Classic/ItemsTable.vue';
import Link from 'src/components/Controls/Link.vue';
import OpenPOSShiftModal from './OpenPOSShiftModal.vue';
import PageHeader from 'src/components/PageHeader.vue';
import PaymentModal from './PaymentModal.vue';
import SelectedItemTable from 'src/components/POS/Classic/SelectedItemTable.vue';
import { computed, defineComponent } from 'vue';
@ -559,7 +558,6 @@ import CouponCodeModal from './CouponCodeModal.vue';
import { AppliedCouponCodes } from 'models/baseModels/AppliedCouponCodes/AppliedCouponCodes';
import MultiLabelLink from 'src/components/Controls/MultiLabelLink.vue';
export default defineComponent({
name: 'ClassicPOS',
components: {
@ -573,7 +571,6 @@ export default defineComponent({
MultiLabelLink,
AlertModal,
OpenPOSShiftModal,
PageHeader,
PaymentModal,
LoyaltyProgramModal,
SavedInvoiceModal,
@ -1054,8 +1051,6 @@ export default defineComponent({
}
},
toggleModal(modal: ModalName, value?: boolean) {
console.log("toggleModal");
if (value) {
return (this[`open${modal}Modal`] = value);
}

View File

@ -258,249 +258,249 @@
</div>
<div class="flex fixed bottom-0 p-1 ml-3 mb-7 gap-x-3">
<div class="relative group">
<div class="bg-gray-100 p-1.5 rounded-md" @click="toggleView">
<FeatherIcon
:name="tableView ? 'grid' : 'list'"
class="w-5 h-5 text-black"
<div class="relative group">
<div class="bg-gray-100 p-1.5 rounded-md" @click="toggleView">
<FeatherIcon
:name="tableView ? 'grid' : 'list'"
class="w-5 h-5 text-black"
/>
</div>
<span
class="
absolute
bottom-full
left-1/2
transform
-translate-x-1/2
mb-2
bg-gray-100
dark:bg-gray-800 dark:text-white
text-black text-xs
rounded-md
p-2
w-20
text-center
opacity-0
group-hover:opacity-100
transition-opacity
duration-300
"
>
{{ tableView ? 'Grid View' : 'List View' }}
</span>
</div>
<div class="relative group">
<div
class="px-1.5 py-1 rounded-md bg-gray-100"
@click="routeToSinvList"
>
<svg
xmlns="http://www.w3.org/2000/svg"
height="24"
viewBox="0 -960 960 960"
width="21"
fill="#000"
>
<path
d="M240-100q-41.92 0-70.96-29.04Q140-158.08 140-199.82V-300h120v-552.31l55.39 47.7 56.15-47.7 56.15 47.7 56.16-47.7 56.15 47.7 56.15-47.7 56.16 47.7 56.15-47.7 56.15 47.7 55.39-47.7V-200q0 41.92-29.04 70.96Q761.92-100 720-100H240Zm480-60q17 0 28.5-11.5T760-200v-560H320v460h360v100q0 17 11.5 28.5T720-160ZM367.69-610v-60h226.92v60H367.69Zm0 120v-60h226.92v60H367.69Zm310-114.62q-14.69 0-25.04-10.34-10.34-10.35-10.34-25.04t10.34-25.04q10.35-10.34 25.04-10.34t25.04 10.34q10.35 10.35 10.35 25.04t-10.35 25.04q-10.35 10.34-25.04 10.34Zm0 120q-14.69 0-25.04-10.34-10.34-10.35-10.34-25.04t10.34-25.04q10.35-10.34 25.04-10.34t25.04 10.34q10.35 10.35 10.35 25.04t-10.35 25.04q-10.35 10.34-25.04 10.34ZM240-160h380v-80H200v40q0 17 11.5 28.5T240-160Zm-40 0v-80 80Z"
/>
</div>
<span
class="
absolute
bottom-full
left-1/2
transform
-translate-x-1/2
mb-2
bg-gray-100
dark:bg-gray-800 dark:text-white
text-black text-xs
rounded-md
p-2
w-20
text-center
opacity-0
group-hover:opacity-100
transition-opacity
duration-300
"
>
{{ tableView ? 'Grid View' : 'List View' }}
</span>
</svg>
</div>
<div class="relative group">
<div
class="px-1.5 py-1 rounded-md bg-gray-100"
@click="routeToSinvList"
>
<svg
xmlns="http://www.w3.org/2000/svg"
height="24"
viewBox="0 -960 960 960"
width="21"
fill="#000"
>
<path
d="M240-100q-41.92 0-70.96-29.04Q140-158.08 140-199.82V-300h120v-552.31l55.39 47.7 56.15-47.7 56.15 47.7 56.16-47.7 56.15 47.7 56.15-47.7 56.16 47.7 56.15-47.7 56.15 47.7 55.39-47.7V-200q0 41.92-29.04 70.96Q761.92-100 720-100H240Zm480-60q17 0 28.5-11.5T760-200v-560H320v460h360v100q0 17 11.5 28.5T720-160ZM367.69-610v-60h226.92v60H367.69Zm0 120v-60h226.92v60H367.69Zm310-114.62q-14.69 0-25.04-10.34-10.34-10.35-10.34-25.04t10.34-25.04q10.35-10.34 25.04-10.34t25.04 10.34q10.35 10.35 10.35 25.04t-10.35 25.04q-10.35 10.34-25.04 10.34Zm0 120q-14.69 0-25.04-10.34-10.34-10.35-10.34-25.04t10.34-25.04q10.35-10.34 25.04-10.34t25.04 10.34q10.35 10.35 10.35 25.04t-10.35 25.04q-10.35 10.34-25.04 10.34ZM240-160h380v-80H200v40q0 17 11.5 28.5T240-160Zm-40 0v-80 80Z"
/>
</svg>
</div>
<span
class="
absolute
bottom-full
left-1/2
transform
-translate-x-1/2
rounded-md
opacity-0
bg-gray-100
dark:bg-gray-800 dark:text-white
text-black text-xs text-center
mb-2
p-2
w-28
group-hover:opacity-100
transition-opacity
duration-300
"
>
Sales Invoice List
</span>
</div>
<span
class="
absolute
bottom-full
left-1/2
transform
-translate-x-1/2
rounded-md
opacity-0
bg-gray-100
dark:bg-gray-800 dark:text-white
text-black text-xs text-center
mb-2
p-2
w-28
group-hover:opacity-100
transition-opacity
duration-300
"
<div class="relative group">
<div
class="p-1 rounded-md bg-gray-100"
:class="{
hidden: !fyo.singles.AccountingSettings?.enableLoyaltyProgram,
'bg-gray-100': loyaltyPoints,
'dark:bg-gray-600 cursor-not-allowed':
!loyaltyPoints || !sinvDoc.party || !sinvDoc.items?.length,
}"
@click="
loyaltyPoints && sinvDoc.party && sinvDoc.items?.length
? toggleModal('LoyaltyProgram', true)
: null
"
>
<svg
xmlns="http://www.w3.org/2000/svg"
height="23px"
viewBox="0 -960 960 960"
width="25px"
fill="#000"
>
Sales Invoice List
</span>
<path
d="M100-180v-600h760v600H100Zm50.26-50.26h659.48v-499.48H150.26v499.48Zm0 0v-499.48 499.48Zm181.64-56.77h50.25v-42.56h48.67q14.37 0 23.6-10.38 9.22-10.38 9.22-24.25v-106.93q0-14.71-9.22-24.88-9.23-10.17-23.6-10.17H298.77v-73.95h164.87v-50.26h-81.49v-42.56H331.9v42.56h-48.41q-14.63 0-24.8 10.38-10.18 10.38-10.18 25v106.27q0 14.62 10.18 23.71 10.17 9.1 24.8 9.1h129.9v76.1H248.51v50.26h83.39v42.56Zm312.97-27.94L705.9-376H583.85l61.02 61.03ZM583.85-574H705.9l-61.03-61.03L583.85-574Z"
/>
</svg>
</div>
<div class="relative group">
<div
class="p-1 rounded-md bg-gray-100"
:class="{
hidden: !fyo.singles.AccountingSettings?.enableLoyaltyProgram,
'bg-gray-100': loyaltyPoints,
'dark:bg-gray-600 cursor-not-allowed':
!loyaltyPoints || !sinvDoc.party || !sinvDoc.items?.length,
}"
@click="
loyaltyPoints && sinvDoc.party && sinvDoc.items?.length
? toggleModal('LoyaltyProgram', true)
: null
"
>
<svg
xmlns="http://www.w3.org/2000/svg"
height="23px"
viewBox="0 -960 960 960"
width="25px"
fill="#000"
>
<path
d="M100-180v-600h760v600H100Zm50.26-50.26h659.48v-499.48H150.26v499.48Zm0 0v-499.48 499.48Zm181.64-56.77h50.25v-42.56h48.67q14.37 0 23.6-10.38 9.22-10.38 9.22-24.25v-106.93q0-14.71-9.22-24.88-9.23-10.17-23.6-10.17H298.77v-73.95h164.87v-50.26h-81.49v-42.56H331.9v42.56h-48.41q-14.63 0-24.8 10.38-10.18 10.38-10.18 25v106.27q0 14.62 10.18 23.71 10.17 9.1 24.8 9.1h129.9v76.1H248.51v50.26h83.39v42.56Zm312.97-27.94L705.9-376H583.85l61.02 61.03ZM583.85-574H705.9l-61.03-61.03L583.85-574Z"
/>
</svg>
</div>
<span
class="
absolute
bottom-full
left-1/2
transform
-translate-x-1/2
mb-2
bg-gray-100
dark:bg-gray-800 dark:text-white
text-black text-xs
rounded-md
p-2
w-28
text-center
opacity-0
group-hover:opacity-100
transition-opacity
duration-300
"
>
Loyalty Program
</span>
</div>
<span
class="
absolute
bottom-full
left-1/2
transform
-translate-x-1/2
mb-2
bg-gray-100
dark:bg-gray-800 dark:text-white
text-black text-xs
rounded-md
p-2
w-28
text-center
opacity-0
group-hover:opacity-100
transition-opacity
duration-300
"
<div class="relative group">
<div
class="p-0.5 rounded-md bg-gray-100"
:class="{
hidden: !fyo.singles.AccountingSettings?.enableCouponCode,
'bg-gray-100': loyaltyPoints,
'dark:bg-gray-600 cursor-not-allowed':
!sinvDoc.party || !sinvDoc.items?.length,
}"
@click="openCouponModal()"
>
<svg
fill="#000000"
width="28px"
height="28px"
viewBox="0 0 512.00 512.00"
enable-background="new 0 0 512 512"
version="1.1"
xml:space="preserve"
xmlns="http://www.w3.org/2000/svg"
xmlns:xlink="http://www.w3.org/1999/xlink"
stroke="#000000"
stroke-width="3.312000000000001"
transform="matrix(1, 0, 0, 1, 0, 0)rotate(0)"
>
Loyalty Program
</span>
</div>
<div class="relative group">
<div
class="p-0.5 rounded-md bg-gray-100"
:class="{
hidden: !fyo.singles.AccountingSettings?.enableCouponCode,
'bg-gray-100': loyaltyPoints,
'dark:bg-gray-600 cursor-not-allowed':
!sinvDoc.party || !sinvDoc.items?.length,
}"
@click="openCouponModal()"
>
<svg
fill="#000000"
width="28px"
height="28px"
viewBox="0 0 512.00 512.00"
enable-background="new 0 0 512 512"
version="1.1"
xml:space="preserve"
xmlns="http://www.w3.org/2000/svg"
xmlns:xlink="http://www.w3.org/1999/xlink"
stroke="#000000"
stroke-width="3.312000000000001"
transform="matrix(1, 0, 0, 1, 0, 0)rotate(0)"
>
<g id="SVGRepo_bgCarrier" stroke-width="0"></g>
<g
id="SVGRepo_tracerCarrier"
stroke-linecap="round"
stroke-linejoin="round"
stroke="#CCCCCC"
stroke-width="19.456"
></g>
<g id="SVGRepo_iconCarrier">
<g id="Layer_1"></g>
<g id="Layer_2">
<g>
<path
d="M412.7,134.4H229.6c-2,0-3.9,0.8-5.3,2.2l-27.8,27.8L169.1,137c-1.4-1.4-3.3-2.2-5.3-2.2H99.3c-4.1,0-7.5,3.4-7.5,7.5 v227.4c0,4.1,3.4,7.5,7.5,7.5h64.5c2,0,3.9-0.8,5.3-2.2l27.4-27.4l27.8,27.8c1.4,1.4,3.3,2.2,5.3,2.2h183.1c4.1,0,7.5-3.4,7.5-7.5 V141.9C420.2,137.7,416.8,134.4,412.7,134.4z M405.2,362.6H232.7l-30.9-30.9c-2.9-2.9-7.7-2.9-10.6,0l-30.5,30.5h-53.9V149.8h53.9 l30.5,30.5c2.9,2.9,7.7,2.9,10.6,0l30.9-30.9h172.5V362.6z"
></path>
<path
d="M276.9,235.2c15.4,0,28-12.6,28-28s-12.6-28-28-28s-28,12.6-28,28S261.4,235.2,276.9,235.2z M276.9,194.2 c7.2,0,13,5.8,13,13s-5.8,13-13,13s-13-5.8-13-13S269.7,194.2,276.9,194.2z"
></path>
<path
d="M360,262.4c-15.4,0-28,12.6-28,28s12.6,28,28,28s28-12.6,28-28S375.4,262.4,360,262.4z M360,303.4c-7.2,0-13-5.8-13-13 s5.8-13,13-13s13,5.8,13,13S367.2,303.4,360,303.4z"
></path>
<path
d="M256.6,310.7c1.5,1.5,3.4,2.2,5.3,2.2s3.8-0.7,5.3-2.2l113.1-113.1c2.9-2.9,2.9-7.7,0-10.6c-2.9-2.9-7.7-2.9-10.6,0 L256.6,300.1C253.6,303,253.6,307.7,256.6,310.7z"
></path>
<path
d="M196.5,202.5c-2,0-3.9,0.8-5.3,2.2c-1.4,1.4-2.2,3.3-2.2,5.3c0,2,0.8,3.9,2.2,5.3c1.4,1.4,3.3,2.2,5.3,2.2 c2,0,3.9-0.8,5.3-2.2c1.4-1.4,2.2-3.3,2.2-5.3c0-2-0.8-3.9-2.2-5.3C200.4,203.3,198.4,202.5,196.5,202.5z"
></path>
<path
d="M196.5,233.2c-2,0-3.9,0.8-5.3,2.2c-1.4,1.4-2.2,3.3-2.2,5.3c0,2,0.8,3.9,2.2,5.3c1.4,1.4,3.3,2.2,5.3,2.2 c2,0,3.9-0.8,5.3-2.2c1.4-1.4,2.2-3.3,2.2-5.3c0-2-0.8-3.9-2.2-5.3C200.4,234,198.4,233.2,196.5,233.2z"
></path>
<path
d="M196.5,263.8c-2,0-3.9,0.8-5.3,2.2c-1.4,1.4-2.2,3.3-2.2,5.3c0,2,0.8,3.9,2.2,5.3c1.4,1.4,3.3,2.2,5.3,2.2 c2,0,3.9-0.8,5.3-2.2c1.4-1.4,2.2-3.3,2.2-5.3c0-2-0.8-3.9-2.2-5.3C200.4,264.6,198.4,263.8,196.5,263.8z"
></path>
<path
d="M196.5,294.5c-2,0-3.9,0.8-5.3,2.2c-1.4,1.4-2.2,3.3-2.2,5.3c0,2,0.8,3.9,2.2,5.3c1.4,1.4,3.3,2.2,5.3,2.2 c2,0,3.9-0.8,5.3-2.2c1.4-1.4,2.2-3.3,2.2-5.3c0-2-0.8-3.9-2.2-5.3C200.4,295.3,198.4,294.5,196.5,294.5z"
></path>
</g>
<g id="SVGRepo_bgCarrier" stroke-width="0"></g>
<g
id="SVGRepo_tracerCarrier"
stroke-linecap="round"
stroke-linejoin="round"
stroke="#CCCCCC"
stroke-width="19.456"
></g>
<g id="SVGRepo_iconCarrier">
<g id="Layer_1"></g>
<g id="Layer_2">
<g>
<path
d="M412.7,134.4H229.6c-2,0-3.9,0.8-5.3,2.2l-27.8,27.8L169.1,137c-1.4-1.4-3.3-2.2-5.3-2.2H99.3c-4.1,0-7.5,3.4-7.5,7.5 v227.4c0,4.1,3.4,7.5,7.5,7.5h64.5c2,0,3.9-0.8,5.3-2.2l27.4-27.4l27.8,27.8c1.4,1.4,3.3,2.2,5.3,2.2h183.1c4.1,0,7.5-3.4,7.5-7.5 V141.9C420.2,137.7,416.8,134.4,412.7,134.4z M405.2,362.6H232.7l-30.9-30.9c-2.9-2.9-7.7-2.9-10.6,0l-30.5,30.5h-53.9V149.8h53.9 l30.5,30.5c2.9,2.9,7.7,2.9,10.6,0l30.9-30.9h172.5V362.6z"
></path>
<path
d="M276.9,235.2c15.4,0,28-12.6,28-28s-12.6-28-28-28s-28,12.6-28,28S261.4,235.2,276.9,235.2z M276.9,194.2 c7.2,0,13,5.8,13,13s-5.8,13-13,13s-13-5.8-13-13S269.7,194.2,276.9,194.2z"
></path>
<path
d="M360,262.4c-15.4,0-28,12.6-28,28s12.6,28,28,28s28-12.6,28-28S375.4,262.4,360,262.4z M360,303.4c-7.2,0-13-5.8-13-13 s5.8-13,13-13s13,5.8,13,13S367.2,303.4,360,303.4z"
></path>
<path
d="M256.6,310.7c1.5,1.5,3.4,2.2,5.3,2.2s3.8-0.7,5.3-2.2l113.1-113.1c2.9-2.9,2.9-7.7,0-10.6c-2.9-2.9-7.7-2.9-10.6,0 L256.6,300.1C253.6,303,253.6,307.7,256.6,310.7z"
></path>
<path
d="M196.5,202.5c-2,0-3.9,0.8-5.3,2.2c-1.4,1.4-2.2,3.3-2.2,5.3c0,2,0.8,3.9,2.2,5.3c1.4,1.4,3.3,2.2,5.3,2.2 c2,0,3.9-0.8,5.3-2.2c1.4-1.4,2.2-3.3,2.2-5.3c0-2-0.8-3.9-2.2-5.3C200.4,203.3,198.4,202.5,196.5,202.5z"
></path>
<path
d="M196.5,233.2c-2,0-3.9,0.8-5.3,2.2c-1.4,1.4-2.2,3.3-2.2,5.3c0,2,0.8,3.9,2.2,5.3c1.4,1.4,3.3,2.2,5.3,2.2 c2,0,3.9-0.8,5.3-2.2c1.4-1.4,2.2-3.3,2.2-5.3c0-2-0.8-3.9-2.2-5.3C200.4,234,198.4,233.2,196.5,233.2z"
></path>
<path
d="M196.5,263.8c-2,0-3.9,0.8-5.3,2.2c-1.4,1.4-2.2,3.3-2.2,5.3c0,2,0.8,3.9,2.2,5.3c1.4,1.4,3.3,2.2,5.3,2.2 c2,0,3.9-0.8,5.3-2.2c1.4-1.4,2.2-3.3,2.2-5.3c0-2-0.8-3.9-2.2-5.3C200.4,264.6,198.4,263.8,196.5,263.8z"
></path>
<path
d="M196.5,294.5c-2,0-3.9,0.8-5.3,2.2c-1.4,1.4-2.2,3.3-2.2,5.3c0,2,0.8,3.9,2.2,5.3c1.4,1.4,3.3,2.2,5.3,2.2 c2,0,3.9-0.8,5.3-2.2c1.4-1.4,2.2-3.3,2.2-5.3c0-2-0.8-3.9-2.2-5.3C200.4,295.3,198.4,294.5,196.5,294.5z"
></path>
</g>
</g>
</svg>
</div>
<span
class="
absolute
bottom-full
left-1/2
transform
-translate-x-1/2
mb-2
bg-gray-100
dark:bg-gray-800 dark:text-white
text-black text-xs
rounded-md
p-2
w-28
text-center
opacity-0
group-hover:opacity-100
transition-opacity
duration-300
"
>
Coupon Code
</span>
<div
v-if="appliedCouponsCount !== 0"
class="
absolute
top-0
right-0
transform
translate-x-1/2
-translate-y-1/2
h-4
w-4
bg-green-400
text-green-900
rounded-full
flex
items-center
justify-center
text-xs
cursor-pointer
border-red-500
p-2
"
>
{{ appliedCouponsCount }}
</div>
</g>
</svg>
</div>
<span
class="
absolute
bottom-full
left-1/2
transform
-translate-x-1/2
mb-2
bg-gray-100
dark:bg-gray-800 dark:text-white
text-black text-xs
rounded-md
p-2
w-28
text-center
opacity-0
group-hover:opacity-100
transition-opacity
duration-300
"
>
Coupon Code
</span>
<div
v-if="appliedCouponsCount !== 0"
class="
absolute
top-0
right-0
transform
translate-x-1/2
-translate-y-1/2
h-4
w-4
bg-green-400
text-green-900
rounded-full
flex
items-center
justify-center
text-xs
cursor-pointer
border-red-500
p-2
"
>
{{ appliedCouponsCount }}
</div>
</div>
</div>
</div>
</div>
</div>
@ -513,7 +513,6 @@ import FloatingLabelCurrencyInput from 'src/components/POS/FloatingLabelCurrency
import FloatingLabelFloatInput from 'src/components/POS/FloatingLabelFloatInput.vue';
import Link from 'src/components/Controls/Link.vue';
import OpenPOSShiftModal from './OpenPOSShiftModal.vue';
import PageHeader from 'src/components/PageHeader.vue';
import PaymentModal from './PaymentModal.vue';
import { computed, defineComponent } from 'vue';
import { fyo } from 'src/initFyo';
@ -572,7 +571,6 @@ export default defineComponent({
Link,
AlertModal,
OpenPOSShiftModal,
PageHeader,
PaymentModal,
LoyaltyProgramModal,
SavedInvoiceModal,
@ -580,7 +578,7 @@ export default defineComponent({
ModernPOSSelectedItemTable,
Barcode,
KeyboardModal,
MultiLabelLink
MultiLabelLink,
},
provide() {
return {