256 lines
7.4 KiB
JavaScript
256 lines
7.4 KiB
JavaScript
let map;
|
|
let markers = {};
|
|
let markerCount = 0;
|
|
let currentMapClickCoords = null;
|
|
|
|
// Initialize map and load markers
|
|
document.addEventListener('DOMContentLoaded', function() {
|
|
initMap();
|
|
loadMarkers();
|
|
setupModal();
|
|
});
|
|
|
|
function setupModal() {
|
|
const modal = document.getElementById('point-modal');
|
|
const addBtn = document.getElementById('add-point-btn');
|
|
const closeBtn = document.querySelector('.close');
|
|
const form = document.getElementById('point-form');
|
|
|
|
addBtn.onclick = function() {
|
|
openPointModal(null);
|
|
}
|
|
|
|
closeBtn.onclick = function() {
|
|
closePointModal();
|
|
}
|
|
|
|
window.onclick = function(event) {
|
|
if (event.target === modal) {
|
|
closePointModal();
|
|
}
|
|
}
|
|
|
|
form.onsubmit = function(e) {
|
|
e.preventDefault();
|
|
submitPointForm();
|
|
}
|
|
}
|
|
|
|
function openPointModal(coords) {
|
|
const modal = document.getElementById('point-modal');
|
|
const form = document.getElementById('point-form');
|
|
const latInput = document.getElementById('point-latitude');
|
|
const lngInput = document.getElementById('point-longitude');
|
|
const nameInput = document.getElementById('point-name');
|
|
const formInfo = document.getElementById('form-info');
|
|
const modalTitle = document.getElementById('modal-title');
|
|
|
|
form.reset();
|
|
currentMapClickCoords = coords;
|
|
|
|
if (coords) {
|
|
latInput.value = coords.lat.toFixed(6);
|
|
lngInput.value = coords.lng.toFixed(6);
|
|
latInput.readOnly = true;
|
|
lngInput.readOnly = true;
|
|
modalTitle.textContent = 'Create Point';
|
|
formInfo.textContent = '✓ Coordinates auto-filled from map click. Just add a name!';
|
|
formInfo.classList.add('show');
|
|
nameInput.focus();
|
|
} else {
|
|
latInput.value = '';
|
|
lngInput.value = '';
|
|
latInput.readOnly = false;
|
|
lngInput.readOnly = false;
|
|
modalTitle.textContent = 'Add New Point';
|
|
formInfo.classList.remove('show');
|
|
nameInput.focus();
|
|
}
|
|
|
|
modal.classList.add('show');
|
|
}
|
|
|
|
function closePointModal() {
|
|
const modal = document.getElementById('point-modal');
|
|
modal.classList.remove('show');
|
|
currentMapClickCoords = null;
|
|
}
|
|
|
|
function submitPointForm() {
|
|
const name = document.getElementById('point-name').value.trim();
|
|
const latitude = parseFloat(document.getElementById('point-latitude').value);
|
|
const longitude = parseFloat(document.getElementById('point-longitude').value);
|
|
const open_24_hours = document.getElementById('point-24hours').checked ? 1 : 0;
|
|
|
|
// Validate inputs
|
|
if (!name) {
|
|
showNotification('Please enter a name for the point', true);
|
|
return;
|
|
}
|
|
|
|
if (isNaN(latitude) || latitude < -90 || latitude > 90) {
|
|
showNotification('Please enter a valid latitude (-90 to 90)', true);
|
|
return;
|
|
}
|
|
|
|
if (isNaN(longitude) || longitude < -180 || longitude > 180) {
|
|
showNotification('Please enter a valid longitude (-180 to 180)', true);
|
|
return;
|
|
}
|
|
|
|
addMarker(name, latitude, longitude, open_24_hours);
|
|
}
|
|
|
|
function initMap() {
|
|
// Create map centered on a default location (San Francisco)
|
|
map = L.map('map').setView([37.7749, -122.4194], 13);
|
|
|
|
// Add OpenStreetMap tile layer
|
|
L.tileLayer('https://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png', {
|
|
attribution: '© OpenStreetMap contributors',
|
|
maxZoom: 19
|
|
}).addTo(map);
|
|
|
|
// Handle map click to add marker with auto-filled coordinates
|
|
map.on('click', function(e) {
|
|
openPointModal({
|
|
lat: e.latlng.lat,
|
|
lng: e.latlng.lng
|
|
});
|
|
});
|
|
}
|
|
|
|
function addMarker(name, lat, lng, open_24_hours) {
|
|
// Save to database
|
|
fetch('api/save_point.php', {
|
|
method: 'POST',
|
|
headers: {
|
|
'Content-Type': 'application/json',
|
|
},
|
|
body: JSON.stringify({
|
|
name: name,
|
|
latitude: lat,
|
|
longitude: lng,
|
|
open_24_hours: open_24_hours
|
|
})
|
|
})
|
|
.then(response => response.json())
|
|
.then(data => {
|
|
if (data.success) {
|
|
displayMarker(data.id, data.name, data.latitude, data.longitude, data.open_24_hours);
|
|
updateMarkerCount();
|
|
showNotification('✓ Point added successfully');
|
|
closePointModal();
|
|
} else {
|
|
showNotification('Error adding point: ' + data.error, true);
|
|
}
|
|
})
|
|
.catch(error => {
|
|
console.error('Error:', error);
|
|
showNotification('Error adding point', true);
|
|
});
|
|
}
|
|
|
|
function displayMarker(id, name, lat, lng, open_24_hours) {
|
|
const marker = L.marker([lat, lng]).addTo(map);
|
|
|
|
const hoursText = open_24_hours ? '🕐 Open 24 Hours' : '🕐 Limited Hours';
|
|
const popupContent = `
|
|
<div class="marker-popup">
|
|
<div class="marker-popup-name">${escapeHtml(name)}</div>
|
|
<div class="marker-popup-hours">${hoursText}</div>
|
|
<div class="marker-popup-info">
|
|
<span>Lat: ${lat.toFixed(4)}</span><br>
|
|
<span>Lng: ${lng.toFixed(4)}</span>
|
|
</div>
|
|
<button onclick="deleteMarker(${id})">Delete</button>
|
|
</div>
|
|
`;
|
|
|
|
marker.bindPopup(popupContent);
|
|
markers[id] = marker;
|
|
markerCount++;
|
|
}
|
|
|
|
function loadMarkers() {
|
|
fetch('api/get_points.php')
|
|
.then(response => response.json())
|
|
.then(data => {
|
|
if (data.success && data.markers) {
|
|
data.markers.forEach(marker => {
|
|
displayMarker(
|
|
marker.id,
|
|
marker.name,
|
|
marker.latitude,
|
|
marker.longitude,
|
|
marker.open_24_hours
|
|
);
|
|
});
|
|
updateMarkerCount();
|
|
}
|
|
})
|
|
.catch(error => console.error('Error loading markers:', error));
|
|
}
|
|
|
|
function deleteMarker(id) {
|
|
if (!confirm('Are you sure you want to delete this point?')) {
|
|
return;
|
|
}
|
|
|
|
fetch('api/delete_point.php', {
|
|
method: 'DELETE',
|
|
headers: {
|
|
'Content-Type': 'application/json',
|
|
},
|
|
body: JSON.stringify({ id: id })
|
|
})
|
|
.then(response => response.json())
|
|
.then(data => {
|
|
if (data.success) {
|
|
if (markers[id]) {
|
|
map.removeLayer(markers[id]);
|
|
delete markers[id];
|
|
markerCount--;
|
|
updateMarkerCount();
|
|
showNotification('✓ Point deleted');
|
|
}
|
|
} else {
|
|
showNotification('Error deleting point: ' + data.error, true);
|
|
}
|
|
})
|
|
.catch(error => {
|
|
console.error('Error:', error);
|
|
showNotification('Error deleting point', true);
|
|
});
|
|
}
|
|
|
|
function updateMarkerCount() {
|
|
const count = Object.keys(markers).length;
|
|
const countElement = document.getElementById('marker-count');
|
|
if (countElement) {
|
|
countElement.textContent = count;
|
|
}
|
|
}
|
|
|
|
function showNotification(message, isError = false) {
|
|
const notification = document.createElement('div');
|
|
notification.className = 'notification' + (isError ? ' error' : '');
|
|
notification.textContent = message;
|
|
document.body.appendChild(notification);
|
|
|
|
setTimeout(() => {
|
|
notification.remove();
|
|
}, 3000);
|
|
}
|
|
|
|
function escapeHtml(text) {
|
|
const map = {
|
|
'&': '&',
|
|
'<': '<',
|
|
'>': '>',
|
|
'"': '"',
|
|
"'": '''
|
|
};
|
|
return text.replace(/[&<>"']/g, m => map[m]);
|
|
}
|