diff --git a/django/forms/models.py b/django/forms/models.py index 527da5e3ba..254cca3db8 100644 --- a/django/forms/models.py +++ b/django/forms/models.py @@ -368,7 +368,7 @@ class ModelForm(BaseModelForm): __metaclass__ = ModelFormMetaclass def modelform_factory(model, form=ModelForm, fields=None, exclude=None, - formfield_callback=None): + formfield_callback=None, widgets=None): # Create the inner Meta class. FIXME: ideally, we should be able to # construct a ModelForm without creating and passing in a temporary # inner class. @@ -379,6 +379,8 @@ def modelform_factory(model, form=ModelForm, fields=None, exclude=None, attrs['fields'] = fields if exclude is not None: attrs['exclude'] = exclude + if widgets is not None: + attrs['widgets'] = widgets # If parent form class already has an inner Meta, the Meta we're # creating needs to inherit from the parent's inner meta. diff --git a/tests/regressiontests/model_forms_regress/tests.py b/tests/regressiontests/model_forms_regress/tests.py index 9860c2e1ad..05b8abd4d3 100644 --- a/tests/regressiontests/model_forms_regress/tests.py +++ b/tests/regressiontests/model_forms_regress/tests.py @@ -275,6 +275,20 @@ class FormFieldCallbackTests(TestCase): Form = modelform_factory(Person, form=BaseForm) self.assertTrue(Form.base_fields['name'].widget is widget) + def test_factory_with_widget_argument(self): + """ Regression for #15315: modelform_factory should accept widgets + argument + """ + widget = forms.Textarea() + + # Without a widget should not set the widget to textarea + Form = modelform_factory(Person) + self.assertNotEqual(Form.base_fields['name'].widget.__class__, forms.Textarea) + + # With a widget should not set the widget to textarea + Form = modelform_factory(Person, widgets={'name':widget}) + self.assertEqual(Form.base_fields['name'].widget.__class__, forms.Textarea) + def test_custom_callback(self): """Test that a custom formfield_callback is used if provided"""