Reputation: 21
I'm having difficulty implementing some simple react-google-maps code where whenever a marker is clicked or an info box is closed, the map will reset its position to the original position. I saw that I should be rendering the map component separately from changing the state, but I'm not sure how to implement this.
Any help is appreciated
import React, {useState} from 'react';
import {Marker, GoogleMap,LoadScript,InfoWindow} from '@react-google-maps/api';
const MapContainer = ({markers}) => {
const [selected, setSelected] = useState<any>({})
const onSelect = (item) => {
setSelected(item)
}
const mapStyles = {
height: "100vh",
width: "100%",
}
const defaultCenter = {
lat: 45.510440, lng: -122.683338
}
const renderMap = () => {
return <>
<div>
<LoadScript
googleMapsApiKey='[GOOGLE API KEY]'>
<GoogleMap
mapContainerStyle={mapStyles}
zoom={13}
center={defaultCenter}
>
{markers.map((marker)=> {
return(
<Marker
position={{
lat: marker.lat,
lng: marker.lng
}}
title={marker.title}
onClick={ () => onSelect(marker) }
/>
)})
}
{
selected.lng &&
<InfoWindow
position={
{
lat: selected.lat,
lng: selected.lng
}
}
onCloseClick={() => setSelected({})}
>
<div>
<h3>{selected.title}</h3>
<p>{selected.info}</p>
</div>
</InfoWindow>
}
</GoogleMap>
</LoadScript>
</div>
</>
}
return renderMap()
}
export default MapContainer; ```
Upvotes: 1
Views: 1777
Reputation: 99
Put the center in a state and set it to null after tiles are loaded, like this:
import React, {useState} from 'react';
import {Marker, GoogleMap,LoadScript,InfoWindow} from '@react-google-maps/api';
const MapContainer = ({markers}) => {
const [selected, setSelected] = useState<any>({})
const onSelect = (item) => {
setSelected(item)
}
const mapStyles = {
height: "100vh",
width: "100%",
}
const defaultCenter = {
lat: 45.510440, lng: -122.683338
}
const [center, setCenter] = useState(defaultCenter)
const renderMap = () => {
return <>
<div>
<LoadScript
googleMapsApiKey='[GOOGLE API KEY]'>
<GoogleMap
mapContainerStyle={mapStyles}
zoom={13}
center={center}
onTilesLoaded={() => setCenter(null)}
>
{markers.map((marker)=> {
return(
<Marker
position={{
lat: marker.lat,
lng: marker.lng
}}
title={marker.title}
onClick={ () => onSelect(marker) }
/>
)})
}
{
selected.lng &&
<InfoWindow
position={
{
lat: selected.lat,
lng: selected.lng
}
}
onCloseClick={() => setSelected({})}
>
<div>
<h3>{selected.title}</h3>
<p>{selected.info}</p>
</div>
</InfoWindow>
}
</GoogleMap>
</LoadScript>
</div>
</>
}
return renderMap()
}
export default MapContainer;
Upvotes: 1
Reputation: 2977
It seems that putting your center value in a state and setting the clicked marker coordinates as the new center will solve the issue. Here's a sample code and a code snippet:
import React, {useState} from 'react';
import {Marker, GoogleMap,LoadScript,InfoWindow} from '@react-google-maps/api';
import { render } from "react-dom";
import markers from "./data.json"
const MapContainer = () => {
const [selected, setSelected] = useState<any>({})
const [center,setCenter]= useState({
lat: 39.952584, lng: -75.165221
})
const onSelect = (item) => {
setSelected(item)
setCenter({
lat: item.lat, lng: item.lng
})
}
const mapStyles = {
height: "100vh",
width: "100%",
}
const renderMap = () => {
return <>
<div>
<LoadScript
googleMapsApiKey='AIzaSyBlfuRgAUDPGJnUpwyyhdSBIs193bXboMQ'>
<GoogleMap
mapContainerStyle={mapStyles}
zoom={13}
center={center}
>
{markers.map((marker,i)=> {
return(
<Marker
key={i}
position={{
lat: marker.lat,
lng: marker.lng
}}
title={marker.title}
onClick={ () => onSelect(marker) }
/>
)})
}
{
selected.lng &&
<InfoWindow
position={
{
lat: selected.lat,
lng: selected.lng
}
}
onCloseClick={() => setSelected({})}
>
<div>
<h3>{selected.id}</h3>
<p>{selected.name}</p>
</div>
</InfoWindow>
}
</GoogleMap>
</LoadScript>
</div>
</>
}
return renderMap()
}
render(<MapContainer />, document.getElementById('root'));
Upvotes: 2