Accessing index in Django template under a for loop - html

#views.py
.
.
.
detailedStatement = {
'selectedOption1' : '90 degrees',
'correctAnswer1' : '180 degrees',
'selectedOption2' : 'angle',
'correctAnswer2' : 'side'
}
#Above dictionary contains 200 elements
diction = {
'detailedStatement' : detailedStatement
}
return render(request, "result.html", diction);
So while on an html file I wanted to access the dictionary's every element via a loop. Like every element should be listed in the html table row like following.
| Sr | Selected Option | Correct Answer |
| 1 | 90 degrees | 180 degrees |
| 2 | angle | side |
Above table is just a representation of html table not an actual table.
But the issue I am facing is... I am not able to access its index in a dynamic way.
I wrote a for loop in Django html template but
{% for dr in detailedResult.items %}
<tr>
<td>{{forloop.counter}}</td>
<td>{{dr.option.forloop.counter}}</td>
<td>{{dr.answer.forloop.counter}}</td>
</tr>
{% endfor %}
I want my code to automatically put 1 after option and answer like option1, answer1;
How can we do this?

I think you should model this with a list instead of including an index in your variable names, e.g.
# views.py
detailed_statements = [{'option': '90 degrees', 'answer': '180 degrees'}, ... ] # contains 200 elements
Then in your template
{% for dr in detailed_statements %}
<tr>
<td>{{forloop.counter}}</td>
<td>{{dr.option}}</td>
<td>{{dr.answer}}</td>
</tr>
{% endfor %}
I was a bit confused by the nested for loops in your template code - I think you only need one?

Related

How to customize the selection form?

I have a model
class Car(models.Model):
class ModelChoise(models.IntegerChoices):
Model_1 = 0
Model_2 = 1
Model_3 = 2
Model_4 = 3
name = models.TextField('Name')
model_id = models.IntegerField('model id', choices=ModelChoise.choices, default=1)
def __str__(self):
return self.name
And I created a form for it
class CarForm(ModelForm):
class Meta:
model = Car
fields = ['model_id']
I need to deduce both key and value from it
{% for mykey,myvalue in form.model_id %}
{{ mykey }} : {{ myvalue }}
{% endfor %}
<!--
Model_1 : 0
Model_2 : 1
Model_3 : 2
Model_4 : 3
-->
How should I do it? I can only get the key.
I'm not sure why in the CarForm you point to the model ExtraUser... model_id seems to be a field in your Car model so I don't know why you reference it in a form pointing to a different model..
However when dealing with choices in templates you can go about it like this:
{{ object.get_model_id_display }}
Basically get_ + field_name + _display will return the choice value

Using liquid to sort posts by the latest date(latest(posted_date, updated_date))

I'm writing a site in Jekyll, which uses Liquid.
I have ymal for pages , like this:
---
title: Mytitle
posted: 2020-06-29
updated: 2020-07-29
....
---
And I have some posts, as follows
{
title: title1
posted: 2020-06-29
updated: 2020-07-29
},
{
title: title2
posted: 2020-07-05
},
{
title: title 3
posted: 2020-07-01
updated: 2020-07-20
},
{
title: title 4
posted: 2020-07-22
},
I expect the order of posts which is sorted by the latest date, i.e. latest(posted, updated).
liquid seems cannot sort by custom function? Can someone tell me what to do?
Thanks
By default site.posts are sorted by the date property (newest fist), which you called posed. So you may want to rename it to date to make your life easier.
For custom sorting you can use the Liquid sort filter, which takes one argument.
So if you want to sort by updated instead, you can do that with:
{% assign my_sorted_list = site.posts | sort:"updated" %}
{% for post in my_sorted_list %}
...
{% endfor %}
You'll need to set the updated property then for every post or use a custom hook as explained here.

Flask generate dynamic table where number of rows and columns depends on number of elements in the list

