diff --git a/.gitignore b/.gitignore index 79d62369..04e61805 100644 --- a/.gitignore +++ b/.gitignore @@ -9,3 +9,4 @@ npm-debug.log yarn-error.log dist +/.vscode diff --git a/docs/stories/index.js b/docs/stories/index.js index ef01c58c..8776023f 100644 --- a/docs/stories/index.js +++ b/docs/stories/index.js @@ -1,5 +1,5 @@ import React from 'react'; -import { View, StyleSheet } from 'react-native'; +import { View, StyleSheet, Text } from 'react-native'; import MapView from 'react-native-maps'; import { storiesOf } from '@storybook/react'; @@ -8,7 +8,8 @@ import { action } from '@storybook/addon-actions'; storiesOf('MapView', module) .add('basic', () => ( - + + )) .add('onRegionChangeComplete', () => ( @@ -27,7 +28,12 @@ storiesOf('MapView', module) .add('options', () => ( )); -storiesOf('Marker', module).add('basic', () => ( - - - - - -)); +storiesOf('Marker', module) + .add('basic', () => ( + + (this.map = map)} region={{ latitude: 48.88, longitude: 2.32 }}> + { + this.map.animateToRegion({ + latitude: 48.8828463, + longitude: 2.3229091, + latitudeDelta: 0.1, + longitudeDelta: 0.1, + }); + }} + /> + { + console.log(this.map.getCamera()); + const zoom = this.map.getCamera().zoom === 20 ? 15 : 20; + this.map.animateCamera({ + zoom, + center: { + lat: 48.8828463, + lng: 2.3, + }, + }); + }} + /> + + + )) + .add('Callout', () => ( + + (this.map = map)} region={{ latitude: 48.88, longitude: 2.32 }}> + (this.marker = marker)} + description="Shape the future of mobile with us" + coordinate={{ latitude: 48.8828463, longitude: 2.3229091 }} + onPress={() => { + this.marker1.showCallout(); + }}> + + + Paris + + + + + + )); const styles = StyleSheet.create({ container: { diff --git a/src/Callout.js b/src/Callout.js new file mode 100644 index 00000000..a2fa52b7 --- /dev/null +++ b/src/Callout.js @@ -0,0 +1,18 @@ +import React, { Component } from 'react'; +import { TouchableOpacity } from 'react-native'; +import { InfoWindow } from 'react-google-maps'; + +class MapViewCallout extends Component { + render() { + const { onPress, ...rest } = this.props; + return ( + + + {this.props.children} + + + ); + } +} + +export default MapViewCallout; diff --git a/src/Marker.js b/src/Marker.js index 9d7e4a92..5cae380e 100644 --- a/src/Marker.js +++ b/src/Marker.js @@ -2,14 +2,29 @@ import React, { Component } from 'react'; import { Marker } from 'react-google-maps'; class MapViewMarker extends Component { + state = { + isOpen: false, + }; + showCallout() { + this.setState({ isOpen: true }); + } + hideCallout() { + this.setState({ isOpen: false }); + } render() { - const { description, title, coordinate, ...rest } = this.props; + const { description, title, coordinate, onPress, ...rest } = this.props; + + const childrenWithProps = React.Children.map(this.props.children, child => { + return React.cloneElement(child, { hideCallout: this.hideCallout.bind(this) }); + }); return ( + onClick={onPress}> + {this.state.isOpen && childrenWithProps} + ); } } diff --git a/src/index.js b/src/index.js index 1bd3cc1b..dab5f226 100755 --- a/src/index.js +++ b/src/index.js @@ -3,6 +3,7 @@ import { View, StyleSheet } from 'react-native'; import { withGoogleMap, GoogleMap } from 'react-google-maps'; import Marker from './Marker'; import Polyline from './Polyline'; +import Callout from './Callout'; const GoogleMapContainer = withGoogleMap(props => ( @@ -18,8 +19,23 @@ class MapView extends Component { this.props.onMapReady && this.props.onMapReady(); }; + getCamera = () => { + return { + zoom: this.map.getZoom(), + center: this.map.getCenter(), + heading: this.map.getHeading(), + }; + }; + + animateCamera(camera) { + this.setState({ zoom: camera.zoom }); + this.setState({ center: camera.center }); + } + animateToRegion(coordinates) { - this.setState({ center: { lat: coordinates.latitude, lng: coordinates.longitude } }); + this.setState({ + center: { lat: coordinates.latitude, lng: coordinates.longitude }, + }); } onDragEnd = () => { @@ -34,36 +50,46 @@ class MapView extends Component { }; render() { - const { region, initialRegion, onRegionChange, onPress, options } = this.props; + const { region, initialRegion, onRegionChange, onPress, options, defaultZoom } = this.props; const { center } = this.state; const style = this.props.style || styles.container; - const centerProps = region + const googleMapProps = center + ? { center } + : region ? { center: { lat: region.latitude, lng: region.longitude, }, } - : center - ? { center } : { defaultCenter: { lat: initialRegion.latitude, lng: initialRegion.longitude, }, }; - + const zoom = + defaultZoom || + (region && region.latitudeDelta + ? Math.round(Math.log(360 / region.latitudeDelta) / Math.LN2) + : initialRegion && initialRegion.latitudeDelta + ? Math.round(Math.log(360 / initialRegion.latitudeDelta) / Math.LN2) + : 15); + googleMapProps['zoom'] = this.state.zoom ? this.state.zoom : zoom; return ( } mapElement={
} - {...centerProps} + onZoomChanged={() => { + this.setState({ zoom: this.map.getZoom() }); + }} + {...googleMapProps} onDragStart={onRegionChange} onIdle={this.onDragEnd} - defaultZoom={15} + defaultZoom={zoom} onClick={onPress} options={options}> {this.props.children} @@ -75,6 +101,7 @@ class MapView extends Component { MapView.Marker = Marker; MapView.Polyline = Polyline; +MapView.Callout = Callout; const styles = StyleSheet.create({ container: {