Django的项目---订单模块(下)和数据统计_11【可读性更好版本】

(0)摘要

# 课程链接

全新 django3 入门到项目实战(零基础学django、项目开发实践、大学毕业设计均可用)_哔哩哔哩_bilibili

# 课程内容

(1)5-5 订单-ajax删除(对话框)

(2)5-6 订单-编辑

(3)5-7 订单-对话框逻辑调整

(4)5-8 数据统计-柱状图

(5)5-9 数据统计-饼图和折线图


# 长风破浪会有时,直挂云帆济沧海

(1)5-5 订单-ajax删除(对话框)

# (1)删除功能(JS 的知识点!!!)

                1)这里有两种方案来做,一种是我们点击了某条数据的删除键,那么前端将选中的数据的 id 值取出来放在某个地方,当点击确认删除后,系统再将这个 id 发给后台进行删除;还有一种就是定义一个全局变量,只要点击了删除,那么对应的 id 就好赋值给这个全局变量,当确认删除后,就将全局变量发给后台(这也是我们后面用的)。

                由上面的方法二可知,我们定义了一个全局变量,那么点击了删除键后,所选数据的 id 就会赋值给这个全局变量,然后确认删除后,再将 id 值发送给后端。 

               

                2)前端代码。那么我们首先要对前端的编辑代码添加一下特有的属性,为了就是后续 js 能够索引到它。这里就只需要记住,不为什么。 那么特有属性,就是 uid="{{obj.id}}" ,相当于就是点击的那条数据的 id 值,即为 uid。

             

                3)然后我们绑定一个点击事件,只要单击了这个删除按钮,就把它的 id 赋值给我们设置的全局变量(因为我们遵循的是第二种方法来做)。当然了,还有删除操作的点击事件的方法函数 formDeleteEvent() 、确认删除点击事件的方法函数 confirmDeleteEvent() ,如图所示。

                4)首先我们来编写 formDeleteEvent()  的函数。流程是这样的,只要在某行点击了删除键,那么模态对话框就会显示出来,然后我们就将这行数据的 id 赋值给全局变量 DELETE_ID。那么我们如何知道是哪一个标签的呢,那就是使用 $(this) 方法,返回当前选中的标签对象,同时调用 attr() 方法,来获取 uid 的值。这种方式,我们只需要记住即可。

                5)在弹出的模态对话框中,如果用户确认了删除,那么我们就要将全局变量获得的 uid 值,返回到后端,让后端执行相应的删除操作了。也就是调用我们的确认删除点击事件的方法函数 confirmDeleteEvent(),流程就是使用 ajax 将 uid 传到后台。但是在此之前,我们需要给 tr 标签也加一个 uid 属性,方便后续的删除操作。 

                6)确认删除的第一种方法,就是要配合上面的 tr 标签的属性来用。直接给出代码。格式可能有点不好看,但是这个方法比较麻烦,详细的注释在下面了。这个主要是拿来学习下 js 的用法而已。

function confirmDeleteEvent() {
   $("#confirmDelete").click(function () {
        $.ajax({
            //其实是可以直接做字符串拼接的,如"/order/"+ DELETE_ID + "/delete/", 
            //那么我们可以更简单点,如下:
            url: '/order/delete/',
            type: 'GET',
            //因为我们用的是 GET 请求,所以请求的时候,会将 url 自动拼接为:
            // 设 DELETE_ID=123,那么发送的时候是 /order/delete/?uid=123
            data: {
            uid: DELETE_ID
            },
            dataType: 'JSON',
            success: function (res) {
                if (res.status) {
                    alert("删除成功");
                    $("#deleteModal").modal('hide');
                    /**   在页面中删除掉被删除的那行数据(之前只是在数据库中删除了)
                     *    $("tr") 索引的就是页面中的 tr 标签。然后我们索引具有删除 uid 的那个 tr 标签,执行删除操作,
                     *    这里的$("tr[uid='" + DELETE_ID + "']") 是字符串拼接,其中 DELETE_ID 会自动转为 str 类型
                     *    设 Str1:  "tr[uid='"
                     *      Str2:   DELETE_ID
                     *      Str3:   "']" , 那么上面的式子就是 $(Str1 + Str2 + Str3)
                     *      删除的话就是执行 remove() 方法。即
                     *      $("tr[uid='" + DELETE_ID + "']").remove();
                     *      【注意】
                     *          但是这种方法,存在问题。如果有分页数据,且执行删除后,
                     *          后面页的数据可能没办法顶到当前页
                     */
                    $("tr[uid='" + DELETE_ID + "']").remove();
                    //全局变量置空
                    DELETE_ID = 0;
                    }else{
                         //返回错误信息
                         alert(res.error)
                        }
                    }
                })
            })
        }

                7)确认删除的方法二,这个是很简单的,就是我们执行删除,并且隐藏模态对话框后,直接自动刷新页面即可。


(2)5-6 订单-编辑

# (1)索引 id(这是初级写法)

                1)其实编辑的索引 id 的逻辑是和删除的索引 id 逻辑是一样的。一样的设置特有属性,和 js 代码,这里我们直接上代码。

                2)js 代码。基本逻辑就是,每次点击事件后,先清空原来模态对话框的数据,不然不同的数据间会冲突。找到选中的 id 值,然后通过 ajax 请求发送 id 值到后台,后台再将原始的数据传回前台,然后放入模态对话框,最后呈现给用户查阅。

        function bindEditEvent(){

            $(".btn-edit").click(function (){
                //清空原来 input 的数据
                $("#formAdd")[0].reset();
                
                //找到选中的那行数据的 id
                DELETE_ID = $(this).attr("uid")
                //ajax 的请求
                $.ajax({
                    url: '/order/edit/',
                    type: 'GET',
                    data: {
                        uid: DELETE_ID
                    },
                    dataType: "JSON",
                    success: function (res){
                        if (res.status){
                            //循环返回的数据
                            $.each(res.data, function (name, key) {
                                $("#id_" + name).val(key)
                            })
                        }else{
                            alert("编辑错误")
                        }
                    }
                })

                //改一下抬头
                $("#myModalLabel").text("编 辑");

                //显示模态对话框
                $('#myModal').modal('show');
            })
        }

               

                3)视图函数的代码如下,更详细注释见后面的图示。

def order_edit(request):

    uid = request.GET.get("uid")

    """
        从数据库中取数据,返回的类型:
            (1) row_object = models.Order.objects.filter(pk=uid).first(), 
                # row_object 是一个对象。取数据的话,比如 title 属性。
                # 获取数据可以 row_object.title 就是点属性的方法。
                # 但是这种查询方式是返回对象,无法以 Json 格式为序列化数据返回。
                
            (2) row_list = models.Order.objects.filter(pk=uid).values("title", "price", "status").first()
                # 还有一种方法。但其实也可以是使用 .values() 方法,
                # 这样子返回的是一个字典,即 row_list = {'title': '电视', 'price': 1231232, 'status': 2}
            
            (3) row = models.Order.objects.all() 
                # 返回的是一个对象查询集合, 即 <QuerySet [<Order: Order object (4)>, ...], 每一个对象都是一条数据
                # 可以通过 row[0].title 来第一条数据的属性值
            
            (4) row = models.Order.objects.all().values("title", "price")
                # 这里我们指定了特定的值,那么返回的就是一个字典查询集合,即 [{}, {}, ...], 每一个 {} 是一条数据。
                # 事实上输出例如:<QuerySet [{'title': '手机', 'price': 12312}, {'title': '1231', 'price': 2131}, ...]>
            (5) row = models.Order.objects.all().values_list("title", "price")
                # 这里返回的是元组查询集。就是 [(), (), ...] , 每一个 () 是一条数据, 
                # 里面元素的个数取决于我们给的 values_list("a", "b", "c", ...)  括号里面的字段个数。 
                # 比如我们只给了两个属性,那么就是这样的 <QuerySet [('手机', 12312), ('1231', 2131), ...]
    """
    
    # 这里我们用上面的第 (2) 种方法
    row_list = models.Order.objects.filter(pk=uid).values("title", "price", "status").first()
    if not row_list:

        ret = {
            "code": 1002,
            "status": False
        }

        return JsonResponse(ret)
    # 查询成功的话,返回相应的数据
    ret = {
        "code": 1000,
        "status": True,
        "data": row_list
    }
    return JsonResponse(ret)

                4)数据库的查询复习。

                5)之所以说这个是因为 json 能返回的数据类型只能局限于基本的数据类型,如下图所示。


(3)5-7 订单-对话框逻辑调整

# (1)完善流程。

                1)如果按照上述的方法来做的话,我们点击保存的时候,就会直接变成新建多一条数据。这是因为我们的新建和编辑的模态对话框是共用的。我们可以加入一个全局变量用来判断,我们的操作是新建还是编辑。下面是 js 代码,同时,我们要把编辑的事件的变量也给改了。【补充一下,如果一个变量为 undefined,那么转换为 boolean 类型的话,就是 False,基于这个思想来判断是新建还是编辑】

                2)以下是编辑部分的完整 js 代码。

        //修改后的代码
        function formAddEvent() {
            $("#btnSave").click(function () {
                $(".error-msg").empty()

                if (EDIT_ID) {
                    //编辑
                    $.ajax({
                        url: '/order/edit/save/' + "?uid=" + EDIT_ID,
                        type: "post",
                        data: $("#formAdd").serialize(),
                        dataType: "JSON",
                        success: function (res) {
                            if (res.status) {
                                alert("编辑成功")
                                //保存成功后,清空表单。
                                // 因为jQuery 没有置空的功能,因此通过$("#formAdd")[0] 来绑定一个 DOM 对象
                                // 调用 .reset() 方法就可以将输入框给置空了。
                                $("#formAdd")[0].reset();
                                //保存成功后自动关闭
                                $("#myModal").modal('hide');
                                //保存成功后,页面自动刷新的方法。
                                location.reload();

                            } else {
                                if (res.err_msg) {
                                    alert(res.err_msg)
                                    console.log(res.status)
                                } else {
                                    $.each(res.error, function (name, err) {
                                        $("#id_" + name).next().text(err[0])
                                    })
                                }
                            }
                        }
                        })
                }

                else {
                    $.ajax({
                    url: '/order/add/',
                    type: "post",
                    data: $("#formAdd").serialize(),
                    dataType: "JSON",
                    success: function (res) {
                        if (res.status) {
                            alert("保存成功")
                            //保存成功后,清空表单。
                            // 因为jQuery 没有置空的功能,因此通过$("#formAdd")[0] 来绑定一个 DOM 对象
                            // 调用 .reset() 方法就可以将输入框给置空了。
                            $("#formAdd")[0].reset();
                            //保存成功后自动关闭
                            $("#myModal").modal('hide');
                            //保存成功后,页面自动刷新的方法。
                            location.reload();

                        } else {
                            $.each(res.error, function (name, err) {
                                {#console.log(name, err)#}
                                $("#id_" + name).next().text(err[0])
                            })
                        }
                    }
                })
                }

        })
            }

                3)我们编辑保存的视图函数如下:


