react-native-map-link 2.11.3 → 3.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (51) hide show
  1. package/README.md +10 -4
  2. package/lib/components/popup/Popup.d.ts +39 -0
  3. package/lib/components/popup/Popup.js +110 -0
  4. package/lib/components/popup/PopupBody.d.ts +16 -0
  5. package/lib/components/popup/PopupBody.js +31 -0
  6. package/lib/components/popup/PopupFlatList.d.ts +10 -0
  7. package/lib/components/popup/PopupFlatList.js +11 -0
  8. package/lib/components/popup/PopupFooter.d.ts +15 -0
  9. package/lib/components/popup/PopupFooter.js +18 -0
  10. package/lib/components/popup/PopupHeader.d.ts +17 -0
  11. package/lib/components/popup/PopupHeader.js +48 -0
  12. package/lib/components/popup/PopupItem.d.ts +13 -0
  13. package/lib/components/popup/PopupItem.js +38 -0
  14. package/lib/components/popup/PopupSeparator.d.ts +8 -0
  15. package/lib/components/popup/PopupSeparator.js +19 -0
  16. package/lib/constants.d.ts +15 -0
  17. package/lib/constants.js +97 -0
  18. package/lib/index.d.ts +3 -0
  19. package/lib/index.js +116 -0
  20. package/lib/type.d.ts +92 -0
  21. package/lib/type.js +2 -0
  22. package/lib/utils.d.ts +44 -0
  23. package/lib/utils.js +307 -0
  24. package/package.json +52 -20
  25. package/index.d.ts +0 -127
  26. package/index.js +0 -8
  27. package/src/components/Popup.js +0 -298
  28. package/src/constants.js +0 -92
  29. package/src/images/apple-maps.png +0 -0
  30. package/src/images/citymapper.png +0 -0
  31. package/src/images/dgis.png +0 -0
  32. package/src/images/gett.png +0 -0
  33. package/src/images/google-maps.png +0 -0
  34. package/src/images/kakao-map.png +0 -0
  35. package/src/images/liftago.png +0 -0
  36. package/src/images/lyft.png +0 -0
  37. package/src/images/maps-me.png +0 -0
  38. package/src/images/mapycz.png +0 -0
  39. package/src/images/moovit.png +0 -0
  40. package/src/images/naver-map.png +0 -0
  41. package/src/images/osmand.png +0 -0
  42. package/src/images/petalmaps.png +0 -0
  43. package/src/images/transit.png +0 -0
  44. package/src/images/truckmap.png +0 -0
  45. package/src/images/uber.png +0 -0
  46. package/src/images/waze.png +0 -0
  47. package/src/images/yandex-maps.png +0 -0
  48. package/src/images/yandex-taxi.png +0 -0
  49. package/src/images/yandex.png +0 -0
  50. package/src/index.js +0 -338
  51. package/src/utils.js +0 -252
