Проблема в том, что вы обходите логику рендеринга виджета, а это значит, что он не знает, как отобразить текущее выбранное значение.
Вы можете сделать что-нибудь взломанное и проверить данные формы в самом шаблоне. Но лучший способ - создать подкласс forms.widgets.RadioFieldRenderer
и написать собственную функцию рендеринга. Я сделал это в этом примере, чтобы отобразить каждый радиовход в отдельном <td>
, я проводил тест с несколькими вариантами ответов, где все вопросы имели одинаковый формат ответа.
from django.utils.safestring import mark_safe
from django.utils.encoding import force_unicode
from django.utils.html import conditional_escape
class ReportRadioInput(forms.widgets.RadioInput):
def __unicode__(self):
return mark_safe(u'%s' % self.tag())
class ReportRadioRenderer(forms.widgets.RadioFieldRenderer):
def __iter__(self):
for i, choice in enumerate(self.choices):
yield ReportRadioInput(self.name, self.value, self.attrs.copy(), choice, i)
def render(self):
"""Outputs a <ul> for this set of radio fields."""
return mark_safe(u'\n'.join([u'<td class="choice">%s</td>'
% force_unicode(w) for w in self]))
class AnswerForm(forms.Form):
def __init__(self, *args, **kwargs):
questionnaire = kwargs.pop('questionnaire')
super(AnswerForm, self).__init__(*args, **kwargs)
self.fieldsets = []
for g in questionnaire.groups.all():
fields = []
for q in g.questions.all():
fieldname = 'question_%i' % q.pk
widget = forms.RadioSelect(renderer=ReportRadioRenderer)
self.fields[fieldname] = forms.TypedChoiceField(coerce=int, empty_value=None, required=True, label=q.text, choices=CHOICES, widget=widget)
fields.append(self[fieldname])
self.fieldsets.append(dict(legend=g.name,fields=fields))
Бит, который вас заинтересует, это ReportRadioRenderer
, а использование widget = forms.RadioSelect(renderer=ReportRadioRenderer)