E
E
Enter_a_nickname2022-02-17 12:45:42
Django
Enter_a_nickname, 2022-02-17 12:45:42

How to use multiple forms on one page?

Good afternoon! In my Django project, it is necessary to use 4 forms associated with the model on one page at once. I tried to implement this solution with a prefix for each form. Forms could be displayed in the html template, but the data could not be saved to the database. Why?
Here is my code:

views.py:

def dog(request):
    error = ''
    if request.method == 'POST':
        form2 = SpeedsForms(request.POST, prefix='form2')
        form3 = DogsForms(request.POST, prefix='form3')
        form4 = ColorForms(request.POST, prefix='form4')
        form5 = DogRequestsForm(request.POST, prefix='form5')
        if form2.is_valid() and form3.is_valid() and form4.is_valid() and form5.is_valid():
            form2.save()
            form3.save()
            form4.save()
            form5.save()
            return redirect('home')
        else:
            error = 'Форма заполненна некорректно'

    form2 = SpeedsForms()
    form3 = DogsForms()
    form4 = ColorForms()
    form5 = DogRequestsForm()
    data = {
        'form2': form2,
        'form3': form3,
        'form4': form4,
        'form5': form5,
        'error': error
    }
    return render(request, 'main/dogsform.html', data)


my urls.py: my forms.py:
path('dog', views.dog, name='dogsform')

class ColorForms(ModelForm):
    class Meta:
        model = Color
        fields = ['temp', 'correct', 'top', 'bottom']
        widgets = {
            'temp': NumberInput(attrs={
                'class': 'form-control',
                'placeholder': 'temp'
            }),
            'correct': NullBooleanSelect(attrs={
                'class': 'form-control',
                'placeholder': 'correct'
            }),
            'top': NumberInput(attrs={
                'class': 'form-control',
                'placeholder': 'top'
            }),
            'bottom': NumberInput(attrs={
                'class': 'form-control',
                'placeholder': 'bottom'
            }),
        }

class SpeedsForms(ModelForm):
    class Meta:
        model = Speed
        fields = ['start',  'end']
        widgets = {
            "start": TimeInput(attrs={
                'class': 'form-control',
                'placeholder': "start"
            }),
            "end": TimeInput(attrs={
                'class': 'form-control',
                'placeholder': "end"
            })
        }

class DogsForm(ModelForm):
    class Meta:
        model = Dog
        fields = ['name', 'number', 'Speed', 'DataTime']
        widgets = {
            "name": TextInput(attrs={
                'class': 'form-control',
                'placeholder': "name"
            }),
            "number": NumberInput(attrs={
                'class': 'form-control',
                'placeholder': "number"
            }),
            "Speed": SelectMultiple(attrs={
                'class': 'form-control',
                'placeholder': "Speed"
            }),
            "DataTime": DateTimeInput(attrs={
                'class': 'form-control',
                'placeholder': "DataTime"
            }),
        }

class DogRequestsForm(ModelForm):
    class Meta:
        model = DogRequest
        fields = ['id_name', 'Color', 'Dog']
        widgets = {
            'id_name': NumberInput(attrs={
                'class': 'form-control',
                'placeholder': 'id_name'
            }),
            'Color': SelectMultiple(attrs={
                'class': 'form-control',
                'placeholder': 'Color'
            }),
            'Dog': SelectMultiple(attrs={
                'class': 'form-control',
                'placeholder': 'Dog'
            }),
        }


And finally my HTML:
{% block content %}
    <div class="features">
        <h1>Color</h1>
        <form method="post">
            {% csrf_token %}<br>
            {{ form4.temp }}<br>
            {{ form4.correct }}<br>
            {{ form4.top }}<br>
            {{ form4.bottom }}<br>
            <button class="btn btn-success" type="submit">Сохранить</button>
            <span>{{ error }}</span>
        </form>
        <form method="post">
            {% csrf_token %}<br>
            {{ form2.start }}<br>
            {{ form2.end }}<br>
            <button class="btn btn-success" type="submit">Сохранить</button>
            <span>{{ error }}</span>
        </form>
        <form method="post">
            {% csrf_token %}<br>
            {{ form3.name }}<br>
            {{ form3.number }}<br>
            {{ form3.Speed}}<br>
            {{ form3.DataTime }}<br>
            <button class="btn btn-success" type="submit">Сохранить</button>
            <span>{{ error }}</span>
        </form>
         <form method="post">
            {% csrf_token %}<br>
            {{ form5.id_name}}<br>
            {{ form5.Color}}<br>
            {{ form5.Dog}}<br>
            <button class="btn btn-success" type="submit">Сохранить</button>
            <span>{{ error }}</span>
        </form>
    </div>
{% endblock %}


At the same time, if I remove prifix for example for color, other forms are no longer displayed on the page, but color is successfully saved in the database.
What needs to be fixed to successfully save data from all forms?
I will also be grateful if you tell me how to deal with related models? After all, for example, in form number 5, I use related models (color and dog) that I need to create before I fill out form number 5.

Answer the question

In order to leave comments, you need to log in

1 answer(s)
D
Dr. Bacon, 2022-02-17
@bacon

1. if form4.is_valid():why is_valid for only one form?
2. a lot of forms already speak about design problems, here it’s more likely that one form needs to be assembled, and rather for such a complex design it’s necessary not from ModelForm, but from Form, and you will have to write the collection of fields in different models yourself.

Didn't find what you were looking for?

Ask your question

Ask a Question

731 491 924 answers to any question