当我在页面之间导航时,我需要保留过滤后的数据。在数据表的筛选单元格中输入数据后,它将显示正确的筛选行。如果在筛选单元格中最后输入的数据与要显示的任何数据行不匹配,并且当我导航到另一个页面并返回时,列标题和筛选单元格不会呈现。只显示分页器。如果在筛选单元格中最后输入的数据与某些数据行匹配,则可以正常工作。如果我不离开数据表的页面,它也可以正常工作。
jsf代码:<p:dataTable id="tableId" var="intance" widgetVar="instance"
value="#{model.rows}" filteredValue="#{model.filteredRows}"
sortBy="#{model.sortBy}" sortMode="multiple" rows="5"
rowsPerPageTemplate="5, 15" paginator="true" paginatorPosition="bottom">
<p:ajax event="filter" listener="#{model.onFilter}"/>
<p:ajax event="sort" listener="#{model.onSort}"/>
<p:columns id="columnId" value="#{instance.columnsData}"
var="instanceColumn" columnIndexVar="ind" rendered="true"
sortBy="#{instance.columnsData[ind]}"
filterBy="#{instance.columnsData[ind]}" filterMatchMode="contains"
filterValue="#{model.tableFilters[''.concat(ind)]}"
headerText="#{labels[ind]}">
<h:outputText value="#{instance.columnsData[ind]}"/>
</p:columns>
</p:dataTable>
java代码:public class Model {
private List<MyRow> filteredRows;
private List<MyRow> rows;
private Map<String, String> tableFilters;
public void onFilter(FilterEvent event) {
tableFilters = event.getFilters();
if (MapUtils.isEmpty(tableFilters)) {
filteredRows = null;
}
}
public void List<MyRow> getRows() {
//retreve data from service and transform to List<MyRow>)
return rows;
}
/* getters and setter */
}
public class MyRow {
private List<Object> columnsData;
/* getters and setters */
}
任何想法吗?代码看起来很好,我应该工作。我使用3.5.
谢谢
问题的根源是p:columns
中的value="#{instance.columnsData}"
。在这种情况下,使用p:dataTable
的#{instance}
变量是错误的。
当第一次加载页面并且#{model.rows}
不是empty
时,它可以正常工作。
当#{model.rows}
不是empty
时,当我们在过滤器单元格中键入与#{model.rows}
中的数据不匹配的值时,没有显示行,但列标题和过滤器单元格无论如何都会被呈现,因为只是部分呈现数据内容(表标题和过滤器单元格在呈现页面时被呈现)。
当我们导航到另一个页面,然后带着数据表中经过筛选的行返回到该页时,会出现该页的全新完整呈现。所以在这种情况下(#{model.filteredRows}
不是null
), #{model.rows}
包含多少数据并不重要。#{model.filteredRows}
将用于呈现数据表的内容。所以当primefaces渲染数据表时,在我的情况下根本没有数据要渲染,因为#{model.filteredRows}
是empty
而不是null
。
因为我在p:columns
中使用p:dataTable
的#{instance}
变量,所以p:columns
将不呈现任何列-没有列标题和筛选单元格要显示。
解决方案:使用单独的字段来包含列info。
//edited class Model
public class Model {
//add a field that contains columns count. For example:
private List<Integer> columns = Collections.nCopies(5, 1);
//another fields
}
需要用value="#{model.columns}"
代替value="#{instance.columnsData}"
<p:columns id="columnId" value="#{model.columns}"
var="instanceColumn" columnIndexVar="ind" rendered="true"
sortBy="#{instance.columnsData[ind]}"
filterBy="#{instance.columnsData[ind]}" filterMatchMode="contains"
filterValue="#{model.tableFilters[''.concat(ind)]}"
headerText="#{labels[ind]}">
<h:outputText value="#{instance.columnsData[ind]}"/>
</p:columns>