summaryrefslogtreecommitdiffhomepage
path: root/app/components/Map.js
diff options
context:
space:
mode:
authorAndrej Mihajlov <and@mullvad.net>2018-01-29 16:13:42 +0100
committerAndrej Mihajlov <and@mullvad.net>2018-01-29 16:13:42 +0100
commitaeb2f9b733e7b11cadb79c114debe5d5e4bdda30 (patch)
tree9fffb4c0fe7042262dfe2be6c85f9b30591b9bc8 /app/components/Map.js
parent2ab013667c028a2e75017080d8cffd37a3a6141d (diff)
parenta5eda4cef865005a13a751c32d42acafcc49a59c (diff)
downloadmullvadvpn-aeb2f9b733e7b11cadb79c114debe5d5e4bdda30.tar.xz
mullvadvpn-aeb2f9b733e7b11cadb79c114debe5d5e4bdda30.zip
Merge branch 'svg-maps'
Diffstat (limited to 'app/components/Map.js')
-rw-r--r--app/components/Map.js114
1 files changed, 81 insertions, 33 deletions
diff --git a/app/components/Map.js b/app/components/Map.js
index 337d5c812b..d416b77961 100644
--- a/app/components/Map.js
+++ b/app/components/Map.js
@@ -1,51 +1,99 @@
// @flow
-import React, { Component } from 'react';
-import ReactMapboxGl, { Marker } from 'react-mapbox-gl';
-import { mapbox as mapboxConfig } from '../config';
-import cheapRuler from 'cheap-ruler';
+import React from 'react';
+import { Component, View } from 'reactxp';
-import type { Coordinate2d } from '../types';
+import SvgMap from './SvgMap';
-const ReactMap = ReactMapboxGl({
- accessToken: mapboxConfig.accessToken,
- attributionControl: false,
- interactive: false,
-});
+export type MapProps = {
+ center: [number, number], // longitude, latitude
+ offset: [number, number], // offset [x, y] from the center of the map
+ zoomLevel: 'high' | 'medium' | 'low',
+ showMarker: boolean,
+ markerStyle: 'secure' | 'unsecure',
+ style: Object,
+};
-export default class Map extends Component {
- props: {
- animate: boolean,
- location: Coordinate2d,
- altitude: number,
- markerImagePath: string,
+type MapState = {
+ bounds: {
+ width: number,
+ height: number
}
+};
+
+export default class Map extends Component {
+
+ props: MapProps;
+
+ state: MapState = {
+ bounds: {
+ width: 0,
+ height: 0,
+ },
+ };
render() {
+ const { width, height } = this.state.bounds;
+ const readyToRenderTheMap = (width > 0 && height > 0);
+ return (
+ <View style={ this.props.style } onLayout={ this._onLayout }>
+ { readyToRenderTheMap && (
+ <SvgMap width={ width }
+ height={ height }
+ center={ this.props.center }
+ offset={ this.props.offset }
+ zoomLevel={ this._zoomLevel(this.props.zoomLevel) }
+ showMarker={ this.props.showMarker }
+ markerImagePath={ this._markerImage(this.props.markerStyle) } />
+ ) }
+ </View>
+ );
+ }
+
+ shouldComponentUpdate(nextProps: MapProps, nextState: MapState) {
+ const oldProps = this.props;
+ const oldState = this.state;
+ return (
+ oldProps.center[0] !== nextProps.center[0] ||
+ oldProps.center[1] !== nextProps.center[1] ||
- const mapBounds = this.calculateMapBounds(this.props.location, this.props.altitude);
+ oldProps.offset[0] !== nextProps.offset[0] ||
+ oldProps.offset[1] !== nextProps.offset[1] ||
- const mapBoundsOptions = { offset: [0, -113], animate: this.props.animate };
+ oldProps.zoomLevel !== nextProps.zoomLevel ||
+ oldProps.showMarker !== nextProps.showMarker ||
+ oldProps.markerStyle !== nextProps.markerStyle ||
- return <ReactMap style={ mapboxConfig.styleURL }
- containerStyle={{ height: '100%' }}
- fitBounds={ mapBounds }
- fitBoundsOptions={ mapBoundsOptions }>
+ oldState.bounds.width !== nextState.bounds.width ||
+ oldState.bounds.height !== nextState.bounds.height
+ );
+ }
- <Marker coordinates={ this.convertToMapCoordinate(this.props.location) } offset={ [0, -10] }>
- <img src={ this.props.markerImagePath } />
- </Marker>
- </ReactMap>;
+ _onLayout = (layoutInfo) => {
+ this.setState({
+ bounds: {
+ width: layoutInfo.width,
+ height: layoutInfo.height,
+ }
+ });
}
- calculateMapBounds(center: Coordinate2d, altitude: number): [Coordinate2d, Coordinate2d] {
- const bounds = cheapRuler(center[0], 'meters').bufferPoint(center, altitude);
- // convert [lat,lng] bounds to [lng,lat]
- return [ [bounds[1], bounds[0]], [bounds[3], bounds[2]] ];
+ // TODO: Remove zoom level in favor of center + coordinate span
+ _zoomLevel(variant: $PropertyType<MapProps, 'zoomLevel'>) {
+ switch(variant) {
+ case 'high': return 1;
+ case 'medium': return 20;
+ case 'low': return 40;
+ }
}
- convertToMapCoordinate(pos: Coordinate2d): Coordinate2d {
- // convert [lat,lng] bounds to [lng,lat]
- return [pos[1], pos[0]];
+ _markerImage(style: $PropertyType<MapProps, 'markerStyle'>) {
+ switch(style) {
+ case 'secure':
+ return './assets/images/location-marker-secure.svg';
+ case 'unsecure':
+ return './assets/images/location-marker-unsecure.svg';
+ }
}
+
}