Ticket #11868: admin-multisort-1.2-beta-SVN-12755.diff
File admin-multisort-1.2-beta-SVN-12755.diff, 8.5 KB (added by , 15 years ago) |
---|
-
django/contrib/admin/media/css/base.css
326 326 background: url(../img/admin/arrow-up.gif) right .4em no-repeat; 327 327 } 328 328 329 table thead th.sorted a span.text { 330 display: block; 331 float: left; 332 } 333 table thead th.sorted a span.sort_pos { 334 display: block; 335 float: right; 336 font-size: .6em; 337 } 338 table thead th.sorted a span.clear{ 339 display: block; 340 clear: both; 341 } 342 329 343 /* ORDERABLE TABLES */ 330 344 331 345 table.orderable tbody tr td:hover { -
django/contrib/admin/templatetags/admin_list.py
103 103 104 104 th_classes = [] 105 105 new_order_type = 'asc' 106 if field_name == cl.order_field or admin_order_field == cl.order_field: 107 th_classes.append('sorted %sending' % cl.order_type.lower()) 108 new_order_type = {'asc': 'desc', 'desc': 'asc'}[cl.order_type.lower()] 106 ordering_fields = cl.get_ordering_fields() 107 sort_pos = '' 108 if field_name in ordering_fields.keys() or admin_order_field in ordering_fields.keys(): 109 if not field_name in ordering_fields.keys(): 110 field_name = admin_order_field 111 order_type = ordering_fields.get(field_name).lower() 112 sort_pos = ordering_fields.keys().index(field_name) + 1 113 th_classes.append('sorted %sending' % order_type) 114 new_order_type = {'':'asc', 'asc': 'desc', 'desc': ''}[order_type] 115 116 # build new ordering param 117 o_list = [] 118 for f in ordering_fields.keys(): 119 try: 120 n = cl.list_display.index(f) 121 except ValueError: 122 continue 123 124 if f == field_name: 125 if new_order_type == '': 126 continue 127 t = new_order_type 128 else: 129 t = ordering_fields.get(f) 109 130 131 o_list.append((t=='desc' and '-' or '') + str(n)) 132 133 if field_name not in ordering_fields.keys() and new_order_type: 134 n = cl.list_display.index(field_name) 135 o_list.append((new_order_type=='desc' and '-' or '') + str(n)) 136 137 o_list = ','.join(o_list) 138 110 139 yield { 111 140 "text": header, 112 141 "sortable": True, 113 "url": cl.get_query_string({ORDER_VAR: i, ORDER_TYPE_VAR: new_order_type}), 142 "sort_pos": sort_pos > 0 and len(ordering_fields) > 0 and unicode(sort_pos) or '', 143 "url": cl.get_query_string({ORDER_VAR: o_list}), 114 144 "class_attrib": mark_safe(th_classes and ' class="%s"' % ' '.join(th_classes) or '') 115 145 } 116 146 -
django/contrib/admin/views/main.py
4 4 from django.core.paginator import Paginator, InvalidPage 5 5 from django.db import models 6 6 from django.db.models.query import QuerySet 7 from django.utils.datastructures import SortedDict 7 8 from django.utils.encoding import force_unicode, smart_str 8 9 from django.utils.translation import ugettext 9 10 from django.utils.http import urlencode … … 63 64 if ERROR_FLAG in self.params: 64 65 del self.params[ERROR_FLAG] 65 66 66 self.order _field, self.order_type= self.get_ordering()67 self.ordering = self.get_ordering() 67 68 self.query = request.GET.get(SEARCH_VAR, '') 68 69 self.query_set = self.get_query_set() 69 70 self.get_results(request) … … 137 138 # those exist, order descending by ID by default. Finally, look for 138 139 # manually-specified ordering from the query string. 139 140 ordering = self.model_admin.ordering or lookup_opts.ordering or ['-' + lookup_opts.pk.name] 140 141 if ordering[0].startswith('-'): 142 order_field, order_type = ordering[0][1:], 'desc' 143 else: 144 order_field, order_type = ordering[0], 'asc' 141 145 142 if ORDER_VAR in params: 146 try: 147 field_name = self.list_display[int(params[ORDER_VAR])] 143 # Clear ordering and used params 144 ordering = [] 145 order_params = params[ORDER_VAR].split(',') 146 for p in order_params: 148 147 try: 149 f = lookup_opts.get_field(field_name) 150 except models.FieldDoesNotExist: 151 # See whether field_name is a name of a non-field 152 # that allows sorting. 148 none, pfx, idx = p.rpartition('-') 149 field_name = self.list_display[int(idx)] 153 150 try: 154 if callable(field_name):155 attr = field_name156 elif hasattr(self.model_admin, field_name):157 attr = getattr(self.model_admin, field_name)158 else:159 attr = getattr(self.model, field_name)160 order_field = attr.admin_order_field161 except AttributeError:162 pass163 else:164 order_field = f.name165 except (IndexError, ValueError):166 pass # Invalid ordering specified. Just use the default.167 if ORDER_TYPE_VAR in params and params[ORDER_TYPE_VAR] in ('asc', 'desc'):168 order_type = params[ORDER_TYPE_VAR]169 return order_field, order_type151 f = lookup_opts.get_field(field_name) 152 except models.FieldDoesNotExist: 153 # See whether field_name is a name of a non-field 154 # that allows sorting. 155 try: 156 if callable(field_name): 157 attr = field_name 158 elif hasattr(self.model_admin, field_name): 159 attr = getattr(self.model_admin, field_name) 160 else: 161 attr = getattr(self.model, field_name) 162 field_name = attr.admin_order_field 163 except AttributeError: 164 pass 165 else: 166 field_name = f.name 170 167 168 ordering.append(pfx + field_name) 169 170 except (IndexError, ValueError): 171 pass # Invalid ordering specified. Skip it. 172 173 return ordering 174 175 def get_ordering_fields(self): 176 # Returns a SortedDict of ordering fields and asc/desc 177 ordering_fields = SortedDict() 178 for o in self.ordering: 179 none, t, f = o.rpartition('-') 180 ordering_fields[f] = t == '-' and 'desc' or 'asc' 181 return ordering_fields 182 171 183 def get_query_set(self): 172 184 qs = self.root_query_set 173 185 lookup_params = self.params.copy() # a dictionary of the query string … … 214 226 break 215 227 216 228 # Set ordering. 217 if self.order _field:218 qs = qs.order_by( '%s%s' % ((self.order_type == 'desc' and '-' or ''), self.order_field))229 if self.ordering: 230 qs = qs.order_by(*self.ordering) 219 231 220 232 # Apply keyword searches. 221 233 def construct_search(field_name): -
django/contrib/admin/templates/admin/change_list_results.html
2 2 <table cellspacing="0"> 3 3 <thead> 4 4 <tr> 5 {% for header in result_headers %}<th{{ header.class_attrib }}> 6 {% if header.sortable %}<a href="{{ header.url }}">{% endif %} 7 {{ header.text|capfirst }} 8 {% if header.sortable %}</a>{% endif %}</th>{% endfor %} 5 {% for header in result_headers %} 6 <th{{ header.class_attrib }}> 7 {% if header.sortable %}<a href="{{ header.url }}">{% endif %} 8 <span class="text">{{ header.text|capfirst }}</span> 9 {% if header.sortable %}<span class="sort_pos">{{ header.sort_pos }}</span> 10 <span class="clear"></span> 11 </a>{% endif %} 12 </th>{% endfor %} 9 13 </tr> 10 14 </thead> 11 15 <tbody>