I am building a Dash app and attempting to utilize Plotly's category_order and color_discrete_sequence to assign a specific color to unique string values that reside in a dataframe column. These parameters seem to be described as taking non-numerical data (e.g. strings) and assigning them colors in an order the user specifies. However, the code doesn't seem to take and I only get monochromatic black dots for all datapoints (image below). Hoping someone can see what I'm missing and offer guidance how to use these parameters, or another process, to get the intended result.

My process is as follows:
I have a dataframe containing the columns "band," "lat," and "lon," where lat and lon will specify the location of a point in a scattermapbox plot and band takes on a list of values such as:
data = {'band':['10m','10m','6m','2m','2m','2m','1.25m','70cm','33cm','33cm','33cm','23cm'],
'Lat': ['35.5','34.2','35.9','36.1','35.2','36.2','33.9','36.4','35.1','34.9','32.9','35.0'],
'Lon': ['-78.5','-77.3','-79.0','-78.6','-79.3','-77.0','-78.5','-77.7','-79.9','-78.8','-79.1','-79.0']}
df = pd.DataFrame.from_dict(data)
This mapplot will need its colors to correspond with other charts, so I want to use category_order as the documentation reads...
By default, in Python 3.6+, the order of categorical values in axes, legends and facets depends on the order in which these values are first encountered in data_frame (and no order is guaranteed by default in Python below 3.6). This parameter is used to force a specific ordering of values per column. The keys of this dict should correspond to column names, and the values should be lists of strings corresponding to the specific display order desired."
band_categories = {'band':['10m', '6m', '2m', '1.25m', '70cm', '33cm', '23cm']}
is set to establish the order I wish the scattermapbox to use.
Lastly, color_discrete_sequence works directly with category_order by definition...
Strings should define valid CSS-colors. When color is set and the values in the corresponding column are not numeric, values in that column are assigned colors by cycling through color_discrete_sequence in the order described in category_orders, unless the value of color is a key in color_discrete_map.
so it receives my desired color order band_colors_list = ['green', 'red', 'blue', 'orange', 'purple', 'gray', 'yellow']
The final marker dict is compiled and is assigned to the scattermapbox dict and pushed to the Dash element.
import pandas as pd
import numpy as np
from pandas.api.types import CategoricalDtype
import dash
import dash_core_components as dcc
import dash_html_components as html
from dash.dependencies import Input, Output
data = {'band':['10m','10m','6m','2m','2m','2m','1.25m','70cm','33cm','33cm','33cm','23cm'],
'Lat': ['35.5','34.2','35.9','36.1','35.2','36.2','33.9','36.4','35.1','34.9','32.9','35.0'],
'Lon': ['-78.5','-77.3','-79.0','-78.6','-79.3','-77.0','-78.5','-77.7','-79.9','-78.8','-79.1','-79.0']}
df = pd.DataFrame.from_dict(data)
df.head()
token = drop_mapbox_token_string_here
layers = []
band_categories = ['10m', '6m', '2m', '1.25m', '70cm', '33cm', '23cm']
band_colors_list = ['green', 'red', 'blue', 'orange', 'purple', 'gray', 'yellow']
app = dash.Dash(__name__)
template = {'layout': {'paper_bgcolor': "#f3f3f1", 'plot_bgcolor': "#f3f3f1"}}
def blank_fig(height):
"""
Build blank figure with the requested height
"""
return {
'data': [],
'layout': {
'height': height,
'template': template,
'xaxis': {'visible': False},
'yaxis': {'visible': False},
}
}
# Build Dash layout
app.layout = html.Div(children=[
html.Div(children=[
dcc.Graph(
id='map-graph',
figure=blank_fig(500),
config={'displayModeBar': False},
),],
id="map-div"
)
])
@app.callback(
Output('map-graph', 'figure'),
[Input('map-graph', 'relayoutData')])
def update_plots(relayout_data):
marker = {
'color': df.band,
'category_order': band_categories,
'color_discrete_sequence': band_colors_list,
'size': 5,
'opacity': 0.6
}
map_graph = {'data': [{
'type': 'scattermapbox',
'lat': df.Lat, 'lon': df.Lon,
'marker': marker
}],
'layout': {
'template': template,
'uirevision':True,
'mapbox':{
'style': "light",
'accesstoken': token,
'layers': layers,
},
'margin': {"r": 0, "t": 0, "l": 0, "b": 0},
'height': 500
},
}
map_graph['layout']['mapbox'].update()
return (map_graph)
app.scripts.config.serve_locally = True
app.css.config.serve_locally = True
app.run_server(debug=True, use_reloader=False)
defdon't look right. And you're missing your imports - vestland