Пешеходные маршруты

Пешеходная маршрутизация предназначена для построения маршрутов, рассчитанных на передвижение пешком. В отличие от автомобильной навигации, такие маршруты учитывают тротуары, пешеходные переходы, парковые дорожки, лестницы, пешеходные зоны, проходы между зданиями и другие элементы городской инфраструктуры, недоступные для транспортных средств.

В экосистеме HERE для расчёта маршрутов используется сервис Routing API, который позволяет строить маршруты для различных видов транспорта:

  • автомобиль;
  • грузовой транспорт;
  • общественный транспорт;
  • велосипед;
  • пешеход.

Для пешеходных маршрутов применяется параметр транспорта pedestrian.


Подключение необходимых библиотек

Перед использованием маршрутизации необходимо подключить основные модули HERE Maps.

<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8">

    <script src="https://js.api.here.com/v3/3.1/mapsjs-core.js"></script>
    <script src="https://js.api.here.com/v3/3.1/mapsjs-service.js"></script>
    <script src="https://js.api.here.com/v3/3.1/mapsjs-ui.js"></script>
    <script src="https://js.api.here.com/v3/3.1/mapsjs-mapevents.js"></script>

    <link
        rel="stylesheet"
        href="https://js.api.here.com/v3/3.1/mapsjs-ui.css"
    />
</head>
<body>
    <div id="map" style="width:100%;height:600px;"></div>
</body>
</html>

Создание карты:

const platform = new H.service.Platform({
    apikey: "YOUR_API_KEY"
});

const defaultLayers = platform.createDefaultLayers();

const map = new H.Map(
    document.getElementById("map"),
    defaultLayers.vector.normal.map,
    {
        zoom: 14,
        center: {
            lat: 55.751244,
            lng: 37.618423
        }
    }
);

const beh * avior = new H.mapevents.Behavior(
    new H.mapevents.MapEvents(map)
);

const ui = H.ui.UI.createDefault(map, defaultLayers);

Получение сервиса маршрутизации

Для работы с маршрутами необходимо получить экземпляр сервиса Routing.

const router = platform.getRoutingService(null, 8);

Число 8 указывает на использование Routing API версии 8.


Построение простого пешеходного маршрута

Маршрут строится между двумя географическими точками.

const routingParameters = {
    transportMode: "pedestrian",

    origin: "55.751244,37.618423",

    destination: "55.758000,37.605000",

    return: "polyline,summary"
};

router.calculateRoute(
    routingParameters,
    onSuccess,
    onError
);

Обработка результата:

function onSuccess(result) {
    console.log(result);
}

function onError(error) {
    console.error(error);
}

Структура ответа маршрута

Ответ Routing API содержит массив маршрутов.

result.routes

Каждый маршрут включает один или несколько участков.

const route = result.routes[0];

const section = route.sections[0];

Основные данные:

section.summary.length

Длина маршрута в метрах.

section.summary.duration

Время прохождения в секундах.

Например:

console.log(
    `Расстояние: ${section.summary.length} м`
);

console.log(
    `Время: ${section.summary.duration} сек`
);

Отображение маршрута на карте

Маршрут возвращается в виде закодированной полилинии.

Для декодирования используется утилита Flexible Polyline.

const lineString =
    H.geo.LineString.fromFlexiblePolyline(
        section.polyline
    );

Создание линии маршрута:

const routeLine = new H.map.Polyline(
    lineString,
    {
        style: {
            strokeColor: "#0066ff",
            lineWidth: 6
        }
    }
);

map.addObject(routeLine);

Центрирование карты:

map.getViewModel().setLookAtData({
    bounds: routeLine.getBoundingBox()
});

Добавление маркеров начала и конца маршрута

Начальная точка:

const startMarker = new H.map.Marker({
    lat: 55.751244,
    lng: 37.618423
});

Конечная точка:

const finishMarker = new H.map.Marker({
    lat: 55.758000,
    lng: 37.605000
});

Добавление на карту:

map.addObjects([
    startMarker,
    finishMarker
]);

Полный пример построения маршрута

router.calculateRoute(
    {
        transportMode: "pedestrian",

        origin: "55.751244,37.618423",

        destination: "55.758000,37.605000",

        return: "polyline,summary"
    },

    result => {

        const route = result.routes[0];

        const section = route.sections[0];

        const lineString =
            H.geo.LineString.fromFlexiblePolyline(
                section.polyline
            );

        const routeLine =
            new H.map.Polyline(lineString, {
                style: {
                    strokeColor: "green",
                    lineWidth: 5
                }
            });

        map.addObject(routeLine);

        map.getViewModel().setLookAtData({
            bounds: routeLine.getBoundingBox()
        });

    },

    error => {
        console.error(error);
    }
);

Получение пошаговых инструкций движения

Для отображения навигационных подсказок необходимо запросить действия маршрута.

const params = {
    transportMode: "pedestrian",

    origin: "55.751244,37.618423",

    destination: "55.758000,37.605000",

    return: "polyline,summary,actions,instructions"
};

После получения результата:

const actions =
    result.routes[0]
          .sections[0]
          .actions;

Вывод инструкций:

actions.forEach(action => {

    console.log(
        action.instruction
    );

});

Пример инструкций:

Двигайтесь на север
Поверните направо
Перейдите дорогу
Продолжайте движение
Прибытие в пункт назначения

Построение маршрута через промежуточные точки

Пешеходный маршрут может проходить через несколько контрольных точек.

