feat(penilai): tambahkan fitur unggah foto dan simpan memo dengan foto

- Menambahkan metode `uploadTempPhoto` untuk mengunggah foto sementara.
- Menambahkan metode `storeMemoWithPhotos` untuk menyimpan memo beserta foto.
- Memperbarui rute untuk mendukung pengunggahan foto dan penyimpanan memo.
- Memperbarui tampilan untuk menampilkan foto yang sudah ada dan mengubah ID dropzone.
This commit is contained in:
Daeng Deni Mardaeni
2025-03-07 09:53:55 +07:00
parent 5d380f1a68
commit f7c85fc24e
3 changed files with 170 additions and 22 deletions

View File

@@ -295,7 +295,7 @@
<h1 class="text-md font-medium text-gray-900">Upload Foto</h1>
</div>
<div class="dropzone" id="upload-dropzone">
<div class="dropzone" id="dropzone-upload">
<div class="dz-message needsclick" data-foto-type="upload_foto">
<i class="ki-duotone ki-file-up text-primary text-3xl"><span class="path1"></span><span
class="path2"></span></i>
@@ -306,6 +306,9 @@
</div>
</div>
</div>
<div class="card-footer">
<div id="existing-photos" class="flex gap-5"></div>
</div>
</div>
{{-- @include('lpj::penilai.components.foto-lampiran') --}}
@@ -337,7 +340,75 @@
</div>
@endsection
@include('lpj::surveyor.js.utils')
<script>
@push('scripts')
<script>
Dropzone.autoDiscover = false;
let myDropzone;
document.addEventListener('DOMContentLoaded', function() {
myDropzone = new Dropzone("#dropzone-upload", {
url: "{{ route('penilai.uploadTempPhoto') }}", // Temporary upload route
paramName: "file",
maxFilesize: 5, // MB
acceptedFiles: "image/*",
addRemoveLinks: true,
headers: {
'X-CSRF-TOKEN': '{{ csrf_token() }}'
},
init: function() {
this.on("success", function(file, response) {
file.serverId = response.id; // Store the server's file ID
});
// Load existing photos
loadExistingPhotos();
}
});
});
function loadExistingPhotos() {
const existingPhotosContainer = document.getElementById('existing-photos');
if (!existingPhotosContainer) return;
@if(isset($memo) && isset($memo->foto))
let existingPhotos;
try {
existingPhotos = @json($memo->foto);
} catch (e) {
console.error('Error parsing existing photos:', e);
return;
}
if (Array.isArray(existingPhotos)) {
existingPhotos.forEach(function(photoPath) {
if (typeof photoPath === 'string') {
const photoDiv = document.createElement('div');
photoDiv.className = 'col-md-3 mb-3';
const img = document.createElement('img');
img.src = photoPath;
img.className = 'img-fluid';
img.style.maxHeight = '150px';
photoDiv.appendChild(img);
existingPhotosContainer.appendChild(photoDiv);
if (myDropzone) {
let mockFile = { name: photoPath.split('/').pop(), size: 12345 };
myDropzone.emit("addedfile", mockFile);
myDropzone.emit("thumbnail", mockFile, photoPath);
myDropzone.emit("complete", mockFile);
mockFile.previewElement.classList.add("dz-success");
mockFile.previewElement.classList.add("dz-complete");
}
}
});
} else {
console.error('Existing photos is not an array:', existingPhotos);
}
@endif
}
function saveMemo() {
const form = document.getElementById('form-memo');
const formData = new FormData(form);
@@ -371,17 +442,26 @@
const documentId = urlParams.get('documentId');
const inspeksiId = urlParams.get('inspeksiId');
const requestUrl = `{{ route('penilai.storeMemo') }}`;
// Create a new FormData object to send both JSON and files
const sendFormData = new FormData();
sendFormData.append('permohonan_id', permohonanId);
sendFormData.append('document_id', documentId);
sendFormData.append('inspeksi_id', inspeksiId);
sendFormData.append('memo', JSON.stringify(jsonData));
// Append all files from Dropzone
myDropzone.getAcceptedFiles().forEach((file, index) => {
sendFormData.append(`foto_${index}`, file);
});
const requestUrl = `{{ route('penilai.storeMemoWithPhotos') }}`;
$.ajax({
url: requestUrl,
type: 'POST',
data: JSON.stringify({
permohonan_id: permohonanId,
document_id: documentId,
inspeksi_id: inspeksiId,
memo: jsonData,
}),
contentType: 'application/json',
data: sendFormData,
processData: false,
contentType: false,
headers: {
'X-CSRF-TOKEN': '{{ csrf_token() }}'
},
@@ -409,17 +489,15 @@
console.log(response);
},
error: function(xhr, status, error) {
let errors = xhr.responseJSON?.errors;
$('.alert').text('');
if (errors) {
$.each(errors, function(key, value) {
$(`#error-${key}`).text(value[0]);
toastrErrorBuild(value[0]);
});
}
hideLoadingSwal();
console.log(errors);
Swal.fire({
title: 'Error!',
text: 'Terjadi kesalahan saat mengirim data',
icon: 'error',
confirmButtonText: 'OK'
});
}
});
}
</script>
@endpush