auto-sync: 2026-05-05 00:30:01

This commit is contained in:
Stream
2026-05-05 00:30:02 +03:00
parent f47d36ad60
commit ea5e23f4fb
2 changed files with 77 additions and 37 deletions

View File

@@ -480,7 +480,7 @@ body {
.recon-radius-btn.active { background: #ff6600; color: #fff; border-color: #ff6600; font-weight: 600; }
/* ─── Фаза 4: Красивый маршрут ─────────────────────────────────────────── */
.scenic-dist-btn {
.scenic-km-btn {
flex: 1;
padding: 4px 0;
border: 1px solid #ccc;
@@ -490,8 +490,8 @@ body {
background: #f0f0f0;
transition: background 0.15s;
}
.scenic-dist-btn:hover { background: #e0e0e0; }
.scenic-dist-btn.active { background: #ff6600; color: #fff; border-color: #ff6600; font-weight: 600; }
.scenic-km-btn:hover { background: #e0e0e0; }
.scenic-km-btn.active { background: #ff6600; color: #fff; border-color: #ff6600; font-weight: 600; }
.scenic-poi-item {
display: flex; align-items: center; gap: 6px;

View File

@@ -1,23 +1,12 @@
// ─── Общее: деактивация всех режимов ────────────────────────────────────────────
function deactivateAllModes() {
if (routeMode) toggleRouteMode();
if (rulerMode) toggleRuler();
if (markerMode) toggleMarkerMode();
if (typeof reconMode !== 'undefined' && reconMode) toggleReconMode();
if (typeof linkMode !== 'undefined' && linkMode) toggleLinkMode();
if (typeof scenicMode !== 'undefined' && scenicMode) toggleScenicMode();
}
// ─── Общее: деактивация всех режимов ────────────────────────────────────────────
function deactivateAllModes() {
if (routeMode) { routeMode = false; document.getElementById('btn-route').classList.remove('active'); document.getElementById('route-panel').style.display = 'none'; clearRoute(); }
if (rulerMode) toggleRuler();
if (markerMode) toggleMarkerMode();
if (reconMode) toggleReconMode();
if (linkMode) toggleLinkMode();
if (scenicMode) toggleScenicMode();
if (typeof reconMode !== 'undefined' && reconMode) toggleReconMode();
if (typeof linkMode !== 'undefined' && linkMode) toggleLinkMode();
if (typeof scenicMode !== 'undefined' && scenicMode) toggleScenicMode();
if (window._map) window._map.getCanvas().style.cursor = '';
}
@@ -948,8 +937,6 @@ function initRouteClicks(map) {
if (!routeMode) return;
const { lng, lat } = e.lngLat;
// Режим добавления промежуточной точки
if (addingWaypoint) {
addingWaypoint = false;
@@ -1252,11 +1239,9 @@ function toggleLinkMode() {
linkMode = true;
btn.classList.add('active');
window._map.getCanvas().style.cursor = 'crosshair';
document.getElementById('route-panel').style.display = 'block';
document.querySelector('#route-panel > div:first-child').textContent = '🔗 Связка';
document.getElementById('route-status').textContent = 'Кликни первую точку';
document.getElementById('route-info').style.display = 'none';
document.getElementById('route-actions').style.display = 'none';
document.getElementById('link-panel').style.display = 'block';
document.getElementById('link-status').textContent = '1⃣ Кликни конец первого трека';
document.getElementById('link-cards').innerHTML = '';
} else {
btn.classList.remove('active');
window._map.getCanvas().style.cursor = '';
@@ -1275,7 +1260,7 @@ function addLinkPoint(lng, lat) {
linkMarkers.push(marker);
if (idx === 1) {
document.getElementById('route-status').textContent = 'Кликни вторую точку';
document.getElementById('link-status').textContent = '2Кликни начало второго трека';
} else if (idx >= 2) {
buildLinkRoute();
}
@@ -1283,7 +1268,7 @@ function addLinkPoint(lng, lat) {
async function buildLinkRoute() {
const map = window._map;
document.getElementById('route-status').textContent = '⏳ Ищу связку...';
document.getElementById('link-status').textContent = '⏳ Ищу связку...';
const basePath = window.location.pathname.replace(/\/[^/]*$/, '') || '';
try {
const resp = await fetch(`${basePath}/api/route`, {
@@ -1294,13 +1279,69 @@ async function buildLinkRoute() {
if (!resp.ok) throw new Error('Не найдена');
const data = await resp.json();
if (data.routes && data.routes.length > 0) {
renderRouteCards(data.routes, 'link');
document.getElementById('route-status').textContent = '✅ Связка найдена';
renderLinkCards(data.routes);
document.getElementById('link-status').textContent = '✅ Связка найдена';
} else {
document.getElementById('route-status').textContent = '❌ Грунтовая связка не найдена';
document.getElementById('link-status').textContent = '❌ Грунтовая связка не найдена';
}
} catch(e) {
document.getElementById('route-status').textContent = '❌ ' + e.message;
document.getElementById('link-status').textContent = '❌ ' + e.message;
}
}
function renderLinkCards(routes) {
const map = window._map;
const colors = ['#0066ff', '#00aa44', '#9933cc'];
const cardsEl = document.getElementById('link-cards');
cardsEl.innerHTML = '';
routes.forEach((r, i) => {
const geojson = { type: 'Feature', geometry: r.geometry, properties: {} };
const sid = `link-src-${i}`;
const lid = `link-line-${i}`;
if (map.getSource(sid)) map.removeSource(sid);
if (map.getLayer(lid)) map.removeLayer(lid);
map.addSource(sid, { type: 'geojson', data: geojson });
map.addLayer({
id: lid, type: 'line', source: sid,
paint: {
'line-color': colors[i % colors.length],
'line-width': i === 0 ? 5 : 3,
'line-opacity': i === 0 ? 0.9 : 0.5,
},
layout: { 'line-cap': 'round', 'line-join': 'round' }
});
const km = (r.distance / 1000).toFixed(0);
const time = formatDuration(r.duration);
const dirt = r.stats?.dirt_total_pct || '?';
const col = colors[i % colors.length];
const card = document.createElement('div');
card.className = 'route-card' + (i === 0 ? ' active' : '');
card.innerHTML = `
<div class="route-card-header">
<span class="route-color-dot" style="background:${col}"></span>
<span class="route-card-title">Вариант ${i+1}</span>
<span class="route-card-dist">${km} км</span>
<span class="route-card-time">${time}</span>
</div>
<div style="font-size:11px;color:#666">${dirt}% грунт</div>
`;
card.onclick = () => selectLinkRoute(i);
cardsEl.appendChild(card);
});
}
function selectLinkRoute(idx) {
const map = window._map;
document.querySelectorAll('#link-cards .route-card').forEach((c, i) => c.classList.toggle('active', i === idx));
// Highlight selected route
for (let i = 0; i < 3; i++) {
const lid = `link-line-${i}`;
if (map.getLayer(lid)) {
map.setPaintProperty(lid, 'line-width', i === idx ? 5 : 3);
map.setPaintProperty(lid, 'line-opacity', i === idx ? 0.9 : 0.5);
}
}
}
@@ -1309,15 +1350,14 @@ function clearLink() {
linkMarkers.forEach(m => m.remove());
linkMarkers = [];
const map = window._map;
// Remove route layers
for (let i = 0; i < 5; i++) {
const lid = `link-line-${i}`;
if (map.getLayer(lid)) map.removeLayer(lid);
const sid = `link-src-${i}`;
if (map.getSource(sid)) map.removeSource(sid);
}
document.getElementById('route-panel').style.display = 'none';
document.getElementById('route-cards').innerHTML = '';
document.getElementById('link-panel').style.display = 'none';
document.getElementById('link-cards').innerHTML = '';
}
// ─── Фаза 4: Красивый маршрут ────────────────────────────────────────────────
@@ -1345,12 +1385,12 @@ function toggleScenicMode() {
}
}
function setScenicDist(km) {
function setScenicKm(km) {
scenicTargetKm = km;
document.querySelectorAll('.scenic-dist-btn').forEach(b => {
b.classList.toggle('active', +b.textContent === km);
document.querySelectorAll('.scenic-km-btn').forEach(b => {
b.classList.toggle('active', +b.dataset.km === km);
});
const inp = document.getElementById('scenic-dist-input');
const inp = document.getElementById('scenic-custom-km');
if (inp) inp.value = km;
}