router.calculateRoute(
    {
        transportMode: "pedestrian",

        origin: "55.751244,37.618423",

        via: [
            "55.754500,37.615000",
            "55.756000,37.612000"
        ],

        destination: "55.758000,37.605000",

        return: "polyline,summary"
    },

    onSuccess,
    onError
);

Каждая промежуточная точка становится обязательной частью маршрута.


Использование координат из событий карты

Часто точки маршрута выбираются пользователем кликом по карте.

Получение координат:

map.addEventListener("tap", event => {

    const coord =
        map.screenToGeo(
            event.currentPointer.viewportX,
            event.currentPointer.viewportY
        );

    console.log(coord.lat);
    console.log(coord.lng);

});

После выбора двух точек можно автоматически строить маршрут.


Маршруты между объектами карты

Предположим, что имеются два маркера.

const pointA = markerA.getGeometry();

const pointB = markerB.getGeometry();

Маршрут:

router.calculateRoute(
    {
        transportMode: "pedestrian",

        origin:
            `${pointA.lat},${pointA.lng}`,

        destination:
            `${pointB.lat},${pointB.lng}`,

        return:
            "polyline,summary"
    },

    onSuccess,
    onError
);

Получение информации о времени прохождения

Данные маршрута содержат суммарную длительность.

const duration =
    section.summary.duration;

Перевод секунд в минуты:

const minutes =
    Math.round(duration / 60);

console.log(
    `Время пешком: ${minutes} мин`
);

Перевод в часы и минуты:

function formatDuration(seconds) {

    const hours =
        Math.floor(seconds / 3600);

    const minutes =
        Math.floor(
            (seconds % 3600) / 60
        );

    return `${hours} ч ${minutes} мин`;
}

Получение длины маршрута

const length =
    section.summary.length;

Перевод в километры:

const km =
    (length / 1000).toFixed(2);

console.log(
    `${km} км`
);

Отображение информации в интерфейсе

Создание информационного блока:

<div id="routeInfo"></div>

Заполнение данными:

const summary =
    route.sections[0].summary;

document.getElementById(
    "routeInfo"
).innerHTML = `
    <p>
        Расстояние:
        ${summary.length} м
    </p>

    <p>
        Время:
        ${summary.duration} сек
    </p>
`;

Очистка старого маршрута

Перед построением нового маршрута обычно удаляются ранее отображённые объекты.

map.removeObjects(
    map.getObjects()
);

Более безопасный вариант:

if (routeLine) {
    map.removeObject(routeLine);
}

Хранение ссылки:

let routeLine = null;

После создания:

routeLine =
    new H.map.Polyline(
        lineString
    );

Использование групп объектов

Для удобного управления всеми элементами маршрута применяется группа.

const routeGroup =
    new H.map.Group();

map.addObject(routeGroup);

Добавление объектов:

routeGroup.addObject(routeLine);

routeGroup.addObject(startMarker);

routeGroup.addObject(endMarker);

Очистка:

routeGroup.removeAll();

Настройка внешнего вида пешеходного маршрута

Толщина линии:

lineWidth: 8

Цвет:

strokeColor: "#00AA00"

Прозрачность:

strokeColor:
"rgba(0,170,0,0.6)"

Пример:

const routeLine =
    new H.map.Polyline(
        lineString,
        {
            style: {
                strokeColor:
                    "rgba(0,150,0,0.8)",

                lineWidth: 7
            }
        }
    );

Альтернативные маршруты

Сервис может возвращать несколько вариантов пути.

const params = {
    transportMode: "pedestrian",

    origin: "55.751244,37.618423",

    destination: "55.758000,37.605000",

    alternatives: 3,

    return: "polyline,summary"
};

Получение маршрутов:

result.routes.forEach(route => {

    console.log(
        route.sections[0]
             .summary
    );

});

Каждый вариант можно отображать своим цветом.

const colors = [
    "blue",
    "green",
    "red"
];

Работа с несколькими участками маршрута

Если используются промежуточные точки, маршрут делится на секции.

route.sections.forEach(
    section => {

        console.log(
            section.summary.length
        );

    }
);

Общая длина:

const totalLength =
    route.sections.reduce(
        (sum, section) =>
            sum +
            section.summary.length,
        0
    );

Общее время:

const totalDuration =
    route.sections.reduce(
        (sum, section) =>
            sum +
            section.summary.duration,
        0
    );

Особенности пешеходной навигации

Пешеходная маршрутизация в HERE обладает рядом особенностей:

  • учитываются пешеходные зоны;
  • используются городские проходы;
  • доступны маршруты через парки;
  • возможен проход через подземные переходы;
  • учитываются лестницы и дорожки;
  • игнорируются ограничения, актуальные только для автомобилей;
  • расчёт времени производится на основе модели движения пешехода.

Благодаря этим особенностям маршрут для пешехода зачастую существенно отличается от автомобильного пути между теми же координатами.


Практические сценарии использования

Туристические приложения

  • построение прогулочных маршрутов;
  • отображение достопримечательностей;
  • экскурсионные маршруты.

Навигация внутри города

  • поиск кратчайшего пути между объектами;
  • сопровождение пешеходов;
  • отображение времени пешего перехода.

Сервисы доставки

  • маршруты курьеров;
  • оценка времени прибытия пешего сотрудника;
  • оптимизация городских перемещений.

Геоинформационные системы

  • анализ доступности объектов;
  • расчёт пешеходных зон;
  • моделирование перемещений людей.

Мобильные приложения

  • фитнес-трекеры;
  • прогулочные сервисы;
  • навигаторы для путешественников;
  • карты кампусов, парков и торговых комплексов.