开发者

Building a list in Django templates

开发者 https://www.devze.com 2023-01-29 09:11 出处:网络
With this code: {% for o in [1,2,3] %} <div class=\"{% cycle \'row1\' \'row2\' %}\"> 开发者_如何学编程{% cycle \'row1\' \'row2\' %}

With this code:

{% for o in [1,2,3] %}
    <div class="{% cycle 'row1' 'row2' %}">
   开发者_如何学编程     {% cycle 'row1' 'row2' %}
    </div>
{% endfor %}

I get a TemplateSyntaxError:

Could not parse the remainder: '[1,2,3]' from '[1,2,3]'

Is there a way of building a list in a template?


We can use split method on str object :

page.html :

{% with '1 2 3' as list %}
  {% for i in list.split %}
    {{ i }}<br>
  {% endfor %}
{% endwith %}

Results :

1
2
3


You can do it via cunning use of the make_list filter, but it's probably a bad idea:

{% for o in "123"|make_list %}
    <div class="{% cycle 'row1' 'row2' %}">
        {% cycle 'row1' 'row2' %}
    </div>
{% endfor %}

p.s. You don't seem to be using o anywhere, so I'm not sure what you're trying to do.


I made this template tag to achieve this goal.

from django import template
register = template.Library()

# use @register.assignment_tag
# only when you're working with django version lower than 1.9
@register.simple_tag
def to_list(*args):
    return args

to use it in template:

{% load your_template_tag_file %}
{% to_list 1 2 3 4 5 "yes" as my_list %}
{% for i in my_list %}
    {{ i }}
{% endfor %}

Reference here: Django simple tags


The other answers here look like the ticket (at least for what I wanted), so I'll provide an answer as to WHY you might want to do something like this (and perhaps there's a better answer for my case than what's been provided):

I came across this question looking for a way to build 3 very similar, but not identical buttons using Bootstrap. One button might look like

<div class="btn-group">
  <a class="btn btn-primary dropdown-toggle" data-toggle="dropdown" href="#">
    Modality
    <span class="caret"></span>
  </a>
  <ul class="dropdown-menu" id="Modality">
    <li><a href="#">Action</a></li>
  </ul>
</div>

where the difference between buttons is limited to the text of the button (Modality, on its own line above) and the contents of the pertaining to the button, which we'll assume is filled dynamically by JS (referencing id="Modality").

If I need to make 10 of these, copy/pasting the HTML seems dumb and tedious, especially if I want to change anything about my button after the fact (like making all of them split-drop-downs) and it goes against DRY.

So, instead, in the template I could do something like

{% with 'Modality Otherbutton Thirdbutton' as list %}
  {% for i in list.split %}
    <!-- copy/paste above code with Modality replaced by {{ i }} -->
  {% endfor %}
{% endwith %}

Now, granted, in this particular case the buttons add functionality to some related data grid, so the button names could be dynamically filled from django model-sourced data as well, but I'm not at that stage in my design right now, and you can see where this sort of functionality is desirable to maintain DRY.


The simplest is to do

{% for x in "123" %}


drodger is correct, you can't do that in the deliberately-crippled Django template lanuage. Either pass in the list as a context variable when you invoke the template or try a template tag like expr. Then you can say {% expr [1,2,3] as my_list %} and then use my_list in your for loop.


This maybe an inspiration. Use the buildin filter add.

{{ first|add:second }}

first is [1, 2, 3] and second is [4, 5, 6], then the output will be [1, 2, 3, 4, 5, 6].

This filter will first try to coerce both values to integers. 
If this fails, it'll attempt to add the values together anyway. 
This will work on some data types (strings, list, etc.) and fail on others. 
If it fails, the result will be an empty string.

The official specification,https://docs.djangoproject.com/zh-hans/2.0/ref/templates/builtins/#built-in-filter-reference

0

精彩评论

暂无评论...
验证码 换一张
取 消