Python Folium: Control marker cluster groups with grouped layer control - markers within featureGroups and FeatureGroupsubgroups

606 views Asked by At

I am attempting to create a folium map with marker clusters and I want to be able to control the visibility of the markers (and update the marker clusters) depending on which layer is selected. My tree would look like:

                                     BASEMAP
                                        |
                           ---------------------------
                           |                          |
 FeatureGroups:            net1                       net2
                           |                          |
                  -------------------         --------------------
                  |        |         |        |.       |.         |
 SubGroups:       a        b         c        d        e          f
                  |.       |         |        |        |          |
 Popups:        mkrsa*.   mkrsb*. mkrsc*.   mkrsd*.  mkrse*.     mrksf*
            |___________________________________________________________|
                                    markerclustergroup

By default, I would have all markers displayed as members of the markercluster group, but if e.g., if the 'net1' feature group is deselected, subgroups a,b, and c would no longer appears. I would also like to be able to de-select (de-display) subgroups, leaving the other subgroups untouched. The markers/popups associated with each subgroup have their own properties (e.g., color).

Below is some code that I have tried (pseudo/trimmed code for easier viewing here) as I my understanding is that I just don't have the right order of children dependency. Their may be a an easier way to rearrange the ordering of the feature/subfeature groups. I appreciate any advice or suggestions to try. Thank you.

#!/usr/bin/env python
# coding: utf-8


import folium
import base64
from folium import IFrame
from PIL import Image
import numpy as np
import xarray as xr
import sys
import glob
import os.path
from folium import plugins

mkr1 = list() # list of the individual markers
mkrc = list() # list of the individual markers for the marker cluster (in case we need to access them separately)

#path to plots
path = './'
#defining the resolution, width, and height of the popup
resolution, width, height = 42, 12, 6
#defining plot type
plot_type = "grp1.timeseries"

species_list = ['a', 'b', 'c', 'd', 'e', 'f']
network_list = ['net1', 'net1', 'net1', 'net2', 'net2', 'net2']
fmap_dict = dict()

fmap = folium.Map(location=[40, -95],zoom_start=4,min_zoom=3,control=False)
fmap_net1 = folium.FeatureGroup(name='net1',overlay=True,control=True,show=True)
fmap_net2 = folium.FeatureGroup(name='net2',overlay=True,control=True,show=True)
fmap_marker_cluster = folium.plugins.MarkerCluster(name='cluster test 1',control=False,show=True,overlay=True,disableClusterAtZoom=16)
mySubGroup = folium.plugins.FeatureGroupSubGroup(fmap_marker_cluster,name='cluster test 2',control=False,show=True,overlay=True)
fmap.add_child(fmap_net1)
fmap.add_child(fmap_net2)
for s in range(len(species_list)):
        species=species_list[s]
 species=species_list[s]
        if species == 'a':
                fmap_a = folium.plugins.FeatureGroupSubGroup(fmap_net1,name='a',overlay=True,control=True,show=True)
                if 'net1' in fmap_dict:
                        fmap_dict['net1'].append(fmap_a)
        if species == 'b':
                fmap_b = folium.plugins.FeatureGroupSubGroup(fmap_net1,name='b',overlay=True,control=True,show=True)
                if 'net1' in fmap_dict:
                        fmap_dict['net1'].append(fmap_b)
        if species == 'c':
                fmap_c = folium.plugins.FeatureGroupSubGroup(fmap_net1,name='c',overlay=True,control=True,show=True)
                if 'net1' in fmap_dict:
                        fmap_dict['net1'].append(fmap_c)
        if species == 'd':
                fmap_d = folium.plugins.FeatureGroupSubGroup(fmap_net1,name='d',overlay=True,control=True,show=True)
                if 'net2' in fmap_dict:
                        fmap_dict['net2'].append(fmap_d)
        if species == 'e':
                fmap_e = folium.plugins.FeatureGroupSubGroup(fmap_net1,name='e',overlay=True,control=True,show=True)
                if 'net2' in fmap_dict:
                        fmap_dict['net2'].append(fmap_e)
        if species == 'f':
                fmap_f = folium.plugins.FeatureGroupSubGroup(fmap_net1,name='f',overlay=True,control=True,show=True)
                if 'net2' in fmap_dict:
                        fmap_dict['net2'].append(fmap_f)
        for i in range(len(site_name)):
                image = Image.open(str(site_name)) #path to original image file
                image = image.resize(((width*resolution),(height*resolution)),Image.ANTIALIAS)
                image.save(fp = path + plot_name) #save back to the original directory? or new
                # opening the resized plot and encoding it
                png = path + plot_name
                # Encoding it
                encoded = base64.b64encode(open(png, 'rb').read())

                # formating the encoded plot as html
               html = '<img src="data:image/png;base64,{}">'.format

                # decoding the plot into an iframe
                iframe = IFrame(html(encoded.decode('UTF-8')), width=(width*resolution)+20, height=(height*resolution)+20)

                #creating a popup of the iframe
                popup = folium.Popup(iframe, max_width=2650,sticky=True)
                if species == "a":
                        x = folium.CircleMarker(location=[site_lat[-1], site_lon[-1]], popup=popup, tooltip=tooltip, radius=5,color = 'blue', fill_color="blue", fill_opacity=0.5)
                        fmap_a.add_child(x)
                if species == "b":
                        x = folium.CircleMarker(location=[site_lat[-1], site_lon[-1]], popup=popup, tooltip=tooltip, radius=5,color = 'blue', fill_color="blue", fill_opacity=0.5)
                        fmap_a.add_child(x)
                if species == "c":
                        x = folium.CircleMarker(location=[site_lat[-1], site_lon[-1]], popup=popup, tooltip=tooltip, radius=5,color = 'blue', fill_color="blue", fill_opacity=0.5)
                        fmap_c.add_child(x)
                if species == "d":
                        x = folium.CircleMarker(location=[site_lat[-1], site_lon[-1]], popup=popup, tooltip=tooltip, radius=5,color = 'blue', fill_color="blue", fill_opacity=0.5)
                        fmap_d.add_child(x)
                if species == "e":
                        x = folium.CircleMarker(location=[site_lat[-1], site_lon[-1]], popup=popup, tooltip=tooltip, radius=5,color = 'blue', fill_color="blue", fill_opacity=0.5)
                        fmap_e.add_child(x)
                if species == "f":
                        x = folium.CircleMarker(location=[site_lat[-1], site_lon[-1]], popup=popup, tooltip=tooltip, radius=5,color = 'blue', fill_color="blue", fill_opacity=0.5)
                        fmap_f.add_child(x)
                mySubGroup.add_child(x)


fmap.add_child(fmap_marker_cluster)
fmap.add_child(mySubGroup)
fmap.add_child(fmap_a)
fmap.add_child(fmap_b)
fmap.add_child(fmap_c)
fmap.add_child(fmap_d)
fmap.add_child(fmap_e)
fmap.add_child(fmap_f)
fmap.keep_in_front(fmap_net1)
fmap.keep_in_front(fmap_net2)
# Add the layer controls
folium.plugins.GroupedLayerControl(fmap_dict, exclusive_groups=False).add_to(fmap)
folium.LayerControl().add_to(fmap)
#saving the map to an html file
output_name = "fullhtml_sfc_f000.html"
fmap.save(output_name)
0

There are 0 answers