#7524 warmfix-useVnTable #862

Merged
alexm merged 4 commits from 7524-warmfix-useVnTable into test 2024-10-24 09:45:55 +00:00
3 changed files with 253 additions and 414 deletions

View File

@ -457,7 +457,11 @@ function handleScroll() {
/> />
</template> </template>
<template #header-cell="{ col }"> <template #header-cell="{ col }">
<QTh v-if="col.visible ?? true"> <QTh
v-if="col.visible ?? true"
:style="col.headerStyle"
:class="col.headerClass"
>
<div <div
class="column self-start q-ml-xs ellipsis" class="column self-start q-ml-xs ellipsis"
:class="`text-${col?.align ?? 'left'}`" :class="`text-${col?.align ?? 'left'}`"

View File

@ -1,24 +1,20 @@
<script setup> <script setup>
import { onMounted, ref, computed, reactive } from 'vue'; import { ref, computed, reactive, watch } from 'vue';
import { useI18n } from 'vue-i18n'; import { useI18n } from 'vue-i18n';
import FetchData from 'components/FetchData.vue'; import FetchData from 'components/FetchData.vue';
import VnInput from 'src/components/common/VnInput.vue';
import VnSelect from 'src/components/common/VnSelect.vue';
import TicketDescriptorProxy from 'src/pages/Ticket/Card/TicketDescriptorProxy.vue'; import TicketDescriptorProxy from 'src/pages/Ticket/Card/TicketDescriptorProxy.vue';
import VnSubToolbar from 'src/components/ui/VnSubToolbar.vue'; import VnSubToolbar from 'src/components/ui/VnSubToolbar.vue';
import VnSearchbar from 'src/components/ui/VnSearchbar.vue'; import VnSearchbar from 'src/components/ui/VnSearchbar.vue';
import VnProgress from 'src/components/common/VnProgressModal.vue'; import VnProgress from 'src/components/common/VnProgressModal.vue';
import RightMenu from 'src/components/common/RightMenu.vue'; import RightMenu from 'src/components/common/RightMenu.vue';
import TicketAdvanceFilter from './TicketAdvanceFilter.vue'; import TicketAdvanceFilter from './TicketAdvanceFilter.vue';
import { dashIfEmpty, toCurrency } from 'src/filters'; import { dashIfEmpty, toCurrency } from 'src/filters';
import { useVnConfirm } from 'composables/useVnConfirm'; import { useVnConfirm } from 'composables/useVnConfirm';
import { useArrayData } from 'composables/useArrayData';
import useNotify from 'src/composables/useNotify.js'; import useNotify from 'src/composables/useNotify.js';
import { useState } from 'src/composables/useState'; import { useState } from 'src/composables/useState';
import { toDateFormat } from 'src/filters/date.js'; import { toDateFormat } from 'src/filters/date.js';
import axios from 'axios'; import axios from 'axios';
import VnTable from 'src/components/VnTable/VnTable.vue';
const state = useState(); const state = useState();
const { t } = useI18n(); const { t } = useI18n();
@ -29,109 +25,58 @@ const user = state.getUser();
const itemPackingTypesOptions = ref([]); const itemPackingTypesOptions = ref([]);
const zonesOptions = ref([]); const zonesOptions = ref([]);
const selectedTickets = ref([]); const selectedTickets = ref([]);
const vnTableRef = ref({});
const exprBuilder = (param, value) => { const originElRef = ref(null);
switch (param) { const destinationElRef = ref(null);
case 'id': let today = Date.vnNew().toISOString();
case 'futureId': const tomorrow = new Date(today);
case 'liters': tomorrow.setDate(tomorrow.getDate() + 1);
case 'futureLiters': const userParams = reactive({
case 'lines': dateFuture: tomorrow,
case 'futureLines': dateToAdvance: today,
case 'totalWithVat': warehouseFk: user.value.warehouseFk,
case 'futureTotalWithVat': ipt: 'H',
case 'futureZone': futureIpt: 'H',
case 'notMovableLines': isFullMovable: true,
case 'futureZoneFk':
return { [param]: value };
case 'iptColFilter':
return { ipt: { like: `%${value}%` } };
case 'futureIptColFilter':
return { futureIpt: { like: `%${value}%` } };
}
};
const userParams = reactive({});
const arrayData = useArrayData('AdvanceTickets', {
url: 'Tickets/getTicketsAdvance',
userParams: userParams,
exprBuilder: exprBuilder,
limit: 0,
}); });
const { store } = arrayData;
const tickets = computed(() =>
(store.data || []).map((ticket, index) => ({ ...ticket, index: index }))
);
const applyColumnFilter = async (col) => {
try {
const paramKey = col.columnFilter?.filterParamKey || col.field;
userParams[paramKey] = col.columnFilter.filterValue;
await arrayData.addFilter({ params: userParams });
} catch (err) {
console.error('Error applying column filter', err);
}
};
const getInputEvents = (col) => {
return col.columnFilter.type === 'select'
? { 'update:modelValue': () => applyColumnFilter(col) }
: {
'keyup.enter': () => applyColumnFilter(col),
};
};
const ticketColumns = computed(() => [ const ticketColumns = computed(() => [
{ {
label: '', label: '',
name: 'icons', name: 'icons',
align: 'left', hidden: true,
columnFilter: null, headerClass: 'horizontal-separator',
}, },
{ {
label: t('advanceTickets.ticketId'),
name: 'ticketId',
align: 'center', align: 'center',
sortable: true, label: t('advanceTickets.ticketId'),
columnFilter: { name: 'id',
component: VnInput, headerClass: 'horizontal-separator',
type: 'text',
filterValue: null,
filterParamKey: 'id',
event: getInputEvents,
attrs: {
dense: true,
},
},
}, },
{ {
align: 'left',
label: t('advanceTickets.ipt'), label: t('advanceTickets.ipt'),
name: 'ipt', name: 'ipt',
field: 'ipt',
align: 'left',
sortable: true,
columnFilter: { columnFilter: {
component: VnSelect, component: 'select',
filterParamKey: 'iptColFilter',
type: 'select',
filterValue: null,
event: getInputEvents,
attrs: { attrs: {
options: itemPackingTypesOptions.value, url: 'itemPackingTypes',
'option-value': 'code', fields: ['code', 'description'],
'option-label': 'description', where: { isActive: true },
dense: true, optionValue: 'code',
optionLabel: 'description',
inWhere: false,
}, },
}, },
format: (val) => dashIfEmpty(val), format: (row, dashIfEmpty) => dashIfEmpty(row.ipt),
headerClass: 'horizontal-separator',
}, },
{ {
align: 'left',
label: t('advanceTickets.state'), label: t('advanceTickets.state'),
name: 'state', name: 'state',
align: 'left', headerClass: 'horizontal-separator',
sortable: true, hidden: true,
columnFilter: null,
}, },
{ {
label: t('advanceTickets.preparation'), label: t('advanceTickets.preparation'),
@ -139,171 +84,105 @@ const ticketColumns = computed(() => [
field: 'preparation', field: 'preparation',
align: 'left', align: 'left',
sortable: true, sortable: true,
columnFilter: null, headerClass: 'horizontal-separator',
columnFilter: false,
}, },
{ {
label: t('advanceTickets.liters'),
name: 'liters',
field: 'liters',
align: 'left', align: 'left',
sortable: true, label: t('advanceTickets.liters'),
columnFilter: { headerClass: 'horizontal-separator',
component: VnInput, name: 'liters',
type: 'text',
filterValue: null,
event: getInputEvents,
attrs: {
dense: true,
},
},
}, },
{ {
align: 'left',
label: t('advanceTickets.lines'), label: t('advanceTickets.lines'),
name: 'lines', name: 'lines',
field: 'lines', headerClass: 'horizontal-separator',
align: 'left', format: (row, dashIfEmpty) => dashIfEmpty(row.lines),
sortable: true,
columnFilter: {
component: VnInput,
type: 'text',
filterValue: null,
event: getInputEvents,
attrs: {
dense: true,
},
},
format: (val) => dashIfEmpty(val),
}, },
{ {
align: 'left',
label: t('advanceTickets.import'), label: t('advanceTickets.import'),
field: 'import', name: 'totalWithVat',
name: 'import', hidden: true,
align: 'left', headerClass: 'horizontal-separator',
sortable: true, format: (row) => toCurrency(row.totalWithVat),
}, },
{ {
align: 'left',
label: t('advanceTickets.futureId'), label: t('advanceTickets.futureId'),
name: 'futureId', name: 'futureId',
align: 'left', headerClass: 'vertical-separator horizontal-separator',
sortable: true, columnClass: 'vertical-separator',
columnFilter: {
component: VnInput,
type: 'text',
filterValue: null,
filterParamKey: 'futureId',
event: getInputEvents,
attrs: {
dense: true,
},
},
}, },
{ {
align: 'left',
label: t('advanceTickets.futureIpt'), label: t('advanceTickets.futureIpt'),
name: 'futureIpt', name: 'futureIpt',
field: 'futureIpt',
align: 'left',
sortable: true,
columnFilter: { columnFilter: {
component: VnSelect, component: 'select',
filterParamKey: 'futureIptColFilter',
type: 'select',
filterValue: null,
event: getInputEvents,
attrs: { attrs: {
options: itemPackingTypesOptions.value, url: 'itemPackingTypes',
'option-value': 'code', fields: ['code', 'description'],
'option-label': 'description', where: { isActive: true },
dense: true, optionValue: 'code',
optionLabel: 'description',
}, },
}, },
format: (val) => dashIfEmpty(val), headerClass: 'horizontal-separator',
format: (row, dashIfEmpty) => dashIfEmpty(row.futureIpt),
}, },
{ {
align: 'left',
label: t('advanceTickets.futureState'), label: t('advanceTickets.futureState'),
name: 'futureState', name: 'futureState',
align: 'left', headerClass: 'horizontal-separator',
sortable: true, hidden: true,
columnFilter: null,
format: (val) => dashIfEmpty(val),
}, },
{ {
align: 'left',
label: t('advanceTickets.futureLiters'), label: t('advanceTickets.futureLiters'),
headerClass: 'horizontal-separator',
name: 'futureLiters', name: 'futureLiters',
field: 'futureLiters',
align: 'left',
sortable: true,
columnFilter: {
component: VnInput,
type: 'text',
filterValue: null,
event: getInputEvents,
attrs: {
dense: true,
},
},
format: (val) => dashIfEmpty(val),
}, },
{ {
align: 'left',
label: t('advanceTickets.futureZone'), label: t('advanceTickets.futureZone'),
name: 'futureZoneName', name: 'futureZoneFk',
field: 'futureZoneName', columnClass: 'expand',
align: 'left',
sortable: true,
columnFilter: { columnFilter: {
component: VnSelect, component: 'select',
type: 'select', inWhere: true,
filterValue: null,
filterParamKey: 'futureZoneFk',
event: getInputEvents,
attrs: { attrs: {
options: zonesOptions.value, url: 'Zones',
'option-value': 'id', fields: ['id', 'name'],
'option-label': 'name',
dense: true,
}, },
}, },
format: (val) => dashIfEmpty(val), columnField: {
component: null,
},
headerClass: 'horizontal-separator',
format: (row, dashIfEmpty) => dashIfEmpty(row.futureZoneName),
}, },
{ {
align: 'left',
label: t('advanceTickets.notMovableLines'), label: t('advanceTickets.notMovableLines'),
headerClass: 'horizontal-separator',
name: 'notMovableLines', name: 'notMovableLines',
field: 'notMovableLines',
align: 'left',
sortable: true,
columnFilter: {
component: VnInput,
type: 'text',
filterValue: null,
event: getInputEvents,
attrs: {
dense: true,
},
},
format: (val) => dashIfEmpty(val),
}, },
{ {
align: 'left',
label: t('advanceTickets.futureLines'), label: t('advanceTickets.futureLines'),
headerClass: 'horizontal-separator',
name: 'futureLines', name: 'futureLines',
field: 'futureLines',
align: 'left',
sortable: true,
columnFilter: {
component: VnInput,
type: 'text',
filterValue: null,
event: getInputEvents,
attrs: {
dense: true,
},
},
format: (val) => dashIfEmpty(val),
}, },
{ {
label: t('advanceTickets.futureImport'),
name: 'futureImport',
align: 'left', align: 'left',
sortable: true, label: t('advanceTickets.futureImport'),
columnFilter: null, name: 'futureTotalWithVat',
hidden: true,
headerClass: 'horizontal-separator',
format: (row) => toCurrency(row.futureTotalWithVat),
}, },
]); ]);
@ -329,7 +208,7 @@ const requestComponentUpdate = async (ticket, isWithoutNegatives) => {
const query = `tickets/${ticket.futureId}/componentUpdate`; const query = `tickets/${ticket.futureId}/componentUpdate`;
if (!ticket.landed) { if (!ticket.landed) {
const newLanded = await getLanded({ const newLanded = await getLanded({
shipped: userParams.dateToAdvance, shipped: vnTableRef.value.params.dateToAdvance,
addressFk: ticket.futureAddressFk, addressFk: ticket.futureAddressFk,
agencyModeFk: ticket.agencyModeFk ?? ticket.futureAgencyModeFk, agencyModeFk: ticket.agencyModeFk ?? ticket.futureAgencyModeFk,
warehouseFk: ticket.futureWarehouseFk, warehouseFk: ticket.futureWarehouseFk,
@ -352,7 +231,7 @@ const requestComponentUpdate = async (ticket, isWithoutNegatives) => {
zoneFk: ticket.zoneFk ?? ticket.futureZoneFk, zoneFk: ticket.zoneFk ?? ticket.futureZoneFk,
warehouseFk: ticket.futureWarehouseFk, warehouseFk: ticket.futureWarehouseFk,
companyFk: ticket.futureCompanyFk, companyFk: ticket.futureCompanyFk,
shipped: userParams.dateToAdvance, shipped: vnTableRef.value.params.dateToAdvance,
alexm marked this conversation as resolved
Review

quitar

quitar
landed: ticket.landed, landed: ticket.landed,
isDeleted: false, isDeleted: false,
isWithoutNegatives, isWithoutNegatives,
@ -364,36 +243,31 @@ const requestComponentUpdate = async (ticket, isWithoutNegatives) => {
}; };
const moveTicketsAdvance = async () => { const moveTicketsAdvance = async () => {
try { let ticketsToMove = [];
let ticketsToMove = []; for (const ticket of selectedTickets.value) {
for (const ticket of selectedTickets.value) { if (!ticket.id) {
if (!ticket.id) { try {
try { const { query, params } = await requestComponentUpdate(ticket, false);
const { query, params } = await requestComponentUpdate(ticket, false); axios.post(query, params);
axios.post(query, params); } catch (e) {
} catch (e) { console.error('Error moving ticket', e);
console.error('Error moving ticket', e);
}
continue;
} }
ticketsToMove.push({ continue;
originId: ticket.futureId,
destinationId: ticket.id,
originShipped: ticket.futureShipped,
destinationShipped: ticket.shipped,
workerFk: ticket.workerFk,
});
} }
ticketsToMove.push({
const params = { tickets: ticketsToMove }; originId: ticket.futureId,
await axios.post('Tickets/merge', params); destinationId: ticket.id,
arrayData.fetch({ append: false }); originShipped: ticket.futureShipped,
selectedTickets.value = []; destinationShipped: ticket.shipped,
if (ticketsToMove.length) workerFk: ticket.workerFk,
notify(t('advanceTickets.moveTicketSuccess'), 'positive'); });
} catch (error) {
console.error('Error moving tickets', error);
} }
const params = { tickets: ticketsToMove };
await axios.post('Tickets/merge', params);
vnTableRef.value.reload();
selectedTickets.value = [];
if (ticketsToMove.length) notify(t('advanceTickets.moveTicketSuccess'), 'positive');
}; };
const progressLength = ref(0); const progressLength = ref(0);
@ -434,10 +308,8 @@ const splitTickets = async () => {
progressAdd(ticket.futureId); progressAdd(ticket.futureId);
} }
} }
} catch (error) {
console.error('Error splitting tickets', error);
} finally { } finally {
arrayData.fetch({ append: false }); vnTableRef.value.reload();
} }
}; };
@ -455,22 +327,52 @@ const handleCloseProgressDialog = () => {
const handleCancelProgress = () => (cancelProgress.value = true); const handleCancelProgress = () => (cancelProgress.value = true);
onMounted(async () => { watch(
let today = Date.vnNew(); () => vnTableRef.value.tableRef?.$el,
const tomorrow = new Date(today); ($el) => {
tomorrow.setDate(tomorrow.getDate() + 1); if (!$el) return;
userParams.dateFuture = tomorrow; const head = $el.querySelector('thead');
userParams.dateToAdvance = today; const firstRow = $el.querySelector('thead > tr');
userParams.scopeDays = 1;
userParams.warehouseFk = user.value.warehouseFk;
userParams.ipt = 'H';
userParams.futureIpt = 'H';
userParams.isFullMovable = true;
const filter = { limit: 0 };
await arrayData.addFilter({ filter, userParams });
});
</script>
const newRow = document.createElement('tr');
destinationElRef.value = document.createElement('th');
originElRef.value = document.createElement('th');
newRow.classList.add('bg-header');
destinationElRef.value.classList.add('text-uppercase', 'color-vn-label');
originElRef.value.classList.add('text-uppercase', 'color-vn-label');
destinationElRef.value.setAttribute('colspan', '7');
originElRef.value.setAttribute('colspan', '9');
destinationElRef.value.textContent = `${t(
'advanceTickets.destination'
)} ${toDateFormat(vnTableRef.value.params.dateToAdvance)}`;
originElRef.value.textContent = `${t('advanceTickets.origin')} ${toDateFormat(
vnTableRef.value.params.dateFuture
)}`;
newRow.append(destinationElRef.value, originElRef.value);
head.insertBefore(newRow, firstRow);
},
{ once: true, inmmediate: true }
);
watch(
() => vnTableRef.value.params,
() => {
if (originElRef.value && destinationElRef.value) {
destinationElRef.value.textContent = `${t(
'advanceTickets.destination'
)} ${toDateFormat(vnTableRef.value.params.dateToAdvance)}`;
originElRef.value.textContent = `${t('advanceTickets.origin')} ${toDateFormat(
vnTableRef.value.params.dateFuture
)}`;
}
},
{ deep: true }
);
</script>
<template> <template>
<FetchData <FetchData
url="itemPackingTypes" url="itemPackingTypes"
@ -491,11 +393,6 @@ onMounted(async () => {
auto-load auto-load
@on-fetch="(data) => (zonesOptions = data)" @on-fetch="(data) => (zonesOptions = data)"
/> />
<VnSearchbar
data-key="WeeklyTickets"
:label="t('weeklyTickets.search')"
:info="t('weeklyTickets.searchInfo')"
/>
<VnSubToolbar> <VnSubToolbar>
<template #st-data> <template #st-data>
<QBtn <QBtn
@ -539,174 +436,109 @@ onMounted(async () => {
</VnSubToolbar> </VnSubToolbar>
<RightMenu> <RightMenu>
<template #right-panel> <template #right-panel>
<TicketAdvanceFilter data-key="AdvanceTickets" /> <TicketAdvanceFilter data-key="advanceTickets" />
</template> </template>
</RightMenu> </RightMenu>
<QPage class="column items-center q-pa-md"> <QPage class="column items-center q-pa-md">
<QTable <VnTable
:rows="tickets" data-key="advanceTickets"
ref="vnTableRef"
url="Tickets/getTicketsAdvance"
search-url="advanceTickets"
:user-params="userParams"
:limit="0"
:columns="ticketColumns" :columns="ticketColumns"
row-key="index" :table="{
selection="multiple" 'row-key': '$index',
selection: 'multiple',
}"
v-model:selected="selectedTickets" v-model:selected="selectedTickets"
:pagination="{ rowsPerPage: 0 }" :pagination="{ rowsPerPage: 0 }"
:no-data-label="t('globals.noResults')" :no-data-label="t('globals.noResults')"
style="max-width: 99%" :right-search="false"
auto-load
:disable-option="{ card: true }"
> >
<template #header="props"> <template #column-icons="{ row }">
{{ userParams.scopeDays }} <QIcon
<QTr :props="props"> v-if="row.futureAgency !== row.agency && row.agency"
<QTh color="primary"
class="horizontal-separator text-uppercase color-vn-label" name="vn:agency-term"
colspan="7" size="xs"
translate >
> <QTooltip class="column">
{{ t('advanceTickets.destination') }} <span>
{{ toDateFormat(userParams.dateToAdvance) }} {{
</QTh> t('advanceTickets.originAgency', {
<QTh agency: row.futureAgency,
class="horizontal-separator text-uppercase color-vn-label" })
colspan="9" }}
translate </span>
> <span>
{{ t('advanceTickets.origin') }} {{
{{ toDateFormat(userParams.dateFuture) }} t('advanceTickets.destinationAgency', {
</QTh> agency: row.agency,
</QTr> })
<QTr> }}
<QTh> </span>
<QCheckbox v-model="props.selected" /> </QTooltip>
</QTh> </QIcon>
<QTh
v-for="(col, index) in ticketColumns"
:key="index"
:class="{ 'vertical-separator': col.name === 'futureId' }"
>
{{ col.label }}
</QTh>
</QTr>
</template> </template>
<template #top-row="{ cols }"> <template #column-id="{ row }">
<QTr> <QBtn flat class="link">
<QTd /> {{ row.id }}
<QTd <TicketDescriptorProxy :id="row.id" />
v-for="(col, index) in cols" </QBtn>
:key="index"
style="max-width: 100px"
>
<component
:is="col.columnFilter.component"
v-if="col.columnFilter"
v-model="col.columnFilter.filterValue"
v-bind="col.columnFilter.attrs"
v-on="col.columnFilter.event(col)"
dense
/>
</QTd>
</QTr>
</template> </template>
<template #header-cell-availableLines="{ col }"> <template #column-state="{ row }">
<QTh class="vertical-separator"> <QBadge
{{ col.label }} v-if="row.state"
</QTh> text-color="black"
:color="row.classColor"
class="q-ma-none"
dense
>
{{ row.state }}
</QBadge>
<span v-else> {{ dashIfEmpty(row.state) }}</span>
</template> </template>
<template #body-cell-icons="{ row }"> <template #column-import="{ row }">
<QTd class="q-gutter-x-xs"> <QBadge
<QIcon :text-color="isLessThan50(row.totalWithVat) ? 'black' : 'white'"
v-if="row.futureAgency !== row.agency && row.agency" :color="totalPriceColor(row.totalWithVat)"
color="primary" class="q-ma-none"
name="vn:agency-term" dense
size="xs" >
> {{ toCurrency(row.totalWithVat || 0) }}
<QTooltip class="column"> </QBadge>
<span>
{{
t('advanceTickets.originAgency', {
agency: row.futureAgency,
})
}}
</span>
<span>
{{
t('advanceTickets.destinationAgency', {
agency: row.agency,
})
}}
</span>
</QTooltip>
</QIcon>
</QTd>
</template> </template>
<template #column-futureId="{ row }">
<template #body-cell-ticketId="{ row }"> <QBtn flat class="link" dense>
<QTd> {{ row.futureId }}
<QBtn flat class="link"> <TicketDescriptorProxy :id="row.futureId" />
{{ row.id }} </QBtn>
<TicketDescriptorProxy :id="row.id" />
</QBtn>
</QTd>
</template> </template>
<template #body-cell-state="{ row }"> <template #column-futureState="{ row }">
<QTd> <QBadge
<QBadge text-color="black"
v-if="row.state" :color="row.futureClassColor"
text-color="black" class="q-ma-none"
:color="row.classColor" dense
class="q-ma-none" >
dense {{ row.futureState }}
> </QBadge>
{{ row.state }}
</QBadge>
<span v-else> {{ dashIfEmpty(row.state) }}</span>
</QTd>
</template> </template>
<template #body-cell-import="{ row }"> <template #column-futureImport="{ row }">
<QTd> <QBadge
<QBadge :text-color="isLessThan50(row.futureTotalWithVat) ? 'black' : 'white'"
:text-color="isLessThan50(row.totalWithVat) ? 'black' : 'white'" :color="totalPriceColor(row.futureTotalWithVat)"
:color="totalPriceColor(row.totalWithVat)" class="q-ma-none"
class="q-ma-none" dense
dense >
> {{ toCurrency(row.futureTotalWithVat || 0) }}
{{ toCurrency(row.totalWithVat || 0) }} </QBadge>
</QBadge>
</QTd>
</template> </template>
<template #body-cell-futureId="{ row }"> </VnTable>
<QTd class="vertical-separator">
<QBtn flat class="link" dense>
{{ row.futureId }}
<TicketDescriptorProxy :id="row.futureId" />
</QBtn>
</QTd>
</template>
<template #body-cell-futureState="{ row }">
<QTd>
<QBadge
text-color="black"
:color="row.futureClassColor"
class="q-ma-none"
dense
>
{{ row.futureState }}
</QBadge>
</QTd>
</template>
<template #body-cell-futureImport="{ row }">
<QTd>
<QBadge
:text-color="
isLessThan50(row.futureTotalWithVat) ? 'black' : 'white'
"
:color="totalPriceColor(row.futureTotalWithVat)"
class="q-ma-none"
dense
>
{{ toCurrency(row.futureTotalWithVat || 0) }}
</QBadge>
</QTd>
</template>
</QTable>
<VnProgress <VnProgress
:progress="progressPercentage" :progress="progressPercentage"
:cancelled="cancelProgress" :cancelled="cancelProgress"
@ -725,11 +557,11 @@ onMounted(async () => {
</template> </template>
<style scoped lang="scss"> <style scoped lang="scss">
.vertical-separator { :deep(.vertical-separator) {
border-left: 4px solid white !important; border-left: 4px solid white !important;
} }
.horizontal-separator { :deep(.horizontal-separator) {
border-bottom: 4px solid white !important; border-top: 4px solid white !important;
} }
</style> </style>

View File

@ -58,6 +58,7 @@ onMounted(async () => await getItemPackingTypes());
auto-load auto-load
/> />
<VnFilterPanel <VnFilterPanel
search-url="advanceTickets"
:data-key="props.dataKey" :data-key="props.dataKey"
:search-button="true" :search-button="true"
:hidden-tags="['search']" :hidden-tags="['search']"
@ -101,6 +102,7 @@ onMounted(async () => await getItemPackingTypes());
dense dense
outlined outlined
rounded rounded
:use-like="false"
> >
</VnSelect> </VnSelect>
</QItemSection> </QItemSection>
@ -118,6 +120,7 @@ onMounted(async () => await getItemPackingTypes());
dense dense
outlined outlined
rounded rounded
:use-like="false"
> >
</VnSelect> </VnSelect>
</QItemSection> </QItemSection>