@maplibre/maplibre-react-native 9.1.0 → 10.0.0-alpha.2
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.
- package/.eslintrc.js +10 -2
- package/.husky/pre-commit +5 -0
- package/.yarn/plugins/@yarnpkg/plugin-typescript.cjs +9 -0
- package/.yarn/sdks/eslint/bin/eslint.js +20 -0
- package/.yarn/sdks/eslint/lib/api.js +20 -0
- package/.yarn/sdks/eslint/package.json +6 -0
- package/.yarn/sdks/integrations.yml +5 -0
- package/.yarn/sdks/prettier/index.js +20 -0
- package/.yarn/sdks/prettier/package.json +6 -0
- package/.yarn/sdks/typescript/bin/tsc +20 -0
- package/.yarn/sdks/typescript/bin/tsserver +20 -0
- package/.yarn/sdks/typescript/lib/tsc.js +20 -0
- package/.yarn/sdks/typescript/lib/tsserver.js +225 -0
- package/.yarn/sdks/typescript/lib/tsserverlibrary.js +225 -0
- package/.yarn/sdks/typescript/lib/typescript.js +20 -0
- package/.yarn/sdks/typescript/package.json +6 -0
- package/CHANGELOG.md +18 -0
- package/android/rctmgl/build.gradle +7 -7
- package/android/rctmgl/src/main/java/com/mapbox/rctmgl/location/LocationManager.java +2 -2
- package/android/rctmgl/src/main/java/com/mapbox/rctmgl/modules/RCTMGLOfflineModule.java +21 -26
- package/docs/Annotation.md +8 -9
- package/docs/BackgroundLayer.md +2 -10
- package/docs/Callout.md +5 -5
- package/docs/Camera.md +18 -47
- package/docs/CircleLayer.md +2 -10
- package/docs/FillExtrusionLayer.md +2 -10
- package/docs/FillLayer.md +2 -10
- package/docs/HeatmapLayer.md +2 -10
- package/docs/ImageSource.md +3 -2
- package/docs/Images.md +5 -3
- package/docs/Light.md +1 -1
- package/docs/LineLayer.md +2 -10
- package/docs/MapView.md +53 -37
- package/docs/MarkerView.md +4 -2
- package/docs/NativeUserLocation.md +2 -2
- package/docs/PointAnnotation.md +5 -8
- package/docs/RasterLayer.md +2 -10
- package/docs/RasterSource.md +3 -2
- package/docs/ShapeSource.md +12 -7
- package/docs/Style.md +1 -1
- package/docs/SymbolLayer.md +3 -10
- package/docs/UserLocation.md +8 -10
- package/docs/VectorSource.md +6 -5
- package/docs/coordinates.md +6 -0
- package/docs/docs.json +518 -1272
- package/docs/location.md +6 -0
- package/docs/snapshotManager.md +3 -3
- package/javascript/@types/assets.d.ts +4 -0
- package/javascript/MGLModule.ts +37 -0
- package/javascript/Maplibre.ts +65 -0
- package/javascript/components/AbstractLayer.tsx +107 -0
- package/javascript/components/AbstractSource.tsx +27 -0
- package/javascript/components/BackgroundLayer.tsx +43 -0
- package/javascript/components/{Callout.js → Callout.tsx} +67 -65
- package/javascript/components/{Camera.js → Camera.tsx} +266 -251
- package/javascript/components/CircleLayer.tsx +46 -0
- package/javascript/components/FillExtrusionLayer.tsx +47 -0
- package/javascript/components/FillLayer.tsx +41 -0
- package/javascript/components/{HeadingIndicator.js → HeadingIndicator.tsx} +8 -8
- package/javascript/components/HeatmapLayer.tsx +44 -0
- package/javascript/components/ImageSource.tsx +78 -0
- package/javascript/components/Images.tsx +134 -0
- package/javascript/components/Light.tsx +67 -0
- package/javascript/components/LineLayer.tsx +42 -0
- package/javascript/components/{MapView.js → MapView.tsx} +365 -354
- package/javascript/components/MarkerView.tsx +104 -0
- package/javascript/components/{NativeBridgeComponent.js → NativeBridgeComponent.tsx} +44 -13
- package/javascript/components/NativeUserLocation.tsx +33 -0
- package/javascript/components/PointAnnotation.tsx +221 -0
- package/javascript/components/RasterLayer.tsx +41 -0
- package/javascript/components/RasterSource.tsx +117 -0
- package/javascript/components/ShapeSource.tsx +383 -0
- package/javascript/components/{Style.js → Style.tsx} +129 -38
- package/javascript/components/SymbolLayer.tsx +72 -0
- package/javascript/components/{UserLocation.js → UserLocation.tsx} +111 -110
- package/javascript/components/VectorSource.tsx +207 -0
- package/javascript/components/annotations/Annotation.tsx +134 -0
- package/javascript/index.ts +4 -0
- package/javascript/modules/location/{locationManager.js → locationManager.ts} +71 -10
- package/javascript/modules/offline/{OfflineCreatePackOptions.js → OfflineCreatePackOptions.ts} +20 -4
- package/javascript/modules/offline/{OfflinePack.js → OfflinePack.ts} +23 -7
- package/javascript/modules/offline/{offlineManager.js → offlineManager.ts} +81 -24
- package/javascript/modules/snapshot/{SnapshotOptions.js → SnapshotOptions.ts} +43 -6
- package/javascript/modules/snapshot/{snapshotManager.js → snapshotManager.ts} +5 -5
- package/javascript/requestAndroidLocationPermissions.ts +29 -0
- package/javascript/types/BaseProps.ts +5 -0
- package/javascript/types/OnPressEvent.ts +13 -0
- package/javascript/types/index.ts +7 -0
- package/javascript/utils/BridgeValue.ts +90 -0
- package/javascript/utils/{Logger.js → Logger.ts} +37 -18
- package/javascript/utils/MaplibreStyles.d.ts +1486 -0
- package/javascript/utils/StyleValue.ts +49 -0
- package/javascript/utils/animated/AbstractAnimatedCoordinates.ts +134 -0
- package/javascript/utils/animated/AnimatedCoordinatesArray.ts +112 -0
- package/javascript/utils/animated/{AnimatedExtractCoordinateFromArray.js → AnimatedExtractCoordinateFromArray.ts} +5 -5
- package/javascript/utils/animated/{AnimatedPoint.js → AnimatedPoint.ts} +20 -12
- package/javascript/utils/animated/{AnimatedRouteCoordinatesArray.js → AnimatedRouteCoordinatesArray.ts} +39 -14
- package/javascript/utils/animated/{AnimatedShape.js → AnimatedShape.ts} +31 -10
- package/javascript/utils/{deprecation.js → deprecation.ts} +9 -6
- package/javascript/utils/filterUtils.ts +9 -0
- package/javascript/utils/geoUtils.ts +79 -0
- package/javascript/utils/{index.js → index.ts} +44 -24
- package/javascript/utils/styleMap.ts +264 -0
- package/package.json +35 -27
- package/plugin/build/withMapLibre.js +18 -3
- package/scripts/autogenHelpers/globals.js +1 -1
- package/scripts/autogenerate.js +14 -6
- package/scripts/download-style-spec.sh +1 -1
- package/scripts/templates/MaplibreStyles.ts.ejs +99 -0
- package/scripts/templates/index.d.ts.ejs +71 -42
- package/scripts/templates/{styleMap.js.ejs → styleMap.ts.ejs} +3 -33
- package/setup-jest.js +1 -10
- package/tsconfig.json +20 -61
- package/index.d.ts +0 -955
- package/javascript/components/AbstractLayer.js +0 -75
- package/javascript/components/AbstractSource.js +0 -15
- package/javascript/components/BackgroundLayer.js +0 -97
- package/javascript/components/CircleLayer.js +0 -101
- package/javascript/components/FillExtrusionLayer.js +0 -98
- package/javascript/components/FillLayer.js +0 -94
- package/javascript/components/HeatmapLayer.js +0 -99
- package/javascript/components/ImageSource.js +0 -82
- package/javascript/components/Images.js +0 -119
- package/javascript/components/Light.js +0 -47
- package/javascript/components/LineLayer.js +0 -94
- package/javascript/components/MarkerView.js +0 -87
- package/javascript/components/NativeUserLocation.js +0 -41
- package/javascript/components/PointAnnotation.js +0 -216
- package/javascript/components/RasterLayer.js +0 -95
- package/javascript/components/RasterSource.js +0 -124
- package/javascript/components/ShapeSource.js +0 -372
- package/javascript/components/SymbolLayer.js +0 -120
- package/javascript/components/VectorSource.js +0 -200
- package/javascript/components/annotations/Annotation.js +0 -122
- package/javascript/index.js +0 -149
- package/javascript/utils/BridgeValue.js +0 -81
- package/javascript/utils/animated/AnimatedCoordinatesArray.js +0 -191
- package/javascript/utils/filterUtils.js +0 -7
- package/javascript/utils/geoUtils.js +0 -73
- package/javascript/utils/styleMap.js +0 -1932
- /package/javascript/utils/animated/{Animated.js → Animated.ts} +0 -0
|
@@ -0,0 +1,72 @@
|
|
|
1
|
+
import {type SymbolLayerStyleProps} from '../utils/MaplibreStyles';
|
|
2
|
+
import BaseProps from '../types/BaseProps';
|
|
3
|
+
|
|
4
|
+
import AbstractLayer, {BaseLayerProps, NativeBaseProps} from './AbstractLayer';
|
|
5
|
+
|
|
6
|
+
import React, {ReactElement} from 'react';
|
|
7
|
+
import {View, NativeModules, requireNativeComponent} from 'react-native';
|
|
8
|
+
|
|
9
|
+
const MapLibreGL = NativeModules.MGLModule;
|
|
10
|
+
|
|
11
|
+
export const NATIVE_MODULE_NAME = 'RCTMGLSymbolLayer';
|
|
12
|
+
|
|
13
|
+
interface SymbolLayerProps extends BaseProps, BaseLayerProps {
|
|
14
|
+
/**
|
|
15
|
+
* Customizable style attributes
|
|
16
|
+
*/
|
|
17
|
+
style?: SymbolLayerStyleProps;
|
|
18
|
+
|
|
19
|
+
/**
|
|
20
|
+
* @deprecated passed children used to create an image with id of symbol in style and also set the iconImageName property accordingly.
|
|
21
|
+
* This is now deprecated, use Image component instead.
|
|
22
|
+
*/
|
|
23
|
+
children?: ReactElement | ReactElement[];
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
interface NativeProps extends Omit<SymbolLayerProps, 'style'>, NativeBaseProps {
|
|
27
|
+
snapshot: boolean;
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
/**
|
|
31
|
+
* SymbolLayer is a style layer that renders icon and text labels at points or along lines on the map.
|
|
32
|
+
*/
|
|
33
|
+
class SymbolLayer extends AbstractLayer<SymbolLayerProps, NativeBaseProps> {
|
|
34
|
+
static defaultProps = {
|
|
35
|
+
sourceID: MapLibreGL.StyleSource.DefaultSourceID,
|
|
36
|
+
};
|
|
37
|
+
|
|
38
|
+
_shouldSnapshot(): boolean {
|
|
39
|
+
let isSnapshot = false;
|
|
40
|
+
|
|
41
|
+
if (React.Children.count(this.props.children) <= 0) {
|
|
42
|
+
return isSnapshot;
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
React.Children.forEach(this.props.children, child => {
|
|
46
|
+
if (child?.type === View) {
|
|
47
|
+
isSnapshot = true;
|
|
48
|
+
}
|
|
49
|
+
});
|
|
50
|
+
|
|
51
|
+
return isSnapshot;
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
render(): ReactElement {
|
|
55
|
+
const props = {
|
|
56
|
+
...this.baseProps,
|
|
57
|
+
snapshot: this._shouldSnapshot(),
|
|
58
|
+
sourceLayerID: this.props.sourceLayerID,
|
|
59
|
+
};
|
|
60
|
+
|
|
61
|
+
return (
|
|
62
|
+
<RCTMGLSymbolLayer ref={this.setNativeLayer} {...props}>
|
|
63
|
+
{this.props.children}
|
|
64
|
+
</RCTMGLSymbolLayer>
|
|
65
|
+
);
|
|
66
|
+
}
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
const RCTMGLSymbolLayer =
|
|
70
|
+
requireNativeComponent<NativeProps>(NATIVE_MODULE_NAME);
|
|
71
|
+
|
|
72
|
+
export default SymbolLayer;
|
|
@@ -1,115 +1,122 @@
|
|
|
1
|
-
import locationManager from '../modules/location/locationManager';
|
|
1
|
+
import locationManager, {Location} from '../modules/location/locationManager';
|
|
2
|
+
import {CircleLayerStyleProps} from '../utils/MaplibreStyles';
|
|
2
3
|
|
|
3
4
|
import Annotation from './annotations/Annotation';
|
|
4
5
|
import CircleLayer from './CircleLayer';
|
|
5
6
|
import HeadingIndicator from './HeadingIndicator';
|
|
6
7
|
import NativeUserLocation from './NativeUserLocation';
|
|
7
8
|
|
|
8
|
-
import
|
|
9
|
-
import React from 'react';
|
|
9
|
+
import React, {ReactElement} from 'react';
|
|
10
10
|
|
|
11
11
|
const mapboxBlue = 'rgba(51, 181, 229, 100)';
|
|
12
12
|
|
|
13
|
-
const layerStyles = {
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
circlePitchAlignment: 'map',
|
|
30
|
-
},
|
|
13
|
+
const layerStyles: Record<string, CircleLayerStyleProps> = {
|
|
14
|
+
pluse: {
|
|
15
|
+
circleRadius: 15,
|
|
16
|
+
circleColor: mapboxBlue,
|
|
17
|
+
circleOpacity: 0.2,
|
|
18
|
+
circlePitchAlignment: 'map',
|
|
19
|
+
},
|
|
20
|
+
background: {
|
|
21
|
+
circleRadius: 9,
|
|
22
|
+
circleColor: '#fff',
|
|
23
|
+
circlePitchAlignment: 'map',
|
|
24
|
+
},
|
|
25
|
+
foreground: {
|
|
26
|
+
circleRadius: 6,
|
|
27
|
+
circleColor: mapboxBlue,
|
|
28
|
+
circlePitchAlignment: 'map',
|
|
31
29
|
},
|
|
32
30
|
};
|
|
33
31
|
|
|
34
|
-
export const normalIcon = (
|
|
32
|
+
export const normalIcon = (
|
|
33
|
+
showsUserHeadingIndicator?: boolean,
|
|
34
|
+
heading?: number,
|
|
35
|
+
): ReactElement[] => [
|
|
35
36
|
<CircleLayer
|
|
36
37
|
key="mapboxUserLocationPluseCircle"
|
|
37
38
|
id="mapboxUserLocationPluseCircle"
|
|
38
|
-
style={layerStyles.
|
|
39
|
+
style={layerStyles.pluse}
|
|
39
40
|
/>,
|
|
40
41
|
<CircleLayer
|
|
41
42
|
key="mapboxUserLocationWhiteCircle"
|
|
42
43
|
id="mapboxUserLocationWhiteCircle"
|
|
43
|
-
style={layerStyles.
|
|
44
|
+
style={layerStyles.background}
|
|
44
45
|
/>,
|
|
45
46
|
<CircleLayer
|
|
46
47
|
key="mapboxUserLocationBlueCicle"
|
|
47
48
|
id="mapboxUserLocationBlueCicle"
|
|
48
49
|
aboveLayerID="mapboxUserLocationWhiteCircle"
|
|
49
|
-
style={layerStyles.
|
|
50
|
+
style={layerStyles.foreground}
|
|
50
51
|
/>,
|
|
51
|
-
...(showsUserHeadingIndicator && heading
|
|
52
|
-
? [HeadingIndicator(heading)]
|
|
52
|
+
...(showsUserHeadingIndicator && heading
|
|
53
|
+
? [HeadingIndicator({heading})]
|
|
53
54
|
: []),
|
|
54
55
|
];
|
|
55
56
|
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
57
|
+
interface UserLocationProps {
|
|
58
|
+
/**
|
|
59
|
+
* Whether location icon is animated between updates
|
|
60
|
+
*/
|
|
61
|
+
animated?: boolean;
|
|
62
|
+
/**
|
|
63
|
+
* Which render mode to use.
|
|
64
|
+
* Can either be `normal` or `native`
|
|
65
|
+
*/
|
|
66
|
+
renderMode?: 'normal' | 'native';
|
|
67
|
+
/**
|
|
68
|
+
* native/android only render mode
|
|
69
|
+
*
|
|
70
|
+
* - normal: just a circle
|
|
71
|
+
* - compass: triangle with heading
|
|
72
|
+
* - gps: large arrow
|
|
73
|
+
*
|
|
74
|
+
* @platform android
|
|
75
|
+
*/
|
|
76
|
+
androidRenderMode?: 'normal' | 'compass' | 'gps';
|
|
77
|
+
/**
|
|
78
|
+
* Whether location icon is visible
|
|
79
|
+
*/
|
|
80
|
+
visible?: boolean;
|
|
81
|
+
/**
|
|
82
|
+
* Callback that is triggered on location icon press
|
|
83
|
+
*/
|
|
84
|
+
onPress?(): void;
|
|
85
|
+
/**
|
|
86
|
+
* Callback that is triggered on location update
|
|
87
|
+
*/
|
|
88
|
+
onUpdate?(location: Location): void;
|
|
89
|
+
/**
|
|
90
|
+
* Show or hide small arrow which indicates direction the device is pointing relative to north.
|
|
91
|
+
*/
|
|
92
|
+
showsUserHeadingIndicator?: boolean;
|
|
93
|
+
/**
|
|
94
|
+
* Minimum amount of movement before GPS location is updated in meters
|
|
95
|
+
*/
|
|
96
|
+
minDisplacement?: number;
|
|
97
|
+
/**
|
|
98
|
+
* Custom location icon of type mapbox-gl-native components
|
|
99
|
+
*
|
|
100
|
+
* NOTE: Forking maintainer does not understand the above comment.
|
|
101
|
+
*/
|
|
102
|
+
children?: ReactElement | ReactElement[];
|
|
103
|
+
}
|
|
104
|
+
|
|
105
|
+
interface UserLocationState {
|
|
106
|
+
shouldShowUserLocation: boolean;
|
|
107
|
+
coordinates?: number[];
|
|
108
|
+
heading?: number;
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
export enum UserLocationRenderMode {
|
|
112
|
+
Native = 'native',
|
|
113
|
+
Normal = 'normal',
|
|
114
|
+
}
|
|
112
115
|
|
|
116
|
+
class UserLocation extends React.Component<
|
|
117
|
+
UserLocationProps,
|
|
118
|
+
UserLocationState
|
|
119
|
+
> {
|
|
113
120
|
static defaultProps = {
|
|
114
121
|
animated: true,
|
|
115
122
|
visible: true,
|
|
@@ -118,18 +125,11 @@ class UserLocation extends React.Component {
|
|
|
118
125
|
renderMode: 'normal',
|
|
119
126
|
};
|
|
120
127
|
|
|
121
|
-
|
|
122
|
-
Native: 'native',
|
|
123
|
-
Normal: 'normal',
|
|
124
|
-
};
|
|
125
|
-
|
|
126
|
-
constructor(props) {
|
|
128
|
+
constructor(props: UserLocationProps) {
|
|
127
129
|
super(props);
|
|
128
130
|
|
|
129
131
|
this.state = {
|
|
130
132
|
shouldShowUserLocation: false,
|
|
131
|
-
coordinates: null,
|
|
132
|
-
heading: null,
|
|
133
133
|
};
|
|
134
134
|
|
|
135
135
|
this._onLocationUpdate = this._onLocationUpdate.bind(this);
|
|
@@ -137,35 +137,36 @@ class UserLocation extends React.Component {
|
|
|
137
137
|
|
|
138
138
|
// required as #setLocationManager attempts to setState
|
|
139
139
|
// after component unmount
|
|
140
|
-
_isMounted = null;
|
|
140
|
+
_isMounted: boolean | null = null;
|
|
141
141
|
|
|
142
|
+
renderMode: UserLocationRenderMode | undefined;
|
|
142
143
|
locationManagerRunning = false;
|
|
143
144
|
|
|
144
|
-
async componentDidMount() {
|
|
145
|
+
async componentDidMount(): Promise<void> {
|
|
145
146
|
this._isMounted = true;
|
|
146
147
|
|
|
147
148
|
await this.setLocationManager({
|
|
148
149
|
running: this.needsLocationManagerRunning(),
|
|
149
150
|
});
|
|
150
151
|
|
|
151
|
-
if (this.renderMode ===
|
|
152
|
+
if (this.renderMode === UserLocationRenderMode.Native) {
|
|
152
153
|
return;
|
|
153
154
|
}
|
|
154
155
|
|
|
155
|
-
locationManager.setMinDisplacement(this.props.minDisplacement);
|
|
156
|
+
locationManager.setMinDisplacement(this.props.minDisplacement ?? 0);
|
|
156
157
|
}
|
|
157
158
|
|
|
158
|
-
async componentDidUpdate(prevProps) {
|
|
159
|
+
async componentDidUpdate(prevProps: UserLocationProps): Promise<void> {
|
|
159
160
|
await this.setLocationManager({
|
|
160
161
|
running: this.needsLocationManagerRunning(),
|
|
161
162
|
});
|
|
162
163
|
|
|
163
164
|
if (this.props.minDisplacement !== prevProps.minDisplacement) {
|
|
164
|
-
locationManager.setMinDisplacement(this.props.minDisplacement);
|
|
165
|
+
locationManager.setMinDisplacement(this.props.minDisplacement ?? 0);
|
|
165
166
|
}
|
|
166
167
|
}
|
|
167
168
|
|
|
168
|
-
async componentWillUnmount() {
|
|
169
|
+
async componentWillUnmount(): Promise<void> {
|
|
169
170
|
this._isMounted = false;
|
|
170
171
|
await this.setLocationManager({running: false});
|
|
171
172
|
}
|
|
@@ -180,7 +181,7 @@ class UserLocation extends React.Component {
|
|
|
180
181
|
* @param {Object} running - Object with key `running` and `boolean` value
|
|
181
182
|
* @return {Promise<void>}
|
|
182
183
|
*/
|
|
183
|
-
async setLocationManager({running}) {
|
|
184
|
+
async setLocationManager({running}: {running: boolean}): Promise<void> {
|
|
184
185
|
if (this.locationManagerRunning !== running) {
|
|
185
186
|
this.locationManagerRunning = running;
|
|
186
187
|
if (running) {
|
|
@@ -199,24 +200,24 @@ class UserLocation extends React.Component {
|
|
|
199
200
|
*
|
|
200
201
|
* @return {boolean}
|
|
201
202
|
*/
|
|
202
|
-
needsLocationManagerRunning() {
|
|
203
|
-
return (
|
|
203
|
+
needsLocationManagerRunning(): boolean {
|
|
204
|
+
return !!(
|
|
204
205
|
!!this.props.onUpdate ||
|
|
205
|
-
(this.props.renderMode ===
|
|
206
|
+
(this.props.renderMode === UserLocationRenderMode.Normal &&
|
|
206
207
|
this.props.visible)
|
|
207
208
|
);
|
|
208
209
|
}
|
|
209
210
|
|
|
210
|
-
_onLocationUpdate(location) {
|
|
211
|
+
_onLocationUpdate(location: Location | null): void {
|
|
211
212
|
if (!this._isMounted || !location) {
|
|
212
213
|
return;
|
|
213
214
|
}
|
|
214
|
-
let coordinates
|
|
215
|
-
let heading
|
|
215
|
+
let coordinates;
|
|
216
|
+
let heading;
|
|
216
217
|
|
|
217
218
|
if (location && location.coords) {
|
|
218
219
|
const {longitude, latitude} = location.coords;
|
|
219
|
-
|
|
220
|
+
heading = location.coords.heading;
|
|
220
221
|
coordinates = [longitude, latitude];
|
|
221
222
|
}
|
|
222
223
|
|
|
@@ -230,17 +231,17 @@ class UserLocation extends React.Component {
|
|
|
230
231
|
}
|
|
231
232
|
}
|
|
232
233
|
|
|
233
|
-
_renderNative() {
|
|
234
|
+
_renderNative(): ReactElement {
|
|
234
235
|
const {androidRenderMode, showsUserHeadingIndicator} = this.props;
|
|
235
236
|
|
|
236
|
-
|
|
237
|
+
const props = {
|
|
237
238
|
androidRenderMode,
|
|
238
239
|
iosShowsUserHeadingIndicator: showsUserHeadingIndicator,
|
|
239
240
|
};
|
|
240
241
|
return <NativeUserLocation {...props} />;
|
|
241
242
|
}
|
|
242
243
|
|
|
243
|
-
render() {
|
|
244
|
+
render(): ReactElement | null {
|
|
244
245
|
const {heading, coordinates} = this.state;
|
|
245
246
|
const {children, visible, showsUserHeadingIndicator, onPress, animated} =
|
|
246
247
|
this.props;
|
|
@@ -249,7 +250,7 @@ class UserLocation extends React.Component {
|
|
|
249
250
|
return null;
|
|
250
251
|
}
|
|
251
252
|
|
|
252
|
-
if (this.props.renderMode ===
|
|
253
|
+
if (this.props.renderMode === UserLocationRenderMode.Native) {
|
|
253
254
|
return this._renderNative();
|
|
254
255
|
}
|
|
255
256
|
|
|
@@ -0,0 +1,207 @@
|
|
|
1
|
+
import {FilterExpression} from '../utils/MaplibreStyles';
|
|
2
|
+
import {cloneReactChildrenWithProps, isFunction, isAndroid} from '../utils';
|
|
3
|
+
import {getFilter} from '../utils/filterUtils';
|
|
4
|
+
import {copyPropertiesAsDeprecated} from '../utils/deprecation';
|
|
5
|
+
import BaseProps from '../types/BaseProps';
|
|
6
|
+
import OnPressEvent from '../types/OnPressEvent';
|
|
7
|
+
|
|
8
|
+
import AbstractSource from './AbstractSource';
|
|
9
|
+
import NativeBridgeComponent from './NativeBridgeComponent';
|
|
10
|
+
|
|
11
|
+
import React, {Component, ReactNode} from 'react';
|
|
12
|
+
import {
|
|
13
|
+
NativeMethods,
|
|
14
|
+
NativeModules,
|
|
15
|
+
NativeSyntheticEvent,
|
|
16
|
+
requireNativeComponent,
|
|
17
|
+
} from 'react-native';
|
|
18
|
+
import {featureCollection} from '@turf/helpers';
|
|
19
|
+
|
|
20
|
+
const MapLibreGL = NativeModules.MGLModule;
|
|
21
|
+
|
|
22
|
+
export const NATIVE_MODULE_NAME = 'RCTMGLVectorSource';
|
|
23
|
+
|
|
24
|
+
interface VectorSourceProps extends BaseProps {
|
|
25
|
+
/**
|
|
26
|
+
* A string that uniquely identifies the source.
|
|
27
|
+
*/
|
|
28
|
+
id: string;
|
|
29
|
+
/**
|
|
30
|
+
* A URL to a TileJSON configuration file describing the source’s contents and other metadata.
|
|
31
|
+
*/
|
|
32
|
+
url?: string;
|
|
33
|
+
/**
|
|
34
|
+
* An array of tile URL templates. If multiple endpoints are specified, clients may use any combination of endpoints.
|
|
35
|
+
* Example: https://example.com/vector-tiles/{z}/{x}/{y}.pbf
|
|
36
|
+
*/
|
|
37
|
+
tileUrlTemplates?: string[];
|
|
38
|
+
/**
|
|
39
|
+
* An unsigned integer that specifies the minimum zoom level at which to display tiles from the source.
|
|
40
|
+
* The value should be between 0 and 22, inclusive, and less than
|
|
41
|
+
* maxZoomLevel, if specified. The default value for this option is 0.
|
|
42
|
+
*/
|
|
43
|
+
minZoomLevel?: number;
|
|
44
|
+
/**
|
|
45
|
+
* An unsigned integer that specifies the maximum zoom level at which to display tiles from the source.
|
|
46
|
+
* The value should be between 0 and 22, inclusive, and less than
|
|
47
|
+
* minZoomLevel, if specified. The default value for this option is 22.
|
|
48
|
+
*/
|
|
49
|
+
maxZoomLevel?: number;
|
|
50
|
+
/**
|
|
51
|
+
* Influences the y direction of the tile coordinates. (tms inverts y axis)
|
|
52
|
+
*/
|
|
53
|
+
tms?: boolean;
|
|
54
|
+
/**
|
|
55
|
+
* An HTML or literal text string defining the buttons to be displayed in an action sheet when the
|
|
56
|
+
* source is part of a map view’s style and the map view’s attribution button is pressed.
|
|
57
|
+
*/
|
|
58
|
+
attribution?: string;
|
|
59
|
+
/**
|
|
60
|
+
* Source press listener, gets called when a user presses one of the children layers only
|
|
61
|
+
* if that layer has a higher z-index than another source layers
|
|
62
|
+
*
|
|
63
|
+
* @param {Object} event
|
|
64
|
+
* @param {Object[]} event.features - the geojson features that have hit by the press (might be multiple)
|
|
65
|
+
* @param {Object} event.coordinates - the coordinates of the click
|
|
66
|
+
* @param {Object} event.point - the point of the click
|
|
67
|
+
*/
|
|
68
|
+
onPress?: (event: OnPressEvent) => void;
|
|
69
|
+
/**
|
|
70
|
+
* Overrides the default touch hitbox(44x44 pixels) for the source layers
|
|
71
|
+
*/
|
|
72
|
+
hitbox?: {
|
|
73
|
+
/**
|
|
74
|
+
* `width` of hitbox
|
|
75
|
+
*/
|
|
76
|
+
width: number;
|
|
77
|
+
/**
|
|
78
|
+
* `height` of hitbox
|
|
79
|
+
*/
|
|
80
|
+
height: number;
|
|
81
|
+
};
|
|
82
|
+
|
|
83
|
+
children?: React.ReactElement | React.ReactElement[];
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
type NativeProps = VectorSourceProps;
|
|
87
|
+
|
|
88
|
+
/**
|
|
89
|
+
* VectorSource is a map content source that supplies tiled vector data in Mapbox Vector Tile format to be shown on the map.
|
|
90
|
+
* The location of and metadata about the tiles are defined either by an option dictionary or by an external file that conforms to the TileJSON specification.
|
|
91
|
+
*/
|
|
92
|
+
class VectorSource extends NativeBridgeComponent(
|
|
93
|
+
AbstractSource<VectorSourceProps, NativeProps>,
|
|
94
|
+
NATIVE_MODULE_NAME,
|
|
95
|
+
) {
|
|
96
|
+
static defaultProps = {
|
|
97
|
+
id: MapLibreGL.StyleSource.DefaultSourceID,
|
|
98
|
+
};
|
|
99
|
+
|
|
100
|
+
constructor(props: VectorSourceProps) {
|
|
101
|
+
super(props);
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
_setNativeRef(
|
|
105
|
+
nativeRef: (Component<NativeProps> & Readonly<NativeMethods>) | null,
|
|
106
|
+
): void {
|
|
107
|
+
if (nativeRef) {
|
|
108
|
+
this.setNativeRef(nativeRef);
|
|
109
|
+
super._runPendingNativeCommands(nativeRef);
|
|
110
|
+
}
|
|
111
|
+
}
|
|
112
|
+
|
|
113
|
+
/**
|
|
114
|
+
* Returns all features that match the query parameters regardless of whether or not the feature is
|
|
115
|
+
* currently rendered on the map. The domain of the query includes all currently-loaded vector tiles
|
|
116
|
+
* and GeoJSON source tiles. This function does not check tiles outside of the visible viewport.
|
|
117
|
+
*
|
|
118
|
+
* @example
|
|
119
|
+
* vectorSource.features(['id1', 'id2'])
|
|
120
|
+
*
|
|
121
|
+
* @param {Array=} layerIDs - A set of strings that correspond to the names of layers defined in the current style. Only the features contained in these layers are included in the returned array.
|
|
122
|
+
* @param {Array=} filter - an optional filter statement to filter the returned Features.
|
|
123
|
+
* @return {GeoJSON.FeatureCollection}
|
|
124
|
+
*/
|
|
125
|
+
async features(
|
|
126
|
+
layerIDs = [],
|
|
127
|
+
filter?: FilterExpression,
|
|
128
|
+
): Promise<GeoJSON.FeatureCollection> {
|
|
129
|
+
if (!this._nativeRef) {
|
|
130
|
+
return featureCollection([]);
|
|
131
|
+
}
|
|
132
|
+
const res: {data: string | GeoJSON.FeatureCollection} =
|
|
133
|
+
await this._runNativeCommand('features', this._nativeRef, [
|
|
134
|
+
[[layerIDs, getFilter(filter)]],
|
|
135
|
+
]);
|
|
136
|
+
|
|
137
|
+
if (isAndroid()) {
|
|
138
|
+
return JSON.parse(res?.data as string);
|
|
139
|
+
}
|
|
140
|
+
|
|
141
|
+
return res.data as GeoJSON.FeatureCollection;
|
|
142
|
+
}
|
|
143
|
+
|
|
144
|
+
onPress(event: NativeSyntheticEvent<{payload: OnPressEvent}>): void {
|
|
145
|
+
const {onPress} = this.props;
|
|
146
|
+
|
|
147
|
+
if (!onPress) {
|
|
148
|
+
return;
|
|
149
|
+
}
|
|
150
|
+
const {
|
|
151
|
+
nativeEvent: {
|
|
152
|
+
payload: {features, coordinates, point},
|
|
153
|
+
},
|
|
154
|
+
} = event;
|
|
155
|
+
let newEvent = {
|
|
156
|
+
features,
|
|
157
|
+
coordinates,
|
|
158
|
+
point,
|
|
159
|
+
};
|
|
160
|
+
newEvent = copyPropertiesAsDeprecated(
|
|
161
|
+
event,
|
|
162
|
+
newEvent,
|
|
163
|
+
(key: string) => {
|
|
164
|
+
console.warn(
|
|
165
|
+
`event.${key} is deprecated on VectorSource#onPress, please use event.features`,
|
|
166
|
+
);
|
|
167
|
+
},
|
|
168
|
+
{
|
|
169
|
+
nativeEvent: (origNativeEvent: OnPressEvent) => ({
|
|
170
|
+
...origNativeEvent,
|
|
171
|
+
payload: features[0],
|
|
172
|
+
}),
|
|
173
|
+
},
|
|
174
|
+
);
|
|
175
|
+
|
|
176
|
+
onPress(newEvent);
|
|
177
|
+
}
|
|
178
|
+
|
|
179
|
+
render(): ReactNode {
|
|
180
|
+
const props = {
|
|
181
|
+
id: this.props.id,
|
|
182
|
+
url: this.props.url,
|
|
183
|
+
tileUrlTemplates: this.props.tileUrlTemplates,
|
|
184
|
+
minZoomLevel: this.props.minZoomLevel,
|
|
185
|
+
maxZoomLevel: this.props.maxZoomLevel,
|
|
186
|
+
tms: this.props.tms,
|
|
187
|
+
attribution: this.props.attribution,
|
|
188
|
+
hitbox: this.props.hitbox,
|
|
189
|
+
hasPressListener: isFunction(this.props.onPress),
|
|
190
|
+
onMapboxVectorSourcePress: this.onPress.bind(this),
|
|
191
|
+
onPress: undefined,
|
|
192
|
+
onAndroidCallback: isAndroid() ? this._onAndroidCallback : undefined,
|
|
193
|
+
};
|
|
194
|
+
return (
|
|
195
|
+
<RCTMGLVectorSource ref={this.setNativeRef} {...props}>
|
|
196
|
+
{cloneReactChildrenWithProps(this.props.children, {
|
|
197
|
+
sourceID: this.props.id,
|
|
198
|
+
})}
|
|
199
|
+
</RCTMGLVectorSource>
|
|
200
|
+
);
|
|
201
|
+
}
|
|
202
|
+
}
|
|
203
|
+
|
|
204
|
+
const RCTMGLVectorSource =
|
|
205
|
+
requireNativeComponent<VectorSourceProps>(NATIVE_MODULE_NAME);
|
|
206
|
+
|
|
207
|
+
export default VectorSource;
|