| | 1 | ============================================ |
| | 2 | Writing (and using) a custom widget renderer |
| | 3 | ============================================ |
| | 4 | |
| | 5 | It's possible to override a renderer for a specific widget by subclassing |
| | 6 | it. A good example is the RadioSelect widget that, by default, outputs |
| | 7 | a list of items. |
| | 8 | |
| | 9 | To override this behavior, we need to subclass the widget. In particular |
| | 10 | its renderer function. For example, take this piece of code that can be |
| | 11 | included in ``myproject/myapp/forms.py``: |
| | 12 | |
| | 13 | .. code-block:: python |
| | 14 | from django.forms.widgets import RadioFieldRenderer, RadioSelect |
| | 15 | from django.utils.encoding import StrAndUnicode, force_unicode |
| | 16 | from django.utils.safestring import mark_safe |
| | 17 | |
| | 18 | class CustomRenderer(RadioFieldRenderer): |
| | 19 | def render(self): |
| | 20 | return mark_safe(u'\n%s\n' % u'\n'.join([u'<tr><td>%s</td></tr>' |
| | 21 | % force_unicode(w) for w in self])) |
| | 22 | |
| | 23 | class CustomRadioSelect(RadioSelect): |
| | 24 | renderer = CustomRenderer |
| | 25 | |
| | 26 | |
| | 27 | You can then use the new widget like this: |
| | 28 | |
| | 29 | .. code-block:: python |
| | 30 | class OSChoiceForm(forms.Form): |
| | 31 | OS_CHOICES = ( |
| | 32 | ('linux', 'Linux'), |
| | 33 | ('windows', 'Windows'), |
| | 34 | ('mac', 'Macintosh'), |
| | 35 | ) |
| | 36 | os = forms.ChoiceField(label='', widget=CustomRadioSelect, choices=OS_CHOICES ) |
| | 37 | |
| | 38 | And the form will be rendered as table rows instead of list items. |
| | 39 | |