Добавить карту на сайт для построения маршрута

В данной статье вы узнаете как встроить Яндекс карты на ваш сайт. Научитесь получать данные о маршрутах, такие как протяженность маршрута, время с учетом пробок и без пробок, узнавать есть ли на маршруте платные дороги или перекрытия. Мы создадим калькулятор, который в режиме реального времени будет считать затраты на топливо, в зависимости от маршрута и от введенных пользователем данных.
Для работы мы будем использовать Яндекс.Карты API. API Яндекс.Карт — это набор сервисов, которые позволяют использовать картографические данные и технологии Яндекса в ваших проектах. Для нас подойдет бесплатная версия, т.к. мы не будем строить коммерческий проект и наша карта будет доступна всем.
Подробнее об ограничениях на бесплатное использование API Яндекс.Карты можете почитать по адресу: https://tech.yandex.ru/maps/commercial/
Добавляем Яндекс.Карты на сайт
Чтобы добавить карты на сайт необходимо подключить библиотеку Javascript API. Сразу подключим плагин JQuery, который нам пригодится в нашем проекте. Для этого между тегами пишем следующий код.
<script src="https://code.jquery.com/jquery-3.3.1.min.js" integrity="sha256-FgpCb/KJQlLNfOu91ta32o/NMZxltwRo8QtmkMRdAu8=" crossorigin="anonymous" type="text/javascript"></script>
<script src="https://api-maps.yandex.ru/2.1/?lang=ru_RU" type="text/javascript"></script>
После подключения библиотеки нам необходимо создать слой с уникальным id=»map» (может быть любым), в который будет выводиться наша карта. Для этого в нужном нам месте пишем следующую строчку.
<div id="map"></div>
Нам осталось написать скрипт, который будет выводить карту на страницу. Для этого после нашего слоя пишем следующий код.
<script type="text/javascript">
ymaps.ready(init);
function init() {
myMap = new ymaps.Map('map', { // Выводим в слой с id="map"
center: [59.9174, 30.3250], // центрируем карту на Санкт-Петербурге
zoom: 11, // Ставим зум кратный 11
controls: [] // Никакие кнопки управления пока не добавляем
})}
</script>
Добавим стили, чтобы карта выводилась на всю страницу.
<style>
body, html, #map {
width: 100%;
height: 100%;
padding: 0;
margin: 0;
position: absolute;
}
</style>
Сохраняем страницу и смотрим на результат!

Настраиваем Яндекс.Карты
Наша задача состоит в построении маршрута от точки А до точки В. Для этого нам необходима навигационная панель для ввода начальной и конечной точек. Добавим панель и кнопки масштабирования на карту, используя Яндекс.Карты API.
routePanelControl = new ymaps.control.RoutePanel({
options: {
showHeader: true, //Показывать заголовок навигационной панели
title: 'Проложить маршрут', //Заголовок панели
allowSwitch: true, //Отображать кнопку для смены местами Откуда/Куда
maxWidth: '300px', //Ширина панели (макс. 400px)
float: 'left' // Расположение в левой части карты
}
}),
zoomControl = new ymaps.control.ZoomControl({
options: {
float: 'right', // Расположение в правой части карты
position: { //Координаты
top: 245, //расположения
right: 10 //кнопок зума
}
}
});
myMap.controls.add(routePanelControl).add(zoomControl);
Теперь мы имеем уже рабочую версию карт и даже можем строить маршруты.

