Fixed #3065 -- newforms: Fixed rendering problem with RadioSelect as a member of a Form. Also fixed some Unicode issues and added unit tests. Thanks for reporting, Derek Hoy
git-svn-id: http://code.djangoproject.com/svn/django/trunk@4106 bcc190cf-cafb-0310-a4f2-bffc1f526a37
This commit is contained in:
parent
95d19384c0
commit
4a14f2e233
|
@ -77,23 +77,23 @@ class Form(object):
|
|||
|
||||
def as_table(self):
|
||||
"Returns this form rendered as HTML <tr>s -- excluding the <table></table>."
|
||||
return u'\n'.join(['<tr><td>%s:</td><td>%s</td></tr>' % (pretty_name(name), BoundField(self, field, name)) for name, field in self.fields.items()])
|
||||
return u'\n'.join([u'<tr><td>%s:</td><td>%s</td></tr>' % (pretty_name(name), BoundField(self, field, name)) for name, field in self.fields.items()])
|
||||
|
||||
def as_ul(self):
|
||||
"Returns this form rendered as HTML <li>s -- excluding the <ul></ul>."
|
||||
return u'\n'.join(['<li>%s: %s</li>' % (pretty_name(name), BoundField(self, field, name)) for name, field in self.fields.items()])
|
||||
return u'\n'.join([u'<li>%s: %s</li>' % (pretty_name(name), BoundField(self, field, name)) for name, field in self.fields.items()])
|
||||
|
||||
def as_table_with_errors(self):
|
||||
"Returns this form rendered as HTML <tr>s, with errors."
|
||||
output = []
|
||||
if self.errors().get(NON_FIELD_ERRORS):
|
||||
# Errors not corresponding to a particular field are displayed at the top.
|
||||
output.append('<tr><td colspan="2"><ul>%s</ul></td></tr>' % '\n'.join(['<li>%s</li>' % e for e in self.errors()[NON_FIELD_ERRORS]]))
|
||||
output.append(u'<tr><td colspan="2"><ul>%s</ul></td></tr>' % u'\n'.join([u'<li>%s</li>' % e for e in self.errors()[NON_FIELD_ERRORS]]))
|
||||
for name, field in self.fields.items():
|
||||
bf = BoundField(self, field, name)
|
||||
if bf.errors:
|
||||
output.append('<tr><td colspan="2"><ul>%s</ul></td></tr>' % '\n'.join(['<li>%s</li>' % e for e in bf.errors]))
|
||||
output.append('<tr><td>%s:</td><td>%s</td></tr>' % (pretty_name(name), bf))
|
||||
output.append(u'<tr><td colspan="2"><ul>%s</ul></td></tr>' % u'\n'.join([u'<li>%s</li>' % e for e in bf.errors]))
|
||||
output.append(u'<tr><td>%s:</td><td>%s</td></tr>' % (pretty_name(name), bf))
|
||||
return u'\n'.join(output)
|
||||
|
||||
def as_ul_with_errors(self):
|
||||
|
@ -101,13 +101,13 @@ class Form(object):
|
|||
output = []
|
||||
if self.errors().get(NON_FIELD_ERRORS):
|
||||
# Errors not corresponding to a particular field are displayed at the top.
|
||||
output.append('<li><ul>%s</ul></li>' % '\n'.join(['<li>%s</li>' % e for e in self.errors()[NON_FIELD_ERRORS]]))
|
||||
output.append(u'<li><ul>%s</ul></li>' % u'\n'.join([u'<li>%s</li>' % e for e in self.errors()[NON_FIELD_ERRORS]]))
|
||||
for name, field in self.fields.items():
|
||||
bf = BoundField(self, field, name)
|
||||
line = '<li>'
|
||||
line = u'<li>'
|
||||
if bf.errors:
|
||||
line += '<ul>%s</ul>' % '\n'.join(['<li>%s</li>' % e for e in bf.errors])
|
||||
line += '%s: %s</li>' % (pretty_name(name), bf)
|
||||
line += u'<ul>%s</ul>' % u'\n'.join([u'<li>%s</li>' % e for e in bf.errors])
|
||||
line += u'%s: %s</li>' % (pretty_name(name), bf)
|
||||
output.append(line)
|
||||
return u'\n'.join(output)
|
||||
|
||||
|
@ -153,7 +153,13 @@ class BoundField(object):
|
|||
"Renders this field as an HTML widget."
|
||||
# Use the 'widget' attribute on the field to determine which type
|
||||
# of HTML widget to use.
|
||||
return self.as_widget(self._field.widget)
|
||||
value = self.as_widget(self._field.widget)
|
||||
if not isinstance(value, basestring):
|
||||
# Some Widget render() methods -- notably RadioSelect -- return a
|
||||
# "special" object rather than a string. Call the __str__() on that
|
||||
# object to get its rendered value.
|
||||
value = value.__str__()
|
||||
return value
|
||||
|
||||
def _errors(self):
|
||||
"""
|
||||
|
|
|
@ -955,6 +955,13 @@ u''
|
|||
<tr><td>Last name:</td><td><input type="text" name="last_name" value="Lennon" /></td></tr>
|
||||
<tr><td>Birthday:</td><td><input type="text" name="birthday" value="1940-10-9" /></td></tr>
|
||||
|
||||
Unicode values are handled properly.
|
||||
>>> p = Person({'first_name': u'John', 'last_name': u'\u0160\u0110\u0106\u017d\u0107\u017e\u0161\u0111'})
|
||||
>>> p.as_table()
|
||||
u'<tr><td>First name:</td><td><input type="text" name="first_name" value="John" /></td></tr>\n<tr><td>Last name:</td><td><input type="text" name="last_name" value="\u0160\u0110\u0106\u017d\u0107\u017e\u0161\u0111" /></td></tr>\n<tr><td>Birthday:</td><td><input type="text" name="birthday" /></td></tr>'
|
||||
>>> p.as_ul()
|
||||
u'<li>First name: <input type="text" name="first_name" value="John" /></li>\n<li>Last name: <input type="text" name="last_name" value="\u0160\u0110\u0106\u017d\u0107\u017e\u0161\u0111" /></li>\n<li>Birthday: <input type="text" name="birthday" /></li>'
|
||||
|
||||
>>> p = Person({'last_name': u'Lennon'})
|
||||
>>> p.errors()
|
||||
{'first_name': [u'This field is required.'], 'birthday': [u'This field is required.']}
|
||||
|
@ -1095,6 +1102,16 @@ For a form with a <select>, use ChoiceField:
|
|||
<option value="J">Java</option>
|
||||
</select>
|
||||
|
||||
>>> class FrameworkForm(Form):
|
||||
... name = CharField()
|
||||
... language = ChoiceField(choices=[('P', 'Python'), ('J', 'Java')], widget=RadioSelect)
|
||||
>>> f = FrameworkForm()
|
||||
>>> print f['language']
|
||||
<ul>
|
||||
<li><label><input type="radio" name="language" value="P" /> Python</label></li>
|
||||
<li><label><input type="radio" name="language" value="J" /> Java</label></li>
|
||||
</ul>
|
||||
|
||||
MultipleChoiceField is a special case, as its data is required to be a list:
|
||||
>>> class SongForm(Form):
|
||||
... name = CharField()
|
||||
|
|
Loading…
Reference in New Issue