使用ajax过滤结果时加载部分html页面

时间:2017-04-01 21:27:29

标签: javascript jquery html ajax django

我想使用3个复选框过滤搜索结果。结果显示在带有id=posts_results

的div中
   <div class="checkbox">
      <label><input type="checkbox" id="id1" class="typePost" value="En groupe"> val1 </label>
   </div>
   <div class="checkbox">
      <label><input type="checkbox" id="id2" class="typePost" value="En groupe"> val2 </label>
   </div>
   <div class="checkbox">
      <label><input type="checkbox" id="id3" class="typePost"  value="A domicile"> val3</label>
   </div>
   <div class="checkbox">
      <label><input type="checkbox" id="id4" class="typePost" value="Par webcam"> val4</label>
   </div>

  <div id="posts_results">

            {% include 'posts/posts_results.html' %}

   </div>


    <script>
        $('.typePost').change(function (request, response) {

        var v1=$('#id1').is(":checked")? 1:0;
        var V2=$('#id2').is(":checked")? 1:0;
        var V3=$('#id3').is(":checked")? 1:0;
        var v4=$('#id4').is(":checked")? 1:0;
        $.ajax({

            url: '/posts/type_lesson/',
            dataType: 'json',
            type: "GET",
            data: {
                group: groupChecked,
                webcam: webcamChecked,
                home: homeChecked,
                move: moveChecked,
                distance: distance,
            },
            success: function (object_list) {

                $('#posts_results').load("my_page.html", object_list);
                alert('after')
            }

        });

    });
   <script>

这是我的网址:

url(r'^filter/$', views.filter, name='filter_type_lesson'),

这是我的观点:

def filter(request):
if request.method=='GET':

    #as an exemple I'll send all posts
    data= PostFullSerializer(Post.objects.all(), many=True)
    return JsonResponse(data.data, safe=False)

过滤功能根据json发送的数据执行一些过滤器,序列化过滤后的帖子并将其发回(在本例中我以发送所有帖子为例)。

使用id为“posts_results”的div中的forloop显示结果,html位于posts_results.html文件中。

发送了json数据,但是ajax success函数没有更新或加载div

也可以留下

2 个答案:

答案 0 :(得分:1)

我希望尽可能远离原始的POST数据,让表单API完成繁重的工作。你可以用更安全的方式用更少的代码完成你已经拥有的东西。

创建一个包含四个BooleanFields的表单,这些BooleanFields是为模型中的BooleanFields命名的。您可以使用label变量覆盖它们在HTML中的显示方式。

class TheForm(forms.Form):
    my_field = forms.BooleanField(required=False, label="What I want it to say")
    my_field2 = forms.BooleanField(required=False, label="What I want it to say 2", help_text="Something else")
    my_field3 = forms.BooleanField(required=False, label="What I want it to say 3", help_text="Something else")

输出为<form class="my_form">{% csrf_token %}{{form.as_table}}</form>

像这样提交JS:

$('.my_form input[type=checkbox]').change(function(e){
    e.preventDefault()
    $.post('module/filer/', $('.my_form').serialize(), function(data) {
        // Handle data
    });
});

提交并验证表单后,请使用cleaning_data属性并按此过滤模型

models = Post.objets.filter(**form.cleaned_data)

这将起作用,因为表单字段和名称与模型中的字段相同。和做Post.objects.filter(my_field=True, my_field2=True, my_field3=False)一样。然后你可以用它做任何你想做的事。我会使用FormView来完成所有这些:

class MyView(FormView):
    form_class = TheForm

    def form_valid(self, form):
        models = Post.objets.filter(**form.cleaned_data)
        data= PostFullSerializer(data, many=True)
        return JsonResponse(data.data, safe=False)

现在没有什么可以自己更新div。它仅在最初请求HTML时创建。在您的成功功能中,您需要手动附加元素,如下所示:

$('.my_form input[type=checkbox]').change(function(e){
    e.preventDefault()
    $.post('module/filer/', $('.my_form').serialize(), function(data) {
        var post_results = $('#post_results').html(''); // Clear out old html
        $.each(data, function(item) {
            // Create new divs from ajax data and append it to main div
            var div = $('<div>');
            div.append($('<div>').html(item.my_field));
            div.append($('<div>').html(item.my_field2).addClass('something'));
            div.appendTo(post_results);
        });
    });
});

您也可以通过ajax过去渲染HTML并执行$('#post_results').html(data);。您可以在FormView上调用self.render_to_response,而不是调用json响应。

答案 1 :(得分:0)

也许您可以尝试在视图中渲染模板,然后在div中加载渲染的数据。

假设您的posts/posts_results.html有些人:

<ul>
{% for post in posts %}
    <li> Post: {{post.name }} / Author: {{post.author}} / Date: {{post.created_at}}</li>
{% endid %}
<ul>

在您的视图中,当您执行相应操作时,您可以呈现模板并将html内容添加到响应中,即(基于您当前的代码):

def filter(request):
    if request.method=='GET':
        json_data = {
            "success": False,
            "message": "Some message",
            "result": "some result",
        }
        posts = Post.object.all()
        template = "posts/posts_results.html"

        things_to_render_in_your_template = {
            "posts": posts, # you can add other objects that you need to render in your template
        }

        my_html = get_template(template)
        html_content = my_html.render(things_to_render_in_your_template)

        # here the html content rendered is added to your response
        json_data["html_content"] = html_content
        json_data["success"] = True
        return JsonResponse(json_data)

然后在你的JS中,在检查ajsx响应的瞬间,你可以将渲染的内容添加到你的div中

$.ajax({

        url: '/posts/type_lesson/',
        dataType: 'json',
        type: "GET",
        data: {
            group: groupChecked,
            webcam: webcamChecked,
            home: homeChecked,
            move: moveChecked,
            distance: distance,
        },
        success: function (response) {
            # response is the json returned from the view, each key defined in your json_data dict in the view, is a key here too 

            # now insert the rendered content in the div
            $('#posts_results').html(response["html_content"]);
            alert('after');
        }

    });

我建议你不要为ajax请求创建逐个数据,使用jquery的serialize方法或创建FormData对象,而不是GET,使用POST来更安全地执行请求