Убираем возможность строить маршруты на общественном транспорте и пешеходные маршруты, т.к. для нашей задачи они не понадобятся. Для этого используйте следующий код:
// Пользователь сможет построить только автомобильный маршрут.
routePanelControl.routePanel.options.set({
types: {auto: true},
});
Для удобства построения маршрутов можно указать в качестве точки отправления текущее положение пользователя. За это отвечает следующая строчка кода:
// Зададим координаты пункта отправления с помощью геолокации.
routePanelControl.routePanel.geolocate('from');
Добавим информацию о пробках на карту:
// Создадим элемент управления "Пробки".
var trafficControl = new ymaps.control.TrafficControl({ state: {
// Отображаются пробки "Сейчас".
providerKey: 'traffic#actual',
// Начинаем сразу показывать пробки на карте (true) или после нажатия на кнопку (false)
trafficShown: false
}});
// Добавим контрол на карту.
myMap.controls.add(trafficControl);
// Получим ссылку на провайдер пробок "Сейчас" и включим показ инфоточек.
trafficControl.getProvider('traffic#actual').state.set('infoLayerShown', true);
Получение информации об активном маршруте Яндекс.Карты
Теперь, когда у нас строятся маршруты, нам необходимо получить информацию о времени и протяженности маршрута. Эти данные нам понадобятся в дальнейшем для автоматизации расчетов затрат на топливо.
Сделаем чтобы при построении маршрутов выводился самый быстрый маршрут с учетом дорожной обстановки на дорогах. Поиск маршрута с учетом пробок полезен еще для того, чтобы маршрут не строился через перекрытые дороги.
// Получим ссылку на маршрут.
routePanelControl.routePanel.getRouteAsync().then(function (route) {
// Зададим максимально допустимое число маршрутов, возвращаемых мультимаршрутизатором.
route.model.setParams({results: 1}, true);
//Искать оптимальный маршрут с учетом пробок
route.model.setParams({avoidTrafficJams: true}, true);
// Повесим обработчик на событие построения маршрута.
route.model.events.add('requestsuccess', function () {
var activeRoute = route.getActiveRoute();
if (activeRoute) {
activeRoute.balloon.open();
}
});
});

В балун выводится краткая информация о маршруте. Мы знаем протяженность маршрута, время в пути с учетом пробок и без пробок, о платных участках на маршруте и о перекрытиях на дороге. Эти данные передаются в параметрах properties активного маршрута. Извлечем эти данные и выведем в консоль браузера для наглядности.
// Получим протяженность маршрута.
length = route.getActiveRoute().properties.get("distance"), // Протяженность маршрута
time = route.getActiveRoute().properties.get("duration"), // Время маршрута
blocked = route.getActiveRoute().properties.get("blocked"), // Есть ли перекрытия на маршруте
tolls = route.getActiveRoute().properties.get("hasTolls"), // Есть ли платные участки дороги
timeintraffic = route.getActiveRoute().properties.get("durationInTraffic"); // Время с учетом пробок
activeRoute.balloon.open();
console.log('Протяженность маршрута ' + length.value); // Протяженность маршрута в метрах
console.log('Протяженность маршрута ' + length.text); // Протяженность маршрута в текстовом представлении
console.log('Время без пробок ' + time.value); // Время в секундах без учета пробок
console.log('Время без пробок ' + time.text); // Время в текстовом представлении без учета пробок
console.log('Время с пробками ' + timeintraffic.value); // Время в секундах с учетом пробок
console.log('Время с пробками ' + timeintraffic.text); // Время в текстовом представлении с учетом пробок
console.log('blocked' + blocked); // На маршруте есть перекрытия дороги
console.log('tolls ' + tolls); // На маршруте есть платные участки дороги

Вывод информации о маршруте в собственное поле на карте
Информацию о маршруте мы будем выводить прямо на карту под навигационной панелью. Вы можете сделать вывод информации в любое место по аналогии. Не буду описывать стили для слоев в статье. Кому интересно, можете посмотреть в исходном коде на странице, которая будет указана в конце статьи.
Создаем свой слой, на который будет выводиться наша информация о маршруте и затратах. Прописываем ему стили, чтобы он располагался под навигационной панелью и был скрыт по умолчанию.
Добавим на слой форму для ввода расхода и стоимости топлива. Эти данные нам позже пригодятся. Сразу пропишем значения, которые будут подставляться по умолчанию.
У вас должно получиться примерно так:
<div id="map">
<div id="info">
<div style="padding-left: 25px; float:left" class="text">
<input type="number" name="fuel" id="fuel" value="40" /> литр/100 км
<input type="number" name="price" id="price" value="45" /> руб/литр
</div>
<div id="infotext"></div>
<div id="infotextprice"></div>
</div>
</div>
В данный момент наша карта никак изменилась и ничего не считает. Нам необходимо заполнять наши слои информацией при выводе маршрута на карту. Для этого пропишем формулы для расчетов и куда выводить информацию.
// Получим протяженность маршрута.
$('#info').css("display", "block"); // Показываем наш блок с информацией
length = route.getActiveRoute().properties.get("distance"), // Протяженность маршрута
time = route.getActiveRoute().properties.get("duration"), // Время маршрута
blocked = route.getActiveRoute().properties.get("blocked"), // Есть ли перекрытия на маршруте
tolls = route.getActiveRoute().properties.get("hasTolls"), // Есть ли платные участки дороги
timeintraffic = route.getActiveRoute().properties.get("durationInTraffic"); // Время с учетом пробок
var fuel = document.getElementById("fuel").value; // Считываем расход топлива из формы
var price = document.getElementById("price").value; // Считываем стоимость топлива из формы
var rashod = Math.round((length.value/100000)*fuel); // Считаем сколько топлива потратим
var money = Math.round(rashod*price); // Считаем сколько денег потратим на топливо
mydis.innerHTML='';
mydisprice.innerHTML='';
mydis.insertAdjacentHTML("beforeend", 'Оптимальный маршрут составляет ' + length.text + '
');
mydis.insertAdjacentHTML("beforeend", 'Время с учетом пробок ' + timeintraffic.text + '
');
mydisprice.insertAdjacentHTML("beforeend", 'Примерные расходы топлива ' + rashod + ' л.
');
mydisprice.insertAdjacentHTML("beforeend", 'Расходы на топливо ' + money + ' руб.
');
if (blocked) {mydis.insertAdjacentHTML("beforeend", 'На участке есть перекрытия дороги!
');}
if (tolls) {mydis.insertAdjacentHTML("beforeend", 'На маршруте есть платные участки дороги!
');}
activeRoute.balloon.open();
console.log('Протяженность маршрута ' + length.value); // Протяженность маршрута в метрах
console.log('Протяженность маршрута ' + length.text); // Протяженность маршрута в текстовом представлении
console.log('Время без пробок ' + time.value); // Время в секундах без учета пробок
console.log('Время без пробок ' + time.text); // Время в текстовом представлении без учета пробок
console.log('Время с пробками ' + timeintraffic.value); // Время в секундах с учетом пробок
console.log('Время с пробками ' + timeintraffic.text); // Время в текстовом представлении с учетом пробок
console.log('blocked' + blocked); // На маршруте есть перекрытия дороги
console.log('tolls ' + tolls); // На маршруте есть платные участки дороги

Теперь нам необходимо пересчитывать затраты при изменении значений в форме. Для этого напишем функцию recalc() и пропишем ее вызов в форме.
<script type="text/javascript">
function recalc() {
var mydis = document.getElementById('infotext');
var mydisprice = document.getElementById('infotextprice');
var fuel = document.getElementById("fuel").value;
var price = document.getElementById("price").value;
var rashod = Math.round((window.length.value/100000)*fuel);
var money = Math.round(rashod*price);
mydisprice.innerHTML='';
mydisprice.insertAdjacentHTML("beforeend", 'Примерные расходы топлива <strong>' + rashod + ' л.</strong><br />');
mydisprice.insertAdjacentHTML("beforeend", 'Расходы на топливо <strong>' + money + ' руб.</strong><br />');
}
</script>
<div style="padding-left: 25px; float:left" class="text">
<input type="number" name="fuel" id="fuel" value="40" oninput="recalc()"> литр/100км
<input type="number" name="price" id="price" value="45" oninput="recalc()"> руб/литр
</div>
Можно разрешить пользователю изменять маршрут простым перетягиванием любой его точки по карте. Для этого добавляем код.
//Разрешаем перетаскивать точки между начальной и конечной точками
route.editor.start();

Теперь вы можете строить оптимальные маршруты с автоматическим расчетом затрат на топливо прямо на вашем сайте.
Разместить форму расчета расстояния и затрат на топливо между городами на сайте
У вас появилась возможность установить нашу форму расчета расстояния между городами, поиска кратчайшего пути и подсчета примерных затрат на топливо на ваш сайт бесплатно!
Вам необходимо разместить в нужном месте на вашем сайте следующий код:
<script src="https://demo.pogrommist.ru/route/embed.js"></script>
После этого на вашем сайте появится форма расчета расстояния между городами. Сервис предоставляется абсолютно бесплатно!
Ваш сайт должен работать по протоколу https
, в противном случае карта подгружаться не будет.
Если у вас возникнут проблемы с установкой формы на ваш сайт, пишите нам в комментарии. Сервис предоставляется на условиях «Как есть».
Исходный код вы можете посмотреть здесь: https://pogrommist.ru/route/
Больше примеров можно посмотреть в Песочнице Яндекса: https://tech.yandex.ru/maps/jsbox/2.1/