File: /home/slfopp7cb1df/public_html/shaneconrad.me/inventory/resources/src/views/app/pages/pos_draft.vue
<template>
<div class="pos_page">
<div class="container-fluid p-0 app-admin-wrap layout-sidebar-large clearfix" id="pos">
<div v-if="isLoading" class="loading_page spinner spinner-primary mr-3"></div>
<b-row v-if="!isLoading">
<!-- Card Left Panel Details Sale-->
<b-col md="5">
<b-card no-body class="card-order">
<div class="main-header">
<div class="logo">
<router-link to="/app/dashboard">
<img :src="'/images/'+currentUser.logo" alt width="60" height="60">
</router-link>
</div>
<div class="mx-auto"></div>
<div class="header-part-right">
<!-- Full screen toggle -->
<i
class="i-Full-Screen header-icon d-none d-sm-inline-block"
@click="handleFullScreen"
></i>
<!-- Grid menu Dropdown -->
<div class="dropdown">
<b-dropdown
id="dropdown"
text="Dropdown Button"
class="m-md-2"
toggle-class="text-decoration-none"
no-caret
right
variant="link"
>
<template slot="button-content">
<i
class="i-Globe text-muted header-icon"
role="button"
id="dropdownMenuButton"
data-toggle="dropdown"
aria-haspopup="true"
aria-expanded="false"
></i>
</template>
<vue-perfect-scrollbar
:settings="{ suppressScrollX: true, wheelPropagation: false }"
ref="myData"
class="dropdown-menu-left rtl-ps-none notification-dropdown ps scroll"
>
<div class="menu-icon-grid">
<a @click="SetLocal('en')">
<i title="en" class="flag-icon flag-icon-squared flag-icon-gb"></i> English
</a>
<a @click="SetLocal('fr')">
<i title="fr" class="flag-icon flag-icon-squared flag-icon-fr"></i>
<span class="title-lang">French</span>
</a>
<a @click="SetLocal('ar')">
<i title="sa" class="flag-icon flag-icon-squared flag-icon-sa"></i>
<span class="title-lang">Arabic</span>
</a>
<a @click="SetLocal('tur')">
<i title="sa" class="flag-icon flag-icon-squared flag-icon-tr"></i>
<span class="title-lang">Turkish</span>
</a>
<a @click="SetLocal('sm_ch')">
<i title="sa" class="flag-icon flag-icon-squared flag-icon-cn"></i>
<span class="title-lang">Simplified Chinese</span>
</a>
<a @click="SetLocal('thai')">
<i title="sa" class="flag-icon flag-icon-squared flag-icon-th"></i>
<span class="title-lang">Thaï</span>
</a>
<a @click="SetLocal('hn')">
<i title="sa" class="flag-icon flag-icon-squared flag-icon-in"></i>
<span class="title-lang">Hindi</span>
</a>
<a @click="SetLocal('de')">
<i title="de" class="flag-icon flag-icon-squared flag-icon-de"></i>
<span class="title-lang">German</span>
</a>
<a @click="SetLocal('es')">
<i title="es" class="flag-icon flag-icon-squared flag-icon-es"></i>
<span class="title-lang">Spanish</span>
</a>
<a @click="SetLocal('it')">
<i title="it" class="flag-icon flag-icon-squared flag-icon-it"></i>
<span class="title-lang">Italien</span>
</a>
<a @click="SetLocal('Ind')">
<i title="sa" class="flag-icon flag-icon-squared flag-icon-id"></i>
<span class="title-lang">Indonesian</span>
</a>
<a @click="SetLocal('tr_ch')">
<i title="sa" class="flag-icon flag-icon-squared flag-icon-cn"></i>
<span class="title-lang">Traditional Chinese</span>
</a>
<a @click="SetLocal('ru')">
<i title="sa" class="flag-icon flag-icon-squared flag-icon-ru"></i>
<span class="title-lang">Russian</span>
</a>
<a @click="SetLocal('vn')">
<i title="sa" class="flag-icon flag-icon-squared flag-icon-vn"></i>
<span class="title-lang">Vietnamese</span>
</a>
<a @click="SetLocal('kr')">
<i title="sa" class="flag-icon flag-icon-squared flag-icon-kr"></i>
<span class="title-lang">Korean</span>
</a>
<a @click="SetLocal('ba')">
<i title="sa" class="flag-icon flag-icon-squared flag-icon-bd"></i>
<span class="title-lang">Bangla</span>
</a>
<a @click="SetLocal('br')">
<i title="pt" class="flag-icon flag-icon-squared flag-icon-pt"></i>
<span class="title-lang">Portuguese</span>
</a>
</div>
</vue-perfect-scrollbar>
</b-dropdown>
</div>
<!-- User avatar dropdown -->
<div class="dropdown">
<b-dropdown
id="dropdown-1"
text="Dropdown Button"
class="m-md-2 user col align-self-end"
toggle-class="text-decoration-none"
no-caret
variant="link"
right
>
<template slot="button-content">
<img
:src="'/images/avatar/'+currentUser.avatar"
id="userDropdown"
alt
data-toggle="dropdown"
aria-haspopup="true"
aria-expanded="false"
>
</template>
<div class="dropdown-menu-left" aria-labelledby="userDropdown">
<div class="dropdown-header">
<i class="i-Lock-User mr-1"></i>
<span>{{currentUser.username}}</span>
</div>
<router-link to="/app/profile" class="dropdown-item">{{$t('profil')}}</router-link>
<router-link
v-if="currentUserPermissions && currentUserPermissions.includes('setting_system')"
to="/app/settings/System_settings"
class="dropdown-item"
>{{$t('Settings')}}</router-link>
<a class="dropdown-item" href="#" @click.prevent="logoutUser">{{$t('logout')}}</a>
</div>
</b-dropdown>
</div>
</div>
</div>
<validation-observer ref="create_pos">
<b-form @submit.prevent="Submit_Pos">
<b-card-body>
<b-row>
<b-modal hide-footer id="open_scan" size="md" title="Barcode Scanner">
<qrcode-scanner
:qrbox="250"
:fps="10"
style="width: 100%; height: calc(100vh - 56px);"
@result="onScan"
/>
</b-modal>
<!-- Customer -->
<b-col lg="12" md="12" sm="12">
<validation-provider name="Customer" :rules="{ required: true}">
<b-input-group slot-scope="{ valid, errors }" class="input-customer">
<v-select
:class="{'is-invalid': !!errors.length}"
:state="errors[0] ? false : (valid ? true : null)"
v-model="sale.client_id"
@input="onClientSelected"
:reduce="label => label.value"
:placeholder="$t('Choose_Customer')"
class="w-100"
:options="clients.map(clients => ({label: clients.name, value: clients.id}))"
/>
<b-input-group-append>
<b-button variant="primary" @click="New_Client()">
<span>
<i class="i-Add-User"></i>
</span>
</b-button>
</b-input-group-append>
</b-input-group>
</validation-provider>
</b-col>
<!-- warehouse -->
<b-col lg="12" md="12" sm="12">
<validation-provider name="warehouse" :rules="{ required: true}">
<b-form-group slot-scope="{ valid, errors }" class="mt-2">
<v-select
:class="{'is-invalid': !!errors.length}"
:state="errors[0] ? false : (valid ? true : null)"
:disabled="details.length > 0"
@input="Selected_Warehouse"
v-model="sale.warehouse_id"
:reduce="label => label.value"
:placeholder="$t('Choose_Warehouse')"
:options="warehouses.map(warehouses => ({label: warehouses.name, value: warehouses.id}))"
/>
</b-form-group>
</validation-provider>
</b-col>
<!-- Details Product -->
<b-col md="12" class="mt-2">
<div class="pos-detail">
<div class="table-responsive">
<table class="table table-striped">
<thead>
<tr>
<th scope="col">{{$t('ProductName')}}</th>
<th scope="col">{{$t('Price')}}</th>
<th scope="col" class="text-center">{{$t('Qty')}}</th>
<th scope="col" class="text-center">{{$t('SubTotal')}}</th>
<th scope="col" class="text-center">
<i class="fa fa-trash"></i>
</th>
</tr>
</thead>
<tbody>
<tr v-if="details.length <= 0">
<td colspan="5">{{$t('NodataAvailable')}}</td>
</tr>
<tr v-for="(detail, index) in details" :key="index">
<td>
<span>{{detail.code}}</span>
<br>
<span class="badge badge-success">{{detail.name}}</span>
<i v-if="currentUserPermissions && currentUserPermissions.includes('edit_product_sale')"
@click="Modal_Updat_Detail(detail)" class="i-Edit text-success cursor-pointer"></i>
</td>
<td>{{currentUser.currency}} {{formatNumber(detail.Total_price, 2)}}</td>
<td>
<div class="quantity">
<b-input-group>
<b-input-group-prepend>
<span
class="btn btn-primary btn-sm"
@click="decrement(detail ,detail.detail_id)"
>-</span>
</b-input-group-prepend>
<input
class="form-control"
@keyup="Verified_Qty(detail,detail.detail_id)"
v-model.number="detail.quantity"
>
<b-input-group-append>
<span
class="btn btn-primary btn-sm"
@click="increment(detail.detail_id)"
>+</span>
</b-input-group-append>
</b-input-group>
</div>
</td>
<td class="text-center">{{currentUser.currency}} {{detail.subtotal.toFixed(2)}}</td>
<td>
<a
@click="delete_Product_Detail(detail.detail_id)"
title="Delete"
>
<i class="i-Close-Window text-25 text-danger cursor-pointer"></i>
</a>
</td>
</tr>
</tbody>
</table>
</div>
</div>
</b-col>
</b-row>
<!-- Calcul Grand Total -->
<div class="footer_panel">
<b-row>
<b-col md="12">
<div class="grandtotal">
<span>{{$t("Total_Payable")}} : {{currentUser.currency}} {{GrandTotal.toFixed(2)}}</span>
</div>
</b-col>
<!-- Order Tax -->
<b-col lg="4" md="4" sm="12" v-if="currentUserPermissions && currentUserPermissions.includes('edit_tax_discount_shipping_sale')">
<validation-provider
name="Order Tax"
:rules="{ regex: /^\d*\.?\d*$/}"
v-slot="validationContext"
>
<b-form-group :label="$t('Tax')" append="%">
<b-input-group append="%">
<b-form-input
:state="getValidationState(validationContext)"
aria-describedby="OrderTax-feedback"
label="Order Tax"
v-model.number="sale.tax_rate"
@keyup="keyup_OrderTax()"
></b-form-input>
</b-input-group>
<b-form-invalid-feedback
id="OrderTax-feedback"
>{{ validationContext.errors[0] }}</b-form-invalid-feedback>
</b-form-group>
</validation-provider>
</b-col>
<!-- Discount -->
<b-col lg="4" md="4" sm="12" v-if="currentUserPermissions && currentUserPermissions.includes('edit_tax_discount_shipping_sale')">
<validation-provider
name="Discount"
:rules="{ regex: /^\d*\.?\d*$/}"
v-slot="validationContext"
>
<b-form-group :label="$t('Discount')" append="%">
<b-input-group :append="currentUser.currency">
<b-form-input
:state="getValidationState(validationContext)"
aria-describedby="Discount-feedback"
label="Discount"
v-model.number="sale.discount"
@keyup="keyup_Discount()"
></b-form-input>
</b-input-group>
<b-form-invalid-feedback
id="Discount-feedback"
>{{ validationContext.errors[0] }}</b-form-invalid-feedback>
</b-form-group>
</validation-provider>
</b-col>
<!-- Shipping -->
<b-col lg="4" md="4" sm="12" v-if="currentUserPermissions && currentUserPermissions.includes('edit_tax_discount_shipping_sale')">
<validation-provider
name="Shipping"
:rules="{ regex: /^\d*\.?\d*$/}"
v-slot="validationContext"
>
<b-form-group :label="$t('Shipping')">
<b-input-group :append="currentUser.currency">
<b-form-input
:state="getValidationState(validationContext)"
aria-describedby="Shipping-feedback"
label="Shipping"
v-model.number="sale.shipping"
@keyup="keyup_Shipping()"
></b-form-input>
</b-input-group>
<b-form-invalid-feedback
id="Shipping-feedback"
>{{ validationContext.errors[0] }}</b-form-invalid-feedback>
</b-form-group>
</validation-provider>
</b-col>
</b-row>
</div>
</b-card-body>
</b-form>
</validation-observer>
<!-- Update Detail Product -->
<validation-observer ref="Update_Detail">
<b-modal hide-footer size="lg" id="form_Update_Detail" :title="detail.name">
<b-form @submit.prevent="submit_Update_Detail">
<b-row>
<!-- Unit Price -->
<b-col lg="6" md="6" sm="12">
<validation-provider
name="Product Price"
:rules="{ required: true , regex: /^\d*\.?\d*$/}"
v-slot="validationContext"
>
<b-form-group :label="$t('ProductPrice') + ' ' + '*'" id="Price-input">
<b-form-input
label="Product Price"
v-model="detail.Unit_price"
:state="getValidationState(validationContext)"
aria-describedby="Price-feedback"
></b-form-input>
<b-form-invalid-feedback
id="Price-feedback"
>{{ validationContext.errors[0] }}</b-form-invalid-feedback>
</b-form-group>
</validation-provider>
</b-col>
<!-- Tax Method -->
<b-col lg="6" md="6" sm="12">
<validation-provider name="Tax Method" :rules="{ required: true}">
<b-form-group slot-scope="{ valid, errors }" :label="$t('TaxMethod') + ' ' + '*'">
<v-select
:class="{'is-invalid': !!errors.length}"
:state="errors[0] ? false : (valid ? true : null)"
v-model="detail.tax_method"
:reduce="label => label.value"
:placeholder="$t('Choose_Method')"
:options="
[
{label: 'Exclusive', value: '1'},
{label: 'Inclusive', value: '2'}
]"
></v-select>
<b-form-invalid-feedback>{{ errors[0] }}</b-form-invalid-feedback>
</b-form-group>
</validation-provider>
</b-col>
<!-- Tax -->
<b-col lg="6" md="6" sm="12">
<validation-provider
name="Tax"
:rules="{ required: true , regex: /^\d*\.?\d*$/}"
v-slot="validationContext"
>
<b-form-group :label="$t('Tax') + ' ' + '*'">
<b-input-group append="%">
<b-form-input
label="Tax"
v-model="detail.tax_percent"
:state="getValidationState(validationContext)"
aria-describedby="Tax-feedback"
></b-form-input>
</b-input-group>
<b-form-invalid-feedback
id="Tax-feedback"
>{{ validationContext.errors[0] }}</b-form-invalid-feedback>
</b-form-group>
</validation-provider>
</b-col>
<!-- Discount Method -->
<b-col lg="6" md="6" sm="12">
<validation-provider name="Discount Method" :rules="{ required: true}">
<b-form-group slot-scope="{ valid, errors }" :label="$t('Discount_Method') + ' ' + '*'">
<v-select
v-model="detail.discount_Method"
:reduce="label => label.value"
:placeholder="$t('Choose_Method')"
:class="{'is-invalid': !!errors.length}"
:state="errors[0] ? false : (valid ? true : null)"
:options="
[
{label: 'Percent %', value: '1'},
{label: 'Fixed', value: '2'}
]"
></v-select>
<b-form-invalid-feedback>{{ errors[0] }}</b-form-invalid-feedback>
</b-form-group>
</validation-provider>
</b-col>
<!-- Discount Rate -->
<b-col lg="6" md="6" sm="12">
<validation-provider
name="Discount Rate"
:rules="{ required: true , regex: /^\d*\.?\d*$/}"
v-slot="validationContext"
>
<b-form-group :label="$t('Discount') + ' ' + '*'">
<b-form-input
label="Discount"
v-model="detail.discount"
:state="getValidationState(validationContext)"
aria-describedby="Discount-feedback"
></b-form-input>
<b-form-invalid-feedback
id="Discount-feedback"
>{{ validationContext.errors[0] }}</b-form-invalid-feedback>
</b-form-group>
</validation-provider>
</b-col>
<!-- Unit Sale -->
<b-col lg="6" md="6" sm="12" v-if="detail.product_type != 'is_service'">
<validation-provider name="Unit Sale" :rules="{ required: true}">
<b-form-group slot-scope="{ valid, errors }" :label="$t('UnitSale') + ' ' + '*'">
<v-select
:class="{'is-invalid': !!errors.length}"
:state="errors[0] ? false : (valid ? true : null)"
v-model="detail.sale_unit_id"
:placeholder="$t('Choose_Unit_Sale')"
:reduce="label => label.value"
:options="units.map(units => ({label: units.name, value: units.id}))"
/>
<b-form-invalid-feedback>{{ errors[0] }}</b-form-invalid-feedback>
</b-form-group>
</validation-provider>
</b-col>
<!-- Imei or serial numbers -->
<b-col lg="12" md="12" sm="12" v-show="detail.is_imei">
<b-form-group :label="$t('Add_product_IMEI_Serial_number')">
<b-form-input
label="Add_product_IMEI_Serial_number"
v-model="detail.imei_number"
:placeholder="$t('Add_product_IMEI_Serial_number')"
></b-form-input>
</b-form-group>
</b-col>
<b-col md="12">
<b-form-group>
<b-button variant="primary" type="submit">{{$t('submit')}}</b-button>
</b-form-group>
</b-col>
</b-row>
</b-form>
</b-modal>
</validation-observer>
</b-card>
</b-col>
<!-- Card right Of Products -->
<b-col md="7">
<b-card class="list-grid">
<b-row>
<b-col md="6">
<button v-b-toggle.sidebar-category class="btn btn-outline-info mt-1 btn-block">
<i class="i-Two-Windows"></i>
{{$t('ListofCategory')}}
</button>
</b-col>
<b-col md="6">
<button v-b-toggle.sidebar-brand class="btn btn-outline-info mt-1 btn-block">
<i class="i-Library"></i>
{{$t('ListofBrand')}}
</button>
</b-col>
<!-- Product -->
<b-col md="12" class="mt-2 mb-2">
<div id="autocomplete" class="autocomplete">
<div class="input-with-icon">
<img src="/assets_setup/scan.png" alt="Scan" class="scan-icon" @click="showModal">
<input
:placeholder="$t('Scan_Search_Product_by_Code_Name')"
@input='e => search_input = e.target.value'
@keyup="search(search_input)"
@focus="handleFocus"
@blur="handleBlur"
ref="product_autocomplete"
class="autocomplete-input" />
</div>
<ul class="autocomplete-result-list" v-show="focused">
<li class="autocomplete-result" v-for="product_fil in product_filter" @mousedown="SearchProduct(product_fil)">{{getResultValue(product_fil)}}</li>
</ul>
</div>
</b-col>
<div class="col-md-12 d-flex flex-row flex-wrap bd-highlight list-item mt-2">
<div
@click="Check_Product_Exist(product , product.id)"
v-for="product in products"
class="card o-hidden bd-highlight m-1"
>
<div class="list-thumb d-flex">
<img alt :src="'/images/products/'+product.image">
</div>
<div class="flex-grow-1 d-bock">
<div
class="card-body align-self-center d-flex flex-column justify-content-between align-items-lg-center"
>
<div class="w-40 w-sm-100 item-title">{{product.name}}</div>
<p class="text-muted text-small w-15 w-sm-100 mb-2">{{product.code}}</p>
<span
class="badge badge-primary w-15 w-sm-100 mb-2"
>{{currentUser.currency}} {{formatNumber(product.Net_price , 2)}}</span>
<p v-if="product.product_type != 'is_service'"
class="m-0 text-muted text-small w-15 w-sm-100 d-none d-lg-block item-badges"
>
<span
class="badge badge-info"
>{{formatNumber(product.qte_sale , 2)}} {{product.unitSale}}</span>
</p>
</div>
</div>
</div>
</div>
</b-row>
<b-row class="mb-3">
<b-col md="12" class="mt-4">
<b-pagination
@change="Product_onPageChanged"
:total-rows="product_totalRows"
:per-page="product_perPage"
v-model="product_currentPage"
class="my-0 gull-pagination align-items-center"
align="center"
first-text
last-text
>
<p class="list-arrow m-0" slot="prev-text">
<i class="i-Arrow-Left text-40"></i>
</p>
<p class="list-arrow m-0" slot="next-text">
<i class="i-Arrow-Right text-40"></i>
</p>
</b-pagination>
</b-col>
</b-row>
</b-card>
</b-col>
<!-- Sidebar Brand -->
<b-sidebar id="sidebar-brand" :title="$t('ListofBrand')" bg-variant="white" right shadow>
<div class="px-3 py-2">
<b-row>
<div class="col-md-12 d-flex flex-row flex-wrap bd-highlight list-item mt-2">
<div
@click="GetAllBrands()"
:class="{ 'brand-Active' : brand_id == ''}"
class="card o-hidden bd-highlight m-1"
>
<div class="list-thumb d-flex">
<img alt :src="'/images/no-image.png'">
</div>
<div class="flex-grow-1 d-bock">
<div
class="card-body align-self-center d-flex flex-column justify-content-between align-items-lg-center"
>
<div class="item-title">{{$t('All_Brand')}}</div>
</div>
</div>
</div>
<div
class="card o-hidden bd-highlight m-1"
v-for="brand in paginated_Brands"
:key="brand.id"
@click="Products_by_Brands(brand.id)"
:class="{ 'brand-Active' : brand.id === brand_id}"
>
<img alt :src="'/images/brands/'+brand.image">
<div class="flex-grow-1 d-bock">
<div
class="card-body align-self-center d-flex flex-column justify-content-between align-items-lg-center"
>
<div class="item-title">{{brand.name}}</div>
</div>
</div>
</div>
</div>
</b-row>
<b-row>
<b-col md="12" class="mt-4">
<b-pagination
@change="BrandonPageChanged"
:total-rows="brand_totalRows"
:per-page="brand_perPage"
v-model="brand_currentPage"
class="my-0 gull-pagination align-items-center"
align="center"
first-text
last-text
>
<p class="list-arrow m-0" slot="prev-text">
<i class="i-Arrow-Left text-40"></i>
</p>
<p class="list-arrow m-0" slot="next-text">
<i class="i-Arrow-Right text-40"></i>
</p>
</b-pagination>
</b-col>
</b-row>
</div>
</b-sidebar>
<!-- Sidebar category -->
<b-sidebar
id="sidebar-category"
:title="$t('ListofCategory')"
bg-variant="white"
right
shadow
>
<div class="px-3 py-2">
<b-row>
<div class="col-md-12 d-flex flex-row flex-wrap bd-highlight list-item mt-2">
<div
@click="getAllCategory()"
:class="{ 'brand-Active' : category_id == ''}"
class="card o-hidden bd-highlight m-1"
>
<div class="list-thumb d-flex">
<img alt :src="'/images/no-image.png'">
</div>
<div class="flex-grow-1 d-bock">
<div
class="card-body align-self-center d-flex flex-column justify-content-between align-items-lg-center"
>
<div class="item-title">{{$t('All_Category')}}</div>
</div>
</div>
</div>
<div
class="card o-hidden bd-highlight m-1"
v-for="category in paginated_Category"
:key="category.id"
@click="Products_by_Category(category.id)"
:class="{ 'brand-Active' : category.id === category_id}"
>
<img alt :src="'/images/no-image.png'">
<div class="flex-grow-1 d-bock">
<div
class="card-body align-self-center d-flex flex-column justify-content-between align-items-lg-center"
>
<div class="item-title">{{category.name}}</div>
</div>
</div>
</div>
</div>
</b-row>
<b-row>
<b-col md="12" class="mt-4">
<b-pagination
@change="Category_onPageChanged"
:total-rows="category_totalRows"
:per-page="category_perPage"
v-model="category_currentPage"
class="my-0 gull-pagination align-items-center"
align="center"
first-text
last-text
>
<p class="list-arrow m-0" slot="prev-text">
<i class="i-Arrow-Left text-40"></i>
</p>
<p class="list-arrow m-0" slot="next-text">
<i class="i-Arrow-Right text-40"></i>
</p>
</b-pagination>
</b-col>
</b-row>
</div>
</b-sidebar>
<!-- Modal Show Invoice POS-->
<b-modal hide-footer size="sm" scrollable id="Show_invoice" :title="$t('Invoice_POS')">
<div id="invoice-POS">
<div style="max-width:400px;margin:0px auto">
<div class="info">
<div class="invoice_logo text-center mb-2">
<img :src="'/images/'+invoice_pos.setting.logo" alt width="60" height="60">
</div>
<p>
<span>{{$t('date')}} : {{invoice_pos.sale.date}} <br></span>
<span v-show="pos_settings.show_address">{{$t('Adress')}} : {{invoice_pos.setting.CompanyAdress}} <br></span>
<span v-show="pos_settings.show_email">{{$t('Email')}} : {{invoice_pos.setting.email}} <br></span>
<span v-show="pos_settings.show_phone">{{$t('Phone')}} : {{invoice_pos.setting.CompanyPhone}} <br></span>
<span v-show="pos_settings.show_customer">{{$t('Customer')}} : {{invoice_pos.sale.client_name}} <br></span>
<span v-show="pos_settings.show_Warehouse">{{$t('warehouse')}} : {{invoice_pos.sale.warehouse_name}} <br></span>
</p>
</div>
<table class="table_data">
<tbody>
<tr v-for="detail_invoice in invoice_pos.details">
<td colspan="3">
{{detail_invoice.name}}
<br v-show="detail_invoice.is_imei && detail_invoice.imei_number !==null">
<span v-show="detail_invoice.is_imei && detail_invoice.imei_number !==null ">{{$t('IMEI_SN')}} : {{detail_invoice.imei_number}}</span>
<br>
<span>{{formatNumber(detail_invoice.quantity,2)}} {{detail_invoice.unit_sale}} x {{formatNumber(detail_invoice.total/detail_invoice.quantity,2)}}</span>
</td>
<td
style="text-align:right;vertical-align:bottom"
>{{formatNumber(detail_invoice.total,2)}}</td>
</tr>
<tr style="margin-top:10px" v-show="pos_settings.show_discount">
<td colspan="3" class="total">{{$t('OrderTax')}}</td>
<td style="text-align:right;" class="total">{{invoice_pos.symbol}} {{formatNumber(invoice_pos.sale.taxe ,2)}} ({{formatNumber(invoice_pos.sale.tax_rate,2)}} %)</td>
</tr>
<tr style="margin-top:10px" v-show="pos_settings.show_discount">
<td colspan="3" class="total">{{$t('Discount')}}</td>
<td style="text-align:right;" class="total">{{invoice_pos.symbol}} {{formatNumber(invoice_pos.sale.discount ,2)}}</td>
</tr>
<tr style="margin-top:10px" v-show="pos_settings.show_discount">
<td colspan="3" class="total">{{$t('Shipping')}}</td>
<td style="text-align:right;" class="total">{{invoice_pos.symbol}} {{formatNumber(invoice_pos.sale.shipping ,2)}}</td>
</tr>
<tr style="margin-top:10px">
<td colspan="3" class="total">{{$t('Total')}}</td>
<td
style="text-align:right;"
class="total"
>{{invoice_pos.symbol}} {{formatNumber(invoice_pos.sale.GrandTotal ,2)}}</td>
</tr>
<tr v-show="invoice_pos.sale.paid_amount < invoice_pos.sale.GrandTotal">
<td colspan="3" class="total">{{$t('Paid')}}</td>
<td
style="text-align:right;"
class="total"
>{{invoice_pos.symbol}} {{formatNumber(invoice_pos.sale.paid_amount ,2)}}</td>
</tr>
<tr v-show="invoice_pos.sale.paid_amount < invoice_pos.sale.GrandTotal">
<td colspan="3" class="total">{{$t('Due')}}</td>
<td
style="text-align:right;"
class="total"
>{{invoice_pos.symbol}} {{parseFloat(invoice_pos.sale.GrandTotal - invoice_pos.sale.paid_amount).toFixed(2)}}</td>
</tr>
</tbody>
</table>
<table
class="change mt-3"
style=" font-size: 10px;"
v-show="invoice_pos.sale.paid_amount > 0"
>
<thead>
<tr style="background: #eee; ">
<th style="text-align: left;" colspan="1">{{$t('PayeBy')}}:</th>
<th style="text-align: center;" colspan="2">{{$t('Amount')}}:</th>
<th style="text-align: right;" colspan="1">{{$t('Change')}}:</th>
</tr>
</thead>
<tbody>
<tr v-for="payment_pos in payments">
<td style="text-align: left;" colspan="1">{{payment_pos.Reglement}}</td>
<td
style="text-align: center;"
colspan="2"
>{{formatNumber(payment_pos.montant ,2)}}</td>
<td
style="text-align: right;"
colspan="1"
>{{formatNumber(payment_pos.change ,2)}}</td>
</tr>
</tbody>
</table>
<div id="legalcopy" class="ml-2">
<p class="legal" v-show="pos_settings.show_note">
<strong>{{pos_settings.note_customer}}</strong>
</p>
<div id="bar" v-show="pos_settings.show_barcode">
<barcode
class="barcode"
:format="barcodeFormat"
:value="invoice_pos.sale.Ref"
textmargin="0"
fontoptions="bold"
fontSize="15"
height="25"
width="1"
></barcode>
</div>
</div>
</div>
</div>
<button @click="print_pos()" class="btn btn-outline-primary">
<i class="i-Billing"></i>
{{$t('print')}}
</button>
</b-modal>
<!-- Modal Add Payment-->
<validation-observer ref="Add_payment">
<b-modal hide-footer size="lg" id="Add_Payment" :title="$t('AddPayment')">
<b-form @submit.prevent="Submit_Payment">
<h1 class="text-center mt-3 mb-3">{{client_name}}</h1>
<b-row>
<b-col md="6">
<b-row>
<!-- Received Amount -->
<b-col lg="12" md="12" sm="12">
<validation-provider
name="Received Amount"
:rules="{ required: true , regex: /^\d*\.?\d*$/}"
v-slot="validationContext"
>
<b-form-group :label="$t('Received_Amount') + ' ' + '*'">
<b-form-input
@keyup="Verified_Received_Amount(payment.received_amount)"
label="Received_Amount"
:placeholder="$t('Received_Amount')"
v-model.number="payment.received_amount"
:state="getValidationState(validationContext)"
aria-describedby="Received_Amount-feedback"
></b-form-input>
<b-form-invalid-feedback
id="Received_Amount-feedback"
>{{ validationContext.errors[0] }}</b-form-invalid-feedback>
</b-form-group>
</validation-provider>
</b-col>
<!-- Paying Amount -->
<b-col lg="12" md="12" sm="12">
<validation-provider
name="Paying Amount"
:rules="{ required: true , regex: /^\d*\.?\d*$/}"
v-slot="validationContext"
>
<b-form-group :label="$t('Paying_Amount') + ' ' + '*'">
<b-form-input
label="Paying_Amount"
@keyup="Verified_paidAmount(payment.amount)"
:placeholder="$t('Paying_Amount')"
v-model.number="payment.amount"
:state="getValidationState(validationContext)"
aria-describedby="Paying_Amount-feedback"
></b-form-input>
<b-form-invalid-feedback
id="Paying_Amount-feedback"
>{{ validationContext.errors[0] }}</b-form-invalid-feedback>
</b-form-group>
</validation-provider>
</b-col>
<!-- change Amount -->
<b-col lg="12" md="12" sm="12">
<label>{{$t('Change')}} :</label>
<p
class="change_amount"
>{{parseFloat(payment.received_amount - payment.amount).toFixed(2)}}</p>
</b-col>
</b-row>
</b-col>
<b-col md="6">
<b-card>
<b-list-group>
<b-list-group-item class="d-flex justify-content-between align-items-center">
{{$t('TotalProducts')}}
<b-badge variant="primary" pill>{{details.length}}</b-badge>
</b-list-group-item>
<b-list-group-item class="d-flex justify-content-between align-items-center">
{{$t('OrderTax')}}
<span
class="font-weight-bold"
>{{currentUser.currency}} {{sale.TaxNet.toFixed(2)}} ({{sale.tax_rate}} %)</span>
</b-list-group-item>
<b-list-group-item class="d-flex justify-content-between align-items-center">
{{$t('Discount')}}
<span
class="font-weight-bold"
>{{currentUser.currency}} {{sale.discount.toFixed(2)}}</span>
</b-list-group-item>
<b-list-group-item class="d-flex justify-content-between align-items-center">
{{$t('Shipping')}}
<span
class="font-weight-bold"
>{{currentUser.currency}} {{sale.shipping.toFixed(2)}}</span>
</b-list-group-item>
<b-list-group-item class="d-flex justify-content-between align-items-center">
{{$t('Total_Payable')}}
<span
class="font-weight-bold"
>{{currentUser.currency}} {{GrandTotal.toFixed(2)}}</span>
</b-list-group-item>
</b-list-group>
</b-card>
</b-col>
</b-row>
<b-row class="mt-4">
<!-- Payment choice -->
<b-col lg="6" md="6" sm="12">
<validation-provider name="Payment choice" :rules="{ required: true}">
<b-form-group slot-scope="{ valid, errors }" :label="$t('Paymentchoice') + ' ' + '*'">
<v-select
:class="{'is-invalid': !!errors.length}"
:state="errors[0] ? false : (valid ? true : null)"
v-model="payment.Reglement"
@input="Selected_PaymentMethod"
:reduce="label => label.value"
:placeholder="$t('PleaseSelect')"
:options="
[
{label: 'Cash', value: 'Cash'},
{label: 'credit card', value: 'credit card'},
{label: 'TPE', value: 'tpe'},
{label: 'cheque', value: 'cheque'},
{label: 'Western Union', value: 'Western Union'},
{label: 'bank transfer', value: 'bank transfer'},
{label: 'other', value: 'other'},
]"
></v-select>
<b-form-invalid-feedback>{{ errors[0] }}</b-form-invalid-feedback>
</b-form-group>
</validation-provider>
</b-col>
<!-- Account -->
<b-col lg="6" md="6" sm="12">
<validation-provider name="Account">
<b-form-group slot-scope="{ valid, errors }" :label="$t('Account')">
<v-select
:class="{'is-invalid': !!errors.length}"
:state="errors[0] ? false : (valid ? true : null)"
v-model="payment.account_id"
:reduce="label => label.value"
:placeholder="$t('Choose_Account')"
:options="accounts.map(accounts => ({label: accounts.account_name, value: accounts.id}))"
/>
<b-form-invalid-feedback>{{ errors[0] }}</b-form-invalid-feedback>
</b-form-group>
</validation-provider>
</b-col>
<b-col md="12">
<b-card v-show="payment.Reglement == 'credit card'">
<div v-once class="typo__p" v-if="submit_showing_credit_card">
<div class="spinner sm spinner-primary mt-3"></div>
</div>
<div v-if="displaySavedPaymentMethods && !submit_showing_credit_card">
<div class="mt-3"><span class="mr-3">Saved Credit Card Info For This Client </span>
<b-button variant="outline-info" @click="show_new_credit_card()">
<span>
<i class="i-Two-Windows"></i>
New Credit Card
</span>
</b-button>
</div>
<table class="table table-hover mt-3">
<thead>
<tr>
<th>Last 4 digits</th>
<th>Type</th>
<th>Exp</th>
<th>Action</th>
</tr>
</thead>
<tbody>
<tr v-for="card in savedPaymentMethods" :class="{ 'bg-selected-card': isSelectedCard(card) }">
<td>**** {{card.last4}}</td>
<td>{{card.type}}</td>
<td>{{card.exp}}</td>
<td>
<b-button variant="outline-primary" @click="selectCard(card)" v-if="!isSelectedCard(card) && card_id != card.card_id">
<span>
<i class="i-Drag-Up"></i>
Use This
</span>
</b-button>
<i v-if="isSelectedCard(card) || card_id == card.card_id" class="i-Yes" style=" font-size: 20px; "></i>
</td>
</tr>
</tbody>
</table>
</div>
<div v-if="displayFormNewCard && !submit_showing_credit_card">
<form id="payment-form">
<label for="card-element" class="leading-7 text-sm text-gray-600">
{{$t('Credit_Card_Info')}}
<b-button variant="outline-info" @click="show_saved_credit_card()" v-if="savedPaymentMethods && savedPaymentMethods.length > 0">
<span>
<i class="i-Two-Windows"></i>
Use Saved Credit Card
</span>
</b-button>
</label>
<div id="card-element">
</div>
<div id="card-errors" class="is-invalid" role="alert"></div>
</form>
</div>
</b-card>
</b-col>
<!-- payment Note -->
<b-col lg="6" md="6" sm="12" class="mt-2">
<b-form-group :label="$t('Payment_note')">
<b-form-textarea
id="textarea"
v-model="payment.notes"
rows="3"
max-rows="6"
></b-form-textarea>
</b-form-group>
</b-col>
<!-- sale Note -->
<b-col lg="6" md="6" sm="12" class="mt-2">
<b-form-group :label="$t('sale_note')">
<b-form-textarea
id="textarea"
v-model="sale.notes"
rows="3"
max-rows="6"
></b-form-textarea>
</b-form-group>
</b-col>
<b-col md="12" class="mt-3">
<b-button
variant="primary"
type="submit"
:disabled="paymentProcessing"
><i class="i-Yes me-2 font-weight-bold"></i> {{$t('submit')}}</b-button>
<div v-once class="typo__p" v-if="paymentProcessing">
<div class="spinner sm spinner-primary mt-3"></div>
</div>
</b-col>
</b-row>
</b-form>
</b-modal>
</validation-observer>
<validation-observer ref="Create_Customer">
<b-modal hide-footer size="lg" id="New_Customer" :title="$t('Add')">
<b-form @submit.prevent="Submit_Customer">
<b-row>
<!-- Customer Name -->
<b-col md="6" sm="12">
<validation-provider
name="Name Customer"
:rules="{ required: true}"
v-slot="validationContext"
>
<b-form-group :label="$t('CustomerName') + ' ' + '*'">
<b-form-input
:state="getValidationState(validationContext)"
aria-describedby="name-feedback"
label="name"
v-model="client.name"
:placeholder="$t('CustomerName')"
></b-form-input>
<b-form-invalid-feedback id="name-feedback">{{ validationContext.errors[0] }}</b-form-invalid-feedback>
</b-form-group>
</validation-provider>
</b-col>
<!-- Customer Email -->
<b-col md="6" sm="12">
<b-form-group :label="$t('Email')">
<b-form-input
label="email"
v-model="client.email"
:placeholder="$t('Email')"
></b-form-input>
</b-form-group>
</b-col>
<!-- Customer Phone -->
<b-col md="6" sm="12">
<b-form-group :label="$t('Phone')">
<b-form-input
label="Phone"
v-model="client.phone"
:placeholder="$t('Phone')"
></b-form-input>
</b-form-group>
</b-col>
<!-- Customer Country -->
<b-col md="6" sm="12">
<b-form-group :label="$t('Country')">
<b-form-input
label="Country"
v-model="client.country"
:placeholder="$t('Country')"
></b-form-input>
</b-form-group>
</b-col>
<!-- Customer City -->
<b-col md="6" sm="12">
<b-form-group :label="$t('City')">
<b-form-input
label="City"
v-model="client.city"
:placeholder="$t('City')"
></b-form-input>
</b-form-group>
</b-col>
<!-- Customer Tax Number -->
<b-col md="6" sm="12">
<b-form-group :label="$t('Tax_Number')">
<b-form-input
label="Tax Number"
v-model="client.tax_number"
:placeholder="$t('Tax_Number')"
></b-form-input>
</b-form-group>
</b-col>
<!-- Customer Adress -->
<b-col md="12" sm="12">
<b-form-group :label="$t('Adress')">
<textarea
label="Adress"
class="form-control"
rows="4"
v-model="client.adresse"
:placeholder="$t('Adress')"
></textarea>
</b-form-group>
</b-col>
<b-col md="12" class="mt-3">
<b-button variant="primary" type="submit"><i class="i-Yes me-2 font-weight-bold"></i> {{$t('submit')}}</b-button>
</b-col>
</b-row>
</b-form>
</b-modal>
</validation-observer>
<b-modal
hide-footer
size="lg"
id="show_draft_sales"
title="Draft Sales"
>
<vue-good-table
mode="remote"
:columns="columns_draft_sales"
:totalRows="totalRows_draft_sales"
:rows="draft_sales"
@on-page-change="onPageChange"
@on-per-page-change="onPerPageChange"
:pagination-options="{
enabled: true,
mode: 'records',
nextLabel: 'next',
prevLabel: 'prev',
}"
styleClass="tableOne table-hover vgt-table"
>
<template slot="table-row" slot-scope="props">
<span v-if="props.column.field == 'actions'">
<router-link
v-b-tooltip.hover
title="Edit"
:to="{ name:'pos_draft', params: { id: props.row.id } }"
>
<i class="i-Edit text-25 text-success"></i>
</router-link>
<a
v-b-tooltip.hover
title="Delete"
class="cursor-pointer"
>
<i class="i-Close-Window text-25 text-danger"></i>
</a>
</span>
</template>
</vue-good-table>
</b-modal>
<div class="pos-button-actions" style="display: flex;margin-top: 10px;bottom: 0px;margin-left: 29px;width: 100%; flex-wrap: wrap; ">
<b-button style="width: auto;margin-bottom: 8px;"
@click="Submit_Pos()" variant="success ripple mr-1 btn-rounded">
<i class="i-Checkout"></i>
{{ $t("payNow") }}
</b-button>
</div>
</b-row>
</div>
</div>
</template>
<script>
import NProgress from "nprogress";
import { mapActions, mapGetters } from "vuex";
import vueEasyPrint from "vue-easy-print";
import VueBarcode from "vue-barcode";
import FlagIcon from "vue-flag-icon";
import Util from "./../../../utils";
import { loadStripe } from "@stripe/stripe-js";
export default {
components: {
vueEasyPrint,
barcode: VueBarcode,
FlagIcon
},
metaInfo: {
title: "POS"
},
data() {
return {
langs: [
"en",
"fr",
"ar",
"de",
"es",
"it",
"Ind",
"thai",
"tr_ch",
"sm_ch",
"tur",
"ru",
"hn",
"vn",
"kr",
"ba",
"br",
],
stripe: {},
stripe_key: "",
cardElement: {},
paymentProcessing: false,
DraftProcessing: false,
savedPaymentMethods: [],
hasSavedPaymentMethod: false,
useSavedPaymentMethod: false,
selectedCard:null,
card_id:'',
is_new_credit_card: false,
submit_showing_credit_card: false,
totalRows_draft_sales: "",
draft_sales:[],
limit: "10",
draft_sale_id:'',
serverParams: {
sort: {
field: "id",
type: "desc"
},
page: 1,
perPage: 10
},
client_name:'',
payment: {
amount: "",
account_id: "",
received_amount: "",
Reglement: "",
notes: ""
},
focused: false,
timer:null,
search_input:'',
product_filter:[],
isLoading: true,
load_product: true,
GrandTotal: 0,
total: 0,
Ref: "",
clients: [],
units: [],
warehouses: [],
payments: [],
products: [],
products_pos: [],
details: [],
detail: {},
categories: [],
brands: [],
accounts: [],
pos_settings:{},
product_currentPage: 1,
paginated_Products: "",
product_perPage: 8,
product_totalRows: "",
paginated_Brands: "",
brand_currentPage: 1,
brand_perPage: 3,
paginated_Category: "",
category_currentPage: 1,
category_perPage: 3,
barcodeFormat: "CODE128",
invoice_pos: {
sale: {
Ref: "",
client_name: "",
discount: "",
taxe: "",
date: "",
tax_rate: "",
shipping: "",
GrandTotal: "",
paid_amount: ""
},
details: [],
setting: {
logo: "",
CompanyName: "",
CompanyAdress: "",
email: "",
CompanyPhone: ""
}
},
sale: {
warehouse_id: "",
client_id: "",
tax_rate: 0,
shipping: 0,
discount: 0,
TaxNet: 0,
notes:'',
},
client: {
id: "",
name: "",
code: "",
email: "",
phone: "",
country: "",
tax_number: "",
city: "",
adresse: ""
},
category_id: "",
brand_id: "",
product: {
id: "",
code: "",
product_type: "",
current: "",
quantity: "",
check_qty: "",
discount: "",
DiscountNet: "",
discount_Method: "",
sale_unit_id: "",
fix_stock: "",
fix_price: "",
name: "",
unitSale: "",
Net_price: "",
Unit_price: "",
Total_price: "",
subtotal: "",
product_id: "",
detail_id: "",
taxe: "",
tax_percent: "",
tax_method: "",
product_variant_id: "",
is_imei: "",
imei_number:"",
},
sound: "/audio/Beep.wav",
audio: new Audio("/audio/Beep.wav")
};
},
computed: {
...mapGetters(["currentUser", "currentUserPermissions"]),
brand_totalRows() {
return this.brands.length;
},
category_totalRows() {
return this.categories.length;
},
displaySavedPaymentMethods() {
if(this.hasSavedPaymentMethod){
return true;
}else{
return false;
}
},
displayFormNewCard() {
if(this.useSavedPaymentMethod){
return false;
}else{
return true;
}
},
isSelectedCard() {
return card => this.selectedCard === card;
},
columns_draft_sales() {
return [
{
label: this.$t("date"),
field: "date",
tdClass: "text-left",
thClass: "text-left",
sortable: false
},
{
label: this.$t("Reference"),
field: "Ref",
tdClass: "text-left",
thClass: "text-left",
sortable: false
},
{
label: this.$t("Customer"),
field: "client_name",
tdClass: "text-left",
thClass: "text-left",
sortable: false
},
{
label: this.$t("warehouse"),
field: "warehouse_name",
tdClass: "text-left",
thClass: "text-left",
sortable: false
},
{
label: this.$t("Total"),
field: "GrandTotal",
tdClass: "text-left",
thClass: "text-left",
sortable: false
},
{
label: this.$t("Action"),
field: "actions",
html: true,
tdClass: "text-right",
thClass: "text-right",
sortable: false
}
];
}
},
mounted() {
this.changeSidebarProperties();
this.paginate_products(this.product_perPage, 0);
},
methods: {
...mapActions(["changeSidebarProperties", "changeThemeMode", "logout"]),
// ...mapGetters(["currentUser"]),
logoutUser() {
this.$store.dispatch("logout");
},
handleFocus() {
this.focused = true
},
handleBlur() {
this.focused = false
},
showModal() {
this.$bvModal.show('open_scan');
},
onScan (decodedText, decodedResult) {
const code = decodedText;
this.search_input = code;
this.search();
this.$bvModal.hide('open_scan');
},
async Selected_PaymentMethod(value) {
if (value === 'credit card') {
this.savedPaymentMethods = [];
this.submit_showing_credit_card = true;
this.selectedCard = null
this.card_id = '';
// Check if the customer has saved payment methods
await axios.get(`/retrieve-customer?customerId=${this.sale.client_id}`)
.then(response => {
// If the customer has saved payment methods, display them
this.savedPaymentMethods = response.data.data;
this.card_id = response.data.customer_default_source;
this.hasSavedPaymentMethod = true;
this.useSavedPaymentMethod = true;
this.is_new_credit_card = false;
this.submit_showing_credit_card = false;
})
.catch(error => {
// If the customer does not have saved payment methods, show the card element for them to enter their payment information
this.hasSavedPaymentMethod = false;
this.useSavedPaymentMethod = false;
this.is_new_credit_card = true;
this.card_id = '';
setTimeout(() => {
this.loadStripe_payment();
}, 1000);
this.submit_showing_credit_card = false;
});
}else{
this.hasSavedPaymentMethod = false;
this.useSavedPaymentMethod = false;
this.is_new_credit_card = false;
}
},
show_saved_credit_card() {
this.hasSavedPaymentMethod = true;
this.useSavedPaymentMethod = true;
this.is_new_credit_card = false;
this.Selected_PaymentMethod('credit card');
},
show_new_credit_card() {
this.selectedCard = null;
this.card_id = '';
this.useSavedPaymentMethod = false;
this.hasSavedPaymentMethod = false;
this.is_new_credit_card = true;
setTimeout(() => {
this.loadStripe_payment();
}, 500);
},
selectCard(card) {
this.selectedCard = card;
this.card_id = card.card_id;
},
async loadStripe_payment() {
this.stripe = await loadStripe(`${this.stripe_key}`);
const elements = this.stripe.elements();
this.cardElement = elements.create("card", {
classes: {
base:
"bg-gray-100 rounded border border-gray-300 focus:border-indigo-500 text-base outline-none text-gray-700 p-3 leading-8 transition-colors duration-200 ease-in-out"
}
});
this.cardElement.mount("#card-element");
},
SetLocal(locale) {
this.$i18n.locale = locale;
this.$store.dispatch("language/setLanguage", locale);
Fire.$emit("ChangeLanguage");
},
handleFullScreen() {
Util.toggleFullScreen();
},
logoutUser() {
this.logout();
},
// ------------------------ Paginate Products --------------------\\
Product_paginatePerPage() {
this.paginate_products(this.product_perPage, 0);
},
paginate_products(pageSize, pageNumber) {
let itemsToParse = this.products;
this.paginated_Products = itemsToParse.slice(
pageNumber * pageSize,
(pageNumber + 1) * pageSize
);
},
Product_onPageChanged(page) {
this.paginate_products(this.product_perPage, page - 1);
this.getProducts(page);
},
// ------------------------ Paginate Brands --------------------\\
BrandpaginatePerPage() {
this.paginate_Brands(this.brand_perPage, 0);
},
paginate_Brands(pageSize, pageNumber) {
let itemsToParse = this.brands;
this.paginated_Brands = itemsToParse.slice(
pageNumber * pageSize,
(pageNumber + 1) * pageSize
);
},
BrandonPageChanged(page) {
this.paginate_Brands(this.brand_perPage, page - 1);
},
// ------------------------ Paginate Categories --------------------\\
Category_paginatePerPage() {
this.paginate_Category(this.category_perPage, 0);
},
paginate_Category(pageSize, pageNumber) {
let itemsToParse = this.categories;
this.paginated_Category = itemsToParse.slice(
pageNumber * pageSize,
(pageNumber + 1) * pageSize
);
},
Category_onPageChanged(page) {
this.paginate_Category(this.category_perPage, page - 1);
},
//--- Submit Validate Create Sale
Submit_Pos() {
// Start the progress bar.
NProgress.start();
NProgress.set(0.1);
this.$refs.create_pos.validate().then(success => {
if (!success) {
NProgress.done();
if (this.sale.client_id == "" || this.sale.client_id === null) {
this.makeToast(
"danger",
this.$t("Choose_Customer"),
this.$t("Failed")
);
} else if (
this.sale.warehouse_id == "" ||
this.sale.warehouse_id === null
) {
this.makeToast(
"danger",
this.$t("Choose_Warehouse"),
this.$t("Failed")
);
} else {
this.makeToast(
"danger",
this.$t("Please_fill_the_form_correctly"),
this.$t("Failed")
);
}
} else {
if (this.verifiedForm()) {
Fire.$emit("pay_now");
} else {
NProgress.done();
}
}
});
},
//---Submit Validation Update Detail
submit_Update_Detail() {
this.$refs.Update_Detail.validate().then(success => {
if (!success) {
return;
} else {
this.Update_Detail();
}
});
},
//------ Validate Form Submit_Payment
Submit_Payment() {
// Start the progress bar.
NProgress.start();
NProgress.set(0.1);
this.$refs.Add_payment.validate().then(success => {
if (!success) {
// Complete the animation of theprogress bar.
NProgress.done();
this.makeToast(
"danger",
this.$t("Please_fill_the_form_correctly"),
this.$t("Failed")
);
} else {
if (this.payment.amount > this.payment.received_amount) {
this.makeToast(
"warning",
this.$t("Paying_amount_is_greater_than_Received_amount"),
this.$t("Warning")
);
this.payment.received_amount = 0;
NProgress.done();
}
else if (this.payment.amount > this.GrandTotal) {
this.makeToast(
"warning",
this.$t("Paying_amount_is_greater_than_Grand_Total"),
this.$t("Warning")
);
this.payment.amount = 0;
NProgress.done();
}else{
this.CreatePOS();
}
}
});
},
//------------- Submit Validation Create & Edit Customer
Submit_Customer() {
// Start the progress bar.
NProgress.start();
NProgress.set(0.1);
this.$refs.Create_Customer.validate().then(success => {
if (!success) {
NProgress.done();
this.makeToast(
"danger",
this.$t("Please_fill_the_form_correctly"),
this.$t("Failed")
);
} else {
this.Create_Client();
}
});
},
//---------------------------------------- Create new Customer -------------------------------\\
Create_Client() {
axios
.post("clients", {
name: this.client.name,
email: this.client.email,
phone: this.client.phone,
tax_number: this.client.tax_number,
country: this.client.country,
city: this.client.city,
adresse: this.client.adresse
})
.then(response => {
NProgress.done();
this.makeToast(
"success",
this.$t("Create.TitleCustomer"),
this.$t("Success")
);
this.Get_Client_Without_Paginate();
this.$bvModal.hide("New_Customer");
})
.catch(error => {
NProgress.done();
this.makeToast("danger", this.$t("InvalidData"), this.$t("Failed"));
});
},
//------------------------------ New Model (create Customer) -------------------------------\\
New_Client() {
this.reset_Form_client();
this.$bvModal.show("New_Customer");
},
//-------------------------------- reset Form -------------------------------\\
reset_Form_client() {
this.client = {
id: "",
name: "",
email: "",
phone: "",
tax_number: "",
country: "",
city: "",
adresse: ""
};
},
//------------------------------------ Get Clients Without Paginate -------------------------\\
Get_Client_Without_Paginate() {
axios
.get("get_clients_without_paginate")
.then(({ data }) => (this.clients = data));
},
//---Validate State Fields
getValidationState({ dirty, validated, valid = null }) {
return dirty || validated ? valid : null;
},
//------ Toast
makeToast(variant, msg, title) {
this.$root.$bvToast.toast(msg, {
title: title,
variant: variant,
solid: true
});
},
//---------------------- Event Select Warehouse ------------------------------\\
Selected_Warehouse(value) {
this.search_input= '';
this.product_filter = [];
this.Get_Products_By_Warehouse(value);
this.getProducts(1);
},
onClientSelected(selectedClient) {
this.client_name = '';
const client = this.clients.find(client => client.id === selectedClient);
this.client_name = client.name;
},
//------------------------------------ Get Products By Warehouse -------------------------\\
Get_Products_By_Warehouse(id) {
// Start the progress bar.
NProgress.start();
NProgress.set(0.1);
axios
.get("get_Products_by_warehouse/" + id + "?stock=" + 1 + "&is_sale=" + 1 + "&product_service=" + 1)
.then(response => {
this.products_pos = response.data;
NProgress.done();
})
.catch(error => {
});
},
//----------------------------------------- Add Detail of Sale -------------------------\\
add_product(code) {
this.audio.play();
if (this.details.some(detail => detail.code === code)) {
this.increment_qty_scanner(code);
} else {
if (this.details.length > 0) {
this.order_detail_id();
} else if (this.details.length === 0) {
this.product.detail_id = 1;
}
this.details.push(this.product);
setTimeout(() => {
this.load_product = true;
}, 300);
if(this.product.is_imei){
this.Modal_Updat_Detail(this.product);
}
}
},
//-------------------------------- order detail id -------------------------\\
order_detail_id() {
this.product.detail_id = 0;
var len = this.details.length;
this.product.detail_id = this.details[len - 1].detail_id + 1;
},
//---------------------- get_units ------------------------------\\
get_units(value) {
axios
.get("get_units?id=" + value)
.then(({ data }) => (this.units = data));
},
//------ Show Modal Update Detail Product
Modal_Updat_Detail(detail) {
this.detail = {};
this.get_units(detail.product_id);
this.detail.detail_id = detail.detail_id;
this.detail.sale_unit_id = detail.sale_unit_id;
this.detail.name = detail.name;
this.detail.product_type = detail.product_type;
this.detail.Unit_price = detail.Unit_price;
this.detail.fix_price = detail.fix_price;
this.detail.fix_stock = detail.fix_stock;
this.detail.current = detail.current;
this.detail.tax_method = detail.tax_method;
this.detail.discount_Method = detail.discount_Method;
this.detail.discount = detail.discount;
this.detail.quantity = detail.quantity;
this.detail.tax_percent = detail.tax_percent;
this.detail.is_imei = detail.is_imei;
this.detail.imei_number = detail.imei_number;
setTimeout(() => {
this.$bvModal.show("form_Update_Detail");
}, 1000);
},
//------ Submit Update Detail Product
Update_Detail() {
for (var i = 0; i < this.details.length; i++) {
if (this.details[i].detail_id === this.detail.detail_id) {
// this.convert_unit();
for (var k = 0; k < this.units.length; k++) {
if (this.units[k].id == this.detail.sale_unit_id) {
if (this.units[k].operator == "/") {
this.details[i].current =
this.detail.fix_stock * this.units[k].operator_value;
this.details[i].unitSale = this.units[k].ShortName;
} else {
this.details[i].current =
this.detail.fix_stock / this.units[k].operator_value;
this.details[i].unitSale = this.units[k].ShortName;
}
}
}
if (this.details[i].current < this.details[i].quantity) {
this.details[i].quantity = this.details[i].current;
} else {
this.details[i].quantity = 1;
}
this.details[i].Unit_price = this.detail.Unit_price;
this.details[i].tax_percent = this.detail.tax_percent;
this.details[i].tax_method = this.detail.tax_method;
this.details[i].discount_Method = this.detail.discount_Method;
this.details[i].discount = this.detail.discount;
this.details[i].sale_unit_id = this.detail.sale_unit_id;
this.details[i].imei_number = this.detail.imei_number;
this.details[i].product_type = this.detail.product_type;
if (this.details[i].discount_Method == "2") {
//Fixed
this.details[i].DiscountNet = this.details[i].discount;
} else {
//Percentage %
this.details[i].DiscountNet = parseFloat(
(this.details[i].Unit_price * this.details[i].discount) / 100
);
}
if (this.details[i].tax_method == "1") {
//Exclusive
this.details[i].Net_price = parseFloat(
this.details[i].Unit_price - this.details[i].DiscountNet
);
this.details[i].taxe = parseFloat(
(this.details[i].tax_percent *
(this.details[i].Unit_price - this.details[i].DiscountNet)) /
100
);
this.details[i].Total_price = parseFloat(
this.details[i].Net_price + this.details[i].taxe
);
} else {
//Inclusive
this.details[i].taxe = parseFloat(
(this.details[i].Unit_price - this.details[i].DiscountNet) *
(this.details[i].tax_percent / 100)
);
this.details[i].Net_price = parseFloat(
this.details[i].Unit_price -
this.details[i].taxe -
this.details[i].DiscountNet
);
this.details[i].Total_price = parseFloat(
this.details[i].Net_price + this.details[i].taxe
);
}
this.$forceUpdate();
}
}
this.CaclulTotal();
setTimeout(() => {
this.$bvModal.hide("form_Update_Detail");
}, 1000);
},
//-- check Qty of details order if Null or zero
verifiedForm() {
if (this.details.length <= 0) {
this.makeToast(
"warning",
this.$t("AddProductToList"),
this.$t("Warning")
);
return false;
} else {
var count = 0;
for (var i = 0; i < this.details.length; i++) {
if (
this.details[i].quantity == "" ||
this.details[i].quantity === 0 ||
this.details[i].quantity > this.details[i].current
) {
count += 1;
if(this.details[i].quantity > this.details[i].current){
this.makeToast("warning", this.$t("LowStock"), this.$t("Warning"));
return false;
}
}
}
if (count > 0) {
this.makeToast("warning", this.$t("AddQuantity"), this.$t("Warning"));
return false;
} else {
return true;
}
}
},
//------------------------------ Print -------------------------\\
print_pos() {
var divContents = document.getElementById("invoice-POS").innerHTML;
var a = window.open("", "", "height=500, width=500");
a.document.write(
'<link rel="stylesheet" href="/css/pos_print.css"><html>'
);
a.document.write("<body >");
a.document.write(divContents);
a.document.write("</body></html>");
a.document.close();
setTimeout(() => {
a.print();
}, 1000);
},
//-------------------------------- Invoice POS ------------------------------\\
Invoice_POS(id) {
// Start the progress bar.
NProgress.start();
NProgress.set(0.1);
axios
.get("sales_print_invoice/" + id)
.then(response => {
this.invoice_pos = response.data;
this.payments = response.data.payments;
this.pos_settings = response.data.pos_settings;
setTimeout(() => {
// Complete the animation of the progress bar.
NProgress.done();
this.$bvModal.show("Show_invoice");
}, 500);
if(response.data.pos_settings.is_printable){
setTimeout(() => this.print_pos(), 1000);
}
})
.catch(() => {
// Complete the animation of the progress bar.
setTimeout(() => NProgress.done(), 500);
});
// Add a setTimeout here
setTimeout(() => {
this.$router.push({ name: "pos" });
}, 2000);
},
//----------------------------------Process Payment ------------------------------\\
async processPayment() {
this.paymentProcessing = true;
const { token, error } = await this.stripe.createToken(this.cardElement);
if (error) {
this.paymentProcessing = false;
NProgress.done();
this.makeToast("danger", this.$t("InvalidData"), this.$t("Failed"));
} else {
axios
.post("pos/submit_sale_from_draft", {
draft_sale_id: this.draft_sale_id,
client_id: this.sale.client_id,
warehouse_id: this.sale.warehouse_id,
tax_rate: this.sale.tax_rate?this.sale.tax_rate:0,
TaxNet: this.sale.TaxNet?this.sale.TaxNet:0,
discount: this.sale.discount?this.sale.discount:0,
shipping: this.sale.shipping?this.sale.shipping:0,
details: this.details,
GrandTotal: this.GrandTotal,
payment: this.payment,
account_id: this.payment.account_id,
amount : parseFloat(this.payment.amount).toFixed(2),
received_amount : parseFloat(this.payment.received_amount).toFixed(2),
change: parseFloat(this.payment.received_amount - this.payment.amount).toFixed(2),
token: token.id,
is_new_credit_card: this.is_new_credit_card,
selectedCard: this.selectedCard,
card_id: this.card_id,
})
.then(response => {
this.paymentProcessing = false;
if (response.data.success === true) {
// Complete the animation of theprogress bar.
NProgress.done();
this.Invoice_POS(response.data.id);
this.$bvModal.hide("Add_Payment");
this.Reset_Pos();
}
})
.catch(error => {
this.paymentProcessing = false;
// Complete the animation of theprogress bar.
NProgress.done();
this.makeToast("danger", this.$t("InvalidData"), this.$t("Failed"));
});
}
},
//----------------------------------Create POS ------------------------------\\
CreatePOS() {
NProgress.start();
NProgress.set(0.1);
if (this.payment.Reglement == "credit card" && this.is_new_credit_card) {
if (this.stripe_key != "") {
this.processPayment();
} else {
this.makeToast(
"danger",
this.$t("credit_card_account_not_available"),
this.$t("Failed")
);
NProgress.done();
}
} else {
this.paymentProcessing = true;
axios
.post("pos/submit_sale_from_draft", {
draft_sale_id: this.draft_sale_id,
client_id: this.sale.client_id,
warehouse_id: this.sale.warehouse_id,
tax_rate: this.sale.tax_rate?this.sale.tax_rate:0,
TaxNet: this.sale.TaxNet?this.sale.TaxNet:0,
discount: this.sale.discount?this.sale.discount:0,
shipping: this.sale.shipping?this.sale.shipping:0,
notes: this.sale.notes,
details: this.details,
GrandTotal: this.GrandTotal,
payment: this.payment,
amount : parseFloat(this.payment.amount).toFixed(2),
received_amount : parseFloat(this.payment.received_amount).toFixed(2),
change: parseFloat(this.payment.received_amount - this.payment.amount).toFixed(2),
is_new_credit_card: this.is_new_credit_card,
selectedCard: this.selectedCard,
card_id: this.card_id,
})
.then(response => {
if (response.data.success === true) {
// Complete the animation of theprogress bar.
NProgress.done();
this.paymentProcessing = false;
this.Invoice_POS(response.data.id);
this.$bvModal.hide("Add_Payment");
this.Reset_Pos();
}
})
.catch(error => {
// Complete the animation of theprogress bar.
NProgress.done();
this.paymentProcessing = false;
this.makeToast("danger", this.$t("InvalidData"), this.$t("Failed"));
});
}
},
//------------------------------Formetted Numbers -------------------------\\
formatNumber(number, dec) {
const value = (typeof number === "string"
? number
: number.toString()
).split(".");
if (dec <= 0) return value[0];
let formated = value[1] || "";
if (formated.length > dec)
return `${value[0]}.${formated.substr(0, dec)}`;
while (formated.length < dec) formated += "0";
return `${value[0]}.${formated}`;
},
//---------------------------------Get Product Details ------------------------\\
Get_Product_Details(product_id, variant_id) {
axios.get("/show_product_data/" + product_id +"/"+ variant_id).then(response => {
this.product.discount = 0;
this.product.DiscountNet = 0;
this.product.discount_Method = "2";
this.product.product_id = response.data.id;
this.product.product_type = response.data.product_type;
this.product.name = response.data.name;
this.product.Net_price = response.data.Net_price;
this.product.Total_price = response.data.Total_price;
this.product.Unit_price = response.data.Unit_price;
this.product.taxe = response.data.tax_price;
this.product.tax_method = response.data.tax_method;
this.product.tax_percent = response.data.tax_percent;
this.product.unitSale = response.data.unitSale;
this.product.product_variant_id = variant_id;
this.product.code = response.data.code;
this.product.fix_price = response.data.fix_price;
this.product.sale_unit_id = response.data.sale_unit_id;
this.product.is_imei = response.data.is_imei;
this.product.imei_number = '';
this.add_product(response.data.code);
this.CaclulTotal();
// Complete the animation of theprogress bar.
NProgress.done();
});
},
//----------- Calcul Total
CaclulTotal() {
this.total = 0;
for (var i = 0; i < this.details.length; i++) {
var tax = this.details[i].taxe * this.details[i].quantity;
this.details[i].subtotal = parseFloat(
this.details[i].quantity * this.details[i].Net_price + tax
);
this.total = parseFloat(this.total + this.details[i].subtotal);
}
const total_without_discount = parseFloat(
this.total - this.sale.discount
);
this.sale.TaxNet = parseFloat(
(total_without_discount * this.sale.tax_rate) / 100
);
this.GrandTotal = parseFloat(
total_without_discount + this.sale.TaxNet + this.sale.shipping
);
var grand_total = this.GrandTotal.toFixed(2);
this.GrandTotal = parseFloat(grand_total);
},
//-------Verified QTY
Verified_Qty(detail, id) {
for (var i = 0; i < this.details.length; i++) {
if (this.details[i].detail_id === id) {
if (isNaN(detail.quantity)) {
this.details[i].quantity = detail.current;
}
if (detail.quantity > detail.current) {
this.makeToast("warning", this.$t("LowStock"), this.$t("Warning"));
this.details[i].quantity = detail.current;
} else {
this.details[i].quantity = detail.quantity;
}
}
}
this.$forceUpdate();
this.CaclulTotal();
},
//----------------------------------- Increment QTY with barcode scanner ------------------------------\\
increment_qty_scanner(code) {
for (var i = 0; i < this.details.length; i++) {
if (this.details[i].code === code) {
if (this.details[i].quantity + 1 > this.details[i].current) {
this.makeToast("warning", this.$t("LowStock"), this.$t("Warning"));
} else {
this.details[i].quantity++;
}
}
}
this.CaclulTotal();
this.$forceUpdate();
NProgress.done();
setTimeout(() => {
this.load_product = true;
}, 300);
},
//----------------------------------- Increment QTY ------------------------------\\
increment(id) {
for (var i = 0; i < this.details.length; i++) {
if (this.details[i].detail_id == id) {
if (this.details[i].quantity + 1 > this.details[i].current) {
this.makeToast("warning", this.$t("LowStock"), this.$t("Warning"));
} else {
this.details[i].quantity++;
}
}
}
this.CaclulTotal();
this.$forceUpdate();
},
//----------------------------------- decrement QTY ------------------------------\\
decrement(detail, id) {
for (var i = 0; i < this.details.length; i++) {
if (this.details[i].detail_id == id) {
if (detail.quantity - 1 > detail.current || detail.quantity - 1 < 1) {
this.makeToast("warning", this.$t("LowStock"), this.$t("Warning"));
} else {
this.details[i].quantity--;
}
}
}
this.CaclulTotal();
this.$forceUpdate();
},
//---------- keyup OrderTax
keyup_OrderTax() {
if (isNaN(this.sale.tax_rate)) {
this.sale.tax_rate = 0;
} else if(this.sale.tax_rate == ''){
this.sale.tax_rate = 0;
this.CaclulTotal();
}else {
this.CaclulTotal();
}
},
//---------- keyup Discount
keyup_Discount() {
if (isNaN(this.sale.discount)) {
this.sale.discount = 0;
} else if(this.sale.discount == ''){
this.sale.discount = 0;
this.CaclulTotal();
}else {
this.CaclulTotal();
}
},
//---------- keyup Shipping
keyup_Shipping() {
if (isNaN(this.sale.shipping)) {
this.sale.shipping = 0;
} else if(this.sale.shipping == ''){
this.sale.shipping = 0;
this.CaclulTotal();
}else {
this.CaclulTotal();
}
},
//---------- keyup paid Amount
Verified_paidAmount() {
if (isNaN(this.payment.amount)) {
this.payment.amount = 0;
} else {
if (this.payment.amount > this.payment.received_amount) {
this.makeToast(
"warning",
this.$t("Paying_amount_is_greater_than_Received_amount"),
this.$t("Warning")
);
this.payment.amount = 0;
}
else if (this.payment.amount > this.GrandTotal) {
this.makeToast(
"warning",
this.$t("Paying_amount_is_greater_than_Grand_Total"),
this.$t("Warning")
);
this.payment.amount = 0;
}
}
},
//---------- keyup Received Amount
Verified_Received_Amount() {
if (isNaN(this.payment.received_amount)) {
this.payment.received_amount = 0;
}
},
//-----------------------------------Delete Detail Product ------------------------------\\
delete_Product_Detail(id) {
for (var i = 0; i < this.details.length; i++) {
if (id === this.details[i].detail_id) {
this.details.splice(i, 1);
this.CaclulTotal();
}
}
},
//----------Reset Pos
Reset_Pos() {
this.details = [];
this.products = [];
this.products_pos = [];
this.product = {};
this.payment = {
amount: "",
account_id: "",
received_amount: "",
Reglement: "",
notes: "",
};
this.savedPaymentMethods= [],
this.hasSavedPaymentMethod= false,
this.useSavedPaymentMethod= false,
this.selectedCard=null,
this.card_id='',
this.is_new_credit_card= false,
this.submit_showing_credit_card= false,
this.sale.tax_rate = 0;
this.sale.TaxNet = 0;
this.sale.shipping = 0;
this.sale.discount = 0;
this.GrandTotal = 0;
this.total = 0;
this.category_id = "";
this.brand_id = "";
this.client_name = "";
// this.getProducts(1);
},
//------------------------- get Result Value Search Product
getResultValue(result) {
return result.code + " " + "(" + result.name + ")";
},
//------------------------- Submit Search Product
SearchProduct(result) {
if(this.load_product){
this.load_product = false;
this.product = {};
if(result.product_type == 'is_service'){
this.product.quantity = 1;
this.product.code = result.code;
}else{
this.product.code = result.code;
this.product.current = result.qte_sale;
this.product.fix_stock = result.qte;
if (result.qte_sale < 1) {
this.product.quantity = result.qte_sale;
} else {
this.product.quantity = 1;
}
}
this.product.product_variant_id = result.product_variant_id;
this.Get_Product_Details(result.id, result.product_variant_id);
this.search_input= '';
this.$refs.product_autocomplete.value = "";
this.product_filter = [];
}else{
this.makeToast(
"warning",
this.$t("Please_wait_until_the_product_is_loaded"),
this.$t("Warning")
);
}
},
// Search Products
search(){
if (this.timer) {
clearTimeout(this.timer);
this.timer = null;
}
if (this.search_input.length < 2) {
return this.product_filter= [];
}
if (this.sale.warehouse_id != "" && this.sale.warehouse_id != null) {
this.timer = setTimeout(() => {
const product_filter = this.products_pos.filter(product => product.code === this.search_input || product.barcode.includes(this.search_input));
if(product_filter.length === 1){
this.Check_Product_Exist(product_filter[0], product_filter[0].id);
}else{
this.product_filter= this.products_pos.filter(product => {
return (
product.name.toLowerCase().includes(this.search_input.toLowerCase()) ||
product.code.toLowerCase().includes(this.search_input.toLowerCase()) ||
product.barcode.toLowerCase().includes(this.search_input.toLowerCase())
);
});
// Check if product_filter is empty and show alert
if (this.product_filter.length <= 0) {
this.makeToast(
"warning",
"Product Not Found",
"Warning"
);
}
}
}, 800);
} else {
this.makeToast(
"warning",
this.$t("SelectWarehouse"),
this.$t("Warning")
);
}
},
//---------------------------------- Check if Product Exist in Order List ---------------------\\
Check_Product_Exist(product, id) {
if(this.load_product){
this.load_product = false;
NProgress.start();
NProgress.set(0.1);
this.product = {};
if( product.product_type == 'is_service'){
this.product.quantity = 1;
}else{
this.product.current = product.qte_sale;
this.product.fix_stock = product.qte;
if (product.qte_sale < 1) {
this.product.quantity = product.qte_sale;
} else {
this.product.quantity = 1;
}
}
this.Get_Product_Details(id, product.product_variant_id);
NProgress.done();
this.search_input= '';
this.$refs.product_autocomplete.value = "";
this.product_filter = [];
}else{
this.makeToast(
"warning",
this.$t("Please_wait_until_the_product_is_loaded"),
this.$t("Warning")
);
}
},
//--- Get Products by Category
Products_by_Category(id) {
this.category_id = id;
this.getProducts(1);
},
//--- Get Products by Brand
Products_by_Brands(id) {
this.brand_id = id;
this.getProducts(1);
},
//--- Get All Category
getAllCategory() {
this.category_id = "";
this.getProducts(1);
},
//--- Get All Brands
GetAllBrands() {
this.brand_id = "";
this.getProducts(1);
},
//------------------------------- Get Products with Filters ------------------------------\\
getProducts(page = 1) {
// Start the progress bar.
NProgress.start();
NProgress.set(0.1);
axios
.get(
"pos/get_products_pos?page=" +
page +
"&category_id=" +
this.category_id +
"&brand_id=" +
this.brand_id +
"&warehouse_id=" +
this.sale.warehouse_id +
"&stock=" + 1 +
"&product_service=" + 1
)
.then(response => {
this.products = response.data.products;
this.product_totalRows = response.data.totalRows;
this.Product_paginatePerPage();
// Complete the animation of theprogress bar.
NProgress.done();
})
.catch(response => {
// Complete the animation of theprogress bar.
NProgress.done();
});
},
//---------------------------------------Get Elements ------------------------------\\
GetElementsPos() {
let id = this.$route.params.id;
this.draft_sale_id = id;
axios
.get(`pos/data_draft_convert_sale/${id}`)
.then(response => {
this.clients = response.data.clients;
this.accounts = response.data.accounts;
this.warehouses = response.data.warehouses;
this.categories = response.data.categories;
this.brands = response.data.brands;
this.sale = response.data.sale;
this.details = response.data.details;
this.client_name = response.data.client_name;
this.GrandTotal = response.data.GrandTotal;
this.getProducts();
if (response.data.warehouse_id != "") {
this.Get_Products_By_Warehouse(response.data.warehouse_id);
}
this.paginate_Brands(this.brand_perPage, 0);
this.paginate_Category(this.category_perPage, 0);
this.stripe_key = response.data.stripe_key;
this.isLoading = false;
})
.catch(response => {
this.isLoading = false;
});
}
},
//-------------------- Created Function -----\\
created() {
this.GetElementsPos();
Fire.$on("pay_now", () => {
setTimeout(() => {
this.payment.amount = this.formatNumber(this.GrandTotal, 2);
this.payment.received_amount = this.formatNumber(this.GrandTotal, 2);
this.payment.Reglement = "Cash";
this.$bvModal.show("Add_Payment");
// Complete the animation of theprogress bar.
NProgress.done();
}, 500);
});
}
};
</script>
<style>
.total {
font-weight: bold;
font-size: 14px;
}
.bg-selected-card{
background-color: #dcdfe6;
}
.input-with-icon {
display: flex;
align-items: center;
}
.scan-icon {
width: 50px; /* Adjust size as needed */
height: 50px;
margin-right: 8px; /* Adjust spacing as needed */
cursor: pointer;
}
/* Media query*/
@media screen and (min-width: 1350px){
.pos-button-actions {
position: fixed;
}
}
</style>