无法使用django实现隐藏和显示功能

时间:2018-07-10 16:05:05

标签: javascript jquery css django python-3.x

我的功能是我的表单中有一个单选按钮。如果用户单击“是”,则他应该在屏幕上看到错误消息,提示这不是提交您的数据并建议他访问其他网站的合适位置。

如果他单击“否”,则表单中的所有其他字段应变为可见且必填。

我的问题是,当我单击“否”并尝试提交而不填写表单中的所有字段时,表单被重新加载,并且字段再次被隐藏。是的,数据没有保存到数据库中,当我单击“否”时,再次显示字段,并突出显示错误。

我主要担心的是,当我单击“否”并显示所有字段时,我不希望再次隐藏它们,直到成功提交表单或用户单击“是”。 我需要一个解决方案,以便仅在所有字段正确且成功提交到数据库后才重新加载表单。

我还将分享我到目前为止编写的代码,以便更好地理解:

1)models.py

from __future__ import unicode_literals
from django.db import models
from bokeh.themes import default
from django.contrib.auth.models import User
from django.db.models.signals import post_save
from django.dispatch import receiver
from django.contrib.auth.models import AbstractUser

# Create your models here.
class MyModel(models.Model):
    CHOICES = (
        ('Yes', 'Yes'),
        ('No', 'No'),
    )

    field1 = models.CharField(max_length=3, choices=CHOICES, blank=False, null=False)
    field2 = models.CharField(max_length=3, choices=CHOICES, blank=False, null=False)
    field3 = models.CharField(max_length=240, blank=True, null=True)
    field4 = models.CharField(max_length=240, blank=True, null=True)
    field5 = models.CharField(max_length=20, choices=CHOICES, blank=True, null=True)
    field6 = models.CharField(max_length=240, blank=True, null=True)
    field7 = models.CharField(max_length=100, choices=CHOICES, blank=True, null=True)
    field8 = models.CharField(max_length=480, blank=True, null=True)
    user = models.ForeignKey(User, on_delete=models.CASCADE)

    def __str__(self):
        return self.id

2)Forms.py

from django import forms
from django.core.validators import EMPTY_VALUES
from .models import MyModel

class MyModelForm(forms.ModelForm):
    CHOICES = (
        ('Yes', 'Yes'),
        ('No', 'No'),
    )


field1 = forms.ChoiceField(choices=CHOICES, widget=forms.RadioSelect())
field2 = forms.ChoiceField(choices=CHOICES, widget=forms.RadioSelect())
field3 = forms.CharField(required=False)
field4 = forms.CharField(required=False)
field5 = forms.ChoiceField(choices=CHOICES, widget=forms.RadioSelect(), required=False)
field6 = forms.CharField(required=False)
field7 = forms.ChoiceField(choices=CHOICES, widget=forms.RadioSelect(), required=False)
field8 = forms.CharField(required=False)
user_input_textbox1 = forms.CharField(max_length=200, widget=forms.HiddenInput(), required=False)

def clean(self):
    field1 = self.cleaned_data.get('field1')
    field2 = self.cleaned_data.get('field2')

    if field2 == 'Yes':
        self._errors['is_tangible_materials_exchanged'] = self.error_class([
            'Please submit a ABC request instead'])

    if field2 == 'No':
        # validate field3
        field3 = self.cleaned_data.get('field3', None)
        if field3 in EMPTY_VALUES:
            self._errors['field3'] = self.error_class([
                'field3 is required here'])

        #validate field4 
        field4 = self.cleaned_data.get('field4', None)
        if field4 in EMPTY_VALUES:
            self._errors['field4'] = self.error_class([
                'field4 is required here'])

        #validate field5
        field5 = self.cleaned_data.get('field5', None)
        if field5 in EMPTY_VALUES:
            self._errors['field5'] = self.error_class([
                'field5 is required here'])

        if field5 == 'Yes':
            # validate field6
            field6 = self.cleaned_data.get('field6', None)
            if field6 in EMPTY_VALUES:
                self._errors['field6'] = self.error_class([
                    'field6 is required here'])


        # validate field7
        field7 = self.cleaned_data.get('field7', None)
        if field7 in EMPTY_VALUES:
            self._errors['field7'] = self.error_class([
                'The purpose of exchanging this confidential information required here'])

        if field7 == 'Yes':
            # validate field8
            field8 = self.cleaned_data.get('field8', None)
            if field8 in EMPTY_VALUES:
                self._errors['field8'] = self.error_class([
                    'field8 is required here'])

    return self.cleaned_data


class Meta:
    model = MyModel
    exclude = ('user',)

3)Javascript / jQuery逻辑