(4)5-8 数据统计-柱状图

# (1)画图的第三方库

                1)当前主要使用的画图库有两种,一个是国外的 highcharts,还有一个是国内 echarts,这节武sir 主要是以 echarts 为例讲的。

                

                2)echarts 的基本使用。打开链接:Handbook - Apache ECharts ,我们可以看到如下的界面,选择通过 jsDelevr CDN 来下载。 

                使用 CDN 下载的时候,我们能来到如下界面,然后直接点红框的下载。下载的是一个类似于 demo 的压缩文件,我们只需要解压找到 /dist/echarts.min.js 即可。然后讲这个 js 文件放在我们 django 项目的 static/js/ 文件夹下即可。CDN 直通车:echarts CDN by jsDelivr - A CDN for npm and GitHub

                3)然后我们直接就配置一个简单的路由和前端页面,来使用 echarts 官方给的示例代码,绘制一个柱状图。当然在此之前我们需要做一个是具有 id = bar ,带有长宽的 div 标签。

                显示的结果如图:


# (2)示例代码的数据配置(本节主要是自己写的)

                这一节主要借助文档来查阅和调试查看,我们只需要知道基本使用,后续根据需要到文档中查阅即可,文档链接: Documentation - Apache ECharts

               

                1)title 的配置。 title 放的是一个字典(注意是 js 的),那格式就是 title: {}。比如下面的例子,我们给常用的一些属性写了备注。更多的可以参考文档。

                结果如下图所示:

                2)legend 的配置。这个是配置数据标识的。直接上代码看:

                 

                那么更直观的就是,显然 data 就是数据标识的名称。

                3)xAxis 就是表的横轴,更多的可以查看文档来使用。 yAxis 说的就是纵轴,这个基本都是查阅文档来做

                如图所示: 

                4)series 就是放数据的,我们放了两条数据进去。如下图所示, 

                那么最后的结果如下:

【总之,要用的时候,直接去查阅文档】


# (3)请求数据的方式来绘制柱状图

                1)模拟请求数据,然后自动绘制。首先是 js 的代码。

    <script type="text/javascript">
        $(function () {
            paintBar();
        })

        function paintBar() {
            // 基于准备好的dom,初始化echarts实例
            var myChart = echarts.init(document.getElementById('bar'));
            //bar 图专用
            var option = {
                color: [],
                title: {},
                tooltip: {},
                legend: {
                    data: [],
                    bottom: 0
                },
                xAxis: {
                    data: []
                },
                yAxis: {},
                series: []
            }

            $.ajax({
                url: '/charts/bar/',
                type: 'get',
                dataType: 'JSON',
                success: function (res) {
                    if (res.status) {
                        option.color = res.color;
                        option.title = res.title
                        option.legend.data = res.title.data
                        option.xAxis.data = res.xAxis.data
                        option.series = res.series
                        //显示
                        myChart.setOption(option);
                    }
                },

            })
        }

    </script>

                2)后端的视图函数:

def charts_bar(request):
    ret = {
        "status": True,

        "color": ["#CC0033", "#3398DB"],
        "title": {
            "text": 'ECharts',
            "subtext": "子标题",
            "left": "20%",
            "textStyle": {
                "s": 30
            }
        },
        "legend": {
            "data": ['销量', "啥也不是"],
            "bottom": "0%"
        },
        "xAxis": {
            "data": ['衬衫', '羊毛衫', '雪纺衫', '裤子', '高跟鞋', '袜子']
        },
        "series": [
            {
                "name": '销量',
                "type": 'bar',
                "data": [5, 20, 36, 10, 10, 20]
            },
            {
                "name": '啥也不是',
                "type": 'bar',
                "data": [5, 20, 36, 10, 10, 20]
            }
        ]
    }

    return JsonResponse(ret)

【总之,多看 echarts 的文档,并且注意返回数据的格式。】


(5)5-9 数据统计-饼图和折线图

# 链接~~~有空再看了。主要是结合文档一起学。 

全新 django3 入门到项目实战(零基础学django、项目开发实践、大学毕业设计均可用)_哔哩哔哩_bilibili

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值