UNPKG

2.9 kBPlain TextView Raw
1import { EventEmitter } from '@unimodules/core';
2
3interface Coordinates {
4 latitude: number;
5 longitude: number;
6 altitude?: number;
7 accuracy?: number;
8 altitudeAccuracy?: number;
9 heading?: number;
10 speed?: number;
11}
12
13interface Position {
14 coords: Coordinates;
15 timestamp: number;
16}
17
18interface PermissionResult {
19 status: string;
20}
21
22class GeocoderError extends Error {
23 code: string;
24
25 constructor() {
26 super('Geocoder service is not available for this device.');
27 this.code = 'E_NO_GEOCODER';
28 }
29}
30
31const emitter = new EventEmitter({} as any);
32
33function positionToJSON(position: any): Position | null {
34 if (!position) return null;
35
36 const { coords = {}, timestamp } = position;
37 return {
38 coords: {
39 latitude: coords.latitude,
40 longitude: coords.longitude,
41 altitude: coords.altitude,
42 accuracy: coords.accuracy,
43 altitudeAccuracy: coords.altitudeAccuracy,
44 heading: coords.heading,
45 speed: coords.speed,
46 },
47 timestamp,
48 };
49}
50
51export default {
52 get name(): string {
53 return 'ExpoLocation';
54 },
55 async getProviderStatusAsync(): Promise<{ locationServicesEnabled: boolean }> {
56 return {
57 locationServicesEnabled: 'geolocation' in navigator,
58 };
59 },
60 async getCurrentPositionAsync(options: Object): Promise<Position | null> {
61 return new Promise<Position | null>((resolve, reject) =>
62 navigator.geolocation.getCurrentPosition(
63 position => resolve(positionToJSON(position)),
64 reject,
65 options
66 )
67 );
68 },
69 async removeWatchAsync(watchId): Promise<void> {
70 navigator.geolocation.clearWatch(watchId);
71 },
72 async watchDeviceHeading(headingId): Promise<void> {
73 console.warn('Location.watchDeviceHeading: is not supported on web');
74 },
75 async hasServicesEnabledAsync(): Promise<boolean> {
76 return 'geolocation' in navigator;
77 },
78 async geocodeAsync(): Promise<Array<any>> {
79 throw new GeocoderError();
80 },
81 async reverseGeocodeAsync(): Promise<Array<any>> {
82 throw new GeocoderError();
83 },
84 async watchPositionImplAsync(watchId: string, options: Object): Promise<string> {
85 return new Promise<string>(resolve => {
86 // @ts-ignore
87 watchId = global.navigator.geolocation.watchPosition(
88 location => {
89 emitter.emit('Expo.locationChanged', { watchId, location: positionToJSON(location) });
90 },
91 null,
92 options
93 );
94 resolve(watchId);
95 });
96 },
97 async requestPermissionsAsync(): Promise<PermissionResult> {
98 return new Promise<PermissionResult>(resolve => {
99 navigator.geolocation.getCurrentPosition(
100 () => resolve({ status: 'granted' }),
101 ({ code }) => {
102 if (code === 1 /* PERMISSION_DENIED */) {
103 resolve({ status: 'denied' });
104 } else {
105 resolve({ status: 'undetermined' });
106 }
107 }
108 );
109 });
110 },
111};
112
\No newline at end of file