I want click on my map and set a Marker with a circle around. It shows the map but I cannot set a marker.
console.log
is not showing anything. It seems my handleMapClick
function does not work.
import React, { useState } from "react";
import { MapContainer, TileLayer, Marker, Circle } from "react-leaflet";
import "leaflet/dist/leaflet.css";
const DynamicMap = () => {
const [markerPosition, setMarkerPosition] = useState(null);
const [circleCenter, setCircleCenter] = useState(null);
const [circleRadius, setCircleRadius] = useState(10000); // Default radius in meters
const handleMapClick = (e) => {
const { lat, lng } = e.latlng;
console.log("Clicked at:", lat, lng);
setMarkerPosition([lat, lng]);
setCircleCenter([lat, lng]);
};
return (
<div>
<MapContainer
center={[51.505, -0.09]}
zoom={10}
style={{ width: "100%", height: "500px" }}
onClick={handleMapClick}
>
<TileLayer
url="https://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png"
attribution='© <a href="https://www.openstreetmap.org/copyright">OpenStreetMap</a> contributors'
/>
{markerPosition && <Marker position={markerPosition} />}
{circleCenter && <Circle center={circleCenter} radius={circleRadius} />}
</MapContainer>
<div>
<input
type="range"
min="10000"
max="200000"
step="1000"
value={circleRadius}
onChange={(e) => setCircleRadius(e.target.value)}
/>
<p>Circle Radius: {circleRadius} meters</p>
</div>
<div id="map"></div>
</div>
);
};
export default DynamicMap;
Unfortunately, React Leaflet does not support setting directly onClick
prop on the <MapContainer>
component.
Instead, you should make a custom "map content component" as a child of <MapContainer>
, which can use useMapEvent
hook:
function MapContent() {
const [markerPosition, setMarkerPosition] = useState(null);
const map = useMapEvent("click", (e) => {
const { lat, lng } = e.latlng;
console.log("Clicked at:", lat, lng);
setMarkerPosition([lat, lng]);
});
return (
<>
{markerPosition && <Marker position={markerPosition} />}
</>
);
}
function DynamicMap() {
return (
<MapContainer>
<MapContent />
</MapContainer>
);
}