package/src/index.js DELETED
@@ -1,338 +0,0 @@
1
- /**
2
- * React Native Map Link
3
- */
4
-
5
- import {Linking} from 'react-native';
6
-
7
- import {generatePrefixes, generateTitles, isIOS, icons} from './constants';
8
- import {
9
- askAppChoice,
10
- checkOptions,
11
- getAvailableApps,
12
- checkNotSupportedApps,
13
- } from './utils';
14
-
15
- /**
16
- * Open a maps app, or let the user choose what app to open, with the given location.
17
- *
18
- * @param {{
19
- * latitude: number | string,
20
- * longitude: number | string,
21
- * sourceLatitude: number | undefined | null,
22
- * sourceLongitude: number | undefined | null,
23
- * alwaysIncludeGoogle: boolean | undefined | null,
24
- * googleForceLatLon: boolean | undefined | null,
25
- * googlePlaceId: number | string | undefined | null,
26
- * title: string | undefined | null,
27
- * app: string | undefined | null
28
- * dialogTitle: string | undefined | null
29
- * dialogMessage: string | undefined | null
30
- * cancelText: string | undefined | null
31
- * appsWhiteList: array | undefined | null
32
- * appTitles: object | undefined | null
33
- * naverCallerName: string | undefined
34
- * directionsMode: 'car' | 'walk' | 'public-transport' | 'bike' | undefined
35
- * }} options
36
- */
37
- export async function showLocation(options) {
38
- const prefixes = generatePrefixes(options);
39
- checkOptions(options, prefixes);
40
-
41
- let useSourceDestiny = false;
42
- let sourceLat;
43
- let sourceLng;
44
- let sourceLatLng;
45
-
46
- if (options.sourceLatitude != null && options.sourceLongitude != null) {
47
- useSourceDestiny = true;
48
- sourceLat = parseFloat(options.sourceLatitude);
49
- sourceLng = parseFloat(options.sourceLongitude);
50
- sourceLatLng = `${sourceLat},${sourceLng}`;
51
- }
52
-
53
- const lat = parseFloat(options.latitude);
54
- const lng = parseFloat(options.longitude);
55
- const latlng = `${lat},${lng}`;
56
- const title = options.title && options.title.length ? options.title : null;
57
- const encodedTitle = encodeURIComponent(title);
58
- let app = options.app && options.app.length ? options.app : null;
59
- const dialogTitle =
60
- options.dialogTitle && options.dialogTitle.length
61
- ? options.dialogTitle
62
- : 'Open in Maps';
63
- const dialogMessage =
64
- options.dialogMessage && options.dialogMessage.length
65
- ? options.dialogMessage
66
- : 'What app would you like to use?';
67
- const cancelText =
68
- options.cancelText && options.cancelText.length
69
- ? options.cancelText
70
- : 'Cancel';
71
- const appsWhiteList =
72
- options.appsWhiteList && options.appsWhiteList.length
73
- ? options.appsWhiteList
74
- : null;
75
-
76
- if (!app) {
77
- app = await askAppChoice({
78
- dialogTitle,
79
- dialogMessage,
80
- cancelText,
81
- appsWhiteList,
82
- prefixes,
83
- appTitles: generateTitles(options.appTitles),
84
- });
85
- }
86
-
87
- let url = null;
88
-
89
- const getDirectionsModeAppleMaps = () => {
90
- switch (options.directionsMode) {
91
- case 'car':
92
- return 'd';
93
-
94
- case 'walk':
95
- return 'w';
96
-
97
- case 'public-transport':
98
- return 'r';
99
-
100
- default:
101
- return undefined;
102
- }
103
- };
104
-
105
- const getDirectionsModeGoogleMaps = () => {
106
- switch (options.directionsMode) {
107
- case 'car':
108
- return 'driving';
109
-
110
- case 'walk':
111
- return 'walking';
112
-
113
- case 'public-transport':
114
- return 'transit';
115
-
116
- case 'bike':
117
- return 'bicycling';
118
-
119
- default:
120
- return undefined;
121
- }
122
- };
123
-
124
- switch (app) {
125
- case 'apple-maps':
126
- const appleDirectionMode = getDirectionsModeAppleMaps();
127
- url = prefixes['apple-maps'];
128
- if (useSourceDestiny || options.directionsMode) {
129
- url = `${url}?daddr=${latlng}`;
130
- url += sourceLatLng ? `&saddr=${sourceLatLng}` : '';
131
- } else if (!options.appleIgnoreLatLon) {
132
- url = `${url}?ll=${latlng}`;
133
- }
134
- url +=
135
- useSourceDestiny || options.directionsMode || !options.appleIgnoreLatLon
136
- ? '&'
137
- : '?';
138
- url += `q=${title ? encodedTitle : 'Location'}`;
139
- url += appleDirectionMode ? `&dirflg=${appleDirectionMode}` : '';
140
- break;
141
- case 'google-maps':
142
- const googleDirectionMode = getDirectionsModeGoogleMaps();
143
- // Always using universal URL instead of URI scheme since the latter doesn't support all parameters (#155)
144
- if (useSourceDestiny || options.directionsMode) {
145
- // Use "dir" as this will open up directions
146
- url = 'https://www.google.com/maps/dir/?api=1';
147
- url += sourceLatLng ? `&origin=${sourceLatLng}` : '';
148
- if (!options.googleForceLatLon && title) {
149
- url += `&destination=${encodedTitle}`;
150
- } else {
151
- url += `&destination=${latlng}`;
152
- }
153
-
154
- url += options.googlePlaceId
155
- ? `&destination_place_id=${options.googlePlaceId}`
156
- : '';
157
-
158
- url += googleDirectionMode ? `&travelmode=${googleDirectionMode}` : '';
159
- } else {
160
- // Use "search" as this will open up a single marker
161
- url = 'https://www.google.com/maps/search/?api=1';
162
-
163
- if (!options.googleForceLatLon && title) {
164
- url += `&query=${encodedTitle}`;
165
- } else {
166
- url += `&query=${latlng}`;
167
- }
168
-
169
- url += options.googlePlaceId
170
- ? `&query_place_id=${options.googlePlaceId}`
171
- : '';
172
- }
173
- break;
174
- case 'citymapper':
175
- url = `${prefixes.citymapper}directions?endcoord=${latlng}`;
176
-
177
- if (title) {
178
- url += `&endname=${encodedTitle}`;
179
- }
180
-
181
- if (useSourceDestiny) {
182
- url += `&startcoord=${sourceLatLng}`;
183
- }
184
- break;
185
- case 'uber':
186
- url = `${prefixes.uber}?action=setPickup&dropoff[latitude]=${lat}&dropoff[longitude]=${lng}`;
187
-
188
- if (title) {
189
- url += `&dropoff[nickname]=${encodedTitle}`;
190
- }
191
-
192
- url += useSourceDestiny
193
- ? `&pickup[latitude]=${sourceLat}&pickup[longitude]=${sourceLng}`
194
- : '&pickup=my_location';
195
-
196
- break;
197
- case 'lyft':
198
- url = `${prefixes.lyft}ridetype?id=lyft&destination[latitude]=${lat}&destination[longitude]=${lng}`;
199
-
200
- if (useSourceDestiny) {
201
- url += `&pickup[latitude]=${sourceLat}&pickup[longitude]=${sourceLng}`;
202
- }
203
-
204
- break;
205
- case 'transit':
206
- url = `${prefixes.transit}directions?to=${latlng}`;
207
-
208
- if (useSourceDestiny) {
209
- url += `&from=${sourceLatLng}`;
210
- }
211
- break;
212
- case 'truckmap':
213
- url = `https://truckmap.com/place/${lat},${lng}`;
214
-
215
- if (useSourceDestiny) {
216
- url = `https://truckmap.com/route/${sourceLat},${sourceLng}/${lat},${lng}`;
217
- }
218
- break;
219
- case 'waze':
220
- url = `${prefixes.waze}?ll=${latlng}&navigate=yes`;
221
- if (title) {
222
- url += `&q=${encodedTitle}`;
223
- }
224
- break;
225
- case 'yandex':
226
- url = `${prefixes.yandex}build_route_on_map?lat_to=${lat}&lon_to=${lng}`;
227
-
228
- if (useSourceDestiny) {
229
- url += `&lat_from=${sourceLat}&lon_from=${sourceLng}`;
230
- }
231
- break;
232
- case 'moovit':
233
- url = `${prefixes.moovit}?dest_lat=${lat}&dest_lon=${lng}`;
234
-
235
- if (title) {
236
- url += `&dest_name=${encodedTitle}`;
237
- }
238
-
239
- if (useSourceDestiny) {
240
- url += `&orig_lat=${sourceLat}&orig_lon=${sourceLng}`;
241
- }
242
- break;
243
- case 'yandex-taxi':
244
- url = `${prefixes['yandex-taxi']}route?end-lat=${lat}&end-lon=${lng}&appmetrica_tracking_id=1178268795219780156`;
245
-
246
- break;
247
- case 'yandex-maps':
248
- url = `${prefixes['yandex-maps']}?pt=${lng},${lat}`;
249
-
250
- break;
251
- case 'kakaomap':
252
- url = `${prefixes.kakaomap}look?p=${latlng}`;
253
-
254
- if (useSourceDestiny) {
255
- url = `${prefixes.kakaomap}route?sp=${sourceLat},${sourceLng}&ep=${latlng}&by=CAR`;
256
- }
257
- break;
258
- case 'mapycz':
259
- url = `${prefixes.mapycz}www.mapy.cz/zakladni?x=${lng}&y=${lat}&source=coor&id=${lng},${lat}`;
260
-
261
- break;
262
- case 'maps-me':
263
- url = `${prefixes['maps-me']}route?sll=${sourceLat},${sourceLng}&saddr= &dll=${lat},${lng}&daddr=${title}&type=vehicle`;
264
-
265
- break;
266
- case 'osmand':
267
- url = isIOS
268
- ? `${prefixes.osmand}?lat=${lat}&lon=${lng}`
269
- : `${prefixes.osmand}?q=${lat},${lng}`;
270
-
271
- break;
272
- case 'gett':
273
- url = `${prefixes.gett}order?pickup=my_location&dropoff_latitude=${lat}&dropoff_longitude=${lng}`;
274
-
275
- break;
276
- case 'navermap':
277
- url = `${prefixes.navermap}map?lat=${lat}&lng=${lng}&appname=${options.naverCallerName}`;
278
-
279
- if (useSourceDestiny) {
280
- url = `${prefixes.navermap}route?slat=${sourceLat}&slng=${sourceLng}&dlat=${lat}&dlng=${lng}&appname=${options.naverCallerName}`;
281
- }
282
- break;
283
- case 'dgis':
284
- url = `${prefixes.dgis}routeSearch/to/${lng},${lat}/go`;
285
-
286
- if (useSourceDestiny) {
287
- url = `${prefixes.dgis}routeSearch/to/${lng},${lat}/from/${sourceLng},${sourceLat}/go`;
288
- }
289
- break;
290
- case 'liftago':
291
- url = `${prefixes.liftago}order?destinationLat=${lat}&destinationLon=${lng}`;
292
-
293
- if (title) {
294
- url += `&destinationName=${encodedTitle}`;
295
- }
296
-
297
- if (useSourceDestiny) {
298
- url += `&pickupLat=${sourceLat}&pickupLon=${sourceLng}`;
299
- }
300
- break;
301
- case 'petalmaps':
302
- url = `${prefixes.petalmaps}navigation?daddr=${lat},${lng}`;
303
-
304
- if (useSourceDestiny) {
305
- url += `&saddr=${sourceLat},${sourceLng}`;
306
- }
307
- break;
308
- }
309
-
310
- if (url) {
311
- return Linking.openURL(url).then(() => Promise.resolve(app));
312
- }
313
- }
314
-
315
- export async function getApps(options) {
316
- let apps = await getAvailableApps(generatePrefixes(options));
317
- if ('appsWhiteList' in options && options.appsWhiteList.length) {
318
- checkNotSupportedApps(options.appsWhiteList);
319
- apps = apps.filter((appName) => options.appsWhiteList.includes(appName));
320
- }
321
-
322
- const titles = generateTitles(options.appTitles);
323
- async function open(app) {
324
- return showLocation({...options, app});
325
- }
326
-
327
- let list = [];
328
- for (const app of apps) {
329
- list.push({
330
- id: app,
331
- name: titles[app],
332
- icon: icons[app],
333
- open: open.bind(this, app),
334
- });
335
- }
336
-
337
- return list;
338
- }
package/src/utils.js DELETED
@@ -1,252 +0,0 @@
1
- /**
2
- * React Native Map Link
3
- */
4
-
5
- import {Linking, ActionSheetIOS, Alert} from 'react-native';
6
-
7
- import {appKeys, isIOS} from './constants';
8
-
9
- /**
10
- * Get available navigation apps.
11
- */
12
- export const getAvailableApps = async (prefixes) => {
13
- const availableApps = [];
14
- const promises = [];
15
-
16
- for (const app in prefixes) {
17
- if (prefixes.hasOwnProperty(app)) {
18
- promises.push(
19
- new Promise(async (resolve) => {
20
- try {
21
- const isInstalled = await isAppInstalled(app, prefixes);
22
-
23
- resolve({
24
- app,
25
- isInstalled,
26
- });
27
- } catch (error) {
28
- resolve({
29
- app,
30
- isInstalled: false,
31
- });
32
- }
33
- }),
34
- );
35
- }
36
- }
37
-
38
- const results = await Promise.all(promises);
39
- results.forEach(
40
- ({isInstalled, app}) => isInstalled && availableApps.push(app),
41
- );
42
-
43
- return availableApps;
44
- };
45
-
46
- /**
47
- * Check if a given map app is installed.
48
- *
49
- * @param {string} app
50
- * @param {object} prefixes
51
- * @returns {Promise<boolean>}
52
- */
53
- export function isAppInstalled(app, prefixes) {
54
- return new Promise((resolve) => {
55
- if (!(app in prefixes)) {
56
- return resolve(false);
57
- }
58
-
59
- Linking.canOpenURL(prefixes[app])
60
- .then((result) => {
61
- resolve(!!result);
62
- })
63
- .catch(() => resolve(false));
64
- });
65
- }
66
-
67
- /**
68
- * Check if a given app is supported by this library
69
- *
70
- * @param {string} app
71
- * @returns {boolean}
72
- */
73
- function isSupportedApp(app) {
74
- return appKeys.includes(app);
75
- }
76
-
77
- /**
78
- * Get a list of not supported apps from a given array of apps
79
- *
80
- * @param {array} apps
81
- * @returns {array}
82
- */
83
- function getNotSupportedApps(apps) {
84
- return apps.filter((app) => !isSupportedApp(app));
85
- }
86
-
87
- /**
88
- * Throws an exception if some of the given apps is not supported
89
- *
90
- * @param {array} apps
91
- */
92
- export function checkNotSupportedApps(apps) {
93
- const notSupportedApps = getNotSupportedApps(apps);
94
- if (notSupportedApps.length) {
95
- throw new MapsException(
96
- `appsWhiteList [${notSupportedApps}] are not supported apps, please provide some of the supported apps [${appKeys}]`,
97
- );
98
- }
99
- }
100
-
101
- /**
102
- * Ask the user to choose one of the available map apps.
103
- * @param {{
104
- * title: string | undefined | null
105
- * message: string | undefined | null
106
- * cancelText: string | undefined | null
107
- * appsWhiteList: string[] | null
108
- * prefixes: string[],
109
- * appTitles: object | undefined | null
110
- * }} options
111
- * @returns {Promise}
112
- */
113
- export function askAppChoice({
114
- dialogTitle,
115
- dialogMessage,
116
- cancelText,
117
- appsWhiteList,
118
- prefixes,
119
- appTitles,
120
- }) {
121
- return new Promise(async (resolve) => {
122
- let availableApps = await getAvailableApps(prefixes);
123
-
124
- if (appsWhiteList && appsWhiteList.length) {
125
- availableApps = availableApps.filter((appName) =>
126
- appsWhiteList.includes(appName),
127
- );
128
- }
129
-
130
- if (availableApps.length < 2) {
131
- return resolve(availableApps[0] || null);
132
- }
133
-
134
- if (isIOS) {
135
- const options = availableApps.map((app) => appTitles[app]);
136
- options.push(cancelText);
137
-
138
- ActionSheetIOS.showActionSheetWithOptions(
139
- {
140
- title: dialogTitle,
141
- message: dialogMessage,
142
- options: options,
143
- cancelButtonIndex: options.length - 1,
144
- },
145
- (buttonIndex) => {
146
- if (buttonIndex === options.length - 1) {
147
- return resolve(null);
148
- }
149
- return resolve(availableApps[buttonIndex]);
150
- },
151
- );
152
-
153
- return;
154
- }
155
-
156
- const options = availableApps.map((app) => ({
157
- text: appTitles[app],
158
- onPress: () => resolve(app),
159
- }));
160
- options.unshift({
161
- text: cancelText,
162
- onPress: () => resolve(null),
163
- style: 'cancel',
164
- });
165
-
166
- return Alert.alert(dialogTitle, dialogMessage, options, {
167
- cancelable: true,
168
- onDismiss: () => resolve(null),
169
- });
170
- });
171
- }
172
-
173
- /**
174
- * Check if options are valid and well passed
175
- *
176
- * @param {{
177
- * latitude: number | string,
178
- * longitude: number | string,
179
- * sourceLatitude: number | undefined | null,
180
- * sourceLongitude: number | undefined | null,
181
- * googleForceLatLon: boolean | undefined | null,
182
- * googlePlaceId: number | undefined | null,
183
- * title: string | undefined | null,
184
- * app: string | undefined | null
185
- * dialogTitle: string | undefined | null
186
- * dialogMessage: string | undefined | null
187
- * cancelText: string | undefined | null
188
- * naverCallerName: string | undefined
189
- * }} options
190
- * @param {object} prefixes
191
- */
192
- export function checkOptions(options, prefixes) {
193
- if (!options || typeof options !== 'object') {
194
- throw new MapsException(
195
- 'First parameter of `showLocation` should contain object with options.',
196
- );
197
- }
198
- if (!('latitude' in options) || !('longitude' in options)) {
199
- throw new MapsException(
200
- 'First parameter of `showLocation` should contain object with at least keys `latitude` and `longitude`.',
201
- );
202
- }
203
- if (
204
- 'title' in options &&
205
- options.title &&
206
- typeof options.title !== 'string'
207
- ) {
208
- throw new MapsException('Option `title` should be of type `string`.');
209
- }
210
- if (
211
- 'googleForceLatLon' in options &&
212
- options.googleForceLatLon &&
213
- typeof options.googleForceLatLon !== 'boolean'
214
- ) {
215
- throw new MapsException(
216
- 'Option `googleForceLatLon` should be of type `boolean`.',
217
- );
218
- }
219
- if (
220
- 'googlePlaceId' in options &&
221
- options.googlePlaceId &&
222
- typeof options.googlePlaceId !== 'string'
223
- ) {
224
- throw new MapsException(
225
- 'Option `googlePlaceId` should be of type `string`.',
226
- );
227
- }
228
- if ('app' in options && options.app && !(options.app in prefixes)) {
229
- throw new MapsException(
230
- 'Option `app` should be undefined, null, or one of the following: "' +
231
- Object.keys(prefixes).join('", "') +
232
- '".',
233
- );
234
- }
235
- if ('appsWhiteList' in options && options.appsWhiteList) {
236
- checkNotSupportedApps(options.appsWhiteList);
237
- }
238
- if (
239
- 'appTitles' in options &&
240
- options.appTitles &&
241
- typeof options.appTitles !== 'object'
242
- ) {
243
- throw new MapsException('Option `appTitles` should be of type `object`.');
244
- }
245
- }
246
-
247
- class MapsException {
248
- constructor(message) {
249
- this.message = message;
250
- this.name = 'MapsException';
251
- }
252
- }