编辑:为清楚起见重写了2019年9月8日1330 UTC
在Jupyter笔记本中,我想浏览由日期选择器小部件选择的日期。我已经知道这样做的方法是使用@interact并使datepicker小部件成为interact函数的参数,例如:
def explore_dates(d1=widgets.DatePicker(value=pd.to_datetime('2018-07-10', format='%Y-%m-%d'), description='Date')):
但是我需要“下一个假期”和“上一个假期”按钮才能从所选日期移至下一个假期。我已经有一系列假日存储为datetime.datetime对象。
所以我尝试将按钮对象添加到@interact函数的参数中,如下所示:
@interact
def explore_dates(d1=widgets.DatePicker(value=pd.to_datetime('2018-07-10', format='%Y-%m-%d'), description='Date'),
prev_button = widgets.Button(description="Prev Holiday"),
next_button = widgets.Button(description="Next Holiday")):
那没有用。错误说带有按钮小部件的行“无法转换为小部件”。嗯,我以为它已经是小部件了……
我的下一个想法是将按钮代码放在函数内部,而不是作为参数:
def explore_dates(d1=widgets.DatePicker(value=pd.to_datetime('2018-07-10', format='%Y-%m-%d'), description='Date')):
prev_button = widgets.Button(description="Prev Holiday")
next_button = widgets.Button(description="Next Holiday")
prev_button.on_click(prev_holiday_callback)
next_button.on_click(next_holiday_callback)
box=widgets.HBox([prev_button,next_button])
display(box)
这在屏幕上显示了按钮,我可以按下它们,然后运行我的回调例程。但是,如果将日期选择器设置为@interact的参数(如上),则似乎无法再使用其.value属性重置其日期了。 (请参见上面的代码)尝试设置d1.value会导致错误。
我想我可以完全摆脱@interact,只需将datepicker和两个按钮都放在主代码中即可。 但是我当时不知道如何重现@interact的功能。缺少等待单击或观察事件来自其中一个小部件(而不是@interact)的无限循环,我不知道如何告诉Python / Jupyter“嘿,只是放松一下,直到小部件事件导致回调唤醒代码”。
如果有帮助,这是我的按钮回调例程。
def button_click_common():
global button_flag
global button_date
global holidays
for i in range(len(holidays)):
if(holidays[i]<button_date): # haven't passed the prior holiday yet
continue
# Now holidays[i] has to either be same as or after button_date
prior_holiday = i-1 # prior holiday is the one we just passed that was prior
next_holiday = i # assume at first we are between dates
if holidays[i]==button_date:
next_holiday +=1 # if we were already on a holiday date, next becomes the following one
return prior_holiday, next_holiday
def prev_holiday_callback(_):
global button_flag
global button_date
global holidays
prior_holiday,_ = button_click_common()
button_date = holidays[prior_holiday]
button_flag = True
def next_holiday_callback(_):
global button_flag
global button_date
global holidays
_,next_holiday = button_click_common()
button_date = holidays[next_holiday]
button_flag = True
这里的想法是回调将button_date更新为下一个假期的日期,并设置标志button_flag。然后explor_dates函数中的代码(未显示)将测试该标志。但是当将它定义为@interact函数的参数时,我不知道如何用新日期更新datepicker小部件。
感觉就像我要解决这个问题。欢迎任何建议或指导...
谢谢!
答案 0 :(得分:0)
我不确定我是否了解您要达到的确切目标,但是与带数字输入的功能(而不是离散输入或日期之类的python对象)进行交互时,交互效果最佳。
我整理了一些代码,这些代码说明了如何使用前进和后退按钮更新日期选择器,它可能并不是您想要的,但也许您可以从那里描述更改?
import ipywidgets as ipyw
from datetime import date
idx = 0
date_picker = ipyw.DatePicker()
date_picker.value = month_starts[idx]
start_button = ipyw.Button(description='Prev')
end_button = ipyw.Button(description='Next')
display(date_picker, start_button, end_button)
def change_date(button):
global idx
if button.description=='Prev':
if idx-1<0:
pass
else:
date_picker.value = month_starts[idx-1]
idx -= 1
elif button.description=='Next':
if idx+1>=len(month_starts):
pass
else:
date_picker.value = month_starts[idx+1]
idx += 1
start_button.on_click(change_date)
end_button.on_click(change_date)