如何为Django表单的SplitDateTimeField添加日期和时间选择器?
为SplitDateTimeWidget的日期和时间输入框分别设置选择器
我太懂这个痛点了——默认的SplitDateTimeWidget会把你设置的attrs一股脑应用到日期和时间两个输入框上,结果两个框全变成了日期选择器,完全不是你想要的效果。其实有两种简单的解决办法:
方法一:自定义SplitDateTimeWidget(推荐,复用性强)
我们可以重写SplitDateTimeWidget的get_widgets方法,给日期和时间子组件分别配置不同的属性:
from django.forms.widgets import SplitDateTimeWidget, DateInput, TimeInput class CustomSplitDateTimeWidget(SplitDateTimeWidget): def get_widgets(self): # 日期输入框用原生date类型,指定格式 date_widget = DateInput(attrs={'type': 'date'}, format='%Y-%m-%d') # 时间输入框用原生time类型,指定格式 time_widget = TimeInput(attrs={'type': 'time'}, format='%H:%M') return (date_widget, time_widget)
之后在你的表单里直接使用这个自定义组件就行:
class MyForm(forms.ModelForm): class Meta: model = MyModel fields = ('name', 'description', 'start', 'end',) widgets = { 'start': CustomSplitDateTimeWidget(), 'end': CustomSplitDateTimeWidget(), }
这样渲染出来的第一个输入框是浏览器原生的日期选择器,第二个是时间选择器,完美分开!
方法二:在表单初始化时修改子组件属性(灵活,适合单表单场景)
如果只是个别表单需要这个效果,也可以不用自定义组件,直接在表单的__init__方法里修改子widget的属性:
class MyForm(forms.ModelForm): class Meta: model = MyModel fields = ('name', 'description', 'start', 'end',) widgets = { 'start': SplitDateTimeWidget(), 'end': SplitDateTimeWidget(), } def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) # 处理start字段的两个输入框:第一个是日期,第二个是时间 self.fields['start'].widget.widgets[0].attrs.update({'type': 'date'}) self.fields['start'].widget.widgets[1].attrs.update({'type': 'time'}) # 同理处理end字段 self.fields['end'].widget.widgets[0].attrs.update({'type': 'date'}) self.fields['end'].widget.widgets[1].attrs.update({'type': 'time'})
这里widgets[0]对应日期输入框,widgets[1]对应时间输入框,直接给它们分别设置type属性就搞定了。
两种方法都能实现你要的效果,选哪种就看你的场景啦~
内容的提问来源于stack exchange,提问作者James
相关产品推荐
相关产品推荐

