Геолокация и карты в TypeScript: библиотеки и практические примеры

Онлайн-тренажер Python для начинающих

Изучайте Python легко и без перегрузки теорией. Решайте практические задачи с автоматической проверкой, получайте подсказки на русском языке и пишите код прямо в браузере — без необходимости что-либо устанавливать.

Начать курс

Геолокация и карты в TypeScript: обзор инструментов и примеры кода

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

1. Основы геолокации в браузере

Прежде чем подключать карты, нужно получить координаты пользователя. Встроенный API геолокации (navigator.geolocation) отлично типизируется в TypeScript.

interface Position {
  latitude: number;
  longitude: number;
  accuracy?: number;
}

function getCurrentPosition(): Promise<Position> {
  return new Promise((resolve, reject) => {
    navigator.geolocation.getCurrentPosition(
      (pos) => {
        resolve({
          latitude: pos.coords.latitude,
          longitude: pos.coords.longitude,
          accuracy: pos.coords.accuracy
        });
      },
      (error) => reject(error)
    );
  });
}

// Использование
getCurrentPosition()
  .then((pos) => console.log(`Широта: ${pos.latitude}, Долгота: ${pos.longitude}`))
  .catch((err) => console.error('Ошибка геолокации:', err));

2. Leaflet — лёгкая и популярная библиотека

Leaflet — одна из самых простых и быстрых библиотек для отображения карт. Для TypeScript существует пакет @types/leaflet.

Установка

npm install leaflet
npm install --save-dev @types/leaflet

Пример: карта с меткой

import L from 'leaflet';
import 'leaflet/dist/leaflet.css';

// Типизированная функция инициализации
function initMap(containerId: string, coords: [number, number]): L.Map {
  const map = L.map(containerId).setView(coords, 13);

  L.tileLayer('https://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png', {
    attribution: '&copy; OpenStreetMap contributors'
  }).addTo(map);

  L.marker(coords)
    .addTo(map)
    .bindPopup('Вы здесь!');

  return map;
}

// Использование
const map = initMap('map', [55.7558, 37.6173]); // Москва

Продвинутая типизация событий

map.on('click', (e: L.LeafletMouseEvent) => {
  const { lat, lng } = e.latlng;
  console.log(`Клик: ${lat}, ${lng}`);
});

3. OpenLayers — мощный инструмент для сложных задач

OpenLayers поддерживает большое количество форматов (GeoJSON, KML, WMS) и подходит для профессиональных геоинформационных систем. Типы поставляются вместе с пакетом.

Установка

npm install ol

Пример: карта с маркером и всплывающей подсказкой

import Map from 'ol/Map';
import View from 'ol/View';
import TileLayer from 'ol/layer/Tile';
import OSM from 'ol/source/OSM';
import { fromLonLat } from 'ol/proj';
import Feature from 'ol/Feature';
import Point from 'ol/geom/Point';
import VectorLayer from 'ol/layer/Vector';
import VectorSource from 'ol/source/Vector';
import Style from 'ol/style/Style';
import Icon from 'ol/style/Icon';
import Overlay from 'ol/Overlay';

function createMap(containerId: string, lon: number, lat: number): void {
  const container = document.getElementById(containerId) as HTMLElement;

  // Создаём маркер
  const marker = new Feature({
    geometry: new Point(fromLonLat([lon, lat]))
  });

  marker.setStyle(new Style({
    image: new Icon({
      anchor: [0.5, 1],
      src: 'https://openlayers.org/en/latest/examples/data/icon.png'
    })
  }));

  // Векторный слой
  const vectorLayer = new VectorLayer({
    source: new VectorSource({
      features: [marker]
    })
  });

  // Карта
  const map = new Map({
    target: container,
    layers: [
      new TileLayer({ source: new OSM() }),
      vectorLayer
    ],
    view: new View({
      center: fromLonLat([lon, lat]),
      zoom: 10
    })
  });

  // Всплывающая подсказка
  const popup = new Overlay({
    element: document.getElementById('popup') as HTMLElement
  });
  map.addOverlay(popup);

  map.on('click', (evt) => {
    const feature = map.forEachFeatureAtPixel(evt.pixel, (f) => f);
    if (feature) {
      const coord = (feature.getGeometry                    

Рекомендаций