Merge branch 'master' into Hotfix-TicketFilter
gitea/salix-front/pipeline/pr-master This commit looks good Details

This commit is contained in:
Jon Elias 2024-12-11 12:39:06 +00:00
commit 2262ef9594
11 changed files with 119 additions and 118 deletions

View File

@ -162,7 +162,9 @@ onMounted(() => {
: $props.defaultMode; : $props.defaultMode;
stateStore.rightDrawer = quasar.screen.gt.xs; stateStore.rightDrawer = quasar.screen.gt.xs;
columnsVisibilitySkipped.value = [ columnsVisibilitySkipped.value = [
...splittedColumns.value.columns.filter((c) => !c.visible).map((c) => c.name), ...splittedColumns.value.columns
.filter((c) => c.visible === false)
.map((c) => c.name),
...['tableActions'], ...['tableActions'],
]; ];
createForm.value = $props.create; createForm.value = $props.create;

View File

@ -152,7 +152,7 @@ onMounted(async () => {
<QCheckbox <QCheckbox
v-for="col in localColumns" v-for="col in localColumns"
:key="col.name" :key="col.name"
:label="col.label" :label="col.label ?? col.name"
v-model="col.visible" v-model="col.visible"
/> />
</div> </div>

View File

@ -264,6 +264,10 @@ input::-webkit-inner-spin-button {
.shrink { .shrink {
max-width: 75px; max-width: 75px;
} }
.number {
text-align: right;
width: 96px;
}
.expand { .expand {
max-width: 400px; max-width: 400px;
} }

View File

@ -78,29 +78,32 @@ async function setItemTypeData(data) {
{{ t('globals.summary.basicData') }} {{ t('globals.summary.basicData') }}
<QIcon name="open_in_new" /> <QIcon name="open_in_new" />
</router-link> </router-link>
<VnLv :label="t('summary.id')" :value="itemType.id" /> <VnLv :label="t('itemType.summary.id')" :value="itemType.id" />
<VnLv :label="t('shared.code')" :value="itemType.code" /> <VnLv :label="t('itemType.shared.code')" :value="itemType.code" />
<VnLv :label="t('shared.name')" :value="itemType.name" /> <VnLv :label="t('itemType.shared.name')" :value="itemType.name" />
<VnLv :label="t('shared.worker')"> <VnLv :label="t('itemType.shared.worker')">
<template #value> <template #value>
<span class="link">{{ itemType.worker?.firstName }}</span> <span class="link">{{ itemType.worker?.firstName }}</span>
<WorkerDescriptorProxy :id="itemType.worker?.id" /> <WorkerDescriptorProxy :id="itemType.worker?.id" />
</template> </template>
</VnLv> </VnLv>
<VnLv :label="t('shared.category')" :value="itemType.category?.name" />
<VnLv <VnLv
:label="t('shared.temperature')" :label="t('itemType.shared.category')"
:value="itemType.category?.name"
/>
<VnLv
:label="t('itemType.shared.temperature')"
:value="itemType.temperature?.name" :value="itemType.temperature?.name"
/> />
<VnLv :label="t('summary.life')" :value="itemType.life" /> <VnLv :label="t('itemType.summary.life')" :value="itemType.life" />
<VnLv :label="t('summary.promo')" :value="itemType.promo" /> <VnLv :label="t('itemType.summary.promo')" :value="itemType.promo" />
<VnLv <VnLv
:label="t('summary.itemPackingType')" :label="t('itemType.summary.itemPackingType')"
:value="itemType.itemPackingType?.description" :value="itemType.itemPackingType?.description"
/> />
<VnLv <VnLv
class="large-label" class="large-label"
:label="t('summary.isUnconventionalSize')" :label="t('itemType.summary.isUnconventionalSize')"
:value="itemType.isUnconventionalSize" :value="itemType.isUnconventionalSize"
/> />
</QCard> </QCard>

View File

@ -1,16 +1,17 @@
shared: itemType:
code: Code shared:
name: Name code: Code
worker: Worker name: Name
category: Category worker: Worker
temperature: Temperature category: Category
life: Life temperature: Temperature
itemPackingType: Item packing type life: Life
maxRefs: Maximum references itemPackingType: Item packing type
fragile: Fragile maxRefs: Maximum references
summary: fragile: Fragile
id: id summary:
life: Life id: id
promo: Promo life: Life
itemPackingType: Item packing type promo: Promo
isUnconventionalSize: Is unconventional size itemPackingType: Item packing type
isUnconventionalSize: Is unconventional size

View File

@ -1,16 +1,17 @@
shared: itemType:
code: Código shared:
name: Nombre code: Código
worker: Trabajador name: Nombre
category: Reino worker: Trabajador
temperature: Temperatura category: Reino
life: Vida temperature: Temperatura
itemPackingType: Tipo de embalaje life: Vida
maxRefs: Referencias máximas itemPackingType: Tipo de embalaje
fragile: Frágil maxRefs: Referencias máximas
summary: fragile: Frágil
id: id summary:
life: Vida id: id
promo: Promoción life: Vida
itemPackingType: Tipo de embalaje promo: Promoción
isUnconventionalSize: Es de tamaño poco convencional itemPackingType: Tipo de embalaje
isUnconventionalSize: Es de tamaño poco convencional

View File

@ -1,5 +1,5 @@
<script setup> <script setup>
import { ref, computed, onMounted, onUnmounted, watch } from 'vue'; import { ref, computed, onMounted, onUnmounted, nextTick } from 'vue';
import { useI18n } from 'vue-i18n'; import { useI18n } from 'vue-i18n';
import ItemDescriptorProxy from 'src/pages/Item/Card/ItemDescriptorProxy.vue'; import ItemDescriptorProxy from 'src/pages/Item/Card/ItemDescriptorProxy.vue';
@ -10,37 +10,15 @@ import { useStateStore } from 'stores/useStateStore';
import { toCurrency } from 'filters/index'; import { toCurrency } from 'filters/index';
import { useRole } from 'src/composables/useRole'; import { useRole } from 'src/composables/useRole';
const $props = defineProps({ const haveNegatives = defineModel('haveNegatives', { type: Boolean, required: true });
formData: { const formData = defineModel({ type: Object, required: true });
type: Object,
required: true,
},
haveNegatives: {
type: Boolean,
required: true,
default: false,
},
});
const emit = defineEmits(['updateForm', 'update:haveNegatives']);
const stateStore = useStateStore(); const stateStore = useStateStore();
const { t } = useI18n(); const { t } = useI18n();
const { hasAny } = useRole(); const { hasAny } = useRole();
const _ticketData = ref($props.formData);
const ticketUpdateActions = ref(null); const ticketUpdateActions = ref(null);
const haveNegatives = computed({ const rows = computed(() => formData.value?.sale?.items || []);
get: () => $props.haveNegatives,
set: (val) => emit('update:haveNegatives', val),
});
const rows = computed(() => _ticketData.value?.sale?.items || []);
watch(
() => _ticketData.value,
(val) => emit('updateForm', val),
{ deep: true }
);
const columns = computed(() => [ const columns = computed(() => [
{ {
@ -57,24 +35,28 @@ const columns = computed(() => [
align: 'left', align: 'left',
hidden: true, hidden: true,
}, },
{
name: 'subName',
align: 'left',
required: true,
},
{ {
label: t('basicData.movable'), label: t('basicData.movable'),
name: 'movable', name: 'movable',
align: 'left',
}, },
{ {
required: true, required: true,
label: t('basicData.quantity'), label: t('basicData.quantity'),
name: 'quantity', name: 'quantity',
field: 'quantity', field: 'quantity',
align: 'left', classes: 'number',
}, },
{ {
required: true, required: true,
label: t('basicData.pricePPU'), label: t('basicData.pricePPU'),
name: 'price', name: 'price',
field: 'price', field: 'price',
align: 'left', classes: 'number',
format: (val) => toCurrency(val), format: (val) => toCurrency(val),
}, },
{ {
@ -82,7 +64,7 @@ const columns = computed(() => [
label: t('basicData.newPricePPU'), label: t('basicData.newPricePPU'),
name: 'newPrice', name: 'newPrice',
field: (row) => row.component.newPrice, field: (row) => row.component.newPrice,
align: 'left', classes: 'number',
format: (val) => toCurrency(val), format: (val) => toCurrency(val),
}, },
{ {
@ -90,14 +72,15 @@ const columns = computed(() => [
label: t('basicData.difference'), label: t('basicData.difference'),
name: 'difference', name: 'difference',
field: (row) => row.component.difference, field: (row) => row.component.difference,
align: 'left', classes: 'number',
format: (val) => toCurrency(val), format: (val) => toCurrency(val),
autoWidth: true,
}, },
]); ]);
const loadDefaultTicketAction = () => { const loadDefaultTicketAction = () => {
const isSalesAssistant = hasAny(['salesAssistant']); const isSalesAssistant = hasAny(['salesAssistant']);
_ticketData.value.option = isSalesAssistant ? 'mana' : 'renewPrices'; formData.value.option = isSalesAssistant ? 'mana' : 'renewPrices';
}; };
const totalPrice = computed(() => { const totalPrice = computed(() => {
@ -115,24 +98,25 @@ const totalDifference = computed(() => {
return rows.value.reduce((acc, item) => acc + item.component?.difference || 0, 0); return rows.value.reduce((acc, item) => acc + item.component?.difference || 0, 0);
}); });
const showMovableColumn = computed(() => (haveDifferences.value > 0 ? ['movable'] : [])); const showMovableColumn = computed(() => (haveDifferences.value > 0 ? ['movable'] : []));
const haveDifferences = computed(() => _ticketData.value.sale?.haveDifferences); const haveDifferences = computed(() => formData.value.sale?.haveDifferences);
const ticketHaveNegatives = () => { async function ticketHaveNegatives() {
let _haveNegatives = false; let _haveNegatives = false;
let haveNotNegatives = false; let haveNotNegatives = false;
_ticketData.value.withoutNegatives = false; formData.value.withoutNegatives = false;
_ticketData.value?.sale?.items.forEach((item) => { formData.value?.sale?.items.forEach((item) => {
if (item.quantity > item.movable) _haveNegatives = true; if (item.quantity > item.movable) _haveNegatives = true;
else haveNotNegatives = true; else haveNotNegatives = true;
}); });
haveNegatives.value = _haveNegatives && haveNotNegatives && haveDifferences.value; haveNegatives.value = _haveNegatives && haveNotNegatives && haveDifferences.value;
if (haveNegatives.value) _ticketData.value.withoutNegatives = true; await nextTick();
}; if (haveNegatives.value) formData.value.withoutNegatives = true;
}
onMounted(() => { onMounted(async () => {
stateStore.rightDrawer = true; stateStore.rightDrawer = true;
loadDefaultTicketAction(); loadDefaultTicketAction();
ticketHaveNegatives(); await ticketHaveNegatives();
}); });
onUnmounted(() => (stateStore.rightDrawer = false)); onUnmounted(() => (stateStore.rightDrawer = false));
@ -191,7 +175,7 @@ onUnmounted(() => (stateStore.rightDrawer = false));
horizontal horizontal
> >
<QRadio <QRadio
v-model="_ticketData.option" v-model="formData.option"
:val="action.code" :val="action.code"
:label="action.description" :label="action.description"
dense dense
@ -208,7 +192,7 @@ onUnmounted(() => (stateStore.rightDrawer = false));
<QCardSection horizontal class="flex row items-center"> <QCardSection horizontal class="flex row items-center">
<QCheckbox <QCheckbox
:label="t('basicData.withoutNegatives')" :label="t('basicData.withoutNegatives')"
v-model="_ticketData.withoutNegatives" v-model="formData.withoutNegatives"
:toggle-indeterminate="false" :toggle-indeterminate="false"
/> />
<QIcon name="info" size="xs" class="q-ml-sm"> <QIcon name="info" size="xs" class="q-ml-sm">
@ -225,7 +209,7 @@ onUnmounted(() => (stateStore.rightDrawer = false));
:columns="columns" :columns="columns"
row-key="id" row-key="id"
:pagination="{ rowsPerPage: 0 }" :pagination="{ rowsPerPage: 0 }"
class="full-width q-mt-md" class="full-width"
:no-data-label="t('globals.noResults')" :no-data-label="t('globals.noResults')"
flat flat
> >
@ -238,21 +222,27 @@ onUnmounted(() => (stateStore.rightDrawer = false));
</QTd> </QTd>
</template> </template>
<template #body-cell-description="{ row }"> <template #body-cell-description="{ row }">
<QTd style="display: contents"> <QTd style="min-width: 120px; max-width: 120px">
<div class="column"> <div class="column q-pb-xs" style="min-width: 120px">
<span>{{ row.item.name }}</span> <span>{{ row.item.name }}</span>
<span class="color-vn-label">{{ row.item.subName }}</span> <FetchedTags :item="row.item" class="full-width" />
<FetchedTags :item="row.item" />
</div> </div>
</QTd> </QTd>
</template> </template>
<template #body-cell-movable="{ row }"> <template #body-cell-subName="{ row }">
<QTd> <QTd>
<QBadge <span class="color-vn-label">{{ row.item.subName }}</span>
v-if="_ticketData?.sale?.haveDifferences" </QTd>
</template>
<template #body-cell-movable="{ row }">
<QTd class="number">
<QChip
v-if="formData?.sale?.haveDifferences"
:text-color="row.quantity > row.movable ? 'black' : 'white'" :text-color="row.quantity > row.movable ? 'black' : 'white'"
:color="row.quantity > row.movable ? 'negative' : 'transparent'" :color="row.quantity > row.movable ? 'negative' : 'transparent'"
:label="row.movable" :label="row.movable"
dense
square
/> />
</QTd> </QTd>
</template> </template>

View File

@ -21,7 +21,6 @@ const formData = defineModel({
required: true, required: true,
}); });
const emit = defineEmits(['updateForm']);
const { validate } = useValidator(); const { validate } = useValidator();
const { notify } = useNotify(); const { notify } = useNotify();
const router = useRouter(); const router = useRouter();
@ -33,18 +32,11 @@ const canEditZone = useAcl().hasAny([
const agencyFetchRef = ref(); const agencyFetchRef = ref();
const warehousesOptions = ref([]); const warehousesOptions = ref([]);
const companiesOptions = ref([]); const companiesOptions = ref([]);
const currenciesOptions = ref([]);
const agenciesOptions = ref([]); const agenciesOptions = ref([]);
const zonesOptions = ref([]); const zonesOptions = ref([]);
const addresses = ref([]); const addresses = ref([]);
const zoneSelectRef = ref(); const zoneSelectRef = ref();
watch(
() => formData.value,
(val) => emit('updateForm', val),
{ deep: true }
);
onMounted(() => onFormModelInit()); onMounted(() => onFormModelInit());
const agencyByWarehouseFilter = computed(() => ({ const agencyByWarehouseFilter = computed(() => ({

View File

@ -155,18 +155,10 @@ onBeforeMount(async () => await getTicketData());
}" }"
> >
<QStep :name="1" :title="t('globals.pageTitles.basicData')" :done="step > 1"> <QStep :name="1" :title="t('globals.pageTitles.basicData')" :done="step > 1">
<TicketBasicDataForm <TicketBasicDataForm v-if="initialDataLoaded" v-model="formData" />
v-if="initialDataLoaded"
@update-form="($event) => (formData = $event)"
v-model="formData"
/>
</QStep> </QStep>
<QStep :name="2" :title="t('basicData.priceDifference')"> <QStep :name="2" :title="t('basicData.priceDifference')">
<TicketBasicData <TicketBasicData v-model="formData" v-model:have-negatives="haveNegatives" />
:form-data="formData"
v-model:haveNegatives="haveNegatives"
@update-form="($event) => (formData = $event)"
/>
</QStep> </QStep>
<template #navigation> <template #navigation>
<QStepperNavigation class="flex justify-between"> <QStepperNavigation class="flex justify-between">

View File

@ -52,6 +52,7 @@ onUnmounted(() => (stateStore.rightDrawer = false));
:last-day="lastDay" :last-day="lastDay"
:events="events" :events="events"
v-model:formModeName="formModeName" v-model:formModeName="formModeName"
@open-zone-form="openForm"
/> />
</QScrollArea> </QScrollArea>
</QDrawer> </QDrawer>

View File

@ -11,10 +11,6 @@ import { dashIfEmpty } from 'src/filters';
import { useWeekdayStore } from 'src/stores/useWeekdayStore'; import { useWeekdayStore } from 'src/stores/useWeekdayStore';
import { useVnConfirm } from 'composables/useVnConfirm'; import { useVnConfirm } from 'composables/useVnConfirm';
const formModeName = defineModel('formModeName', {
type: String,
required: true,
});
const props = defineProps({ const props = defineProps({
firstDay: { firstDay: {
type: Date, type: Date,
@ -31,8 +27,18 @@ const props = defineProps({
required: true, required: true,
default: () => [], default: () => [],
}, },
formModeName: {
type: String,
required: true,
default: 'include',
},
}); });
const formName = computed({
get: () => props.formModeName,
set: (value) => emit('update:formModeName', value),
});
const emit = defineEmits(['openZoneForm', 'update:formModeName']);
const { t } = useI18n(); const { t } = useI18n();
const route = useRoute(); const route = useRoute();
const weekdayStore = useWeekdayStore(); const weekdayStore = useWeekdayStore();
@ -80,6 +86,15 @@ const deleteEvent = async (id) => {
await fetchData(); await fetchData();
}; };
const openInclusionForm = (event) => {
formName.value = 'include';
emit('openZoneForm', {
date: event.dated,
event,
isNewMode: false,
});
};
onMounted(async () => { onMounted(async () => {
weekdayStore.initStore(); weekdayStore.initStore();
}); });
@ -92,13 +107,13 @@ onMounted(async () => {
t('eventsPanel.editMode') t('eventsPanel.editMode')
}}</span> }}</span>
<QRadio <QRadio
v-model="formModeName" v-model="formName"
dense dense
val="include" val="include"
:label="t('eventsPanel.include')" :label="t('eventsPanel.include')"
/> />
<QRadio <QRadio
v-model="formModeName" v-model="formName"
dense dense
val="exclude" val="exclude"
:label="t('eventsPanel.exclude')" :label="t('eventsPanel.exclude')"