Skip to content

Instantly share code, notes, and snippets.

@dually8
Created February 14, 2017 13:48
Show Gist options
  • Save dually8/9e056d8a678982539338529ebc2e2d42 to your computer and use it in GitHub Desktop.
Save dually8/9e056d8a678982539338529ebc2e2d42 to your computer and use it in GitHub Desktop.
Example MapView.Callout that works like the native one.
import React, { Component } from 'react';
import {
Dimensions,
Modal,
Platform,
StyleSheet,
Text,
TouchableHighlight,
View,
} from 'react-native';
import MapView from 'react-native-maps';
import { modalActionCreators } from '../redux'
export default class SomeMapView extends Component {
constructor(props) {
super(props);
}
_closeModal() {
// dispatch modal visibility to false
this.props.dispatch(modalActionCreators.closeModal());
}
_onRowPress(...args) {
// args is array of a single object
const data = args[0];
this.props.dispatch(modalActionCreators.showModal(data));
}
_getInitialRegion() {
if (this.props.modalData && this.props.modalData.coordinates) {
return {
latitude: this.props.modalData.coordinates.latitude,
longitude: this.props.modalData.coordinates.longitude,
latitudeDelta: 0.922,
longitudeDelta: 0.421,
}
}
return {
latitude: 40.674,
longitude: -73.954,
latitudeDelta: 0.922,
longitudeDelta: 0.421,
}
}
_onCalloutPress = (data) => {
console.log(data);
}
render() {
return (
<View style={styles.container}>
<Modal
animationType={'fade'}
transparent={true}
visible={this.props.modalVisible}
onRequestClose={() => this._closeModal()}
supportedOrientations={['portrait', 'landscape']}
>
<View style={[styles.pushDown, styles.container]}>
<View style={styles.modalHeader}>
<View style={styles.modalHeaderSection} />
<TouchableHighlight
style={styles.closeButton}
underlayColor='transparent'
onPress={() => this._closeModal()}>
<Text style={styles.closeButtonText}>Close</Text>
</TouchableHighlight>
</View>
<MapView
style={styles.map}
ref={(ref) => this.mapView = ref}
initialRegion={this._getInitialRegion()}
pitchEnabled={false}
onRegionChangeComplete={null}
showsUserLocation={true}
showsPointsOfInterests={false}
showsCompass={false}
showsBuildings={false}
showsTraffic={false}
showsIndoors={false}
>
<MapMarker
{...this.props}
onPress={(data) => this._onCalloutPress(data)}
/>
</MapView>
</View>
</Modal>
</View>
);
}
}
const MapMarker = (props) => {
if (props.modalData.coordinates) {
const key = props.modalData.name.toLowerCase().replace(/\s/g, '');
return (
<MapView.Marker
key={key}
coordinate={props.modalData.coordinates}
>
<MapView.Callout tooltip style={styles.callout}>
<View style={[styles.calloutContainer, props.style]}>
<TouchableHighlight onPress={() => props.onPress(props.modalData)} underlayColor='transparent'>
<View style={styles.bubble}>
<View style={styles.amount}>
<Text style={styles.calloutHeaderText} numberOfLines={1} ellipsizeMode={'tail'}>{props.modalData.name}</Text>
<Text style={styles.calloutDescriptionText}>Tap to open in Maps</Text>
</View>
</View>
</TouchableHighlight>
<View style={styles.arrowBorder} />
<View style={styles.arrow} />
</View>
</MapView.Callout>
</MapView.Marker>
)
}
return (null);
}
const styles = StyleSheet.create({
container: {
flex: 1,
backgroundColor: 'white',
},
pushDown: {
marginTop: (Platform.OS === 'ios') ? 20 : 0
},
map: {
height: (Dimensions.get('window').height / 2),
width: (Dimensions.get('window').width)
},
callout: {
width: 140,
height: 100,
},
calloutContainer: {
flexDirection: 'column',
alignSelf: 'flex-start',
},
calloutHeaderText: {
fontSize: 18,
},
calloutDescriptionText: {
},
bubble: {
width: 300,
flexDirection: 'row',
alignSelf: 'center',
backgroundColor: 'white',
paddingHorizontal: 12,
paddingVertical: 12,
borderRadius: 6,
borderColor: 'white',
borderWidth: 0.5,
marginTop: 32,
},
amount: {
flex: 1,
},
arrow: {
backgroundColor: 'transparent',
borderWidth: 16,
borderColor: 'transparent',
borderTopColor: 'white',
alignSelf: 'center',
marginTop: -32,
},
arrowBorder: {
backgroundColor: 'transparent',
borderWidth: 16,
borderColor: 'transparent',
borderTopColor: 'white',
alignSelf: 'center',
marginTop: -0.5,
},
closeButton: {
},
closeButtonText: {
padding: 5,
fontSize: 18,
color: 'blue',
textAlign: 'right',
fontWeight: '300',
},
modalHeader: {
flexDirection: 'row',
},
modalHeaderSection: {
flexGrow: 2,
},
})
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment