Python 如何使用@app.callback计算值更改仪表板滑块范围

Python 如何使用@app.callback计算值更改仪表板滑块范围,python,plotly,plotly-dash,Python,Plotly,Plotly Dash,我有一个范围从IETsr到0的绘图仪仪表板滑块。启动时,IETsr是根据两个下拉菜单中的默认设置计算得出的值。 我希望发生的是,当用户更改下拉列表的值并计算新的IETsr时,滑块范围将更改为使用新值。 这段代码的所有其他部分都正常工作,每次我更改下拉列表(它是滑块下面三个数字中的最后一个)时都会计算IETsr,但我不知道如何将其反馈回滑块。 忽略顶部的#项,这是在硬编码时使用的 import dash import dash_core_components as dcc import dash_

我有一个范围从IETsr到0的绘图仪仪表板滑块。启动时,IETsr是根据两个下拉菜单中的默认设置计算得出的值。 我希望发生的是,当用户更改下拉列表的值并计算新的IETsr时,滑块范围将更改为使用新值。 这段代码的所有其他部分都正常工作,每次我更改下拉列表(它是滑块下面三个数字中的最后一个)时都会计算IETsr,但我不知道如何将其反馈回滑块。 忽略顶部的#项,这是在硬编码时使用的

import dash
import dash_core_components as dcc
import dash_html_components as html
from dash.dependencies import Input, Output
import plotly.graph_objects as go


Dep=363                 #Water depth (m)
Speed = 2.2            #Ship's speed (m/s)
ASV=1.5                 #Speed of sound in water (m/s)
SPI=6.25                #Distance between sample stations (m)
SB=0-((Dep*2)/ASV)      #Sound travel time to seabed (milliseconds) - negative to denote below time zero
IET=(SPI/Speed)         #Inter Event Time (s) time to travel SPI
IETs=IET*1000           #IET in milliseconds
IETsr=0-round(IETs)          


external_stylesheets = ['https://codepen.io/chriddyp/pen/bWLwgP.css']

app = dash.Dash(__name__, external_stylesheets=external_stylesheets)

app.layout = html.Div([
    html.H6("Calculate available record lengths"),    
    html.Label('Shot Point Interval'),
    dcc.Dropdown(id='SPIDD',
        options=[
            {'label': '3.125', 'value': 3.125},
            {'label': u'6.25', 'value': 6.25},
            {'label': '12.5', 'value': 12.5},
            {'label': '25.0', 'value': 25.0},
        ],
        value='6.25'
    ),
    html.Label('Vessel Speed m/s / Knots'),
    dcc.Dropdown(id='SpeedDD',
        options=[
            {'label': '1.95/3.8', 'value': 1.955},
            {'label': '2.05/4.0', 'value': 2.058},
            {'label': u'2.16/4.2', 'value': 2.161},
            {'label': '2.26/4.4', 'value': 2.264},            
            {'label': '2.37/4.6', 'value': 2.366},
            {'label': '2.47/4.8', 'value': 2.469},            
        ],
        value='2.16'
    ),
    html.Label('Depth to Seabed'),
    dcc.Input(id="Depth", type="text",value="123")
    ,  
    
    dcc.Graph(id='graph-with-slider'),
    dcc.Slider(
        id='3DHR Slider',
        min=IETsr,
        max=0,
        value=(IETsr-0)/2,
        marks={i: f"{i}" for i in range(round(IETsr,-2),0,100)},        
        step=50
    ),
    html.Div(id='display1'),
    html.Div(id='display2'),
    html.Div(id='display3')     
])
@app.callback(
    Output('display1', 'children'),
    Output('3DHR Slider', 'min'),    
    Input('SPIDD','value'),
    Input('SpeedDD','value'))
def do_maths(SPIDD,SpeedDD):
    SPIDD=float(SPIDD)
    SpeedDD=float(SpeedDD)
    global IET
    global IETs
    global IETsr
    IET=round(SPIDD/SpeedDD,2)
    IETs=IET*1000
    IETsr=0-round(IETs)
    return u'Inter Event Time: {}s'.format(IET),IETsr

@app.callback(
    Output('graph-with-slider', 'figure'),
    Output('display2', 'children'),     
    Input('3DHR Slider', 'value'),   
    Input('Depth','value'))
def update_figure(REC1,Depth):
    REC2= round((0-IETs)-REC1)  #UHRS record length - Function of above
    SB=float(Depth)
    SB=round(0-((SB*2)/ASV),0)
    fig = go.Figure()

    #Add seabeds    
    fig.add_trace(go.Scatter(x=[0,1,None,1.1,1.6],y=[SB,SB,None,SB,SB],name="Seabed",line=dict(color='green',dash='dash'))) 
    fig.add_trace(go.Scatter(x=[1.1,1.6],y=[REC1+SB,REC1+SB],name="Seabed-UHRS",line=dict(color='blue',dash='dash'))) ##Stacked Rec2    
 

    #Add record length windows
    fig.add_trace(go.Scatter(
        x=[0, 0.5,0.5, 0,0,None,1.1, 1.6,1.6, 1.1,1.1],
        y=[0, 0, REC1, REC1,0,None,0, 0, REC1, REC1,0],
        fill='toself', # fill area between trace0 and trace1
        mode='lines', line_color='#bd3786',name="3DHR " +str(REC1)))    
 
    fig.add_trace(go.Scatter(
        x=[0.5, 1,1, 0.5,0.5,None,1.1, 1.6,1.6, 1.1,1.1],
        y=[0, 0, REC2, REC2,0,None,REC1,REC1,REC1+REC2, REC1+REC2,REC1],
        fill='toself', # fill area between trace0 and trace1
        mode='lines', line_color='#0d0887',name="UHRS " +str(REC2)))   
       
    
    fig.update_xaxes(showticklabels=False,showgrid=False)
    fig.update_layout(template='none')
    fig.update_yaxes(range=[IETsr,0])
    return fig,u'TWT Seabed: {}ms'.format(SB)


if __name__ == '__main__':
    app.run_server(debug=True)

您可以将滑块放入某个对象,例如
div
,然后使用回调替换该
div
子对象。只需给它一个全新的滑块,使用相同的ID,但根据需要更新所有其他道具。

我现在已经完全解决了这个问题。更新@app.callback以将IETsr返回到“min”,并返回修改后的“marks”代码行

@app.callback(
Output('IET_output', 'children'),
Output('3DHR Slider', 'min'),    
Output('3DHR Slider','marks'),
Input('SPIDD','value'),
Input('SpeedDD','value'))
def do_maths(SPIDD,SpeedDD):
    SPIDD=float(SPIDD)
    SpeedDD=float(SpeedDD)
    global IET
    global IETs
    global IETsr
    IET=round(SPIDD/SpeedDD,2)
    IETs=IET*1000
    IETsr=0-round(IETs)
    return u'Inter Event Time: {}s'.format(IET),IETsr,{i: f"{i}" for i in range(round(IETsr,-2),0,200)}

我已经用修订版更新了代码,其中我将新计算的IETsr发送到滑块的“min”部分,而不是“value”。这就是我想要的滑块范围。现在我所需要的就是更新“标记”部分中的IETsr。