1. ======================
    
  2. The form rendering API
    
  3. ======================
    
  4. 
    
  5. .. module:: django.forms.renderers
    
  6.    :synopsis: Built-in form renderers.
    
  7. 
    
  8. Django's form widgets are rendered using Django's :doc:`template engines
    
  9. system </topics/templates>`.
    
  10. 
    
  11. The form rendering process can be customized at several levels:
    
  12. 
    
  13. * Widgets can specify custom template names.
    
  14. * Forms and widgets can specify custom renderer classes.
    
  15. * A widget's template can be overridden by a project. (Reusable applications
    
  16.   typically shouldn't override built-in templates because they might conflict
    
  17.   with a project's custom templates.)
    
  18. 
    
  19. .. _low-level-widget-render-api:
    
  20. 
    
  21. The low-level render API
    
  22. ========================
    
  23. 
    
  24. The rendering of form templates is controlled by a customizable renderer class.
    
  25. A custom renderer can be specified by updating the :setting:`FORM_RENDERER`
    
  26. setting. It defaults to
    
  27. ``'``:class:`django.forms.renderers.DjangoTemplates`\ ``'``.
    
  28. 
    
  29. By specifying a custom form renderer and overriding
    
  30. :attr:`~.BaseRenderer.form_template_name` you can adjust the default form
    
  31. markup across your project from a single place.
    
  32. 
    
  33. You can also provide a custom renderer per-form or per-widget by setting the
    
  34. :attr:`.Form.default_renderer` attribute or by using the ``renderer`` argument
    
  35. of :meth:`.Form.render`, or :meth:`.Widget.render`.
    
  36. 
    
  37. Matching points apply to formset rendering. See :ref:`formset-rendering` for
    
  38. discussion.
    
  39. 
    
  40. Use one of the :ref:`built-in template form renderers
    
  41. <built-in-template-form-renderers>` or implement your own. Custom renderers
    
  42. must implement a ``render(template_name, context, request=None)`` method. It
    
  43. should return a rendered templates (as a string) or raise
    
  44. :exc:`~django.template.TemplateDoesNotExist`.
    
  45. 
    
  46. .. class:: BaseRenderer
    
  47. 
    
  48.     The base class for the built-in form renderers.
    
  49. 
    
  50.     .. attribute:: form_template_name
    
  51. 
    
  52.         .. versionadded:: 4.1
    
  53. 
    
  54.         The default name of the template to use to render a form.
    
  55. 
    
  56.         Defaults to ``"django/forms/default.html"``, which is a proxy for
    
  57.         ``"django/forms/table.html"``.
    
  58. 
    
  59.         .. deprecated:: 4.1
    
  60. 
    
  61.         The ``"django/forms/default.html"`` template is deprecated and will be
    
  62.         removed in Django 5.0. The default will become
    
  63.         ``"django/forms/div.html"`` at that time.
    
  64. 
    
  65.     .. attribute:: formset_template_name
    
  66. 
    
  67.         .. versionadded:: 4.1
    
  68. 
    
  69.         The default name of the template to use to render a formset.
    
  70. 
    
  71.         Defaults to ``"django/forms/formsets/default.html"``, which is a proxy
    
  72.         for ``"django/forms/formsets/table.html"``.
    
  73. 
    
  74.         .. deprecated:: 4.1
    
  75. 
    
  76.         The ``"django/forms/formset/default.html"`` template is deprecated and
    
  77.         will be removed in Django 5.0. The default will become
    
  78.         ``"django/forms/formset/div.html"`` template.
    
  79. 
    
  80.     .. method:: get_template(template_name)
    
  81. 
    
  82.         Subclasses must implement this method with the appropriate template
    
  83.         finding logic.
    
  84. 
    
  85.     .. method:: render(template_name, context, request=None)
    
  86. 
    
  87.         Renders the given template, or raises
    
  88.         :exc:`~django.template.TemplateDoesNotExist`.
    
  89. 
    
  90. .. _built-in-template-form-renderers:
    
  91. 
    
  92. Built-in-template form renderers
    
  93. ================================
    
  94. 
    
  95. ``DjangoTemplates``
    
  96. -------------------
    
  97. 
    
  98. .. class:: DjangoTemplates
    
  99. 
    
  100. This renderer uses a standalone
    
  101. :class:`~django.template.backends.django.DjangoTemplates`
    
  102. engine (unconnected to what you might have configured in the
    
  103. :setting:`TEMPLATES` setting). It loads templates first from the built-in form
    
  104. templates directory in ``django/forms/templates`` and then from the installed
    
  105. apps' templates directories using the :class:`app_directories
    
  106. <django.template.loaders.app_directories.Loader>` loader.
    
  107. 
    
  108. If you want to render templates with customizations from your
    
  109. :setting:`TEMPLATES` setting, such as context processors for example, use the
    
  110. :class:`TemplatesSetting` renderer.
    
  111. 
    
  112. .. class:: DjangoDivFormRenderer
    
  113. 
    
  114. .. versionadded:: 4.1
    
  115. 
    
  116. Subclass of :class:`DjangoTemplates` that specifies
    
  117. :attr:`~BaseRenderer.form_template_name` and
    
  118. :attr:`~BaseRenderer.formset_template_name` as ``"django/forms/div.html"`` and
    
  119. ``"django/forms/formset/div.html"`` respectively.
    
  120. 
    
  121. This is a transitional renderer for opt-in to the new ``<div>`` based
    
  122. templates, which are the default from Django 5.0.
    
  123. 
    
  124. Apply this via the :setting:`FORM_RENDERER` setting::
    
  125. 
    
  126.     FORM_RENDERER = "django.forms.renderers.DjangoDivFormRenderer"
    
  127. 
    
  128. Once the ``<div>`` templates are the default, this transitional renderer will
    
  129. be deprecated, for removal in Django 6.0. The ``FORM_RENDERER`` declaration can
    
  130. be removed at that time.
    
  131. 
    
  132. ``Jinja2``
    
  133. ----------
    
  134. 
    
  135. .. class:: Jinja2
    
  136. 
    
  137. This renderer is the same as the :class:`DjangoTemplates` renderer except that
    
  138. it uses a :class:`~django.template.backends.jinja2.Jinja2` backend. Templates
    
  139. for the built-in widgets are located in ``django/forms/jinja2`` and installed
    
  140. apps can provide templates in a ``jinja2`` directory.
    
  141. 
    
  142. To use this backend, all the forms and widgets in your project and its
    
  143. third-party apps must have Jinja2 templates. Unless you provide your own Jinja2
    
  144. templates for widgets that don't have any, you can't use this renderer. For
    
  145. example, :mod:`django.contrib.admin` doesn't include Jinja2 templates for its
    
  146. widgets due to their usage of Django template tags.
    
  147. 
    
  148. .. class:: Jinja2DivFormRenderer
    
  149. 
    
  150. .. versionadded:: 4.1
    
  151. 
    
  152. A transitional renderer as per :class:`DjangoDivFormRenderer` above, but
    
  153. subclassing :class:`Jinja2` for use with the Jinja2 backend.
    
  154. 
    
  155. Apply this via the :setting:`FORM_RENDERER` setting::
    
  156. 
    
  157.     FORM_RENDERER = "django.forms.renderers.Jinja2DivFormRenderer"
    
  158. 
    
  159. ``TemplatesSetting``
    
  160. --------------------
    
  161. 
    
  162. .. class:: TemplatesSetting
    
  163. 
    
  164. This renderer gives you complete control of how form and widget templates are
    
  165. sourced. It uses :func:`~django.template.loader.get_template` to find templates
    
  166. based on what's configured in the :setting:`TEMPLATES` setting.
    
  167. 
    
  168. Using this renderer along with the built-in templates requires either:
    
  169. 
    
  170. * ``'django.forms'`` in :setting:`INSTALLED_APPS` and at least one engine
    
  171.   with :setting:`APP_DIRS=True <TEMPLATES-APP_DIRS>`.
    
  172. 
    
  173. * Adding the built-in templates directory in :setting:`DIRS <TEMPLATES-DIRS>`
    
  174.   of one of your template engines. To generate that path::
    
  175. 
    
  176.     import django
    
  177.     django.__path__[0] + '/forms/templates'  # or '/forms/jinja2'
    
  178. 
    
  179. Using this renderer requires you to make sure the form templates your project
    
  180. needs can be located.
    
  181. 
    
  182. Context available in formset templates
    
  183. ======================================
    
  184. 
    
  185. .. versionadded:: 4.0
    
  186. 
    
  187. Formset templates receive a context from :meth:`.BaseFormSet.get_context`. By
    
  188. default, formsets receive a dictionary with the following values:
    
  189. 
    
  190. * ``formset``: The formset instance.
    
  191. 
    
  192. Context available in form templates
    
  193. ===================================
    
  194. 
    
  195. .. versionadded:: 4.0
    
  196. 
    
  197. Form templates receive a context from :meth:`.Form.get_context`. By default,
    
  198. forms receive a dictionary with the following values:
    
  199. 
    
  200. * ``form``: The bound form.
    
  201. * ``fields``: All bound fields, except the hidden fields.
    
  202. * ``hidden_fields``: All hidden bound fields.
    
  203. * ``errors``: All non field related or hidden field related form errors.
    
  204. 
    
  205. Context available in widget templates
    
  206. =====================================
    
  207. 
    
  208. Widget templates receive a context from :meth:`.Widget.get_context`. By
    
  209. default, widgets receive a single value in the context, ``widget``. This is a
    
  210. dictionary that contains values like:
    
  211. 
    
  212. * ``name``
    
  213. * ``value``
    
  214. * ``attrs``
    
  215. * ``is_hidden``
    
  216. * ``template_name``
    
  217. 
    
  218. Some widgets add further information to the context. For instance, all widgets
    
  219. that subclass ``Input`` defines ``widget['type']`` and :class:`.MultiWidget`
    
  220. defines ``widget['subwidgets']`` for looping purposes.
    
  221. 
    
  222. .. _overriding-built-in-formset-templates:
    
  223. 
    
  224. Overriding built-in formset templates
    
  225. =====================================
    
  226. 
    
  227. .. versionadded:: 4.0
    
  228. 
    
  229. :attr:`.BaseFormSet.template_name`
    
  230. 
    
  231. To override formset templates, you must use the :class:`TemplatesSetting`
    
  232. renderer. Then overriding widget templates works :doc:`the same as
    
  233. </howto/overriding-templates>` overriding any other template in your project.
    
  234. 
    
  235. .. _overriding-built-in-form-templates:
    
  236. 
    
  237. Overriding built-in form templates
    
  238. ==================================
    
  239. 
    
  240. .. versionadded:: 4.0
    
  241. 
    
  242. :attr:`.Form.template_name`
    
  243. 
    
  244. To override form templates, you must use the :class:`TemplatesSetting`
    
  245. renderer. Then overriding widget templates works :doc:`the same as
    
  246. </howto/overriding-templates>` overriding any other template in your project.
    
  247. 
    
  248. .. _overriding-built-in-widget-templates:
    
  249. 
    
  250. Overriding built-in widget templates
    
  251. ====================================
    
  252. 
    
  253. Each widget has a ``template_name`` attribute with a value such as
    
  254. ``input.html``. Built-in widget templates are stored in the
    
  255. ``django/forms/widgets`` path. You can provide a custom template for
    
  256. ``input.html`` by defining ``django/forms/widgets/input.html``, for example.
    
  257. See :ref:`built-in widgets` for the name of each widget's template.
    
  258. 
    
  259. To override widget templates, you must use the :class:`TemplatesSetting`
    
  260. renderer. Then overriding widget templates works :doc:`the same as
    
  261. </howto/overriding-templates>` overriding any other template in your project.