0

I want to create a custom helper div layer on the map on a button click or mouse-over over the button. The button is also a custom control button on the map. Here is the example control button

My custom layer will provide map related information. The whole functionality should work like the React leaflet Layers control,

That is, upon a mouse-hover/click on a custom control div/button a custom layer should popup with map related information.

I created the custom div layer. However, I'm facing two problems.

  1. I couldn't position it on the map. I tried first with "bottomleft" option. It didn't work. My actual intention is to position just near the help-control-button exactly like "Layers control" from React.leaflet documentation.
  2. Right now, the code is listening to any "click" event on the map. I want to make it specific to my control button. How to make the connection between the control layer and control button ? How to pass this control button to the layer ?

Any help is much appreciated. Here is my code as below.

custom layer component

import React, { Component } from "react";
import { useMap } from "react-leaflet";
import L, { LeafletMouseEvent, Map } from "leaflet";

class CustomMapHelpGuide extends React.Component<{},{props:any}>{

helpDesc:any;
createDescLayer(opts:any){
    const DescHelp = L.Layer.extend({
        onAdd: (map: Map) => {
            const helpDesc = L.DomUtil.create('div','');
            helpDesc.innerHTML = "this is a map description div";
            this.helpDesc = helpDesc;
            map.getPanes().overlayPane.appendChild(this.helpDesc);
            map.on('click',this.testFunc, this);
            return helpDesc;
        }
    });

    return new DescHelp(); //I tried to pass the "opts" parameter but it is throwing error saying it doesn't expect an argument
}

testFunc(){
    console.log("layer is implemenetd"); //upon click anywhere in the map this is getting printed on console
    
}

componentDidMount() {
    const { map} = this.props as any;
    const layer = this.createDescLayer({ position: 'bottomleft' });
   // map.addLayer(layer);
    layer.addTo(map);
}

componentWillUnmount() {
    this.helpDesc.remove();
  }

  render() {
    return null;
  }
}

function withMap(Component : any) {
  return function WrappedComponent(props : any) {
    const map = useMap();
    return <Component {...props} map={map} />;
  };
}

export default withMap(CustomMapHelpGuide);

Here is how it is called for the time being,

<MapContainer
        center={customPosition}
        zoom={9}
        zoomControl={false}
        >
             <DescriptionButton/>
            <CustomMapDescLayer/>

            <TileLayer
                attribution="Map tiles by Carto, under CC BY 3.0. Data by OpenStreetMap, under ODbL."
                url="https://cartodb-basemaps-{s}.global.ssl.fastly.net/light_all/{z}/{x}/{y}.png"
            />
        </MapContainer>
3
  • Why are you extending L.Layer instead of L.Control? Are you trying to create a little info-div that appears in the upper right corner of the map, in line with the other controls? Or do you want more of a modal? If this is ultimately a modal-type functionality with information in it, why does this need to be a leaflet feature at all? Why not just a modal that is completely separate from the Map component? Not all UI features of a leaflet application have to be leaflet components. If you want a L.Control type feature, try extending L.Control Commented Jul 18, 2021 at 3:47
  • Hello @SethLutske thank you for reaching out. Your answer gave some food for thought for me. Actually, I want to create an info-div but that should appear on button control click/hover just like react-leaflet.js.org/docs/example-layers-control. Reading the documentation leafletjs.com/examples/extending/extending-3-controls.html of layer and controls I felt the button should be control and the popup info div should be layer. Correct me if I'm wrong.
    – sandy
    Commented Jul 18, 2021 at 10:52
  • @SethLutske : Obviously, a modal is another option. But if I create the info div as a control then how shall connect it to my button control so that on button click this info div appears ?
    – sandy
    Commented Jul 18, 2021 at 10:52

0