Dynamic multi dropdown not showing default value on page load

I have a multiple dropdown in Dash that is dependent on 6 other dropdowns. The options of the dropdown update correctly, it shows all the correct values, but it does not show the default value when the page first loads. However, the graph shows up and it has the correct variable (as is evident when hovering on the graph), although there is no legend. Then when you select something from the dropdown, that value appears and the graph updates and everything works fine. It’s just when the page first loads that it doesn’t work. What can be the problem?

Here is a picture:

Here are the relevant parts of my code:

html.Div(
        className="row", children=[
            html.Div(className="col-4", children=[
                dcc.Dropdown(
                 id='est_method',
                 options=[{'label': i, 'value': i} for i in sorted(list(set(estimation_method)))],
                 value='Production'
             )
            ]),
            html.Div(className="col-4", children=[
                dcc.Dropdown(
                 id='seasonality',
                 options=[{'label': i, 'value': i} for i in sorted(list(set(seasonality)))],
                 value='Seasonally adjusted',
             )
            ]),
            html.Div(className="col-4", children=[ 
                dcc.Dropdown(
                 id='prices',
                 options=[{'label': i, 'value': i} for i in sorted(list(set(prices)))],
                 value='Real',
             )
            ]),

        ]
    ),
html.Div(
        className="row", children=[
            html.Div(className="col-4", children=[
                dcc.Dropdown(
                 id='level',
                 options=[{'label': i, 'value': i} for i in sorted(list(set(level)))],
                 value='Total'
             )
            ]),
            html.Div(className="col-4", children=[
                dcc.Dropdown(
                 id='value_$',
                 options=[{'label': i, 'value': i} for i in sorted(list(set(value)))],
                 value='Dollars',
             )
            ]),
            html.Div(className="col-4", children=[ 
                dcc.Dropdown(
                 id='frequency',
                 options=[{'label': i, 'value': i} for i in sorted(list(set(frequency)))],
                 value='Quarterly',
             )
            ]),

        ]
    ),
                html.Div(
                className="row", children=[
                    html.Div(className="col-12", children=[
                        dcc.Dropdown(
                        id='indicator_long',
                        options=[{'label': i, 'value': i} for i in sorted(list(set(indicator_long)))],
                        value='Gross Domestic Product - production measure, Quarterly, Seasonally adjusted, Real',
                        multi=True,
             )
            ]),
        ]
    ),
        html.Div(className="row", children=[
            html.Div(className='col-4', children=[
            dcc.RadioItems(
            id='measure',
            options=[{'label': i, 'value': i} for i in ['Level', 'qpc', 'apc', 'aapc']],
            value='qpc',
            labelStyle={'margin-right': '15px', 'color': '#1B1B1B'}
            )
    ])
        ]),
    dcc.Loading(id='loading-icon', color='#539255', children=[
        html.Div(children=[
            dcc.Graph(id='mygraph', className="d-flex justify-center-content"),
    ]),
    ], type='default'),

#callback to update the indicator dropdown
@app.callback(
    Output('indicator_long', 'options'),
    Output('indicator_long', 'value'),
    Input('est_method', 'value'),
    Input('seasonality', 'value'),
    Input('prices', 'value'),
    Input('level', 'value'),
    Input('value_$', 'value'),
    Input('frequency', 'value'),
)

def dropdown_value(e, s, p, l, v, f):
    start()
    
    e_list = [a for a, b in series_dict.items() if e in b] 
    s_list = [a for a, b in series_dict.items() if s in b] 
    p_list = [a for a, b in series_dict.items() if p in b] 
    l_list = [a for a, b in series_dict.items() if l in b] 
    v_list = [a for a, b in series_dict.items() if v in b]
    f_list = [a for a, b in series_dict.items() if f in b] 

    common_keys = list(set.intersection(*map(set, [e_list, s_list, p_list, l_list, v_list, f_list])))

    # common_labels = []
    # for key in common_keys:
    #     common_labels.append(series_dict[key][0])

    common_labels_long = []
    for key in common_keys:
        common_labels_long.append(series_dict[key][1])
    
    return [{'label': i, 'value': i} for i in sorted(list(set((common_labels_long))))], next(iter(sorted(common_labels_long)), None)

#update figure callback
@app.callback(
    Output('mygraph', 'figure'),
    Input('indicator_long', 'value'),
    Input('range-slider', 'value'),
    Input('measure', 'value'),
    State('value_$', 'value'),
    State('frequency', 'value'),
)

def update_graph(indicator, range, measure, v, frequency):

    if measure=='Level' and v=='Dollars':
        df_filt = df_gdp_piv.iloc[range[0]:range[1]]
        unit='Dollars'

    elif measure=='Level' and v=='Index':
        df_filt = df_gdp_piv.iloc[range[0]:range[1]]
        unit='Index'

    elif measure=='qpc':
        df_filt = df_gdp_qpc.iloc[range[0]:range[1]]
        unit = 'Quarterly percentage change'

    elif measure=='apc':
        df_filt = df_gdp_apc.iloc[range[0]:range[1]]
        unit = 'Annual percentage change'

    elif measure=='aapc':
        df_filt = df_gdp_aapc.iloc[range[0]:range[1]]
        unit = 'Annual average percentage change'
        
    else:
        pass
 
    fig = px.line(df_filt, x=df_filt.index, y=indicator, title='Gross domestic product') 
    fig.update_layout(margin={'l': 40, 'b': 40, 't': 40, 'r': 0}, hovermode='closest', legend_title_text='', yaxis=dict(tickformat=".1f"), yaxis_title=unit, \
        xaxis_title=frequency, template='seaborn', legend=dict(orientation="h", y=-0.15))

    return fig

Hi,

You are returning the value prop via next(...), which returns a single element (the first in this case) of an iterator. On the other hand, the dropdown expects a list of values when multi=True. That’s probably the issue here.

You can try to return [next(iter(....))] (wrapped in a list) instead.

1 Like

That solved it, thank you so much! :slight_smile: