JSF 2 dataTable row index without dataModel
Asked Answered
C

1

12

I've been using ui:repeat to generate tables. With ui:repeat it's easy to get the rows numbered using the varStatus. I'm depending on the row id's from varStatus when calling the backing bean to handle list navigation, for example moving an item up or down in the list.

Now I'd like to create a composite component that builds a customizable table with all functionality needed for marking rows, moving them up/down etc. To do this, the ui:repeat won't work as I can't see a way of handling different number of columns; I need to specify headings in one place and the body in another (and I've not reached the knowledge point where I can create a custom component). Therefore I went on to datatable instead, as using that means specifying the headers as facets at the same place as the body content.

That worked well until I noticed that for some reason there were no varStatus anymore. I have put a lot of work into handling list presentation without any need for a datamodel and I do not want to start using that. Is there any way that I can get the current row number as it is displayed in the table, without using datamodel?

Also I'm using viewScope and if I've understood correctly that means I cannot bind the dataTable to the bean.

Circumstantiate answered 31/1, 2013 at 18:52 Comment(0)
H
32

Just bind the table to the view itself instead of to a bean.

<h:dataTable binding="#{table}" ...>

Then you can use #{table.rowIndex} where necessary. E.g.

<h:column>#{table.rowIndex + 1}</h:column>

Note that the code is as-is and that the EL variable name table is fully to your choice.

See also:

High answered 31/1, 2013 at 19:14 Comment(11)
I read another post where you had this as a solution, although I thought that the binding="#{table}" was some shorthand for binding to the bean. I didn't know this was possible. Thank you BalusC!Circumstantiate
I thought exactly the same way as @nivis. Maybe because value of var attribute does NOT need EL statement, but value of binding attribute DOES. I had prejudice that any named values inside the EL statement should already be declared (by myself), and I felt like giving some name to variable (eg. table , rowItem) should NOT happen with EL statements.Diarmit
what is table "view itself", please?Roye
I do not get it, table.rowIndex always -1 here. What is #{table}?Roye
@Palo: code is as-is. Of course the <h:column> must go inside the <h:dataTable>. You can use any non-existent variable name you want such as #{foo}. See also https://mcmap.net/q/17703/-how-does-the-39-binding-39-attribute-work-in-jsf-when-and-how-should-it-be-usedHigh
@High many thanks. One of the mistakes I made was trying to use that in id attribute of h:commandButton, but that one does not accept EL at all. So now I have misused tabindex attribute for the purpose of passing a parameter to actionListener. My scenario is probably ill, but I have bunch of buttons in a table, which are all the same, but each corresponds to another row, so I'd like to know in the actionListener that is shared by all these buttons, which button was pressed (in which row).Roye
I only had plain list of strings in the table, so decorating button with the row number would have helped. But now I have changed it to a list of compound object that has the row number and the original string, and thus I happen to avoid the table.rowIndex completely, because that did not work in tabindex neither. So now I misuse the tabindex for passing the parameter to the button's actionListener, but the row number comes from the list. I think I still do not understand what are you talking about and what this table.rowIndex means, where does it come from and how could it be used.Roye
@Palo: <h:dataTable binding> refers a HtmlDataTable instance. It has among others a getRowIndex() method.High
It does not work with Mojarra 2.1.7. The table is not displayed anymore. Instead, you have to use the "magic word" table without bindingRightwards
@Marco: it will indeed fail when you store the variable in a scope broader than the request scope and therefore incorrectly reuse the very same component in all other views/states tied to the same bean (components are request scoped and never designed to be thread safe as that's otherwise way too expensive/inefficient). See the "See also" link in updated answer.High
I checked the entire project for "table" and there's no other component that uses this variable, only HTML tablesRightwards

© 2022 - 2024 — McMap. All rights reserved.