<script>
    $(document).ready(function () {
        //hide all
        $(".hidden-md").hide();
        $(".hidden-lg").hide();
        $(".hidden-xs").hide();


        $("input[name='field2']").change(function () {//change event on radio button
            if (this.value == 'No') {
                $(".hidden-md").show();     
            }
            else {
                $(".hidden-md").hide();
                $(".hidden-lg").hide();
                $(".hidden-xs").hide(); 
                $("input[name='field5']").prop('checked', false);
                $("input[name='field7']").prop('checked', false);
            }
        });

        $("input[name='field5']").change(function () {//click event on radio button
            if (this.value == 'Yes') {
                $(".hidden-lg").show();
            }
            else {
                $(".hidden-lg").hide();
            }
        });

        $("input[name='field7']").change(function () {//click event on radio button
            if (this.value == 'Yes') {
                $(".hidden-xs").show();
            }
            else {
                $(".hidden-xs").hide();
            }
        });
    });

    document.getElementByClassName("btn").addEventListener("click", function(event){
        event.preventDefault();
        handleFireButton();
    });
</script>

任何帮助或建议将不胜感激!

2 个答案:

答案 0 :(得分:0)

模板加载后的动态逻辑将使用Javascript而不是Django实现,因为Django一次处理您的请求并将其发送到Web浏览器,因此,如果您尝试仅使用django显示和隐藏内容,每次都重新加载页面...

在javascript中创建一个函数(如果您是初学者,则使用Jquery,jquery非常简单),因此您可以在想要显示或隐藏输入时实现逻辑

https://www.w3schools.com/jS/default.asp

https://www.w3schools.com/Jquery/default.asp

编辑:为避免表单在不验证数据的情况下继续将数据发送到后端,您应该停止默认操作,如此操作

$("#btn_submit").click((e) => {
    e.preventDefault(); // This will make your button to submit it
    ... // Validade your logic here
    $("#form_id").submit()
});

谈论捉迷藏,确实很容易

$("#chk_a").click(function(e){
    if(this.checked) {
        $(".group_b").hide(); // hide everything from group B

        $("#input_a").show();
        $("#button_a").show();
        $("#somethingelse_a").show();
    }
});

// Same logic to group b

<input id="chk_a">
<input id="input_a" class="group_a">
<input id="button_a" class="group_a">
<input id="somethingelse_a" class="group_a">

<input id="chk_b">
<input id="input_b" class="group_b">
<input id="button_b" class="group_b">
<input id="somethingelse_b" class="group_b">

答案 1 :(得分:0)

我能够解决我的问题。 我使用其他隐藏字段实现了我的解决方案。 请在下面找到此问题的解决方案:

1)如下所示在forms.py中添加一个隐藏字段:

source = forms.CharField(max_length=50, widget=forms.HiddenInput(), required=False)

2)更新了Javascript / jQuery逻辑:

<script>
    $(document).ready(function () {
        //hide all
        if($("#id_source").val()!="postback" ) {
            $(".hidden-md").hide();
            $(".hidden-lg").hide();
            $(".hidden-xs").hide();
            $("#id_source").val("postback");
        }

        if ($('#id_field2_0').is(':checked') || $("input[name='field2']").is(':checked') == false) {
            $(".hidden-md").hide();
            $(".hidden-lg").hide();
            $(".hidden-xs").hide();
            $("input[name='field5']").prop('checked', false);
            $("input[name='field7']").prop('checked', false);   
        }

        if ($("input[name='field5']").is(':checked') == false || $('#id_field5_1').is(':checked')) {
            $(".hidden-lg").hide(); 
            $("#id_field6").html('');
        }

        if ($("input[name='field7']").is(':checked') == false || $('#id_field7_1').is(':checked')) {
            $(".hidden-xs").hide(); 
            $("#id_field8").html('');
        }

        $("input[name='field2']").click(function () {//change event on radio button
            if (this.value == 'No') {
                $(".hidden-md").show();     
            }
            else {
                $(".hidden-md").hide();
                $(".hidden-lg").hide();
                $(".hidden-xs").hide(); 
                $("input[name='field5']").prop('checked', false);
                $("input[name='field7']").prop('checked', false);
            }
        });

         $("input[name='field5']").click(function () {//click event on radio button
            if (this.value == 'Yes') {
                $(".hidden-lg").show();
            }
            else {
                $(".hidden-lg").hide();
                $("#id_field6").html('');
            }
        });

        $("input[name='field7']").click(function () {//click event on radio button
            if (this.value == 'Yes') {
                $(".hidden-xs").show();
            }
            else {
                $(".hidden-xs").hide();
                $("#id_field8").html('');
            }
        });
    });
</script>

使用上述逻辑,我能够使用jquery / django实现隐藏和显示功能,尽管重新加载了表单,但它可以解决我的问题并满足我所寻找的功能。

此致

Amey Kelekar