Plotly scattermapbox: Native functionality to update map layout

I am building a Dash App that uses plotly scattermapbox graph object. Is there a way to natively (without a callback) let users select a map layout in plotly mapbox? Iโ€™d like users to switch between different styles.

import dash
from dash import dcc
import pandas as pd

df = pd.DataFrame({'x': [1, 2, 3]}) 

layout = html.Div(
                   dcc.Graph(id="map"),
                   dcc.Input(id="inp")
                 )

@app.callback(
              Output('map','figure'),
              Input('inpt','value')
             )
def fin(val):
    
    # do something

    data = []
    
    data.append({

                                 "type": "scattermapbox",
                                 "lat": df["Lat"],
                                 "lon": df["Long"],
                                 "name": "Location",
                                 "showlegend": False,
                                 "hoverinfo": "text",
                                 "mode": "markers",
                                 "clickmode": "event+select",
                                 "customdata": df.loc[:,cd_cols].values,
                                 "marker": {
                                            "symbol": "circle",
                                            "size": 8,
                                            "opacity": 0.7,
                                            "color": "black"
                                           }
                                 }
                   )

      layout = {

                     "autosize": True,
                     "hovermode": "closest",
                     "mapbox": {

                         "accesstoken": MAPBOX_KEY,
                         "bearing": 0,
                         "center": {
                             "lat": xxx,
                             "lon": xxx
                         },
                         "pitch": 0,
                         "zoom": zoom,
                         "style": "satellite-streets",

                     },

                    
        }

        return ({'data': data, 'layout': layout})

You can use Plotly Buttons to update the figureโ€™s layout (with relayout).

1 Like

@RenaudLN

This looks promising. However, itโ€™s not clear how this would update the style attribute which takes values streets, satellite, light, dark.

You would need to specify what you want to update in the layout (mapbox.style), check out the examples in that link.

Yeah, I modified layout dict with updatemenus. I am not sure how to define streets, satstreets as buttons that update mapbox layout style attribute. Itโ€™s not quite clear from the example.

layout = {

                     "autosize": True,
                     "hovermode": "closest",
                     "updatemenus" : {

                        "type":"buttons",
                        "buttons" : [

                            dict(label="None",
                                 method="relayout",
                                 args=["style", []]),

                            dict(label="B1",
                                 method="relayout",
                                 args=["mapbox.style", streets]),

                            dict(label="B2",
                                 method="relayout",
                                 args=["mapbox.style", satstreets]),

                            dict(label="B3",
                                 method="relayout",
                                 args=["mapbox.style", satellite]),

                        ],
                        "type": "buttons",
                        "direction":"right",
                        "pad": {"r": 10, "t": 10},
                        "showactive": True,
                        "x": 0.1,
                        "xanchor": "left",
                        "y": 2,
                        "yanchor": "top"
                     },

                     "mapbox": {

                         "accesstoken": MAPBOX_KEY,
                         "bearing": 0,
                         "center": {
                             "lat": layout_lat,
                             "lon": layout_lon
                         },
                         "pitch": 0,
                         "zoom": zoom,
                         "style": "satellite-streets",

                     },

                     "margin": {
                        "r": 0,
                        "t": 0,
                        "l": 0,
                        "b": 0,
                        "pad": 0
                    }

        }
1 Like

Hi! By any chance, were you able to figure out how to solve this issue?