# 排序功能开发; # 单条件排序; # 在表头每个字段上都添加a标签,点击降序,记住这次操作,再次点击反序(用箭头图标展示); # table_obj_list.html <th><a href="?_o=">{{ column }}</a></th> # _0等于字段的索引,如果为负,反序; # 所以可以通过模板标签forloop.count0来取; <th><a href="?_o={{forloop.count0}}">{{ column }}</a></th> # 考虑排序与过滤的关系; # 即可以过滤后排序,又可以排序后过滤; # 先忽略过滤条件,做筛选; # views.py def get_filter_result(request,querysets): filter_conditions = {} for key,val in request.GET.items(): # 排除分页的影响 if key in (‘page‘,‘_o‘):continue if val: filter_conditions[key] = val print("filter_conditions",filter_conditions) return querysets.filter(**filter_conditions),filter_conditions # 在筛选条件下做筛选搜索;考虑分页,排序,筛选的前后顺序; # 先排序再分页!分页后再排序的话,排序不受分页参数影响;==>>全局排序; # views.py def get_orderby_result(request,querysets,admin_class): """排序""" field_index = request.GET.get(‘_o‘,‘‘) if field_index: # 从list_display中拿到字段名 field_name = admin_class.list_filter[int(field_index)] # 获取字段名,根据字段名做正方排序 return querysets.order_by(field_name) else: return querysets @login_required def table_obj_list(request,app_name,model_name): ... # 排序 querysets = get_orderby_result(request,querysets,admin_class) # 只有单方向排序; # 怎么记住上次排序?再次点击做反方向排序;考虑-0的情况; # views.py @login_required def table_obj_list(request,app_name,model_name): ... # 排序后端数据查询 querysets,current_order_field = get_orderby_result(request,querysets,admin_class) ... return render(request,‘kingadmin/table_obj_list.html‘, { ‘querysets‘:querysets, ‘admin_class‘:admin_class, ‘current_page‘:current_page, ‘current_order_field‘:current_order_field }) def get_orderby_result(request,querysets,admin_class): """排序""" # 1.从url中获取排序下表参数 field_index = request.GET.get(‘_o‘,‘‘) current_order_field = {} # 2.判断是否已经排序 if field_index: print("当前下标:%s"%field_index) # 2.1 如果有排序,根据下标绝对值从list_display中拿到字段名; field_name = admin_class.list_display[abs(int(field_index))] print(‘当前排序字典:%s‘%field_name) # kingadmin_tags.order_handle 中需要的数据:用于前端获知当前字段上次排序参数正负情况; current_order_field[field_name] = field_index print(‘当前访问后的字典:%s‘%current_order_field) # 4.如果排序的参数为负数,做反序查询 if field_index.startswith(‘-‘): field_name = ‘-‘+field_name # 5.返回排序后的查询对象 return querysets.order_by(field_name),current_order_field # 2.2 如果没有排序,返回原始查询集 else: return querysets,current_order_field # table_obj_list.html <thead> <tr> {% if admin_class.list_display %} {% for column in admin_class.list_display %} <th><a href="?_o={% get_order_factor column current_order_field forloop.counter0 %}"> {{ column }}</a> </th> {% endfor %} {% else %} <th>{% get_model_name admin_class %}</th> {% endif %} </tr> </thead> # kingadmin_tag.py @register.simple_tag def get_order_factor(column,current_order_field,forloop): """前端访问参数设置,访问后参数取反""" # 1.判断当前列是否排序 # 前端怎么知道当前列是否已经排序?需要记住上次访问传入的参数; # 后端在处理一次排序之后,将此次排序参数依据存在一个字典中,然后传到前端做判断; if column in current_order_field: # print(‘current_order_field:%s column:%s‘%(current_order_field,column)) last_sort_index = current_order_field[column] print(‘已经点击的链接中下标:%s‘%last_sort_index) if last_sort_index.startswith(‘-‘): current_sort_index = last_sort_index.strip(‘-‘) else: current_sort_index = ‘-%s‘%last_sort_index print(‘生成下次点击的下标:%s‘%current_sort_index) return current_sort_index else: return forloop # 增加排序标志 # table_obj_list.html <span class="glyphicon glyphicon-triangle-{% arror_direction current_order_field column %}" aria-hidden="true"></span> # kingadmin_tag.py # 箭头方向展示 @register.simple_tag def arror_direction(current_order_field,column): arror_direction = ‘‘ # 先判断是否已经排序 if column in current_order_field: print(‘column:%s‘%column) if current_order_field[column].startswith(‘-‘): arror_direction = ‘top‘ else: arror_direction = ‘bottom‘ return arror_direction # 附:注意要有bootstrap的fonts文件才可以显示箭头;