Dash客户端JS未执行页面返回



我有一个dash应用程序,在那里我添加了一个JS代码来打印.window on按钮。该代码在多页应用程序的每个页面上以及在页面上多次打印时都能很好地工作,但一旦我迁移回以前按下按钮的页面,它就无法工作。这会是JS不执行的问题吗?还是别的什么?代码应该在"点击"时执行,而不是在n_clicks计数时执行,因此不需要将任何内容重置为零。谢谢

from dash import Dash, dcc, html, Input, Output, callback
import dash_bootstrap_components as dbc
app = Dash(__name__, suppress_callback_exceptions=True)
app.layout = html.Div([
dcc.Location(id='url', refresh=False),
html.Div(id='page-content')
])

index_page = html.Div([
dcc.Link('Go to Page 1', href='/page-1'),
html.Br(),
dcc.Link('Go to Page 2', href='/page-2'),
])
page_1_layout = html.Div([
html.H1('Page 1'),
html.Div(id='hidden-content'),
dbc.Button('Print', id='printing', color="#D3D3D3", outline=False, style={"background": "transparent",
        'color': 'grey',
        'border': '0px'},
className="mr-1"),
html.Div(id='page-1-content'),
html.Br(),
dcc.Link('Go to Page 2', href='/page-2'),
html.Br(),
dcc.Link('Go back to home', href='/'),
])
@callback(Output('page-1-content', 'children'),
[Input('page-1-dropdown', 'value')])
def page_1_dropdown(value):
return f'You have selected {value}'

page_2_layout = html.Div([
html.H1('Page 2'),
dbc.Button('Print', id='printing', color="#D3D3D3", outline=False, style={"background": "transparent",
        'color': 'grey',
        'border': '0px'},
className="mr-1"),
html.Div(id='page-2-content'),
html.Br(),
dcc.Link('Go to Page 1', href='/page-1'),
html.Br(),
dcc.Link('Go back to home', href='/')
])
@callback(Output('page-2-content', 'children'),
[Input('page-2-radios', 'value')])
def page_2_radios(value):
return f'You have selected {value}'

# Update the index
@callback(Output('page-content', 'children'),
[Input('url', 'pathname')])
def display_page(pathname):
if pathname == '/page-1':
return page_1_layout
elif pathname == '/page-2':
return page_2_layout
else:
return index_page
# You could also return a 404 "URL not found" page here

app.clientside_callback(
"""
(function() {
registerPrintButtonHandler();
return;
function registerPrintButtonHandler() {
var button = document.getElementById("printing");
if (!button || button.onclick === onPrintButtonClick) {
setTimeout(registerPrintButtonHandler, 500);
return;
}
button.onclick = onPrintButtonClick;
}
function onPrintButtonClick() {
{
setTimeout(window.print, 700);
};
}
})();
""",
Output('blank-output2', 'children'),
Input('printing', 'value')
)
if __name__ == '__main__':
app.run_server(debug=True)

我认为问题是由您在JavaScript层中执行的复杂的自定义事件注册引起的。在Dash中,通常建议将回调直接附加到相关属性。对于您的情况,这样的回调可能是,

app.clientside_callback("""function(n_clicks){
if(n_clicks){setTimeout(window.print, 700)};
}""", Output("dummy", "children"), Input("printing", "n_clicks"))

其中输出是我添加到布局中的伪元素,

app.layout = html.Div([
dcc.Location(id='url', refresh=False),
html.Div(id='page-content'),
html.Div(id='dummy')
])

为了完整起见,以下是完整的代码

from dash import Dash, dcc, html, Input, Output, callback
import dash_bootstrap_components as dbc
app = Dash(__name__, suppress_callback_exceptions=True)
app.layout = html.Div([
dcc.Location(id='url', refresh=False),
html.Div(id='page-content'),
html.Div(id='dummy')
])
index_page = html.Div([
dcc.Link('Go to Page 1', href='/page-1'),
html.Br(),
dcc.Link('Go to Page 2', href='/page-2'),
])
page_1_layout = html.Div([
html.H1('Page 1'),
html.Div(id='hidden-content'),
dbc.Button('Print', id='printing'),
html.Div(id='page-1-content'),
html.Br(),
dcc.Link('Go to Page 2', href='/page-2'),
html.Br(),
dcc.Link('Go back to home', href='/'),
])

@callback(Output('page-1-content', 'children'),
[Input('page-1-dropdown', 'value')])
def page_1_dropdown(value):
return f'You have selected {value}'

page_2_layout = html.Div([
html.H1('Page 2'),
dbc.Button('Print', id='printing'),
html.Div(id='page-2-content'),
html.Br(),
dcc.Link('Go to Page 1', href='/page-1'),
html.Br(),
dcc.Link('Go back to home', href='/')
])

@callback(Output('page-2-content', 'children'),
[Input('page-2-radios', 'value')])
def page_2_radios(value):
return f'You have selected {value}'

# Update the index
@callback(Output('page-content', 'children'),
[Input('url', 'pathname')])
def display_page(pathname):
if pathname == '/page-1':
return page_1_layout
elif pathname == '/page-2':
return page_2_layout
else:
return index_page
# You could also return a 404 "URL not found" page here

app.clientside_callback("""function(n_clicks){
if(n_clicks){setTimeout(window.print, 700)};
}""", Output("dummy", "children"), Input("printing", "n_clicks"))
if __name__ == '__main__':
app.run_server(debug=True)

最新更新