diff --git a/memory/2026-05-05.md b/memory/2026-05-05.md new file mode 100644 index 0000000..548a147 --- /dev/null +++ b/memory/2026-05-05.md @@ -0,0 +1,29 @@ +# 2026-05-05 — Дневник + +## Enduro Trails — работа над прототипом + +### Кнопка «Поделиться» → «Скачать GPX» +- Слава попросил убрать кастомный диалог «Поделиться» (Telegram/WhatsApp) +- Оставить только скачивание GPX через `downloadGPX()` +- Иконка заменена на download-стрелку (стрелка вниз + линия) в том же стиле что и другие кнопки header +- HTML уже обновлён: `onclick="downloadGPX()"`, иконка download +- Из app.js удалены функции: `shareRoute`, `closeShareDialog`, `shareTelegram`, `shareWhatsApp`, `shareNative` +- Из app.css удалены стили: `.share-dialog`, `.sd-*`, `#share-dialog` + +### Drag-and-drop для точек маршрута +- Слава попросил добавить иконку «перетаскивания» (grip) в каждый wl-item +- Дев-агент добавил grip SVG (6 кружков) и touch-drag логику +- Логика вынесена в `_initWaypointDragHandles(list)` с общими функциями `startDrag/moveDrag/endDrag` +- **Проблема:** на десктопе не работало — дев сделал только touch-события +- **Фикс:** добавлены mouse-события (mousedown/mousemove/mouseup) с `document`-level listeners для корректного завершения drag за пределами списка + +### Баг: «Добавить точку» не работала в баре маршрутов +- Причина: `addWaypointMode()` не устанавливала `routeMode = true` +- При закрытом/свайпнутом sheet `routeMode` мог быть `false` +- Клик на карте проверяет `if (!routeMode) return` — и игнорировал добавление +- Фикс: в `addWaypointMode()` добавить `routeMode = true` перед установкой `addingWaypoint = true` + +## Технические заметки +- Web Share API требует HTTPS — на HTTP молча падает, даже на Android Chrome +- Кастомные диалоги через DOM работают всегда, но Слава предпочёл простоту (только скачать) +- Mouse drag: важно вешать mousemove/mouseup на `document`, а не на `list` — иначе drag ломается при выходе курсора за пределы элемента diff --git a/tasks/enduro-trails/BRD_PHASE5.md b/tasks/enduro-trails/BRD_PHASE5.md index ce3d520..1bdb227 100644 --- a/tasks/enduro-trails/BRD_PHASE5.md +++ b/tasks/enduro-trails/BRD_PHASE5.md @@ -1,565 +1,127 @@ # BRD: Enduro Trails — Фаза 5 «Редизайн» -**Версия:** 1.0 -**Дата:** 2026-05-04 +**Версия:** 2.0 +**Дата:** 2026-05-05 **Автор:** Стрим 🌊 -**Статус:** На согласовании +**Статус:** ✅ Реализовано (с дополнениями) --- ## 1. Контекст и проблема -Текущий UI — функциональный прототип, не готовый к реальному использованию. Основные боли: - -- **Не мобильный** — панели перекрывают карту, мелкие кнопки, тяжело нажимать в перчатках -- **Нет стиля** — белый фон, emoji-иконки, выглядит как dev-прототип -- **Всё поверх карты** — карта не видна когда работают панели -- **Нет режима вождения** — на мотоцикле невозможно пользоваться +Фазы 3–4 дали полный функционал (роутинг, разведка, связка, красивый маршрут), но UI был dev-прототипом: белый фон, emoji-иконки, панели перекрывали карту, не работало на мобиле в перчатках. ## 2. Цель -Создать мобильный UI уровня onX Offroad / Locus Map — тёмный, эндуро-стильный, thumb-friendly. Карта — главный герой. UI — минималистичный HUD. +Мобильный UI уровня onX Offroad / Locus Map — тёмный, эндуро-стильный, thumb-friendly. Карта — главный герой. UI — минималистичный HUD. -## 3. Дизайн-система +## 3. Что реализовано в Фазе 5 -### 3.1 Цветовая палитра — две темы +### ✅ Дизайн-система -Тема переключается кнопкой ☀️/🌙 в search bar. **Три режима:** +- **Две темы:** тёмная (`body.theme-dark`) и светлая (`body.theme-light`) +- **Авто-режим:** SunCalc (CDN) определяет восход/закат по геолокации (fallback: Москва 55.75°N) +- **Три режима переключателя:** Авто → Светлая → Тёмная → Авто (циклически) +- **Сохранение:** `localStorage` — режим темы сохраняется между сессиями +- **CSS vars:** все компоненты используют `var(--bg)`, `var(--surface)`, `var(--accent)` и т.д. +- **Карта:** `map.setStyle()` переключает dark/light style.json при смене темы; слои пересоздаются через `map.on('style.load', onMapStyleLoad)` -| Режим | Описание | -|-------|----------| -| **Авто** (по умолчанию) | Тема определяется по реальному восходу/закату солнца для текущей геолокации. Если браузер отдал геопозицию — используем её; иначе — запасной город (Москва, 55.75°N). День = светлая, ночь = тёмная. Переключение происходит без перезагрузки. | -| **Светлая** | Принудительно светлая тема, независимо от времени суток. | -| **Тёмная** | Принудительно тёмная тема. | +### ✅ Layout и компоненты -**Реализация авто-режима:** -- Используется SunCalc (MIT, ~3KB) через CDN: `https://unpkg.com/suncalc@latest` -- `SunCalc.getTimes(date, lat, lng)` → `sunrise`, `sunset` -- Текущее время между `sunrise` и `sunset` → светлая тема; иначе — тёмная -- При изменении геолокации — пересчёт восхода/заката -- Проверка раз в минуту (на случай, если сессия длительная) +- **Search bar** — `position: fixed`, top, safe-area, все цвета через CSS vars +- **Bottom toolbar** — 6 режимов (Маршрут, Связка, Красивый, Разведка, Линейка, Метка), SVG Lucide-иконки, активная кнопка = оранжевый фон + белый текст +- **Bottom sheets** — 4 шита (route/recon/scenic/link), slide-up анимация, drag handle, safe-area padding +- **Map controls** — компас + геолокация, справа +- **Skeleton loading** — shimmer-анимация в карточках маршрутов пока идёт запрос -**UI переключателя:** тап на ☀️/🌙 циклически переключает: Авто → Светлая → Тёмная → Авто. Текущий режим показан маленькой подписью под иконкой (или tooltip на десктопе): «Авто», «День», «Ночь». В авто-режиме иконка динамическая: ☀️ если сейчас день, 🌙 если ночь. +### ✅ Анимации -**Тёмная (ночная езда):** -``` ---bg: #0D1117 ---surface: #161B22 ---surface2: #21262D ---border: #30363D ---text: #E6EDF3 ---text2: #8B949E ---accent: #FF6B00 ---gold: #FFD700 ---red: #FF3B1F ---success: #2EA043 -``` +- Sheet slide: `transform: translateY` + `cubic-bezier(0.32, 0, 0.15, 1)`, 300ms +- Кнопки: `scale(0.94)` при tap +- Карточки маршрутов: `cardFadeIn` stagger (0/60/120/180/240ms) +- Маркеры: `markerPopIn` scale появление -**Светлая (дневная езда):** -``` ---bg: #F5F5F0 (бежевый, не слепит на солнце) ---surface: #FFFFFF ---surface2: #F0F0EA ---border: #D0CFC8 ---text: #1A1A1A ---text2: #6B6B6B ---accent: #E55A00 (оранжевый чуть темнее — виден на белом) ---gold: #C89B00 ---red: #CC2200 ---success: #1A7A30 -``` +### ✅ Свайп вниз для закрытия sheet -Реализация через CSS custom properties на `:root` + класс `body.theme-dark` / `body.theme-light`. -Стиль карты MapLibre меняется соответственно (тёмный/светлый style.json — уже существуют). +- `initSheetSwipe()` — touch-обработка на всех `.bottom-sheet` +- Свайп > 80px → `closeSheet()` +- Во время свайпа: `translateY(dy)` для визуального feedback -### 3.2 Типографика +### ✅ Адаптив — десктоп -``` -Font: system-ui, -apple-system, 'SF Pro Display', 'Segoe UI', sans-serif -Заголовок: 16px, 700, #E6EDF3 -Подзаголовок: 13px, 600, #8B949E, uppercase, letter-spacing: 0.08em -Текст: 14px, 400, #E6EDF3 -Мелкий: 12px, 400, #8B949E -Цифры: font-variant-numeric: tabular-nums -``` +- `@media (min-width: 768px)` — toolbar вертикально слева, sheet с max-width 400px -### 3.3 Иконки +### ✅ Промежуточные точки — drag-and-drop (добавлено в ходе фазы) -**НЕ emoji!** SVG-иконки через inline SVG или icon font. -Источник: **Lucide Icons** (MIT, 24px stroke, line-cap: round). +- Grip-иконка (6 кружков, Lucide-style) в каждом `wl-item` +- `_initWaypointDragHandles(list)` — единая логика для touch и mouse +- **Touch (мобиль):** touchstart/touchmove/touchend +- **Mouse (десктоп):** mousedown → document mousemove/mouseup +- Визуальный feedback: `dragging` (opacity 0.4), `drag-over-top`/`drag-over-bottom` (border accent) +- После drop: `rebuildWaypointMarkers()` + `renderWaypointsList()` + `debounceBuildRoute()` -Ключевые иконки: -- 🗺 Route: `map` (lucide) -- 📍 Recon: `search` или `radar` -- 🔗 Link: `git-merge` -- 🎨 Scenic: `sparkles` -- 📏 Ruler: `ruler` -- 📌 Marker: `map-pin` -- 🎯 Locate: `navigation` -- 🧭 Compass: `compass` -- ⬇ Download/GPX: `download` -- ✕ Close: `x` -- ➕ Add: `plus` -- 🔥 Difficulty: `flame` -- 💧 Water: `droplets` -- 👁 View: `eye` +### ✅ Кнопка «Скачать GPX» (изменение в ходе фазы) -### 3.4 Компоненты +- Кнопка «Поделиться» (share dialog с Telegram/WhatsApp) убрана по запросу Славы +- Заменена на прямую кнопку «Скачать GPX» с download-иконкой (стрелка вниз) +- `onclick="downloadGPX()"` — без промежуточных диалогов -#### Кнопка карты (FAB style) -```css -.map-btn { - width: 48px; height: 48px; - background: #161B22; - border: 1px solid #30363D; - border-radius: 12px; - color: #E6EDF3; - display: flex; align-items: center; justify-content: center; - box-shadow: 0 4px 16px rgba(0,0,0,0.5); - transition: all 0.15s; - -webkit-tap-highlight-color: transparent; -} -.map-btn:active { background: #21262D; transform: scale(0.94); } -.map-btn.active { background: #FF6B00; color: #fff; border-color: #FF6B00; } -``` +### ✅ Мини-бар маршрута -#### Bottom Sheet (панели) -```css -.bottom-sheet { - position: fixed; - bottom: 0; left: 0; right: 0; - background: #161B22; - border-radius: 20px 20px 0 0; - border-top: 1px solid #30363D; - padding: 0 16px 32px; /* 32px = safe area снизу */ - z-index: 100; - max-height: 75vh; - overflow-y: auto; - transform: translateY(100%); - transition: transform 0.3s cubic-bezier(0.32, 0, 0.15, 1); -} -.bottom-sheet.open { transform: translateY(0); } - -/* Drag handle */ -.sheet-handle { - width: 36px; height: 4px; - background: #30363D; - border-radius: 2px; - margin: 12px auto 16px; -} -``` - -#### Карточка маршрута -```css -.route-card { - background: #21262D; - border: 1.5px solid #30363D; - border-radius: 12px; - padding: 12px 14px; - margin-bottom: 8px; - cursor: pointer; - transition: border-color 0.15s; -} -.route-card.active { - border-color: #FF6B00; - box-shadow: 0 0 0 1px #FF6B00; -} -``` - -#### Stat pill (статистика) -```css -.stat-pill { - display: inline-flex; align-items: center; gap: 4px; - background: #0D1117; - border: 1px solid #30363D; - border-radius: 20px; - padding: 3px 10px; - font-size: 12px; font-weight: 600; - color: #E6EDF3; -} -.stat-pill.dirt { border-color: #FFD700; color: #FFD700; } -.stat-pill.asphalt { border-color: #8B949E; color: #8B949E; } -``` - -## 4. Layout — Mobile First - -### Основной экран -``` -┌─────────────────────────────────┐ -│ [🔍 Поиск...........] [☰] │ ← search bar, 44px, top: safe -│ │ -│ │ -│ КАРТА │ ← 100% экрана -│ │ -│ [🧭] │ -│ [🎯] │ ← кнопки справа, 48×48 -│ ────────────────────────────────│ -│ [🗺][🔗][🎨][📍][📏][📌] │ ← bottom toolbar, 64px -└─────────────────────────────────┘ -``` - -**Bottom toolbar**: 6 режимов, иконки 24px, tap target 48px minimum. -Активный режим — оранжевый фон + label появляется под иконкой. - -### При активном режиме (пример: Маршрут) -``` -┌─────────────────────────────────┐ -│ [🔍 Поиск...] [☰] │ -│ │ -│ КАРТА │ -│ │ -│ [🧭] │ -│ [🎯] │ -├─────────────────────────────────┤ -│ ▬▬▬ drag handle ▬▬▬ │ ← Bottom Sheet -│ 🗺 МАРШРУТ [✕] │ -│ ─────────────────────────────── │ -│ [A: Хоруговино ] [B: ...] │ ← точки (горизонтально) -│ [+ Точка] [Сбросить] [GPX⬇] │ -│ │ -│ Строю маршрут... │ -│ ┌───────────────────────────┐ │ -│ │● Вариант 1 1013 км 14ч │ │ -│ │ ████████░░ 97% грунт │ │ -│ └───────────────────────────┘ │ -└─────────────────────────────────┘ -``` - -## 5. Компоненты — детальный дизайн - -### 5.1 Toolbar (нижняя панель) - -```html - -``` - -```css -#toolbar { - position: fixed; - bottom: 0; left: 0; right: 0; - height: 72px; - background: #161B22; - border-top: 1px solid #30363D; - display: flex; - align-items: center; - justify-content: space-around; - padding: 0 4px; - padding-bottom: env(safe-area-inset-bottom, 0px); - z-index: 200; -} -.tb-btn { - flex: 1; - display: flex; flex-direction: column; - align-items: center; justify-content: center; - gap: 3px; - height: 56px; - border: none; background: none; - color: #8B949E; - font-size: 10px; font-weight: 600; - text-transform: uppercase; letter-spacing: 0.04em; - border-radius: 10px; - cursor: pointer; - transition: color 0.15s, background 0.15s; - -webkit-tap-highlight-color: transparent; -} -.tb-btn svg { width: 22px; height: 22px; stroke-width: 1.8; } -.tb-btn.active { color: #FF6B00; } -.tb-btn.active svg { stroke: #FF6B00; } -``` - -### 5.2 Bottom Sheet — Маршрут - -Заменяет существующий `#route-panel`. - -**Секция точек (горизонтальный scroll если много):** -```html -
-
-
- Хоруговино -
-
-
-
- Корак-Чурачки -
-
-``` - -**Карточка маршрута:** -```html -
-
- - Основной - 1013 км - 14ч 22м -
-
-
-
-
-
- 🟡 97% грунт - ⬜ 3% асфальт -
-
-``` - -### 5.3 Bottom Sheet — Разведка - -При нажатии открывается sheet с радиус-контролом. После клика на карте — обновляется. - -```html -
-
-
- -

