javascript - Add onClick on MapContainer in Component in 3.x
问题描述
I'm using the following versions:
"leaflet": "^1.7.1",
"react-leaflet": "^3.0.2",
I want to perform some action on map-click, e.g. add a marker.
I tried the stateless component approach which seems to work, but I don't really like it for several reasons.
I tried using eventHandlers
attribute:
render() {
return <div>
<MapContainer center={[ 48, 11 ]} zoom={10} scrollWheelZoom={true} eventHandlers={{
click: () => {
console.log('map clicked')
},
}}>
<TileLayer .../>
</MapContainer>
</div>
}
but it never fires.
I also read about MapConsumer but can't find good examples to it.
Any hints on building in onClick event handler are appreciated.
TIA
解决方案
It seems that eventHandlers
, although it is available as a prop on MapContainer
(if you press ctlr + space on vscode f.i it will pop up) it is not available in the official API and is intended only for child components of MapContainer
, see here and here for Marker.
what you want to achieve can be implemented using useMapEvents
on a separate comp and then included as a child on MapContainer
:
function App() {
function MyComponent() {
const map = useMapEvents({
click: (e) => {
const { lat, lng } = e.latlng;
L.marker([lat, lng], { icon }).addTo(map);
}
});
return null;
}
return (
<MapContainer center={[50.5, 30.5]} zoom={13} style={{ height: "100vh" }}>
<TileLayer
attribution='© <a href="http://osm.org/copyright">OpenStreetMap</a> contributors'
url="https://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png"
/>
<MyComponent />
</MapContainer>
);
}
Another approach is listen to whenReady
prop (not officially documented but seems to work similarly to whenCreated
prop but map instance is accessible via object.target
) on MapContainer
:
<MapContainer
center={[50.5, 30.5]}
zoom={13}
style={{ height: "100vh" }}
whenReady={(map) => {
console.log(map);
map.target.on("click", function (e) {
const { lat, lng } = e.latlng;
L.marker([lat, lng], { icon }).addTo(map.target);
});
}}
>
...
</MapContainer>
3rd approach is to use MapConsumer
as a child of MapContainer
(docs):
<MapContainer center={[50.5, 30.5]} zoom={13}>
<MapConsumer>
{(map) => {
console.log("map center:", map.getCenter());
map.on("click", function (e) {
const { lat, lng } = e.latlng;
L.marker([lat, lng], { icon }).addTo(map);
});
return null;
}}
</MapConsumer>
</MapContainer>
4th approach is to use whenCreated
prop (officially documented) on MapContainer
:
<MapContainer
center={[50.5, 30.5]}
zoom={13}
style={{ height: "100vh" }}
whenCreated={(map) => {
map.on("click", function (e) {
const { lat, lng } = e.latlng;
L.marker([lat, lng], { icon }).addTo(map.target);
});
}}
>
...
推荐阅读
- angular - 延迟加载错误:找不到模块 - Angular 7
- php - 具有两个数组和 if 条件的 Foreach 循环
- excel - 一个接一个地双击多个单元格的VBA
- java - java.lang.Exception:不是实体:com.domain.package.User 类
- go - 处理超时和收听频道
- python - TypeError:输入不正确:N=3 不得超过 M=1,不确定我的尺寸有什么问题?
- sass - npm 脚本的 SASS 问题(autoprefix 和 postcss)
- reactjs - Formik 验证模式是的,什么时候是“答案”或“另一个答案”
- jenkins - 在 Jenkins 管道中创建 Robot Framework output.xml 的副本
- javascript - 将道具传递给散布在对象内的函数