Merge remote-tracking branch 'composer/feature/senior-officer' into staging

# Conflicts:
#	resources/views/surveyor/components/tanah.blade.php
This commit is contained in:
Daeng Deni Mardaeni
2024-12-27 08:50:01 +07:00
12 changed files with 2841 additions and 1875 deletions

View File

@@ -107,7 +107,8 @@
value="rute_{{ $index }}">
<input id="inputRute-{{ $index }}" type="file" name="foto_rute[]"
class="file-input file-input-bordered w-full" accept="image/*"
capture="camera" onchange="previewImage(this, 'foto_rute-preview-{{ $index }}')">
capture="camera"
onchange="previewImage(this, 'foto_rute-preview-{{ $index }}')">
<button type="button" id="btnCamera-{{ $index }}" class="btn btn-light"
@@ -370,117 +371,99 @@
@endif
@endforeach
@if (isset($formFoto['foto_lantai_unit']))
<div class="flex flex-wrap gap-4 w-full">
<div class="w-full">
<div class="text-white py-4 flex items-center justify-between w-full">
<label class="form-label">
<span class="form-label">Lantai</span>
</label>
<button type="button" id="btnAddLantai" class="btn btn-primary btn-sm">
<i class="ki-filled ki-plus text-lg"></i> Tambah Lantai
</button>
</div>
<div id="lantaiContainer" class="w-full">
@foreach ($formFoto['foto_lantai_unit'] as $lantaiKey => $lantaiFotos)
<div class="lantai-item w-full mb-4">
<div class="flex w-full items-center justify-between">
<label class="form-label">Lantai {{ $lantaiKey }}</label>
<button type="button" class="btn btn-danger btn-sm btnRemoveLantai"
style="{{ $lantaiKey == 1 ? 'display: none;' : '' }}">
Hapus
</button>
</div>
<div class="dropzone w-full border-2 border-dashed border-gray-400 rounded-lg p-4 mt-2"
ondrop="handleDrop(event)" ondragover="allowDrop(event)">
<div class="preview-container grid grid-cols-2 md:grid-cols-4 gap-4">
@foreach ($lantaiFotos as $foto)
<div class="preview-item relative">
<img src="{{ asset('storage/' . $foto['path']) }}"
alt="{{ $foto['name'] }}"
class="w-full h-40 object-cover rounded-lg">
<button type="button"
class="absolute top-2 right-2 btn btn-sm btn-danger btn-icon btnRemoveFoto"
data-path="{{ $foto['path'] }}">
<i class="ki-solid ki-cross"></i>
</button>
</div>
@endforeach
</div>
<input type="file"
name="foto_lantai_unit[{{ $lantaiKey }}][]"
class="file-input hidden"
multiple
accept="image/*"
onchange="handleFileInput(this)"
data-lantai="{{ $lantaiKey }}">
<button type="button" class="btn btn-light btn-sm btnUploadFiles mt-2">
<i class="ki-outline ki-upload"></i> Unggah Gambar
</button>
</div>
</div>
@endforeach
</div>
</div>
</div>
@else
<div class="flex flex-wrap gap-4 w-full">
<div class="w-full">
<div class="text-white py-4 flex items-center justify-between w-full">
<label class="form-label">
<span class="form-label">Lantai</span>
</label>
<button type="button" id="btnLantai" class="btn btn-primary btn-sm">
<i class="ki-filled ki-plus text-lg"></i>
<button type="button" id="btnAddLantai" class="btn btn-primary btn-sm">
<i class="ki-filled ki-plus text-lg"></i> Tambah Lantai
</button>
</div>
@if (isset($formFoto['foto_lantai_unit']))
@foreach ($formFoto['foto_lantai_unit'] as $item)
<div id="inputContainerLantai" class="w-full">
<div class="flex w-full items-center justify-center gap-4">
<label class="form-label max-w-56">
<span class="form-label">Foto Lantai {{ $loop->iteration }}</span>
</label>
<div class="input-group w-full grid gap-5">
<div class="preview-container">
<img id="foto_lantai-preview-{{ $loop->iteration }}"
src="{{ asset('storage/' . old('foto_lantai_unit', $item['foto_lantai_unit'])) }}"
alt="Foto Lantai" class="mt-2 h-auto"
style="{{ old('foto_lantai_unit', $item['foto_lantai_unit']) ? 'display: block;' : 'display: none;' }} width: 30rem;">
</div>
<input type="hidden" name="name_lantai_unit[]" value="lantai">
<input id="inputLantai" type="file" name="foto_lantai_unit[]"
class="file-input file-input-bordered w-full" accept="image/*"
onchange="previewImage(this, 'foto_lantai-preview')" capture="camera">
<button type="button" class="btn btn-danger btn-sm delete-btn"
style="display: none;" id="btnDelete">
<i class="ki-filled ki-trash"></i>
</button>
</div>
</div>
<span id="inputLantaiError" class="alert text-danger text-sm"></span>
</div>
@endforeach
@else
<div id="inputContainerLantai" class="w-full">
<div class="flex w-full items-center justify-center gap-4">
<label class="form-label max-w-56">
<span class="form-label">Foto Lantai 1</span>
</label>
<div class="input-group w-full flex gap-2">
<input type="hidden" name="name_lantai_unit[]" value="lantai">
<div class="preview-container">
<img id="foto_lantai-preview"
alt="Foto Lantai" class="mt-2 h-auto"
style="display: none; width: 30rem;">
</div>
<input id="inputLantai" type="file" name="foto_lantai_unit[]"
class="file-input file-input-bordered w-full" accept="image/*"
onchange="previewImage(this, 'foto_lantai-preview')" capture="camera">
<button type="button" id="btnCamera" class="btn btn-light"
data-modal-toggle="#cameraModal">
<i class="ki-outline ki-abstract-33"></i> Camera
</button>
</div>
<button type="button" class="btn btn-danger btn-sm delete-btn"
style="display: none;" id="btnDelete">
<i class="ki-filled ki-trash"></i>
<div id="lantaiContainer" class="w-full">
<!-- Template Lantai -->
<div class="lantai-item w-full mb-4">
<div class="flex w-full items-center justify-between">
<label class="form-label">Lantai 1</label>
<button type="button" class="btn btn-danger btn-sm btnRemoveLantai"
style="display: none;">
Hapus
</button>
</div>
@error('foto_lantai_unit.*')
<span class="alert text-danger text-sm">{{ $message }}</span>
@enderror
</div>
@endif
<div id="inputContainerBasement" class="w-full" style="margin-top: 10px">
<div class="flex w-full items-center justify-center gap-4">
<label class="form-label max-w-56">
<span class="form-label">Basement</span>
</label>
<div class="input-group w-full flex flex-col gap-2">
<input type="hidden" name="name_basement" value="basement">
<img id="foto_basement_preview"
src="{{ isset($formFoto['foto_basement']) ? asset('storage/' . old('foto_basement', $formFoto['foto_basement'])) : '#' }}"
alt="Gambar foto_basement" style="width: 30rem;"
onerror="this.style.display='none';"
onchange="previewImage(this, 'foto_basement_preview')">
<div class="input-group w-full flex gap-2">
<input id="inputBasement" type="file" name="foto_basement"
class="file-input file-input-bordered w-full" accept="image/*"
onchange="previewImage(this, 'foto_basement_preview')" capture="camera">
<button type="button" id="btnCamera" class="btn btn-light"
data-modal-toggle="#cameraModal">
<i class="ki-outline ki-abstract-33"></i> Camera
</button>
</div>
<div class="dropzone w-full border-2 border-dashed border-gray-400 rounded-lg p-4 mt-2"
ondrop="handleDrop(event)" ondragover="allowDrop(event)">
<div class="preview-container grid grid-cols-2 md:grid-cols-4 gap-4"></div>
<input type="file" name="foto_lantai_unit[1][]" class="file-input hidden"
multiple accept="image/*" onchange="handleFileInput(this)" data-lantai="1">
<button type="button" class="btn btn-light btn-sm btnUploadFiles mt-2">
<i class="ki-outline ki-upload"></i> Unggah Gambar
</button>
</div>
<button type="button" class="btn btn-danger btn-sm delete-btn"
style="display: none;" id="btnDelete">
<i class="ki-filled ki-trash"></i>
</button>
</div>
<span id="alertBasement" class="alert text-danger text-sm"></span>
</div>
<div id="lantaiLainnya" style="margin-top: 10px"></div>
<button type="button" class="btn btn-primary btn-sm" id="btnAddMoreObject"
style="margin-top: 10px">
<i class="ki-outline ki-plus text-2sm"></i>
Lainnya
</button>
</div>
</div>
@endif
</div>
</div>
@@ -619,12 +602,191 @@
@include('lpj::surveyor.js.utils')
@push('scripts')
<script>
console.log('@json($formFoto)');
document.addEventListener("DOMContentLoaded", () => {
const lantaiContainer = document.getElementById("lantaiContainer");
const btnAddLantai = document.getElementById("btnAddLantai");
const updateRemoveButtonVisibility = () => {
const lantaiItems = lantaiContainer.querySelectorAll(".lantai-item");
lantaiItems.forEach((item, index) => {
const btnRemove = item.querySelector(".btnRemoveLantai");
const labelLantai = item.querySelector(".form-label");
// Update label lantai
labelLantai.textContent = `Lantai ${index + 1}`;
// Tampilkan tombol hapus jika lebih dari 1 lantai
btnRemove.style.display = lantaiItems.length > 1 ? "inline-block" : "none";
});
};
const attachEventListeners = (lantaiItem) => {
// Event listener untuk tombol Hapus
lantaiItem.querySelector(".btnRemoveLantai").addEventListener("click", () => {
lantaiItem.remove();
updateRemoveButtonVisibility();
});
// Event listener untuk tombol Unggah Gambar
lantaiItem.querySelector(".btnUploadFiles").addEventListener("click", () => {
lantaiItem.querySelector(".file-input").click();
});
};
// Tambahkan lantai baru
btnAddLantai.addEventListener("click", () => {
const lantaiCount = lantaiContainer.children.length + 1;
const lantaiItem = document.createElement("div");
lantaiItem.classList.add("lantai-item", "w-full", "mb-4");
lantaiItem.innerHTML = `
<div class="flex w-full items-center justify-between">
<label class="form-label">Lantai ${lantaiCount}</label>
<button type="button" class="btn btn-danger btn-sm btnRemoveLantai">
Hapus
</button>
</div>
<div class="dropzone w-full border-2 border-dashed border-gray-400 rounded-lg p-4 mt-2"
ondrop="handleDrop(event)"
ondragover="allowDrop(event)">
<div class="preview-container grid grid-cols-2 md:grid-cols-4 gap-4"></div>
<input type="file"
name="foto_lantai_unit[${lantaiCount}][]"
class="file-input hidden"
multiple
accept="image/*"
data-lantai="${lantaiCount}"
onchange="handleFileInput(this)">
<button type="button" class="btn btn-light btn-sm btnUploadFiles">
<i class="ki-outline ki-upload"></i> Unggah Gambar
</button>
</div>
`;
lantaiContainer.appendChild(lantaiItem);
attachEventListeners(lantaiItem);
updateRemoveButtonVisibility();
});
window.handleFileInput = (input) => {
const lantaiNomor = input.getAttribute('data-lantai');
const previewContainer = input.closest(".dropzone").querySelector(".preview-container");
// Tidak reset preview, tambahkan gambar baru
Array.from(input.files).forEach((file) => {
if (file.type.startsWith('image/')) {
const reader = new FileReader();
reader.onload = (e) => {
const imgWrapper = document.createElement("div");
imgWrapper.classList.add("relative", "preview-item");
const img = document.createElement("img");
img.src = e.target.result;
img.alt = `Foto Lantai ${lantaiNomor}`;
img.classList.add("rounded", "w-full", "h-40", "object-cover");
// Tombol hapus gambar
const removeBtn = document.createElement("button");
removeBtn.innerHTML = '<i class="ki-outline ki-trash"></i>';
removeBtn.classList.add(
"absolute", "top-0", "right-0",
"btn", "btn-danger", "text-white",
"rounded-full", "w-6", "h-6",
"flex", "items-center", "justify-center"
);
removeBtn.addEventListener("click", () => {
removeImageFromPreview(input, imgWrapper, file);
});
imgWrapper.appendChild(img);
imgWrapper.appendChild(removeBtn);
previewContainer.appendChild(imgWrapper);
};
reader.readAsDataURL(file);
}
});
};
function removeImageFromPreview(input, imgWrapper, fileToRemove) {
// Hapus dari preview
imgWrapper.remove();
// Hapus file dari input
const dataTransfer = new DataTransfer();
Array.from(input.files)
.filter(file => file !== fileToRemove)
.forEach(file => dataTransfer.items.add(file));
input.files = dataTransfer.files;
}
window.handleDrop = (event) => {
event.preventDefault();
const dropzone = event.target.closest(".dropzone");
const fileInput = dropzone.querySelector(".file-input");
const previewContainer = dropzone.querySelector(".preview-container");
const dataTransfer = new DataTransfer();
// Tambahkan file yang sudah ada di input
Array.from(fileInput.files).forEach((file) => dataTransfer.items.add(file));
// Tambahkan file baru yang di-drop
Array.from(event.dataTransfer.files).forEach((file) => {
// Cek duplikasi
const isDuplicate = Array.from(fileInput.files).some(
existFile => existFile.name === file.name && existFile.size === file.size
);
if (!isDuplicate) {
dataTransfer.items.add(file);
}
});
fileInput.files = dataTransfer.files;
handleFileInput(fileInput);
};
// Inisialisasi lantai pertama
const initialLantaiItem = lantaiContainer.querySelector(".lantai-item");
if (initialLantaiItem) {
attachEventListeners(initialLantaiItem);
}
updateRemoveButtonVisibility();
});
function submitFoto() {
showLoadingSwal('Mengirim data ke server...');
const formElement = $('#formFoto')[0];
const formData = new FormData(formElement);
const lantaiInputs = document.querySelectorAll('.lantai-input');
lantaiInputs.forEach((input, index) => {
const files = input.files;
if (files.length > 0) {
// Gunakan dot notation sesuai Laravel
Array.from(files).forEach((file, fileIndex) => {
formData.append(`foto_lantai_unit.${index}`, file);
// Nama lantai unit
const namaLantai = document.querySelector(`[name="name_lantai_unit.${index}"]`);
if (namaLantai && namaLantai.value) {
formData.append(`name_lantai_unit.${index}`, namaLantai.value);
}
});
}
});
console.log(formData.value);
$.ajax({
url: '{{ route('surveyor.storeFoto') }}',
type: 'POST',
@@ -644,10 +806,10 @@
icon: 'success',
confirmButtonText: 'OK'
}).then((response) => {
if (response.isConfirmed) {
window.location.href =
'{{ route('surveyor.show', ['id' => $permohonan->id]) }}';
}
// if (response.isConfirmed) {
// window.location.href =
// '{{ route('surveyor.show', ['id' => $permohonan->id]) }}';
// }
console.log(response);
});

View File

@@ -408,14 +408,8 @@
<div class="mt-2">
<div class="flex flex-wrap items-baseline w-full text-sm">
@foreach ($permohonan->debiture->documents as $dokumen)
@php
$hubCadebPenghuni = $dokumen->penghuni->hubungan_penghuni->name ?? 'N/A';
@endphp
{{ $hubCadebPenghuni }}
<input type="hidden" name="hub_cadeb_penghuni_sesuai"
value="{{ isset($hubCadebPenghuni) ?? '' }}" id="">
@endforeach
value="ditempati sendiri" id="">
</div>
<div class="flex-wrap items-stretch">

View File

@@ -14,12 +14,8 @@
@foreach ($permohonan->debiture->documents as $item)
@php
$luas = $item->detail;
if(is_array($luas)){
$details = json_decode($luas[0]->details, true);
$luas_tanah = isset($details['luas']) ? $details['luas'] : 'N/A';
} else {
$luas_tanah = 'N/A';
}
$details = json_decode($luas[0]->details, true);
$luas_tanah = isset($details['luas_tanah']) ? $details['luas_tanah'] : 'N/A';
@endphp
<input type="hidden" name="luas_tanah_sesuai" class="input" value="{{ $luas_tanah }}">
<p class="text-2sm text-gray-700">{{ $luas_tanah }} m<sup>2</sup></p>