From dc335d4dab2801fb8396776ae7f5ae003d2993e7 Mon Sep 17 00:00:00 2001 From: Yoga Pangestu Date: Fri, 12 Jun 2026 16:50:44 +0700 Subject: [PATCH] Refactor PurchasePosForm to replace MediaImageUpload with ImageUploadField for improved photo upload handling. Update form data structure to accommodate new photo logic and streamline code. Introduce MultipleImageUploadField for variant images in ProductForm and RawMaterialForm, enhancing user experience with better image management. --- .../manage/purchases/PurchasePosForm.vue | 23 ++- .../admin/master/products/ProductForm.vue | 6 +- .../master/raw-materials/RawMaterialForm.vue | 4 +- .../js/components/media/MediaImageUpload.vue | 157 ----------------- .../MultipleImageUploadField.vue | 160 ++++++++++++++++++ .../components/ui/image-upload-field/index.ts | 1 + 6 files changed, 182 insertions(+), 169 deletions(-) delete mode 100644 resources/js/components/media/MediaImageUpload.vue create mode 100644 resources/js/components/ui/image-upload-field/MultipleImageUploadField.vue diff --git a/resources/js/components/admin/manage/purchases/PurchasePosForm.vue b/resources/js/components/admin/manage/purchases/PurchasePosForm.vue index 67cb369..70b8da9 100644 --- a/resources/js/components/admin/manage/purchases/PurchasePosForm.vue +++ b/resources/js/components/admin/manage/purchases/PurchasePosForm.vue @@ -5,7 +5,6 @@ import { computed, ref, watch } from 'vue'; import { toast } from 'vue-sonner'; import PosCatalogCard from '@/components/admin/manage/PosCatalogCard.vue'; import PosCatalogVariantThumb from '@/components/admin/manage/PosCatalogVariantThumb.vue'; -import MediaImageUpload from '@/components/media/MediaImageUpload.vue'; import { Badge } from '@/components/ui/badge'; import { Button } from '@/components/ui/button'; import { Card, CardContent, CardHeader, CardTitle } from '@/components/ui/card'; @@ -22,6 +21,7 @@ import { FieldLabel, FieldSet, } from '@/components/ui/field'; +import { ImageUploadField } from '@/components/ui/image-upload-field'; import { Input } from '@/components/ui/input'; import { RupiahInput } from '@/components/ui/rupiah-input'; import { @@ -38,7 +38,6 @@ import { getFirstCoverImage } from '@/lib/catalog-cover'; import { formErrors } from '@/lib/form'; import { formatRupiah, parseRupiah } from '@/lib/rupiah'; import type { MediaItem } from '@/types/media'; -import { appendRootPhotosToFormData, createMediaUploadState } from '@/types/media'; import type { PurchaseCartItem, PurchaseCatalogItem, SelectOption } from '@/types/purchase'; const props = defineProps<{ suppliers: SelectOption[]; @@ -57,12 +56,15 @@ const props = defineProps<{ const search = ref(''); const cart = ref([]); +const existingPhotoId = ref(null); + +const currentPhotoUrl = computed(() => props.initialData?.photos?.url ?? null); const form = useForm({ supplier_id: '', discount: '', notes: '', - media: createMediaUploadState(), + photo: null as File | null, }); function populateForm() { @@ -73,7 +75,8 @@ function populateForm() { form.supplier_id = props.initialData.supplier_id; form.discount = props.initialData.discount; form.notes = props.initialData.notes; - form.media = createMediaUploadState(props.initialData.photos ? [props.initialData.photos] : []); + form.photo = null; + existingPhotoId.value = props.initialData.photos?.id ?? null; cart.value = props.initialData.items.map((item) => ({ ...item })); } @@ -176,7 +179,13 @@ function buildFormData(): FormData { formData.append(`items[${index}][quantity]`, item.quantity); }); - appendRootPhotosToFormData(formData, form.media); + if (form.photo) { + formData.append('photos[]', form.photo); + + if (existingPhotoId.value) { + formData.append('remove_media_ids[]', String(existingPhotoId.value)); + } + } return formData; } @@ -378,8 +387,8 @@ function submit() { - +