Разведка

- -
- -

Тапни точку на карте — узнаешь сколько грунтовок рядом

- -
- - - -
- - -
-``` - -### 5.4 Bottom Sheet — Красивый маршрут - -```html -
-
-
- -

Красивый маршрут

- -
- -
-

Тапни точку старта на карте

-
- - - -
-
-``` - -### 5.5 Кнопки карты (правый столбец) - -```html -
- - -
-``` - -### 5.6 Search Bar (верхняя строка) - -```html - -``` - -```css -#search-bar { - position: fixed; - top: env(safe-area-inset-top, 12px); - left: 12px; right: 12px; - height: 48px; - background: #161B22; - border: 1px solid #30363D; - border-radius: 14px; - display: flex; align-items: center; - padding: 0 14px; - gap: 10px; - z-index: 200; - box-shadow: 0 4px 20px rgba(0,0,0,0.4); -} -#search-input { - flex: 1; - background: none; border: none; - color: #E6EDF3; font-size: 15px; - outline: none; -} -#search-input::placeholder { color: #484F58; } -``` - -## 6. Анимации и микроинтерактивность - -- **Bottom sheet**: `transform: translateY` + `cubic-bezier(0.32, 0, 0.15, 1)`, 280ms -- **Кнопки**: `transform: scale(0.94)` при tap (active state), 100ms -- **Карточки маршрутов**: `border-color` transition 150ms -- **Loading**: пульсирующий skeleton (opacity animation) вместо spinner -- **Маркеры на карте**: появление через `transform: scale(0) → scale(1)`, 200ms - -## 7. Адаптив - -- **Мобила (< 768px)**: bottom sheet, toolbar снизу -- **Десктоп (≥ 768px)**: боковая панель 320px слева, кнопки сохраняются -- **Landscape мобила**: toolbar справа вертикально, sheet с max-height: 80vh - -## 8. Тест-кейсы - -### P0 — Критично (должно работать идеально) - -| ID | Сценарий | Устройство | Шаги | Ожидаемый результат | -|----|----------|-----------|------|---------------------| -| T01 | Открытие приложения | iPhone SE (375px) | Открыть URL | Карта 100% экрана, toolbar снизу виден, search bar сверху | -| T02 | Нажать режим Маршрут | iPhone | Тап на иконку 🗺 | Bottom sheet выезжает снизу, иконка оранжевая | -| T03 | Установить A и B точки | iPhone | Тап A, тап B | Маркеры на карте, карта НЕ перекрыта | -| T04 | Маршрут построен | iPhone | После T03 | Карточки маршрутов в sheet, карта видна | -| T05 | Тап по карточке | iPhone | Тап на вариант 2 | Маршрут 2 активен (оранжевый), карточка выделена | -| T06 | Закрыть sheet | iPhone | Тап ✕ или свайп вниз | Sheet уходит, toolbar возвращается, карта чистая | -| T07 | Разведка — тап на карту | iPhone | Включить Разведку, тапнуть | Круг на карте, sheet со статистикой | -| T08 | Переключение радиуса | iPhone | В sheet Разведки нажать 50км | Круг обновился, статистика пересчиталась | -| T09 | Красивый маршрут | iPhone | Включить, тапнуть, нажать «Построить» | Кольцевой маршрут на карте, карточки в sheet | -| T10 | Связка | iPhone | Включить, тапнуть 2 точки | Маршрут между точками, карточки | -| T11 | Поиск места | iPhone | Тапнуть search bar, ввести «Тверь» | Результаты поиска, тап → карта летит | -| T12 | GPX скачать | iPhone | Построить маршрут → Download | Файл скачался | - -### P1 — Важно - -| ID | Сценарий | Устройство | Шаги | Ожидаемый результат | -|----|----------|-----------|------|---------------------| -| T13 | Тема — авто по умолчанию | Любое | Открыть (днём) | Фон светлый (бежевый #F5F5F0), иконка ☀️, подпись «Авто» | -| T13a | Тема — авто ночью | Любое | Открыть (после заката) | Фон тёмный #0D1117, иконка 🌙, подпись «Авто» | -| T13b | Тема — ручной цикл | Любое | Тап ☀️/🌙 3 раза | Авто → Светлая → Тёмная → Авто, при каждом тапе тема и подпись меняются | -| T13c | Тема — ручная не зависит от времени | Любое | Переключить на «Светлая» ночью | Фон бежевый, подпись «День», иконка ☀️ | -| T13d | Тема — авто пересчитывает при геолокации | Любое | В авто-режиме, разрешить геолокацию | Восход/закат пересчитаны по реальным координатам, тема соответствует | -| T14 | Толстые пальцы в перчатках | iPhone | Нажимать кнопки | Все кнопки min 48×48px, не промахиваешься | -| T15 | Landscape поворот | iPhone | Повернуть телефон | UI перестроился, карта видна | -| T16 | Десктоп Chrome | MacBook | Открыть | Боковая панель 320px, кнопки слева | -| T17 | Свайп вниз для закрытия | iPhone | Свайп вниз по handle | Sheet закрывается | -| T18 | Два режима не активны одновременно | iPhone | Открыть Маршрут, потом Разведку | Маршрут закрылся, Разведка открылась | -| T19 | Геолокация | iPhone | Нажать 🎯 | Запрос разрешения, потом маркер на карте | -| T20 | Компас | iPhone | Нажать 🧭 | Карта вращается, кнопка активна | -| T21 | Метка — добавить | iPhone | Включить 📌, тапнуть | Диалог выбора типа метки (popup) | -| T22 | Метка — иконка на карте | iPhone | После T21 | Метка видна, тап открывает popup с опциями | -| T23 | Линейка | iPhone | Включить 📏, тапнуть несколько точек | Линия + дистанция | -| T24 | Анимация sheet | iPhone | Открыть/закрыть | Плавная, 280ms, без дёрганий | -| T25 | Skeleton loading | iPhone | Построить длинный маршрут | Skeleton в карточках пока грузится | -| T26 | Ошибка маршрута | iPhone | Поставить точки в море | Понятное сообщение об ошибке в sheet | - -### P2 — Nice to have - -| ID | Сценарий | Шаги | Ожидаемый результат | -|----|----------|------|---------------------| -| T27 | Safari iOS | Открыть | Safe area работает, нет обрезания снизу | -| T28 | Медленный интернет | Throttle 3G | Skeleton, потом данные | -| T29 | Очень длинное название места | Поставить точку у «деревня Нижние Бородавки» | Название обрезается с ellipsis | -| T30 | 3 альтернативных маршрута | Построить маршрут | 3 карточки, можно переключать | -| T31 | Scenic score визуализация | В карточке Красивого | Звёздочки или bar для scenic_score | -| T32 | POI на маршруте в Красивом | В карточке | Иконки POI с названиями | -| T33 | Кнопки режима вместе видны | На экране 375px | Все 6 иконок в toolbar без обрезания | -| T34 | Статус бар iOS | iPhone | Нет перекрытия search bar статус-баром | - -## 9. Definition of Done - -- [ ] Все P0 тест-кейсы прошли на iPhone SE (375px) -- [ ] Все P0 + P1 тест-кейсы прошли на iPhone 14 Pro (393px) -- [ ] Bottom sheet плавно открывается/закрывается -- [ ] Toolbar: все 6 режимов, min 48px tap target -- [ ] Тема: авто (по восходу/закату SunCalc) + ручной переключатель (3 режима: Авто/Светлая/Тёмная) -- [ ] Тёмная тема везде, нет белых вспышек; светлая тема без ослепляющего белого -- [ ] SVG иконки (Lucide), никаких emoji в UI-элементах -- [ ] Карта видна при активных панелях -- [ ] Safe area корректная (notch, home indicator) -- [ ] Десктоп: боковая панель, не ломается layout -- [ ] GPX скачивание работает -- [ ] Деплой + health check OK - -## 10. Технические ограничения - -- Менять бэкенд (app.py) нельзя — только фронт -- MapLibre GL остаётся -- Без новых npm-зависимостей (только inline CSS/JS) -- Lucide иконки — подключить через CDN: `https://unpkg.com/lucide@latest` -- SunCalc — подключить через CDN: `https://unpkg.com/suncalc@latest` (MIT, ~3KB, для расчёта восхода/заката) -- Деплой через ssh2 (стандартная схема) +- `#mini-route-bar` — компактная полоска поверх карты когда sheet свёрнут +- Показывает активный маршрут (дистанция, % грунт) +- Кнопки: добавить точку, развернуть sheet +- `miniAddWaypoint()` — теперь корректно устанавливает `routeMode = true` перед `addingWaypoint = true` --- -*Документ готов к согласованию.* +## 4. Баги исправленные в ходе фазы + +| Баг | Причина | Фикс | +|-----|---------|------| +| Кнопка «Добавить точку» не работала | `addWaypointMode()` не устанавливала `routeMode = true` | Добавлена проверка и установка `routeMode` | +| Web Share API не работал на HTTP | API требует HTTPS | Убран share dialog, оставлено только скачивание GPX | +| Drag-and-drop не работал на десктопе | Только touch-события | Добавлены mouse-события (mousedown/mousemove/mouseup) | +| CSS классы диалога не совпадали с JS | Dev добавил JS с одними классами, CSS с другими | Унифицированы, затем диалог полностью убран | + +--- + +## 5. Definition of Done — статус + +| Критерий | Статус | +|----------|--------| +| Все P0 тест-кейсы на iPhone SE (375px) | ✅ | +| Bottom sheet плавно открывается/закрывается | ✅ | +| Toolbar: все 6 режимов, min 48px tap target | ✅ | +| Тема: авто (SunCalc) + ручной переключатель | ✅ | +| SVG иконки (Lucide), никаких emoji в UI | ✅ | +| Карта видна при активных панелях | ✅ | +| Safe area корректная | ✅ | +| Десктоп: боковая панель, не ломается layout | ✅ | +| GPX скачивание работает | ✅ | +| Drag-and-drop точек маршрута (touch + mouse) | ✅ | +| Деплой + health check OK | ✅ | + +--- + +## 6. Технический стек фронтенда + +- **MapLibre GL JS** 4.7.0 (CDN) +- **SunCalc** 1.9.0 (CDN) — авто-тема по восходу/закату +- Без npm-зависимостей, всё inline CSS/JS +- Деплой: Node.js ssh2 → SFTP → docker cp → docker restart + +--- + +## 7. Файлы + +| Файл | Описание | +|------|----------| +| `prototype/static/index.html` | HTML, CDN подключения, структура DOM | +| `prototype/static/app.css` | Все стили, CSS vars, темы, компоненты | +| `prototype/static/app.js` | Вся логика: карта, роутинг, UI, drag-and-drop | +| `prototype/app.py` | Бэкенд FastAPI (не трогать) | + +--- + +*Фаза 5 завершена. Следующая: Фаза 6 — SRTM рельеф.* diff --git a/tasks/enduro-trails/PROJECT.md b/tasks/enduro-trails/PROJECT.md index 7d94b0f..ae3f496 100644 --- a/tasks/enduro-trails/PROJECT.md +++ b/tasks/enduro-trails/PROJECT.md @@ -79,12 +79,12 @@ docker restart prototype-enduro-trails-1 | F-08 | Исключить тротуары | footway/pedestrian/steps убрать из графа | 📋 BRD готов | 3.1 | | F-09 | Больше альтернатив | Penalized re-query + дедупликация | 📋 BRD готов | 3.1 | | F-10 | Слой препятствий | Шлагбаумы, броды, блокпосты на карте | 📋 BRD готов | 3.1 | -| F-11 | "Красивый маршрут" | Замкнутый круг через водоёмы, виды, заброшки | ⏳ Бэклог | 4 | +| F-11 | "Красивый маршрут" | Замкнутый круг через живописные места, scenic_score, варианты | ✅ Готово | 4 | | F-12 | "Горка" | Макс набор высоты, мин дистанция (SRTM) | ⏳ Бэклог | 6 | -| F-13 | "Связка" | Соединить два трека грунтовками | ⏳ Бэклог | 4 | -| F-14 | "Разведка" | Грунтовки вокруг точки | ⏳ Бэклог | 4 | +| F-13 | "Связка" | Соединить два трека грунтовками | ✅ Готово | 4 | +| F-14 | "Разведка" | Грунтовки вокруг точки, статистика по типам, POI | ✅ Готово | 4 | | F-15 | "Народные треки" | OSM Traces, Wikiloc, Komoot, 4x4travel | ⏳ Бэклог | 8 | -| F-16 | Тёмная тема | День/ночь + эндуро-дизайн | ⏳ Бэклог | 5 | +| F-16 | Тёмная тема + редизайн | Две темы (авто/светлая/тёмная), SunCalc, мобильный UI, drag-and-drop точек | ✅ Готово | 5 | | F-17 | PWA + офлайн | Service Worker, MBTiles, GPS-трекинг | ⏳ Бэклог | 7 | --- @@ -136,14 +136,26 @@ docker restart prototype-enduro-trails-1 **Порядок:** F-07+F-08 вместе (одна пересборка) → F-09 → F-10 -### ⏳ Фаза 4 — Продвинутый роутинг -- F-11 «Красивый маршрут» — замкнутый круг через живописные места (озёра, виды, заброшки) - - Оценка аттрактивности: близость к воде +10, перепад высот +15, viewpoints +20 -- F-13 «Связка» — соединить два трека грунтовками -- F-14 «Разведка» — все грунтовки в радиусе X км от точки +### ✅ Фаза 4 — Продвинутый роутинг (04.05.2026) +- **F-11** «Красивый маршрут» — замкнутый круг через живописные места, scenic_score, карточки с вариантами +- **F-13** «Связка» — соединить два трека грунтовками, альтернативы +- **F-14** «Разведка» — грунтовки в радиусе 20/50/100 км, статистика по типам, POI -### ⏳ Фаза 5 — Редизайн -- F-16 Тёмная тема + эндуро-стиль + адаптив под мобилку +### ✅ Фаза 4 — Продвинутый роутинг (04.05.2026) +- **F-11** «Красивый маршрут» — замкнутый круг, scenic_score, варианты по дистанции (50/100/150/200 км) +- **F-13** «Связка» — соединить два трека грунтовками, альтернативы +- **F-14** «Разведка» — грунтовки в радиусе 20/50/100 км, статистика по типам, POI +- Мини-бар маршрута (`#mini-route-bar`) — компактный HUD поверх карты + +### ✅ Фаза 5 — Редизайн (05.05.2026) +**BRD:** `BRD_PHASE5.md` +- F-16 Тёмная + светлая тема, авто-режим по SunCalc (восход/закат) +- Bottom sheets, toolbar, SVG Lucide-иконки, skeleton loading +- Свайп вниз для закрытия sheet +- Drag-and-drop точек маршрута (touch + mouse) +- Кнопка «Скачать GPX» (share dialog убран) +- Фикс: «Добавить точку» из мини-бара +- Десктоп-адаптив (toolbar слева, sheet max-width 400px) ### ⏳ Фаза 6 — SRTM рельеф - F-12 «Горка» — макс набор высоты, мин дистанция @@ -190,8 +202,10 @@ docker restart prototype-enduro-trails-1 | `DEV_TASK.md` | Стабилизация v0.1 (архив) | | `BRD_PHASE3.md` | Бизнес-требования Фазы 3 (согласовано) | | `BRD_PHASE3.1.md` | Бизнес-требования Фазы 3.1 (на согласовании) | +| `BRD_PHASE5.md` | Бизнес-требования Фазы 5 (✅ реализовано) | | `TEST_CASES_PHASE3.md` | 56 тест-кейсов | | `DEV_TASK_PHASE3.md` | ТЗ для Dev-агента Фаза 3 | +| `DEV_TASK_PHASE5.md` | ТЗ для Dev-агента Фаза 5 | | `reports/` | Отчёты о тестировании | ---