why does display what i want:
<c:forEach var="temp" items="${AvailableLessonBean.lessons['description']}">
<form action="" method="POST">
<tr>
<td>
<c:out value="${temp}"/>
</td>
which displays in a html table:
Description Start Date Start Time End Time Level Make Booking
Snowboarding for dummies
Advanced Carving Techniques
How to not fall off the draglift
Gnarliness Extreeeeeeeme
Parallel turns
How to splint a broken leg with a s
Cross-country techniques
Aerobatics
Intermediate Slalom
and this does not display anything but an exception:
<c:forEach var="temp" items="${AvailableLessonBean.lessons}">
<form action="" method="POST">
<tr>
<td>
<c:out value="${temp['description']}"/>
</td>
I have no hair left because of this!!
Once again, you didn't tell us what these objects are, which makes it impossible to answer. Hopefully for you, I remember the data structure from a previous question.
So, AvailableLessonBean.getLessons() returns a Map<String, List<String>>.
In your first snippet, you iterate over AvailableLessonBean.lessons['description']. What this EL code does is that it gets the value associated with the key "description" in the map:
map.get("description")
that works fine. It returns a List<String>. It iterates over that list, and stores the current element of the list in a variable named temp. And at each iteration, it prints temp. This is thus equivalent to the following Java code:
List<String> list = availableLessonBean.getLessons().get("description");
for (String temp : list) {
out.println(temp);
}
In the second snippet, you're iterating over the map itself. The JSTL specifies that when you iterate over a map, you iterate over all the entries of the map. Each entry has a key and a value. So the iteration is equivalent to doing, in Java:
for (Map.Entry<String, List<String>> temp : availableLessonBean.getLessons().entrySet()) {
...
}
But then you're trying to access temp["description"]. That doesn't make any sense. temp is a Map Entry. A Map Entry has a key and a value. That's all. In this case, the key is a String and the value is a List<String>.
Related
I have a generic thymeleaf table as follows:
<tbody>
<th:block th:each="row : ${page.getContent()}">
<tr>
<td th:each="header : ${headers}" th:text="${row.__${header}__}"/>
</tr>
</th:block>
</tbody>
The table is simply backed by a list containing my domain objects:
List<Header> headers = List.of("firstname", "lastname");
List<Person> page;
What it does is: it loops my predefined list headers, and selects only those attributes defined in the headers list.
Question: how could I add an evaluation on the classtype of the extracted value of each field, so that I could apply a custom style in case of digits?
The problem is: when I output the class of the value that is shown, the output is a java.util.ArrayList always!
th:text="${{row.__${header}__}.class.name}"
Why doesn't this show the correct class of the td element?
You should be able to evaluate the header if you go down a level. My thought is that the preprocessor operation may not give you a reference to the header object on the same td element.
This use case may also be a good candidate for th:classappend since you may want to inherit some style.
Also, not sure whether it applies, but table headings are typically wrapped in a <thead> element. Then, I would assume you'd want a list of Person objects iterated in a <tbody>.
Haven't tested it, but try:
<thead>
<th:block th:each="header : ${headers}">
<th th:text="${header}" class="someClass" th:classappend="${header.name.class instanceof T(java.math.BigDecimal) ? 'someDigitClassStyle' : ''}" />
</th:block>
<thead>
Assumes use of Spring. Reference
Lastly, you can consider an Apache util for isNumeric if you want to more broadly catch digits.
Solution as follows to apply a specific css style based on instance check:
th:text="${row.__${header}__}"
th:style="${{row.__${header}__}.get(0) instanceof T(java.math.BigDecimal)} ? 'text-align:right' : ''"/>
I need to show some data inside a table (jsp). The data are being passed like this:
request.setAttribute("name", nameVariable);
request.setAttribute("surname", surnameVariable);
request.setAttribute("list", list); //Here are stored ultimately all the data (so name and surname also)
My list is being updated and I need to have the list being updated also. I know my list gets more items, but this code prints only last record from that list. What should I change in my code to be able to print all records from list in table?
My jsp:
<c:forEach items="${list}">
<tr>
<td>${name}</td>
<td>${surname}</td>
</tr>
</c:forEach>
You're always printing the same request attributes, at each iteration of the loop, completely ignoring the current element of the list. Assuming the list contains objects of type Person (for example), which has a getName() and a getSurname() method, the code should be
<c:forEach items="${list}" var="person">
<tr>
<td>${person.name}</td>
<td>${person.surname}</td>
</tr>
</c:forEach>
Just like, in Java, a foreach loop would define a person variable for the current person during the itertion:
for (Person person: list) {
System.out.println(person.getName());
System.out.println(person.getSurname());
}
I have created a list of lists that contains content that I want to display through a jsp file. when trying to just display the items through one list, the file works and I see it. But when I split the items in different arraylists and try to iterate over that, nothing shows up. My initialization is,
private final List<ArrayList<DisplayableProduct>> listOfThreeProducts = new ArrayList<ArrayList<DisplayableProduct>>();
I have verified that there is content inside each list of it through debugging.
my model.listofThreePorducts is a list of lists. so I want to loop through the list of lists and then loop inside each loop and so stuff. Is it correct to pass the var="listoflists" value to the second for loop as such below? would it be items="${listoflists}" to access everything in that list ?
<c:forEach items="${model.listOfThreeProducts}" var="listoflists">
<div id="hero-featureSwap">
<c:forEach items="${listoflists}" var="product">
<div class="widget-element-brand"
title='<awsmp:formatText text="${product.vendorName}" />'>
<awsmp:formatText text="${product.vendorName}" maxLength="25" />
</div>
</c:forEach>
</div>
</c:forEach>
You need standard getter in model object for property listOfThreeProducts
further detail discussed in question's comment section
I'm new to using JSP and need to figure out how to do this. I'd appreciate any pointers on how to do this ?
I need to display images in this table-like structure. To simplify the problem,
A B C
D E F
G H I
where each of these elements are a part of the Set names in action class.
Set<String> names = new HashSet<String>(0);
names.add("A");
names.add("B");
names.add("C");
names.add("D");
names.add("E");
names.add("F");
names.add("G");
names.add("H");
names.add("I");
Its fairly trivial to do it in java, however, I am having a hard time to figure out, how do I ask the iterator to point to next element manually.
<s:iterator value="names">
<s:property/>
I'd now like to point iterator to point to next or run a nested iterator loop here.
</s:iterator>
You can use JSTL forEach loop. You can find a number of examples here.
You can easily accomplish it with JSTL:
<table>
<tr>
<c:forEach items="names" var="name" varStatus="i">
<c:if test="${!i.first && !i.last && i.index % 3 == 0}">
</tr>
<tr>
</c:if>
<td><c:out value="${name}" /></td>
</c:forEach>
</tr>
</table>
Doing so, a new line (</tr><tr>) will be added every 3 elements.
(not tested)
As CoolBeans said, you can use JSTL forEach loop.
If you'd like to see an example of that (alongside other good JSTL examples), check out JSTL Examples.
"Iterating over data structures" has some info and examples on what you're trying to do.
I have a jsp page that receives a HashMap object of this type:
Map<Long, Map<String, Object>>.
An example of this map would be: foo = {1 = {id=1, response="someText"}, 2={id=99, response="random"}};
I am trying to iterate over the contents of both maps in foo like this:
<c:forEach items="${fooMap.content}" var="outerMap">
<c:forEach items="${outerMap.value}" var = "innerMap">
<p>${innerMap.response}</p>
</c:foreach>
</c:forEach>
But this throws "Property 'response' not found on type java.util.HashMap.....
Would someone please tell me what I am doing wrong?
I know that I can access the contents of innerMap using Map.EntrySet. But I want to access the value using specific keys.
The ${outerMap.value} returns a Map<String, Object> of which one entry has "response" as key. So you need to get it straight from there instead of iterating over its entryset in ${innerMap}.
<c:forEach items="${fooMap.content}" var="outerMap">
<p>${outerMap.value.response}</p>
</c:forEach>
An (more clumsy) alternative is checking the ${innerMap} entry key:
<c:forEach items="${fooMap.content}" var="outerMap">
<c:forEach items="${outerMap.value}" var="innerMap">
<c:if test="${innerMap.key == 'response'}">
<p>${innerMap.value}</p>
</c:if>
</c:foreach>
</c:forEach>
Can you now still wrap your head around it? :)