Prosty licznik podróży korzystający z interfejsu Geolocation API

Michael Mahemoff
Michael Mahemoff

Wprowadzenie

Interfejs Geolocation API pozwala określić, gdzie znajduje się użytkownik, i śledzić jego lokalizację, gdy się przemieszcza – zawsze za jego zgodą. Ta funkcja może być używana w ramach zapytań użytkowników, np. do kierowania kogoś do miejsca docelowego. Może też służyć do dodawania tagów geograficznych do treści utworzonych przez użytkownika, np. do oznaczania miejsca, w którym zrobiono zdjęcie. Interfejs API jest niezależny od urządzenia. Nie ma znaczenia, jak przeglądarka określa lokalizację, o ile klienci mogą żądać danych o lokalizacji i otrzymywać je w standardowy sposób. Mechanizm może działać na podstawie GPS-u, Wi-Fi lub po prostu prosić użytkownika o ręczne wpisanie lokalizacji. Ponieważ każde z tych wyszukiwań zajmuje trochę czasu, interfejs API jest asynchroniczny. Za każdym razem, gdy wysyłasz żądanie lokalizacji, przekazujesz mu metodę wywołania zwrotnego.

W tym przykładzie jest to licznik podróży, który pokazuje początkową lokalizację i wyświetla odległość przebytą od momentu załadowania strony.

Krok 1. Sprawdzanie zgodności

Browser Support

  • Chrome: 5.
  • Edge: 12.
  • Firefox: 3.5.
  • Safari: 5.

Source

Zgodność możesz łatwo sprawdzić, testując obecność obiektu geolokalizacji:

// check for Geolocation support
if (navigator.geolocation) {
  console.log('Geolocation is supported!');
}
else {
  console.log('Geolocation is not supported for this Browser/OS version yet.');
}

Krok 2. Deklarowanie kodu HTML licznika podróży

W tym przykładzie tworzysz licznik podróży, więc zadeklaruj ten kod HTML:

<div id="tripmeter">
<p>
Starting Location (lat, lon):<br/>
<span id="startLat">???</span>°, <span id="startLon">???</span>°
</p>
<p>
Current Location (lat, lon):<br/>
<span id="currentLat">???</span>°, <span id="currentLon">???</span>°
</p>
<p>
Distance from starting location:<br/>
<span id="distance">0</span> km
</p>
</div>

W następnych kilku krokach użyjemy interfejsu Geolocation API, aby wypełnić wszystkie puste elementy span.

Krok 3. określanie bieżącej lokalizacji użytkownika,

getCurrentPosition() będzie asynchronicznie raportować bieżącą lokalizację użytkownika. Wywołaj ją, gdy tylko strona się wczyta, aby prawidłowo wypełnić i zapisać na później pozycję początkową:

window.onload = function() {
var startPos;
navigator.geolocation.getCurrentPosition(function(position) {
startPos = position;
document.getElementById('startLat').innerHTML = startPos.coords.latitude;
document.getElementById('startLon').innerHTML = startPos.coords.longitude;
});
};

Jeśli aplikacja w tej domenie po raz pierwszy prosi o uprawnienia, przeglądarka zwykle sprawdza, czy użytkownik wyraził zgodę. W zależności od przeglądarki mogą być też dostępne ustawienia, które zawsze zezwalają na sprawdzanie uprawnień lub nie zezwalają na to. W takim przypadku proces potwierdzania zostanie pominięty.

Po uruchomieniu tego kodu powinna być widoczna pozycja początkowa. W zależności od urządzenia lokalizacyjnego, którego używa przeglądarka, obiekt pozycji może zawierać znacznie więcej informacji niż tylko szerokość i długość geograficzną, np. wysokość lub kierunek. Możesz dowiedzieć się więcej, rejestrując zmienną pozycji w konsoli.

Krok 4. Obsługuj błędy

Niestety nie wszystkie wyszukiwania lokalizacji kończą się powodzeniem. Być może nie udało się zlokalizować GPS lub użytkownik nagle wyłączył wyszukiwanie lokalizacji. Drugi, opcjonalny argument funkcji getCurrentPosition() zostanie wywołany w przypadku błędu, dzięki czemu możesz powiadomić użytkownika w ramach wywołania zwrotnego:

window.onload = function() {
var startPos;
navigator.geolocation.getCurrentPosition(function(position) {
// same as above
}, function(error) {
alert('Error occurred. Error code: ' + error.code);
// error.code can be:
//   0: unknown error
//   1: permission denied
//   2: position unavailable (error response from locaton provider)
//   3: timed out
});
};

Krok 5. śledzić lokalizację użytkownika,

Poprzednie wywołanie funkcji getCurrentPosition() zostało wykonane tylko raz, podczas wczytywania strony. Aby śledzić zmiany, użyj watchPosition(). Będzie ona automatycznie powiadamiać funkcję wywołania zwrotnego za każdym razem, gdy użytkownik się poruszy:

navigator.geolocation.watchPosition(function(position) {
document.getElementById('currentLat').innerHTML = position.coords.latitude;
document.getElementById('currentLon').innerHTML = position.coords.longitude;
});

Krok 6. Pokaż przebyty dystans

Ten krok nie jest bezpośrednio związany z interfejsem Geolocation API, ale stanowi podsumowanie wersji demonstracyjnej i pokazuje, jak można wykorzystać dane o lokalizacji. Dodaj dodatkowy wiersz do modułu obsługi watchPosition(), aby wypełnić przebytą odległość:

navigator.geolocation.watchPosition(function(position) {
// same as above
document.getElementById('distance').innerHTML =
    calculateDistance(startPos.coords.latitude, startPos.coords.longitude,
                    position.coords.latitude, position.coords.longitude);
});

Funkcja calculateDistance() wykonuje algorytm geometryczny, aby określić odległość między 2 współrzędnymi. Implementacja JavaScriptu została dostosowana na podstawie skryptu udostępnionego przez Moveable Type na licencji Creative Commons:

function calculateDistance(lat1, lon1, lat2, lon2) {
var R = 6371; // km
var dLat = (lat2 - lat1).toRad();
var dLon = (lon2 - lon1).toRad();
var a = Math.sin(dLat / 2) * Math.sin(dLat / 2) +
        Math.cos(lat1.toRad()) * Math.cos(lat2.toRad()) *
        Math.sin(dLon / 2) * Math.sin(dLon / 2);
var c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1 - a));
var d = R * c;
return d;
}
Number.prototype.toRad = function() {
return this * Math.PI / 180;
}