Another option to consider in newer versions of Django is to use Reusable form templates to create a form template to call as {{ form.as_td }}
, just like you would call {{ form.as_table }}
in your template.
This has a few nice features:
- A
FormSet
with each form wrapped in a <tr>
but fields wrapped in <td>
can coexist with other nice add-ons like django-dynamic-formset
- This method can be used for other elements your might want to render forms with
Steps:
- Create a
RenderMixin
that implements as as_td()
method, to be called as {{ form.as_td }}
in your template
from django.forms.utils import RenderableMixin
class ColumnRenderableFormMixin(RenderableMixin):
def as_td(self):
"""Render as <td> elements excluding the surrounding <table> tag."""
return self.render(self.template_name_td)
- Create a reusable template in your app templates directory (or other suitable directory)
{% for field, errors in fields %}
<td>
{{ errors }}
{{ field }}
</td>
{% endfor %}
- Add the custom mixin to your form, and specify the
td.html
template file path in the template_name_td
class variable:
class SomeForm(ModelForm, ColumnRenderableFormMixin):
template_name_td = "someapp/td.html"
- In your view's template, render the form with
{{ form.as_td }}
.
- If you're using a formset this would look like the following:
<table class="table">
{% for form in formset %}
<tr>
{{ form.as_td }}
</tr>
{% endfor %}
</table>