Dear stackoverflow users,
I am creating a website with flask as a backend. It will fetch some data from different systems e.x. jenkins.
one of the "data packs" will be a list of Jenkins jobs
the main .py file will include route to a page
#app.route("/simplejenkins")
def simple_jenkins():
return render_template('simplejenkins.html', job_list=job_list)
and the simplejenkins.html will iterate over the job_list and list them
{% for job in jobs_list %}
<tr>
<td>{{ job }}</td>
<td>
<p>Successful!</p>
</td>
</tr>
{% endfor %}
the idea is that the number of elements in the list will change over time.
and I want to put them in the table - each element (job) in different cell. And let's say I want to have 6 columns (depends on the screen resolution, but let's ignore this for now). So in case of 44 jobs I should have 7 full rows and 2 more job in 8th row.
and my question is, how to achieve this?
the script below generates a table with dynamic number of rows and columns but how to populate the cells using jinja?
<!DOCTYPE html>
<html>
<head>
<meta charset=utf-8 />
<title>Dynamic Table</title>
<script>
window.onload = createTable;
function createTable()
{
rn = window.prompt("Input number of rows", 1);
cn = window.prompt("Input number of columns",1);
for(var r=0;r<parseInt(rn,10);r++)
{
var x=document.getElementById('myTable').insertRow(r);
for(var c=0;c<parseInt(cn,10);c++)
{
var y= x.insertCell(c);
y.innerHTML="Row-"+r+" Column-"+c;
}
}
}
</script>
<style type="text/css">
body {margin: 30px;}
</style>
</head>
<body>
<table id="myTable" border="1">
</table><form>
</form>
</body>
</html>
i don't expect full solution of course, a link to existing similar case should be more than enough... somehow i cannot find one
thanks in advance for help
regards
Mariusz
To use that JS script all you need is an ajax call, once the page is ready, the ajax call will retrieve the data (jobs) from your flask route as JSON data and insert it in the table, with no need for jinja at all.
Or if it's not necessary for you to use a table, you can use the inline display in your frontend where your jobs will float next to each other as long as there is space, otherwise they will fall to the next line, you will loop over those jobs exactly as you did, but instead of having rows and cells you will have divs or something like that.
would you mind trying this ?
<table>
{% max_columns = 6 %}
{% interval = jobs_list|length / max_columns }
{% rows = interval|int + 1 } # +1 for the last/incomplete row
{% for p in range(rows) %}
<tr>
{% for n in range(max_columns) %}
{% cell_pos = (p * max_columns) + n }
<td>{{ jobs_list[cell_pos] }}</td>
{% endfor %}
</tr>
{% endfor %}
</table>

Jekyll Liquid Array ID Not Working

I have a CSV file in my _data folder and I am trying to specify the row of the CSV to access in my Front Matter and then return specific columns from the CSV based on the row specificed in the Front Matter.
Here's the CSV file:
name,description
Dallas,Big City in Texas
And here's the contents of my index.html file:
---
city: "Dallas"
---
{{ site.data.data[page.city].description }}
Per the Jekyll Docs page on using data files, I should be able to use this syntax to access data files in this way, but the compiled html file does not include any data.
I have tested other ways of accessing the contents of the CSV file and those work, so it doesn't appear to be a problem with the data file or the site itself but rather with using the [ ] array id Liquid syntax.
Looks like you have misunderstood the [] notation for a hash structure.
I will first orient you on how the [] is supposed to work..
Expanding your data.csv a bit:
name,description
Dallas,Big City in Texas
Houston,Another City in Texas
and "inspecting" your the data object obtained from the above CSV file,
{{ site.data.data | inspect }}
on building the site, you'll see that the resultant object is simply an Array of Hashes :
<p>
[
{"name"=>"Dallas", "description"=>"Big City in Texas"},
{"name"=>"Houston", "description"=>"Another City in Texas"}
]
</p>
which means you can only access individual hash entry by referencing its index number.
i.e. {{ site.data.data[0] }} will give you the first hash and {{ site.data.data[1] }} will give you the next hash.
and therefore {{ site.data.data[0].description }} will give you the result you expect to get:
<p>
Big City in Texas
</p>
Now that you know how [] works for data hashes, lets simply get to the solution.
To access elements in an Array, one can simply iterate through the Array objects and reference necessary entries:
{% for entry in site.data.data %}
<div>
<span>{{ entry.name }}</span> : <span>{{ entry.description }}</span>
</div>
{% endfor %}
will give you:
<div>
<span>Dallas</span>
<span>Big City in Texas</span>
</div>
<div>
<span>Houston</span>
<span>Another City in Texas</span>
</div>

Loop in django with 2 parameter [duplicate]

This question already has answers here:
is there a way to loop over two lists simultaneously in django?
(6 answers)
Closed 6 years ago.
I am new to Django, I have passed two list(rawmaterial and food) to my template, and then I want to have a loop like this :(it is the logic of my aim, the syntax is not correct)
for(i=0;i<food.length;i++)
<div ,id="menuFood>
<h4> food.name(i)</h4>
<h4> rawmaterial.name(i)</h4>
</div>
but when i searched, i can find only loop like this:
{% for o in some_list %}
{% endfor %}
so with this syntax , I can't understand how to create that loop. I think only nested loop can make by this syntax..
here is my view code :
def foods(request):
food = Food.objects.all()
raw = [];
.
.
.
raw.append(warehouse)
return render(request, 'polls/foods.html', {'food': food,'rawmaterial': raw})
You can't do index on django template, but you could just put 2 lists together in your views.py using zip function:
food = Food.objects.all()
raw = []
# ...
raw.append(warehouse)
result = zip(food, raw)
return render(request, 'polls/foods.html', {'result': result})
Then in your template:
{% for food, raw in result %}
<h4>{{ food }}</h4>
<h4>{{ raw }}</h4>
{% endfor %}
By the way, you seems to come from java/c++ background because in python people never do:
for(i=0; i<food.length; i++)
print food[i]
instead, we do:
for i in food:
print i
Django template is adopting the similar syntax, it makes writing a loop a lot easier.