How to annotate choropleth map with call out arrow

Hi, is there a way to add a select callout annotation to a choropleth map in Python with Plotly/Express and/or Dash? Using the Plotly Express built-in US map 2 letter State code, map coordinates, or otherwise?

I am looking to add a descriptive story callout element that points to a specific state. Similar to how this is possible with x-axis elements on a bar chart, like this (from Styling Plotly Express Figures | Python | Plotly):

fig.add_annotation( # add a text callout with arrow
text=“below target!”, x=“Fri”, y=400, arrowhead=1, showarrow=True
)

*Here’s my Plotly Express code currently that works great up until wanting to annotate the figure:

#Plot dataframe df as a choropleth map
fig = px.choropleth(df_map,
locations = ‘State_code’,
color=“Seat change”,
hover_name=“State”, #column to add to hover information
hover_data={#determines what shows in hover text
‘Year’, ‘Seat change’,‘Apportionment population’,
‘Number of representatives’,
‘Average persons per representative’
},
labels={#replaces default labels by column name
‘Seat_change’: ‘Seat change’
},
animation_frame=“Year”,
color_continuous_scale=“Inferno”,
locationmode=‘USA-states’,
scope=“usa”,
range_color=(-5, 10),
title=‘Change in Number of Seats in U.S. House of Representatives by State: 1910 to 2020’,
height=600
)

#Can I add something like this to insert a text blob somewhere with an arrow pointing to California?
fig.add_annotation(#add text callout with arrow
text=“California saw significant increases in House seats over the first half of the 20th century, with massive early 1900s population growth including foreign immigrants, then more workers from other states following the Great Depression which lasted until the late 1930s, and again after World War II ended in 1945.”, ‘State_code’=‘CA’, arrowhead=1, showarrow=True
)

@kmhurchla
The text you intend to be displayed for each state is unusually long, but you can split it into multiple lines.
Due to its length it would be difficult to display such a long text as an annotation, because some states have small area.
I give below an example with text as tooltip (I’m not sure what are you calling, callout, in this context).

from urllib.request import urlopen
import json
import numpy as np
import pandas as pd

import plotly.express as px
with urlopen('https://raw.githubusercontent.com/PublicaMundi/MappingAPI/master/data/geojson/us-states.json') as response:
    states = json.load(response)
ids = [f['id']  for f in states['features']]
d =  {'id': ids, 'val': np.random.randint(5, 34, size=52)}
df = pd.DataFrame(d)

fig = px.choropleth(df, geojson=states, locations='id', color='val',
                           color_continuous_scale="Viridis",
                           scope="usa",
                         
                          )
fig.update_layout(margin={"r":0,"t":0,"l":0,"b":0});

#define a list of 52 strings(texts), one for each state; Here I appended the same text for all states
text_list = ["California saw significant increases in House seats over the first half of the 20th century,"+
             "with massive early 1900s population growth including foreign immigrants, then more workers"+
             "from other states following the Great Depression which lasted until the late 1930s,"
             "and again after World War II ended in 1945."]*52

#split each text into multiple lines of sub-texts, delimited by the html tag <br>
new_text_list=[]
L =50# L= number of characters to be displayed on a line of text
for t in text_list:
    sb = []
    while t:
        sb.append(t[:L]+'<br>')
        t = t[L:]
    new_t = " ".join(sb)  
    new_text_list.append(new_t[:-4])

fig.update_traces(customdata=new_text_list,
                 hovertemplate="%{customdata}<extra></extra>")
fig.show()

As you can notice the splitting is not perfect: some words are truncated at the line end, but you can manually move them to the next line.

I’ll give this a go @empet, thank you for your response!

By callout I mean I’m looking for a select note that can point to a certain state/location, but that would not fit inside the state itself. Maybe I need to do something different like on hover, but I’ll see what this can help me do. I would not want text for all of the states for this use, just one or a few select states I want to draw attention to and give context.