【发布时间】:2014-01-31 14:00:45
【问题描述】:
我想做的是更改前端内联表单集的界面,以便复选框可以与“通过”模型上的两个不同外键字段相关联。基本上,我想将两个下拉菜单折叠成一个复选框。
在models.py中:
class Food(models.Model):
name = models.CharField(max_length=10)
class Day(models.Model):
"""Days of the week: Sunday, Monday, Tuesday, etc."""
name = models.CharField(max_length=10)
class Meal(models.Model):
"""Breakfast, Lunch, Dinner"""
name = models.CharField(max_length=10)
class Plan(models.Model):
name = models.CharField()
foods = models.ManyToManyField('Food',related_name='plans')
days = models.ManyToManyField('Day',related_name='plans',through='Schedule')
meals = models.ManyToManyField('Meal',related_name='plans',through='Schedule')
class Schedule(models.Model):
plan = models.ForeignKey(Plan)
day = models.ForeignKey(Day)
meal = models.ForeignKey(Meal)
每个计划都有一组关联的食物,然后通过计划模型与特定日期的特定膳食相关联。
我想要一个模型表单,用户可以在其中创建膳食计划,并在其中说明他们将在哪几天吃什么食物。例如,用户可以先从一组食物中选择苹果和香蕉,然后他们应该能够选择在哪一天吃苹果和香蕉。
我的看法是:
def plan_add(request):
form = forms.PlanForm();
ScheduleFormSet = inlineformset_factory(Plan, Schedule)
formset_schedule = ScheduleFormSet()
response = render(request, 'template.html', {
'form' : form,
'formset_schedule' : formset_schedule,
})
return response
这给了我一个可以工作的表单,但是一个不友好的用户界面。对于您要添加的每个时间表,您必须首先从下拉列表中选择日期,然后从第二个下拉列表中选择餐点。我想要的是 7 个表行,每行都有一个用于每餐的复选框,您只需选中要放在日程表上的餐食的复选框。所以,我想让一个表单字段(一个复选框)与 Schedule 模型上的两个外键字段相关联:日和餐。
我想知道是否有“Django”方法来解决这个问题,可能是通过覆盖 inlineformset_factory,或者如果这是一件很奇怪的事情,我应该手动构建这个表单,手动验证它,然后手动解析并保存数据。
【问题讨论】:
-
我喜欢手动构建表单。我认为
django.forms是 django 框架中最不灵活和不直观的部分。但是,您可能希望查看清晰的表单或 django 表单向导以获得更好的 UI -
知道在这种情况下手动构建表单并不是坏习惯,这很有帮助。我知道我可以让它工作,感觉就像我可以通过这样做来解决 Django 拥有的许多强大的内置功能。
-
你可以把表单域分解成你喜欢的任何形式,然后在客户端使用js来收集数据并发送它,就像你正确使用它一样。这样您就拥有灵活性,但不会失去内置功能
标签: django foreign-keys many-to-many inline-formset