Django表单:如何动态创建ModelChoiceField标签 [英] Django forms: how to dynamically create ModelChoiceField labels

查看:721
本文介绍了Django表单:如何动态创建ModelChoiceField标签的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想为forms.ModelChoiceField创建动态标签,我想知道如何做到这一点。我有以下表单类:

I would like to create dynamic labels for a forms.ModelChoiceField and I'm wondering how to do that. I have the following form class:

class ProfileForm(forms.ModelForm):

    def __init__(self, data=None, ..., language_code='en', family_name_label='Family name', horoscope_label='Horoscope type', *args, **kwargs):
        super(ProfileForm, self).__init__(data, *args, **kwargs)

        self.fields['family_name'].label = family_name_label
        .
        .
        self.fields['horoscope'].label = horoscope_label
        self.fields['horoscope'].queryset = Horoscope.objects.all()

    class Meta:
        model = Profile

    family_name = forms.CharField(widget=forms.TextInput(attrs={'size':'80', 'class': 'contact_form'}))
    .
    .
    horoscope = forms.ModelChoiceField(queryset = Horoscope.objects.none(), widget=forms.RadioSelect(), empty_label=None)

默认标签由Profile定义中指定的 unicode 函数定义。然而,由ModelChoiceField创建的单选按钮的标签需要动态创建。

The default labels are defined by the unicode function specified in the Profile definition. However the labels for the radio buttons created by the ModelChoiceField need to be created dynamically.

首先我以为我可以简单地覆盖ModelChoiceField,如Django文档中所述。但是创建静态标签。它允许您定义任何标签,但一旦选择,该选择是固定的。

First I thought I could simply override ModelChoiceField as described in the Django documentation. But that creates static labels. It allows you to define any label but once the choice is made, that choice is fixed.

所以我想我需要适应添加一些东西到 init like:

So I think I need to adapt add something to init like:

class ProfileForm(forms.ModelForm):

    def __init__(self, data=None, ..., language_code='en', family_name_label='Family name', horoscope_label='Horoscope type', *args, **kwargs):
        super(ProfileForm, self).__init__(data, *args, **kwargs)

        self.fields['family_name'].label = family_name_label
        .
        .
        self.fields['horoscope'].label = horoscope_label
        self.fields['horoscope'].queryset = Horoscope.objects.all()
        self.fields['horoscope'].<WHAT>??? = ???

任何帮助将非常感激。

我发现了一些东西,但我不知道这是否是最好的解决方案。我添加一些东西到类ProfileForm的 init 部分,如下所示:

I found something but I don't know if it's the best solution. I add something to the init part of class ProfileForm as follows:

class ProfileForm((forms.ModelForm):

    def __init__(self, data=None, ..., language_code='en', family_name_label='Family name', horoscope_label='Horoscope type', *args, **kwargs):
    super(ProfileForm, self).__init__(data, *args, **kwargs)

        # this function is added
        def get_label(self, language_code):
            """
            returns the label in the designated language, from a related object (table)
            """
            return HoroscopeLanguage.objects.get(horoscope=obj, language__language_code=language_code).horoscope_type_language

        self.fields['family_name'].label = family_name_label
        .
        .
        self.fields['horoscope'].queryset = Horoscope.objects.all()
        self.fields['horoscope'].label_from_instance = lambda obj: "%s: Euro %.2f" % (HoroscopeLanguage.objects.get(horoscope=obj, language__language_code=language_code).horoscope_type_language, obj.price)
        .
        .
        """
        The next code also works, the lambda function without the get_label function
        """
        self.fields['horoscope'].label_from_instance = lambda obj: "%s: Euro %.2f" % (obj.horoscope_type, obj.price)
        .
        .
        """
        But this code doesn't work. Anyone?
        """
        self.fields['horoscope'].label_from_instance = get_label(obj, language_code)


推荐答案

您可以使用 ModelChoiceField 然后动态更改您的 ProfileForm .__ init __ 中的选项,例如(假设它已经是ModelChoiceField):

You could use a ModelChoiceField and then change the choices in you ProfileForm.__init__ dynamically, eg (assuming that it is already a ModelChoiceField):

horoscopes = Horoscope.objects.all()
self.fields['horoscope'].choices = [(h.pk, h.name) for h in horoscopes]

h.name 在这个例子中将被用作标签的选择!

h.name in this example will be used as the label of the choice!

这篇关于Django表单:如何动态创建ModelChoiceField标签的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