Рисунок не сохраняется в графическом виде из функции. Как это исправить?
У меня есть функция, которая берет график matplotlib и превращает его в график, используя tls.matplotlib_to_pyplot. В конце концов я назвал его plotly_fig. Теперь я пытаюсь добавить ползунки в веб-приложение. Но когда я его компилирую, я получаю сообщение о том, что plotly_fig не определено. Ниже приведен пример кода, который воссоздает ошибку.
import dash
import dash_core_components as dcc
import dash_html_components as html
import numpy as np
from numpy.linalg import matrix_power
import matplotlib.pyplot as plt
import plotly.tools as tls
from mpl_toolkits.mplot3d import Axes3D
from dash.dependencies import Input, Output
app = dash.Dash()
#begin with the knobs
app.layout = html.Div([
dcc.Graph(
id = 'graph',
figure = plotly_fig),
html.Label('Config L'), ## this is the knob for the length
dcc.Slider(
id = 'l',
min = 5,
max = 10,
marks = {i: 'Label ={}'.format(i) if i == 1 else str(i) for i in range(5,10)},
value = L,
),
html.Label('Config n'), ##knob for the n-gon
dcc.Slider(
id = 'n',
min = 0,
max = 10,
marks = {i: 'Label ={}'.format(i) if i == 1 else str(i) for i in range(1,10)},
value = n,
),
html.Label('Config N'), ##knob for the number of n-gons outside initial
dcc.Slider(
id = 'N',
min = 0,
max = 10,
marks = {i: 'Label ={}'.format(i) if i == 1 else str(i) for i in range(1,10)},
value = N,
),
html.Label('Config r'), ##knob for r only works on integers for now
dcc.Slider(
id = 'r',
min = 0,
max = 2,
marks = {i: 'Label ={}'.format(i) if i == 1 else str(i) for i in range(1,2)},
value = r,
),
html.Label('Config d'), ##knoc for the depth of the dip
dcc.Slider(
id = 'd',
min = 0,
max = 2,
marks = {i: 'Label ={}'.format(i) if i == 1 else str(i) for i in range(1,2)},
value = d,
)
],
style = {'columnCount': 1})
@app.callback(
dash.dependencies.Output('graph', 'figure'),
[dash.dependencies.Input('l', 'value'),
dash.dependencies.Input('n', 'value'),
dash.dependencies.Input('N', 'value'),
dash.dependencies.Input('r', 'value'),
dash.dependencies.Input('d', 'value')])
def output(L,n,N,r,d):
x = np.linspace(np.pi, L*n*N*r*d*np.pi, 1000)
fig = plt.figure()
ax = fig.add_subplot(111)
ax.plot(x, sinx)
plotly_fig = tls.mpl_to_plotly(mpl_fig)
return{plotly_fig}
if __name__=='__main__':
app.run_server(debug = True)
Что я делаю неправильно?
1 ответ
Проблема в том, что переменная plotly_fig
даже не объявляется, когда вы пытаетесь использовать его в графе figure
поле. Это просто объявлено локально в обратном вызове.
Не требуется устанавливать figure
свойство Graph явно, оно будет автоматически отображено во время обратного вызова, так что вы можете сделать это напрямую,
#your code here
app = dash.Dash()
#begin with the knobs
app.layout = html.Div([
dcc.Graph(
id = 'graph'), # ==> here you can remove the figure as it will be automatically set during the callback.
#your code here
],
style = {'columnCount': 1})
@app.callback(
dash.dependencies.Output('graph', 'figure'), #here figure represents the field
[dash.dependencies.Input('l', 'value'),
dash.dependencies.Input('n', 'value'),
dash.dependencies.Input('N', 'value'),
dash.dependencies.Input('r', 'value'),
dash.dependencies.Input('d', 'value')])
def output(L,n,N,r,d):
#your code here
plotly_fig = tls.mpl_to_plotly(mpl_fig)
return{plotly_fig}
if __name__=='__main__':
app.run_server(debug = True)
В приведенном выше фрагменте value
Свойство Slider является входом приложения, а выход приложения - figure
свойство графа. Всякий раз, когда значение Slider изменяется, Dash вызывает функцию обратного вызова output
с новыми входными значениями. Функция фильтрует информационный кадр с этим новым значением, создает объект рисунка и возвращает его в приложение Dash.
Между тем, если вы хотите, чтобы значение по умолчанию было установлено еще до вызова функции обратного вызова, вы можете объявить plotly_fig
как глобальная переменная, как это,
#your code here
plotly_fig = None # declare the default figure here
app = dash.Dash()
#begin with the knobs
app.layout = html.Div([
dcc.Graph(
id = 'graph', figure = plotly_fig),
#your code here
],
style = {'columnCount': 1})
@app.callback(
dash.dependencies.Output('graph', 'figure'),
[dash.dependencies.Input('l', 'value'),
dash.dependencies.Input('n', 'value'),
dash.dependencies.Input('N', 'value'),
dash.dependencies.Input('r', 'value'),
dash.dependencies.Input('d', 'value')])
def output(L,n,N,r,d):
#your code here
plotly_fig = tls.mpl_to_plotly(mpl_fig)
return{plotly_fig}
if __name__=='__main__':
app.run_server(debug = True)
Для получения дополнительной информации обратитесь к официальной странице документации, которая имеет аналогичный пример,