Server : Apache/2.4.18 (Ubuntu) System : Linux canvaswebdesign 3.13.0-71-generic #114-Ubuntu SMP Tue Dec 1 02:34:22 UTC 2015 x86_64 User : oppastar ( 1041) PHP Version : 7.0.33-0ubuntu0.16.04.15 Disable Function : pcntl_alarm,pcntl_fork,pcntl_waitpid,pcntl_wait,pcntl_wifexited,pcntl_wifstopped,pcntl_wifsignaled,pcntl_wifcontinued,pcntl_wexitstatus,pcntl_wtermsig,pcntl_wstopsig,pcntl_signal,pcntl_signal_dispatch,pcntl_get_last_error,pcntl_strerror,pcntl_sigprocmask,pcntl_sigwaitinfo,pcntl_sigtimedwait,pcntl_exec,pcntl_getpriority,pcntl_setpriority, Directory : /var/www/laciasmara.com/public_html/shop/application/views/account/ |
Upload File : |
<?php defined('BASEPATH') or exit('No direct script access allowed'); ?> <div class="account-shipping-container"> <h1><?= ucfirst(lang('shipping_title')) ?></h1> <div class="account-shipping-header"> <div class="shipping-search-and-button"> <div class="shipping-search-box"> <i class="fas fa-search shipping-search-icon"></i> <input type="text" placeholder="Tulis Nama Alamat / Kota tujuan pengiriman kamu" /> </div> <button class="add-address-btn" onclick="openModal()">+ Tambah Alamat Baru</button> </div> </div> <div class="shipping-address-list"> <?php if (empty($addresses)): ?> <div class="shipping-empty-state"> <div class="shipping-empty-icon"> <i class="fas fa-map-marker-alt"></i> </div> <h3>Belum ada alamat tersimpan</h3> <p>Tambahkan alamat pengiriman untuk mempermudah proses checkout</p> <button class="shipping-btn-card shipping-btn-primary" onclick="openModal()"> Masukin Alamat Pertama </button> </div> <?php else: ?> <?php foreach ($addresses as $address): ?> <div class="shipping-address-card <?= $address->is_default ? 'default' : '' ?>" data-id="<?= $address->id ?>"> <div class=" shipping-address-header"> <div class="shipping-address-label"> <span class="shipping-label-text"><?= htmlspecialchars($address->label) ?></span> <?php if ($address->is_default): ?> <span class="shipping-default-badge">Utama</span> <?php endif; ?> </div> </div> <div class="shipping-address-body"> <div class="shipping-recipient-info"> <div class="shipping-recipient-name"> <i class="fas fa-user"></i> <span><?= htmlspecialchars($address->recipient_name) ?></span> </div> <div class="shipping-recipient-phone"> <i class="fas fa-phone"></i> <span><?= htmlspecialchars($address->phone) ?></span> </div> </div> <div class="shipping-full-address"> <i class="fas fa-map-marker-alt"></i> <div class="shipping-address-text"> <div class="shipping-address-main"><?= htmlspecialchars($address->address) ?> <?php if (!empty($address->notes)): ?> (<?= htmlspecialchars($address->notes) ?>) <?php endif; ?> </div> </div> </div> </div> <div class="shipping-address-footer"> <!-- <button class="shipping-btn-card shipping-btn-edit" onclick="editAddress(<?= $address->id ?>)"> Ubah Alamat </button> --> <?php if (!$address->is_default): ?> <button class="shipping-btn-card shipping-btn-outline" onclick="setDefaultAddress(<?= $address->id ?>)"> Jadikan Alamat Utama </button> <?php endif; ?> </div> </div> <?php endforeach; ?> <?php endif; ?> </div> <div class="shipping-modal-overlay" id="addressModal"> <div class="shipping-modal-container"> <!-- Modal Header --> <div class="shipping-modal-header"> <h2>Tambah Alamat</h2> <button class="shipping-close-btn" onclick="closeModal()"> <i class="fas fa-times"></i> </button> </div> <!-- Progress Bar --> <div class="shipping-progress-container"> <div class="shipping-progress-bar"> <div class="shipping-progress-line"> <div class="shipping-progress-line-fill" id="progressFill"></div> </div> <div class="step-wrapper"> <div class="shipping-step active" id="step1">1</div> <div class="shipping-step-label active" id="label1">Cari lokasi pengirimanmu</div> </div> <div class="step-wrapper"> <div class="shipping-step" id="step2">2</div> <div class="shipping-step-label" id="label2">Tentukan pinpoint lokasi</div> </div> <div class="step-wrapper"> <div class="shipping-step" id="step3">3</div> <div class="shipping-step-label" id="label3">Lengkapi detail alamat</div> </div> </div> </div> <!-- Modal Content --> <div class="shipping-modal-content"> <!-- Step 1: Search Location --> <div class="shipping-step-content active" id="content1"> <div class="shipping-search-location"> <h3>Cari Lokasi Pengiriman</h3> <div class="shipping-search-input-group"> <input type="text" id="addressSearch" placeholder="Masukkan nama jalan, gedung, atau area"> </div> <button class="shipping-current-location-btn" onclick="getCurrentLocation()"> <i class="fas fa-location-crosshairs"></i> Gunakan Lokasi Saat Ini </button> </div> </div> <!-- Step 2: Map --> <div class="shipping-step-content" id="content2"> <div class="shipping-map-container"> <h3>Tentukan Pinpoint Lokasi</h3> <div id="map"></div> <p style="color: #666; font-size: 14px;"> <i class="fas fa-info-circle"></i> Drag pin untuk menyesuaikan lokasi yang tepat </p> </div> </div> <!-- Step 3: Address Details --> <div class="shipping-step-content" id="content3"> <div class="shipping-address-details"> <h3>Lengkapi detail alamat</h3> <form id="addressForm"> <div class="shipping-form-group"> <label for="addressLabel">Label Alamat *</label> <input type="text" id="addressLabel" placeholder="Contoh: Rumah, Kantor, Apartemen"> </div> <div class="shipping-form-group"> <label for="fullAddress">Alamat Lengkap *</label> <textarea id="fullAddress" placeholder="Alamat lengkap akan diisi otomatis"></textarea> </div> <div class="shipping-form-group"> <label for="addressNotes">Catatan Alamat</label> <textarea id="addressNotes" placeholder="Contoh: Rumah cat hijau, sebelah warung Pak Budi"></textarea> </div> <div class="shipping-form-row"> <div class="shipping-form-group"> <label for="receiverName">Nama Penerima *</label> <input type="text" id="receiverName" placeholder="Nama lengkap penerima"> </div> <div class="shipping-form-group"> <label for="receiverPhone">Nomor HP *</label> <input type="tel" id="receiverPhone" placeholder="08xxxxxxxxxx"> </div> </div> <div class="shipping-checkbox-group"> <input type="checkbox" id="isMainAddress"> <label for="isMainAddress">Jadikan sebagai alamat utama</label> </div> <!-- Hidden fields for coordinates --> <input type="hidden" id="latitude"> <input type="hidden" id="longitude"> <input type="hidden" id="province"> <input type="hidden" id="city"> <input type="hidden" id="district"> <input type="hidden" id="subdistrict"> <input type="hidden" id="postal-code"> </form> </div> </div> </div> <!-- Modal Footer --> <div class="shipping-modal-footer"> <button class="shipping-btn shipping-btn-secondary" id="backBtn" onclick="prevStep()" style="display: none;"> <i class="fas fa-arrow-left"></i> Kembali </button> <div style="flex: 1;"></div> <button class="shipping-btn shipping-btn-primary" id="nextBtn" onclick="nextStep()"> Lanjutkan <i class="fas fa-arrow-right"></i> </button> </div> </div> </div> </div> <script async src="https://maps.googleapis.com/maps/api/js?key=<?php echo $this->config->item('google_maps_api_key'); ?>&loading=async&libraries=places,marker&callback=initMap&language=id®ion=ID&v=beta" defer></script> <script> let currentStep = 1; let map; let marker; let autocomplete; let geocoder; let selectedPlace = null; const searchAddressInput = document.querySelector('.shipping-search-box input'); const addressCards = document.querySelectorAll('.shipping-address-card'); const notyf = new Notyf({ duration: 3500, position: { x: 'right', y: 'top' }, types: [{ type: 'success', background: '#7A4397', icon: { className: 'fas fa-check', tagName: 'i', color: 'white' } }, { type: 'error', background: '#dc3545', icon: { className: 'fas fa-circle-xmark', tagName: 'i', color: 'white' } } ] }); // Modal functions function openModal() { document.getElementById('addressModal').classList.add('active'); document.body.style.overflow = 'hidden'; // Initialize map when modal opens setTimeout(() => { if (typeof google !== 'undefined' && google.maps) { initMap(); } else { console.log('Google Maps not loaded yet'); } }, 300); } function closeModal() { document.getElementById('addressModal').classList.remove('active'); document.body.style.overflow = 'auto'; resetModal(); } function resetModal() { currentStep = 1; updateStepDisplay(); document.getElementById('addressForm').reset(); document.getElementById('addressSearch').value = ''; selectedPlace = null; } // Step navigation function nextStep() { if (currentStep < 3) { if (validateCurrentStep()) { currentStep++; updateStepDisplay(); // Initialize map when entering step 2 if (currentStep === 2) { setTimeout(() => { if (map && selectedPlace) { map.setCenter(selectedPlace.geometry.location); map.setZoom(17); if (marker.position !== undefined) { marker.position = selectedPlace.geometry.location; } else { marker.setPosition(selectedPlace.geometry.location); } } }, 100); } } } else { // Save address (step 3) saveAddress(); } } function prevStep() { if (currentStep > 1) { currentStep--; updateStepDisplay(); } } function updateStepDisplay() { // Update progress bar const progressFill = document.getElementById('progressFill'); const progressPercentage = ((currentStep - 1) / 2) * 100; progressFill.style.width = progressPercentage + '%'; // Update steps for (let i = 1; i <= 3; i++) { const step = document.getElementById(`step${i}`); const label = document.getElementById(`label${i}`); const content = document.getElementById(`content${i}`); // Reset all classes first step.classList.remove('active', 'completed'); label.classList.remove('active'); content.classList.remove('active'); if (i < currentStep) { step.classList.add('completed'); } else if (i === currentStep) { step.classList.add('active'); label.classList.add('active'); content.classList.add('active'); } } // Update footer buttons const backBtn = document.getElementById('backBtn'); const nextBtn = document.getElementById('nextBtn'); if (currentStep === 1) { backBtn.style.display = 'none'; nextBtn.innerHTML = 'Lanjutkan <i class="fas fa-arrow-right"></i>'; } else if (currentStep === 2) { backBtn.style.display = 'block'; nextBtn.innerHTML = 'Lanjutkan <i class="fas fa-arrow-right"></i>'; } else { backBtn.style.display = 'block'; nextBtn.innerHTML = 'Simpan Alamat <i class="fas fa-save"></i>'; } } function validateCurrentStep() { if (currentStep === 1) { if (!selectedPlace) { notyf.error('Silakan pilih lokasi terlebih dahulu'); return false; } } else if (currentStep === 2) { // Map validation (always valid as long as marker exists) return true; } else if (currentStep === 3) { // Form validation const label = document.getElementById('addressLabel').value; const fullAddress = document.getElementById('fullAddress').value; const receiverName = document.getElementById('receiverName').value; const receiverPhone = document.getElementById('receiverPhone').value; if (!label || !fullAddress || !receiverName || !receiverPhone) { notyf.error('Silakan lengkapi semua field yang wajib diisi'); return false; } } return true; } function setDefaultAddress(addressId) { const csrfName = '<?php echo $this->security->get_csrf_token_name(); ?>'; const csrfHash = '<?php echo $this->security->get_csrf_hash(); ?>'; const formData = new FormData(); formData.append(csrfName, csrfHash); fetch(`<?= base_url('account/set_default_address/') ?>${addressId}`, { method: 'POST', body: formData }) .then(response => response.json()) .then(data => { if (data.status === 'success') { notyf.success(data.message); setTimeout(() => location.reload(), 1000); } else { notyf.error(data.message); } }) .catch(error => { console.error('Error:', error); notyf.error('Terjadi kesalahan saat mengubah alamat utama'); }); } function saveAddress() { if (!validateCurrentStep()) return; // Collect address data const addressData = { label: document.getElementById('addressLabel').value, fullAddress: document.getElementById('fullAddress').value, notes: document.getElementById('addressNotes').value, receiverName: document.getElementById('receiverName').value, receiverPhone: document.getElementById('receiverPhone').value, isMainAddress: document.getElementById('isMainAddress').checked, latitude: document.getElementById('latitude').value, longitude: document.getElementById('longitude').value, province: document.getElementById('province') ? document.getElementById('province').value : '', city: document.getElementById('city') ? document.getElementById('city').value : '', district: document.getElementById('district') ? document.getElementById('district').value : '', subdistrict: document.getElementById('subdistrict') ? document.getElementById('subdistrict').value : '', postalCode: document.getElementById('postal-code') ? document.getElementById('postal-code').value : '' }; // Show loading state const saveButton = document.getElementById('nextBtn'); if (saveButton) { saveButton.disabled = true; saveButton.innerHTML = 'Menyimpan...'; } // Create form data for POST request const formData = new FormData(); Object.keys(addressData).forEach(key => { formData.append(key, addressData[key]); }); const csrfName = '<?php echo $this->security->get_csrf_token_name(); ?>'; const csrfHash = '<?php echo $this->security->get_csrf_hash(); ?>'; if (csrfName && csrfHash) { formData.append(csrfName, csrfHash); } // Send POST request fetch('<?php echo base_url('account/save_address'); ?>', { method: 'POST', body: formData, headers: { 'X-Requested-With': 'XMLHttpRequest' } }) .then(response => { if (!response.ok) { throw new Error('Network response was not ok'); } return response.json(); }) .then(data => { if (data.success) { notyf.success(data.message || 'Alamat berhasil disimpan!'); closeModal(); setTimeout(() => { location.reload(); }, 1000); } else { notyf.error(data.message || 'Gagal menyimpan alamat. Silakan coba lagi.'); } }) .catch(error => { console.error('Error:', error); notyf.error('Terjadi kesalahan. Silakan coba lagi.'); }) .finally(() => { if (saveButton) { saveButton.disabled = false; saveButton.innerHTML = 'Simpan Alamat <i class="fas fa-save"></i>'; } }); } // async function editAddress(address_id) { // try { // const response = await fetch(`<?= base_url('account/get_address_by_id/') ?>${address_id}`); // const data = await response.json(); // if (data.success) { // openEditModal(data.address); // } else { // notyf.error(data.message || 'Gagal mengambil data alamat'); // } // } catch (error) { // console.error('Error fetching address data:', error); // notyf.error('Terjadi kesalahan saat mengambil data alamat'); // } // } // Google Maps functions async function initMap() { try { const { Map } = await google.maps.importLibrary("maps"); const { AdvancedMarkerElement } = await google.maps.importLibrary("marker"); const defaultLocation = { lat: -6.194985, lng: 106.823070 }; map = new Map(document.getElementById('map'), { center: defaultLocation, zoom: 13, mapId: '1873c42fd77c25f9fad736e6', mapTypeControl: false, streetViewControl: false, fullscreenControl: false }); marker = new AdvancedMarkerElement({ map: map, position: defaultLocation, gmpDraggable: true, title: 'Drag untuk memilih lokasi' }); geocoder = new google.maps.Geocoder(); setupAutocomplete(); setupEventListeners(); } catch (error) { console.error('Error initializing map:', error); initMapFallback(); } } function initMapFallback() { const defaultLocation = { lat: -6.2088, lng: 106.8456 }; map = new google.maps.Map(document.getElementById('map'), { center: defaultLocation, zoom: 13, mapTypeControl: false, streetViewControl: false, fullscreenControl: false }); marker = new google.maps.Marker({ position: defaultLocation, map: map, draggable: true, title: 'Drag untuk memilih lokasi' }); geocoder = new google.maps.Geocoder(); setupAutocomplete(); setupEventListeners(); } function setupAutocomplete() { const searchInput = document.getElementById('addressSearch'); if (!searchInput) return; autocomplete = new google.maps.places.Autocomplete(searchInput, { componentRestrictions: { country: 'ID' }, fields: ['formatted_address', 'geometry', 'address_components', 'name'], }); autocomplete.addListener('place_changed', function() { const place = autocomplete.getPlace(); if (!place.geometry) { notyf.error('Alamat tidak ditemukan'); return; } selectedPlace = place; reverseGeocode(place.geometry.location); }); } function setupEventListeners() { if (marker.addListener) { marker.addListener('dragend', function() { let position; if (marker.position && marker.position.lat) { position = marker.position; } else { position = marker.getPosition(); } reverseGeocode(position); }); } if (map.addListener) { map.addListener('click', function(event) { if (marker.position !== undefined) { marker.position = event.latLng; } else { marker.setPosition(event.latLng); } reverseGeocode(event.latLng); }); } if (searchAddressInput) { searchAddressInput.addEventListener('input', function() { const query = this.value.toLowerCase().trim(); addressCards.forEach(card => { const label = card.querySelector('.shipping-label-text')?.textContent.toLowerCase() || ''; const name = card.querySelector('.shipping-recipient-name span')?.textContent.toLowerCase() || ''; const phone = card.querySelector('.shipping-recipient-phone span')?.textContent.toLowerCase() || ''; const addressText = card.querySelector('.shipping-address-main')?.textContent.toLowerCase() || ''; const matches = label.includes(query) || name.includes(query) || phone.includes(query) || addressText.includes(query); card.style.display = matches ? '' : 'none'; }); }); } } function getCurrentLocation() { if (navigator.geolocation) { navigator.geolocation.getCurrentPosition( function(position) { const userLocation = { lat: position.coords.latitude, lng: position.coords.longitude }; // Create a place object similar to autocomplete result geocoder.geocode({ location: userLocation }, function(results, status) { if (status === 'OK' && results[0]) { selectedPlace = { formatted_address: results[0].formatted_address, geometry: { location: userLocation }, address_components: results[0].address_components }; document.getElementById('addressSearch').value = results[0].formatted_address; reverseGeocode(selectedPlace.geometry.location); } }); }, function(error) { alert('Tidak dapat mengakses lokasi saat ini'); } ); } else { alert('Geolocation tidak didukung oleh browser ini'); } } function reverseGeocode(location) { geocoder.geocode({ location: location }, function(results, status) { if (status === 'OK' && results[0]) { // Update address details const components = results[0].address_components; let addressData = { province: '', city: '', district: '', subdistrict: '', postal_code: '' }; if (components) { components.forEach(function(component) { const types = component.types; if (types.includes('administrative_area_level_1')) { addressData.province = component.long_name; } else if (types.includes('administrative_area_level_2')) { addressData.city = component.long_name; } else if (types.includes('administrative_area_level_3')) { addressData.district = component.long_name; } else if (types.includes('administrative_area_level_4')) { addressData.subdistrict = component.long_name; } else if (types.includes('postal_code')) { addressData.postal_code = component.long_name; } }); } // Fill form fields document.getElementById('fullAddress').value = results[0].formatted_address; // PERBAIKAN KOORDINAT - Handle berbagai format location let lat, lng; // Cek apakah ini LatLng object dengan method lat() dan lng() if (typeof location.lat === 'function' && typeof location.lng === 'function') { lat = location.lat(); lng = location.lng(); } // Cek apakah ada property position (seperti di marker) else if (location.position && typeof location.position.lat === 'function') { lat = location.position.lat(); lng = location.position.lng(); } // Cek apakah ini object literal dengan property lat/lng else if (typeof location.lat === 'number' && typeof location.lng === 'number') { lat = location.lat; lng = location.lng; } // Cek apakah menggunakan latitude/longitude else if (typeof location.latitude === 'number' && typeof location.longitude === 'number') { lat = location.latitude; lng = location.longitude; } // Fallback - coba getPosition() jika ada else if (typeof location.getPosition === 'function') { const pos = location.getPosition(); lat = pos.lat(); lng = pos.lng(); } else { console.error('Unknown location format:', location); console.error('Available properties:', Object.keys(location)); return; } // Set nilai ke input field document.getElementById('latitude').value = lat; document.getElementById('longitude').value = lng; console.log('Coordinates successfully set:', { lat, lng, addressData }); // Fill other fields if (document.getElementById('province')) { document.getElementById('province').value = addressData.province; } if (document.getElementById('city')) { document.getElementById('city').value = addressData.city; } if (document.getElementById('district')) { document.getElementById('district').value = addressData.district; } if (document.getElementById('subdistrict')) { document.getElementById('subdistrict').value = addressData.subdistrict; } if (document.getElementById('postal-code')) { document.getElementById('postal-code').value = addressData.postal_code; } } else { console.error('Geocoding failed:', status); } }); } // Close modal when clicking outside document.getElementById('addressModal').addEventListener('click', function(e) { if (e.target === this) { closeModal(); } }); // Close modal with Escape key document.addEventListener('keydown', function(e) { if (e.key === 'Escape' && document.getElementById('addressModal').classList.contains('active')) { closeModal(); } }); </script>