Вопрос по django, forms, multiple-select, python, field – Джанго: Как я могу создать форму множественного выбора?

11

Я начинающий в Django / Python, и мне нужно создать форму множественного выбора. Я знаю это'легко, но я могуНе могу найти ни одного примера. Я знаю, как создать CharField с виджетом, но я запутался во всех параметрах внутриfields.py.

Например, я неНе знаю, какое из следующих утверждений лучше всего подходит для формы множественного выбора.

'ChoiceField', 'MultipleChoiceField',
'ComboField', 'MultiValueField',
'TypedChoiceField', 'TypedMultipleChoiceField'

И вот форма, которую мне нужно создать.

        
        
            Austria
            Germany
            Netherlands
            United States
        
        <p></p>
    

РЕДАКТИРОВАТЬ:

Еще один маленький вопрос. Если я хочу добавить к каждой опции еще один атрибут, какданные:

 Austria

Как мне это сделать?

Спасибо за любую помощь!

Ваш Ответ

5   ответов
1

ModelMultipleChoiceField твой друг. CharField способен хранить один выбор, но не несколько, без дополнительной работы, против которой я бы рекомендовал.

Документ API для ModelMultipleChoiceField

1

Вы также можете определить поле стран в вашем классе формы как

Countries = forms.MultipleChoiceField(widget=forms.SelectMultiple,
                                             choices=OPTIONS_TUPPLE)

Я неНе знаю, какой из них лучше в SelectMultiple и CheckboxSelectMultiple, но он также работает.

Для более подробной информации вы можете использовать документацию Django овиджеты.

4

forms.py

class ChoiceForm(ModelForm):
    class Meta:
        model = YourModel

    def __init__(self, *args, **kwargs):
        super(ChoiceForm, self).__init__(*args, **kwargs)
        self.fields['countries'] =  ModelChoiceField(queryset=YourModel.objects.all()),
                                             empty_label="Choose a countries",)

urls.py

from django.conf.urls.defaults import * 
from django.views.generic import CreateView
from django.core.urlresolvers import reverse

urlpatterns = patterns('',
    url(r'^$',CreateView.as_view(model=YourModel, get_success_url=lambda: reverse('model_countries'),
        template_name='your_countries.html'), form_class=ChoiceForm, name='model_countries'),)

your_countries.html

<form action="" method="post">
    {% csrf_token %}
    {{ form.as_table }}
    <input type="submit" value="Submit">
</form> 

Это нормально работает в моем примере, если вам нужно что-то еще, просто спросите меня!

27

что CheckboxSelectMultiple должен работать. В соответствии с вашей проблемой, в вашей форме.

from django import forms

class CountryForm(forms.Form):
        OPTIONS = (
                ("AUT", "Austria"),
                ("DEU", "Germany"),
                ("NLD", "Neitherlands"),
                )
        Countries = forms.MultipleChoiceField(widget=forms.CheckboxSelectMultiple,
                                             choices=OPTIONS)

РЕДАКТИРОВАТЬ: Я думал о написании полного потока кода, чтобы вы могли понять это лучше. Потому что вы можете запутаться

В вашем Views.py определите следующую функцию

def countries_view(request):
    if request.method == 'POST':
        form = CountryForm(request.POST)
        if form.is_valid():
            countries = form.cleaned_data.get('countries')
            # do something with your results
    else:
        form = CountryForm

    return render_to_response('render_country.html', {'form':form },
        context_instance=RequestContext(request))

В вашем render_country.html

<form method="post">
    {% csrf_token %}
    {{ form.as_p }}
    <input type="submit" value="submit">
</form>

Я надеюсь, что это поможет. Дайте мне знать, если это то, что вы ожидали.

и если мой первый ответ удовлетворит ваш запрос, пожалуйста, подумайте о принятии ответа. :) vibhor
Хороший ответ @vibhor ноAUT» знак равноАвстралия" как указано в вашем коде, это 'с Австрией. Извините за педантизм, мы, австралийцы, много чего получаем, и мынемного чувствительны к этому :-) Nexus
Точно сказать не могу!! сделать форму как модель формы. Я полагаю, что по крайней мере в бэкэнде будет связан первичный ключ. Нужно проверить это. vibhor
Да, это еще одна маленькая вещь ... Если я хочу добавить к каждой опции свойство данных, как это <значение параметра = "ДЭУ» = выбран»выбран» Данные индекс = 1>Германия <Опция /> как я могу это сделать? Также отсутствует последний вариант, который не выбран. Спасибо, в любом случае CodeArtist
2

from django import forms
from django.utils.encoding import force_unicode
from itertools import chain
from django.utils.html import escape, conditional_escape

class Select(forms.Select):
    """
    A subclass of Select that adds the possibility to define additional 
    properties on options.

    It works as Select, except that the ``choices`` parameter takes a list of
    3 elements tuples containing ``(value, label, attrs)``, where ``attrs``
    is a dict containing the additional attributes of the option.
    """
    def render_options(self, choices, selected_choices):
        def render_option(option_value, option_label, attrs):
            option_value = force_unicode(option_value)
            selected_html = (option_value in selected_choices) and u' selected="selected"' or ''
            attrs_html = []
            for k, v in attrs.items():
                attrs_html.append('%s="%s"' % (k, escape(v)))
            if attrs_html:
                attrs_html = " " + " ".join(attrs_html)
            else:
                attrs_html = ""
            return u'<option value="{0}" {1}{2}="">{3}</option>'.format(
                escape(option_value), selected_html, attrs_html, 
                conditional_escape(force_unicode(option_label))
                )
            '''
            return u'<option value="%s" %s%s="">%s</option>' % (
                escape(option_value), selected_html, attrs_html,
                conditional_escape(force_unicode(option_label)))
            '''
        # Normalize to strings.
        selected_choices = set([force_unicode(v) for v in selected_choices])
        output = []
        for option_value, option_label, option_attrs in chain(self.choices, choices):
            if isinstance(option_label, (list, tuple)):
                output.append(u'<optgroup label="%s">' % escape(force_unicode(option_value)))
                for option in option_label:
                    output.append(render_option(*option))
                output.append(u'</optgroup>')
            else:
                output.append(render_option(option_value, option_label,
                    option_attrs))
        return u'\n'.join(output)

class SelectMultiple(forms.SelectMultiple, Select):
    pass

Пример:

OPTIONS = [
        ["AUT", "Australia", {'selected':'selected', 'data-index':'1'}],
        ["DEU", "Germany", {'selected':'selected'}],
        ["NLD", "Neitherlands", {'selected':'selected'}],
        ["USA", "United States", {}]
    ]

Похожие вопросы