Ticket #3987: dynamic.diff

File dynamic.diff, 4.3 KB (added by Xniver, 7 years ago)

sorry, forgot to change extension

  • django/contrib/admin/options.py

     
    3838    radio_fields = {}
    3939    prepopulated_fields = {}
    4040
    41     def formfield_for_dbfield(self, db_field, **kwargs):
     41    def formfield_for_dbfield(self, db_field, request, **kwargs):
    4242        """
    4343        Hook for specifying the form Field instance for a given database Field
    4444        instance.
     
    106106
    107107        # For ForeignKey or ManyToManyFields, use a special widget.
    108108        if isinstance(db_field, (models.ForeignKey, models.ManyToManyField)):
     109            if hasattr(self, 'dynamic_%s_choices' % db_field.name):
     110                formfield = db_field.formfield(queryset = getattr(self, 'dynamic_%s_choices' % db_field.name)(request, db_field.rel.to), **kwargs)
     111            else:
     112                formfield = db_field.formfield(**kwargs)
    109113            if isinstance(db_field, models.ForeignKey) and db_field.name in self.raw_id_fields:
    110                 kwargs['widget'] = widgets.ForeignKeyRawIdWidget(db_field.rel)
     114                formfield.widget = widgets.ForeignKeyRawIdWidget(db_field.rel)
    111115            elif isinstance(db_field, models.ForeignKey) and db_field.name in self.radio_fields:
    112                 kwargs['widget'] = widgets.AdminRadioSelect(attrs={
     116                formfield.widget = widgets.AdminRadioSelect(attrs={
    113117                    'class': get_ul_class(self.radio_fields[db_field.name]),
    114118                })
    115                 kwargs['empty_label'] = db_field.blank and _('None') or None
     119                formfield.empty_label = db_field.blank and _('None') or None
    116120            else:
    117121                if isinstance(db_field, models.ManyToManyField):
    118122                    # If it uses an intermediary model, don't show field in admin.
    119123                    if db_field.rel.through is not None:
    120124                        return None
    121125                    elif db_field.name in self.raw_id_fields:
    122                         kwargs['widget'] = widgets.ManyToManyRawIdWidget(db_field.rel)
    123                         kwargs['help_text'] = ''
     126                        formfield.widget = widgets.ManyToManyRawIdWidget(db_field.rel)
     127                        formfield.help_text = ''
    124128                    elif db_field.name in (list(self.filter_vertical) + list(self.filter_horizontal)):
    125                         kwargs['widget'] = widgets.FilteredSelectMultiple(db_field.verbose_name, (db_field.name in self.filter_vertical))
     129                        formfield.widget = widgets.FilteredSelectMultiple(db_field.verbose_name, (db_field.name in self.filter_vertical))
    126130            # Wrap the widget's render() method with a method that adds
    127131            # extra HTML to the end of the rendered output.
    128             formfield = db_field.formfield(**kwargs)
    129132            # Don't wrap raw_id fields. Their add function is in the popup window.
    130133            if not db_field.name in self.raw_id_fields:
    131134                # formfield can be None if it came from a OneToOneField with
     
    134137                    formfield.widget = widgets.RelatedFieldWidgetWrapper(formfield.widget, db_field.rel, self.admin_site)
    135138            return formfield
    136139
     140        if isinstance(db_field, (models.OneToOneField)) and hasattr(self, 'dynamic_%s_choices' % db_field.name):
     141            return db_field.formfield(queryset = getattr(self, 'dynamic_%s_choices' % db_field.name)(request, db_field.rel.to), **kwargs)
     142           
    137143        # For any other type of field, just call its formfield() method.
    138144        return db_field.formfield(**kwargs)
    139145
     
    262268        defaults = {
    263269            "form": self.form,
    264270            "fields": fields,
    265             "formfield_callback": self.formfield_for_dbfield,
     271            "formfield_callback": lambda f, **kwargs: self.formfield_for_dbfield(f, request, **kwargs),
    266272        }
    267273        defaults.update(kwargs)
    268274        return modelform_factory(self.model, **defaults)
     
    770776            "formset": self.formset,
    771777            "fk_name": self.fk_name,
    772778            "fields": fields,
    773             "formfield_callback": self.formfield_for_dbfield,
     779            "formfield_callback": lambda f, **kwargs: self.formfield_for_dbfield(f, request, **kwargs),
    774780            "extra": self.extra,
    775781            "max_num": self.max_num,
    776782        }
Back to Top