Code

Ticket #6285: columns_rows_filters.diff

File columns_rows_filters.diff, 2.1 KB (added by taylanpince, 5 years ago)

Suggestion for filters to slice lists into rows and columns

Line 
1Index: django/template/defaultfilters.py
2===================================================================
3--- django/template/defaultfilters.py   (revision 10031)
4+++ django/template/defaultfilters.py   (working copy)
5@@ -633,6 +633,69 @@
6 unordered_list.is_safe = True
7 unordered_list.needs_autoescape = True
8 
9+def columns(thelist, n):
10+    """
11+    Breaks a list into ``n`` number of columns, filling up each column to the
12+    maximum equal length possible. This filter will always return ``n``
13+    columns, even if some are empty.
14+
15+    Usage::
16+
17+        {% for item_column in item_list|columns:3 %}
18+        <li class="column">
19+            <ul>
20+                {% for item in item_column %}
21+                <li><a href="#">{{ item }}</a></li>
22+                {% endfor %}
23+            </ul>
24+        </li>
25+        {% endfor %}
26+
27+    """
28+    try:
29+        n = int(n)
30+        thelist = list(thelist)
31+    except (ValueError, TypeError):
32+        return [thelist]
33+
34+    list_len = len(thelist)
35+    split = list_len // n
36+
37+    if list_len % n != 0:
38+        split += 1
39+
40+    return [thelist[split*i:split*(i+1)] for i in range(n)]
41+
42+def rows(thelist, n):
43+    """
44+    Breaks a list into rows with a maximum number of ``n`` elements in each.
45+
46+    Usage::
47+
48+        {% for item_row in item_list|rows:4 %}
49+        <li class="row">
50+            <ul>
51+                {% for item in item_row %}
52+                <li><a href="#">{{ item }}</a></li>
53+                {% endfor %}
54+            </ul>
55+        </li>
56+        {% endfor %}
57+
58+    """
59+    try:
60+        n = int(n)
61+        thelist = list(thelist)
62+    except (ValueError, TypeError):
63+        return [thelist]
64+
65+    newlists = [list() for i in range(int(ceil(len(thelist) / float(n))))]
66+
67+    for i, val in enumerate(thelist):
68+        newlists[i/n].append(val)
69+
70+    return newlists
71+
72 ###################
73 # INTEGERS        #
74 ###################
75@@ -896,6 +959,8 @@
76 register.filter(truncatewords)
77 register.filter(truncatewords_html)
78 register.filter(unordered_list)
79+register.filter(columns)
80+register.filter(rows)
81 register.filter(upper)
82 register.filter(urlencode)
83 register.filter(urlize)