Reputation: 23
I'm new at plotly dash python. I need help updating the graph after input value and clicking the Set button. I tried many ways but I can't make it right. Also, the refresh button is to refresh the graph back to 0 input value. I'm so stuck here. Do I have to update the graph after the input or just update the value?
from dash import html, Dash, dcc, Input, Output, State
import plotly.express as px
import pandas as pd
app = Dash(__name__)
df = pd.DataFrame({
"Minimum/Maximum":["Minimum", "Maximum"],
"Numbers of Beat": [2,60]
})
fig = px.bar(df, x = "Minimum/Maximum", y = "Numbers of Beat", color="Minimum/Maximum")
app.layout = html.Div(
children=[
html.H1(children= 'HTML Dashboard Application'),
html.Div(children=
'''
Dash: Minimum/Maximum Bar Graph
'''),
dcc.Graph(
id='dash_graph',
figure = fig
),
html.Div(dcc.Input(placeholder='Enter a min value...' ,id='min_value', type='text')),
html.Div(dcc.Input(placeholder='Enter a max value...' ,id='max_value', type='text')),
html.Button(id='Set-val', n_clicks=0, children= 'Set'),
html.Button(id='Refresh_current_BPM', n_clicks=0, children= 'Refresh'),
])
@app.callback(
Output('dash_graph', 'figure'),
Input('Set-val', 'n_clicks'),
State('min_value', 'value'),
State('max_value', 'value')
)
def update_value(min_value, max_value, n_clicks):
#new value should appear in the graph here
return fig
if __name__ == '__main__':
app.run_server(debug = True)
Upvotes: 2
Views: 5717
Reputation: 1200
I need help updating the graph after input value and clicking the Set button. I tried many ways but I can't make it right.
You have the design right for your callback (although in your provided code, you mixed the order of the arguments). You just have to reconstruct the dataframe with the appropriate values you capture from the inputs. Since you pass both inputs min
and max
to the callback, you can reconstruct the dataframe, pass that into the plotly figure and return it back to the dcc.Graph
component.
Also, the refresh button is to refresh the graph back to 0 input value. I'm so stuck here. Do I have to update the graph after the input or just update the value?
You want to refresh the graph so that both subplots are zero, in which case you have 2 options:
You can set the inputs back to 0 in a new callback, which in turn will trigger the original callback you have and set the graphs to 0.
In your original callback, use dash.ctx.triggered
to establish which button was clicked on, then set the dataframe values to 0 for both min and max.
The first solution might be more elegant in terms of design.
Here is an example modified from original code:
from dash import html, Dash, dcc, Input, Output, State
import plotly.express as px
import pandas as pd
import dash
app = Dash(__name__)
df = pd.DataFrame({
"Minimum/Maximum":["Minimum", "Maximum"],
"Numbers of Beat": [2,60]
})
fig = px.bar(df, x = "Minimum/Maximum", y = "Numbers of Beat", color="Minimum/Maximum")
app.layout = html.Div(
children=[
html.H1(children= 'HTML Dashboard Application'),
html.Div(children=
'''
Dash: Minimum/Maximum Bar Graph
'''),
dcc.Graph(
id='dash_graph'
),
html.Div(dcc.Input(placeholder='Enter a min value...', id='min_value', type='number', value=0)),
html.Div(dcc.Input(placeholder='Enter a max value...', id='max_value', type='number', value=0)),
html.Button(id='Set-val', n_clicks=0, children= 'Set'),
html.Button(id='Refresh_current_BPM', n_clicks=0, children= 'Refresh'),
])
@app.callback(
Output('dash_graph', 'figure'),
State('min_value', 'value'),
State('max_value', 'value'),
Input('Set-val', 'n_clicks'),
Input('Refresh_current_BPM', 'n_clicks'),
)
def update_value(min_value, max_value, *_):
# check if a button was triggered, if not then just render both plots with 0
ctx = dash.callback_context
if ctx.triggered:
# grab the ID of the button that was triggered
button_id = ctx.triggered[0]['prop_id'].split('.')[0]
# if the button that was triggered is the refresh one, then set min,max to 0
# otherwise, the set button was triggered and so carry on normally
if button_id == "Refresh_current_BPM":
min_value = 0
max_value = 0
df = pd.DataFrame({
"Minimum/Maximum":["Minimum", "Maximum"],
"Numbers of Beat": [min_value, max_value]
})
fig = px.bar(df, x = "Minimum/Maximum", y = "Numbers of Beat", color="Minimum/Maximum")
return fig
if __name__ == '__main__':
app.run_server(debug = True)
NOTE
Try not to use a global dataframe or variable in your dash app. What I did in the example is set the inputs to a default of 0, and just construct the graph in the callback that will be triggered upon the initial loading of the app.
Upvotes: 1