Лето в самом разгаре, и вы наверняка уже готовы отправиться в путешествие. Эта статья как раз поможет его распланировать. 

Интернет пестрит туристическими путеводителями, рассказывающими о достопримечательностях городов. Остается лишь скачать карту и следовать указаниям. Но что если у вас особая поездка, и вы намерены посетить конкретные места. 

В данном руководстве мы создадим собственную карту и отметим на ней места посещений. Такая наглядность намного упростит планирование маршрутов передвижения в течении дней. Например, можно сгруппировать лучшие пивоварни, магазинчики сладостей, музеи и т. д. 

Приступим! 

Подготовка проекта

Составление списка интересных мест 

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

Определение координат 

Список с названиями пабов готов, и теперь нам нужна библиотека Python geopy для обнаружения их координат.

Устанавливаем библиотеку посредством pip или pip3:

pip install geopy

Получаем широту и долготу конкретного местоположения паба следующим способом: 

geolocator = Nominatim(user_agent="your_app_name")
location = geolocator.geocode("London")
print((location.latitude, location.longitude))(51.5073219, -0.1276474)

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

На этом этапе отмечаем полученные координаты на карте. Вы можете воспользоваться Google Maps API для создания карты с помощью библиотеки Python gmplot. Но поскольку данный API платный, то прибегнем к альтернативе: HERE API.

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

Для работы с HERE Location Services создаем ключ API, следуя данным инструкциям

HERE Maps API для JavaScript понадобится для построения карты, а такой простой, но высоко эффективный фреймворк для веб-проектов, как Flask, обеспечит интеграцию интерфейса с Python.

Устанавливаем Flask:

pip install Flask

Теперь нужен новый файл Python для создания простого шаблона Flask:

from flask import Flask,render_template
from geopy.geocoders import Nominatim
app = Flask(__name__)

@app.route('/')
def get_data():

    geolocator = Nominatim(user_agent="map_marker")
    city = geolocator.geocode("London")
    loc_list = []
    loc_list.append(geolocator.geocode("Prospect of Whitby"))
    loc_list.append(geolocator.geocode("The Ship & Shovell"))
    loc_list.append(geolocator.geocode("The Crosse Keys"))
    loc_list.append(geolocator.geocode("The Spread Eagle"))
    loc_dict = {loc.latitude:loc.longitude for loc in loc_list}
        
    return render_template('map.html', city = city, coordinates=loc_dict)	
	
if __name__ == '__main__':
    app.run(debug = True)
  • Импортируем Flask и библиотеки geopy.
  • Определяем основную функцию, которая выполнит отрисовку карты на основе файла map.html, созданием которого мы займемся далее. 
  • Составляем список местоположений пабов и извлекаем широту и долготу в словарь. Обратите внимание, что в нашем примере фигурируют только названия места, но вы можете также написать точный адрес. 
  • Передаем переменные city и coordinates из Python в код JavaScript. Заключив их в скобки {{}}, мы можем на них ссылаться в коде HTML или JavaScript. 

Теперь приступаем к созданию файла HTML для отрисовки карты в браузере. 

Для Flask потребуется каталог templates, в котором мы и создадим файл map.html

Полученный код выглядит следующим образом: 

<html>  
<head>
<meta name="viewport" content="initial-scale=1.0, width=device-width" />
<script src="https://js.api.here.com/v3/3.1/mapsjs-core.js"type="text/javascript" charset="utf-8"></script>
<script src="https://js.api.here.com/v3/3.1/mapsjs-service.js"type="text/javascript" charset="utf-8"></script>
    <script type="text/javascript" src="https://js.api.here.com/v3/3.1/mapsjs-mapevents.js"></script>
    <script type="text/javascript" src="https://js.api.here.com/v3/3.1/mapsjs-ui.js"></script>
</head>
<body style='margin: 0'>
<div style="width: 100%; height: 100%" id="map"></div>
<script> 
var platform = new H.service.Platform({
        'apikey': 'your_api_key'
         }); 
// Получаем предустановленные типы карты из объекта platform
var defaultLayers = platform.createDefaultLayers();

var map = new H.Map(document.getElementById('map'), defaultLayers.vector.normal.map, {
  // изначальный центр и уровень масштабирования карты 
  center: new H.geo.Point({{ city.latitude}}, {{ city.longitude }}),
  zoom: 11.5,
  pixelRatio: window.devicePixelRatio || 1
});

window.addEventListener('resize', () => map.getViewPort().resize());
// Behavior реализует предустановленные взаимодействия для панорамирования/масштабирования 
var behavior = new H.mapevents.Behavior(new H.mapevents.MapEvents(map));
var ui = H.ui.UI.createDefault(map, defaultLayers);

Object.entries({{ coordinates }}).forEach(([key, value]) => {
    var marker = new H.map.Marker({
   lat: `${key}`,
   lng: `${value}`
  });
    map.addObject(marker);
});  
</script>
</body>
</html>
  • Импортируем требуемые скрипты из js.api.here.
  • Меняем apikey на свои ключи.
  • Создаем карту с Лондоном в центре. Обратите внимание, что посредством вызова {{ city.latitude}}, {{ city.longitude }} мы получаем доступ к координатам, переданным кодом Python. 
  • Добавляем addAventListener('resize') для полной уверенности, что карта занимает весь контейнер. 
  • Перебираем значения {{ coordinates }} для создания нового объекта H.map.Marker согласно значениям широты и долготы. 
  • Добавляем все маркеры на карту. 

Тестирование проекта 

Проверяем проект в действии. Запускаем программу, выполняя код Python: 

python3 map_runner.py

Открываем браузер http://127.0.0.1:5000/ и видим карту с маркерами, кликая на которые регулируем масштаб. То же самое вы можете делать и с помощью сенсорной панели. 

Обновление карты 

Предлагаю немного поэкспериментировать и добавить на карту пользовательские иконки. Воспользуемся одной подходящей бесплатной иконкой и изменим следующую часть кода: 

var pubIcon = new H.map.Icon("https://cdn0.iconfinder.com/data/icons/st-patrick-s-day-22/24/Beer_Mug_drink-128.png",  {size: {w: 30, h: 30}});
Object.entries({{ coordinates }}).forEach(([key, value]) => {
    var marker = new H.map.Marker({
   lat: `${key}`,
   lng: `${value}`
  }, {icon: pubIcon});
    map.addObject(marker);
});

В результате карта принимает вот такой привлекательный вид:

Отлично! Наш план готов. Вы можете немного изменить код, дополнив его другими достопримечательностями и визуализировав их все на одной карте. 

Как сделать карту портативной 

Для этой цели существуют следующие варианты.

  • Выполнить скриншот карты.
  • Развернуть код на сервере и получать к нему доступ через телефон или ноутбук. 
  • Развернуть код в облаке, например с помощью AWS. 

Заключение

Теперь вы знаете, как создать маркеры на собственной пользовательской карте и как просто получить координаты с помощью библиотеки geopy. 

И это лишь малая часть того, что можно сделать с HERE Map API. В документации вы найдете дополнительные примеры. 

Кроме того, вы приобрели опыт работы с фреймворком Flask, создав простой веб-проект. 

Надеюсь, благодаря этой статье вам удастся распланировать свой следующий отпуск. 

Благодарю за внимание! Программируйте с удовольствием! 

Читайте также:

Читайте нас в TelegramVK и Яндекс.Дзен


Перевод статьи Kirshi Yin: Plan Your Holiday With Python and HERE Maps

Предыдущая статьяScrum: 5–3–5–3–3
Следующая статьяКакой язык программирования учить в 2022 году?