JSF中有一個叫作DataTable
的控制元件,可用來渲染和格式化html
表格。使用DataTable
,我們可以疊代收集或陣列陣列來顯示資料。下面我們來學習如何向DataTable
使用DataModel
排序資料。
要使用DataTable
,我們需要新增以下HTML頭。
<html
xmlns="http://www.w3.org/1999/xhtml"
xmlns:h="http://java.sun.com/jsf/html">
</html>
以下JSF標籤 -
<h:dataTable value="#{userData.employees}" var="employee"
styleClass="employeeTable"
headerClass="employeeTableHeader"
rowClasses="employeeTableOddRow,employeeTableEvenRow">
<h:column>
<f:facet name="header">Name</f:facet>
#{employee.name}
</h:column>
<h:column>
<f:facet name="header">Department</f:facet>
#{employee.department}
</h:column>
<h:column>
<f:facet name="header">Age</f:facet>
#{employee.age}
</h:column>
<h:column>
<f:facet name="header">Salary</f:facet>
#{employee.salary}
</h:column>
</h:dataTable>
被渲染成以下HTML標籤。
<table class="employeeTable">
<thead><tr>
<th class="employeeTableHeader" scope="col">Name</th>
<th class="employeeTableHeader" scope="col">Department</th>
<th class="employeeTableHeader" scope="col">Age</th>
<th class="employeeTableHeader" scope="col">Salary</th>
</tr></thead>
<tbody>
<tr class="employeeTableOddRow">
<td>Tom</td>
<td>Marketing</td>
<td>10</td>
<td>2000.0</td>
</tr>
<tr class="employeeTableEvenRow">
<td>Robert</td>
<td>Marketing</td>
<td>15</td>
<td>1000.0</td>
</tr>
</table>
開啟 NetBeans IDE 建立一個Web工程:DataTableSortDataModel,其目錄結構如下所示 -
建立以下檔案程式碼,檔案:index.xhtml 的程式碼內容如下所示 -
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:c="http://java.sun.com/jsp/jstl/core"
>
<h:head>
<h:outputStylesheet library="css" name="table-style.css" />
</h:head>
<h:body>
<h1>JSF 2 dataTable sorting example</h1>
<h:form>
<h:dataTable value="#{book.bookList}" var="o"
styleClass="book-table"
headerClass="book-table-header"
rowClasses="book-table-odd-row,book-table-even-row">
<h:column>
<f:facet name="header">
<h:commandLink action="#{book.sortByBookNo}">
Book No
</h:commandLink>
</f:facet>
#{o.bookNo}
</h:column>
<h:column>
<f:facet name="header">
Product Name
</f:facet>
#{o.productName}
</h:column>
<h:column>
<f:facet name="header">Price</f:facet>
#{o.price}
</h:column>
<h:column>
<f:facet name="header">Quantity</f:facet>
#{o.qty}
</h:column>
</h:dataTable>
</h:form>
</h:body>
</html>
檔案:User.java 的程式碼內容如下所示 -
/*
* To change this license header, choose License Headers in Project Properties.
* To change this template file, choose Tools | Templates
* and open the template in the editor.
*/
package com.yiibai;
/**
*
* @author Maxsu
*/
import java.io.Serializable;
import java.math.BigDecimal;
import java.util.Comparator;
import javax.faces.bean.ManagedBean;
import javax.faces.bean.SessionScoped;
import javax.faces.model.ArrayDataModel;
import javax.faces.model.DataModel;
import java.util.Arrays;
import java.util.Comparator;
import javax.faces.model.DataModel;
@ManagedBean(name = "book")
@SessionScoped
public class User implements Serializable {
private static final long serialVersionUID = 1L;
private SortableDataModel<Book> sotableDataModel;
private boolean sortAscending = true;
private static final Book[] bookList = {
new Book("1", "CSS", new BigDecimal("1500.00"), 3),
new Book("2", "HTML", new BigDecimal("421.00"), 6),
new Book("3", "Java", new BigDecimal("5222.00"), 10),
new Book("4", "Javascript", new BigDecimal("1111.00"), 9),
new Book("5", "SQL", new BigDecimal("211.00"), 20)
};
public User() {
sotableDataModel = new SortableDataModel<Book>(new ArrayDataModel<Book>(bookList));
}
public DataModel<Book> getBookList() {
return sotableDataModel;
}
//sort by book no
public String sortByBookNo() {
if (sortAscending) {
sotableDataModel.sortBy(new Comparator<Book>() {
@Override
public int compare(Book o1, Book o2) {
return o1.getBookNo().compareTo(o2.getBookNo());
}
});
sortAscending = false;
} else {
//descending book
sotableDataModel.sortBy(new Comparator<Book>() {
@Override
public int compare(Book o1, Book o2) {
return o2.getBookNo().compareTo(o1.getBookNo());
}
});
sortAscending = true;
}
return null;
}
public static class Book {
String bookNo;
String productName;
BigDecimal price;
int qty;
public Book(String bookNo, String productName,
BigDecimal price, int qty) {
this.bookNo = bookNo;
this.productName = productName;
this.price = price;
this.qty = qty;
}
public String getBookNo() {
return bookNo;
}
public void setBookNo(String bookNo) {
this.bookNo = bookNo;
}
public String getProductName() {
return productName;
}
public void setProductName(String productName) {
this.productName = productName;
}
public BigDecimal getPrice() {
return price;
}
public void setPrice(BigDecimal price) {
this.price = price;
}
public int getQty() {
return qty;
}
public void setQty(int qty) {
this.qty = qty;
}
}
}
class SortableDataModel<E> extends DataModel<E> {
DataModel<E> model;
private Integer[] rows;
SortableDataModel(DataModel<E> model) {
this.model = model;
initRows();
}
public void initRows() {
int rowCount = model.getRowCount();
if (rowCount != -1) {
this.rows = new Integer[rowCount];
for (int i = 0; i < rowCount; ++i) {
rows[i] = i;
}
}
}
public void sortBy(final Comparator<E> comparator) {
Comparator<Integer> rowComp = new Comparator<Integer>() {
public int compare(Integer i1, Integer i2) {
E o1 = getData(i1);
E o2 = getData(i2);
return comparator.compare(o1, o2);
}
};
Arrays.sort(rows, rowComp);
}
private E getData(int row) {
int originalRowIndex = model.getRowIndex();
model.setRowIndex(row);
E newRowData = model.getRowData();
model.setRowIndex(originalRowIndex);
return newRowData;
}
@Override
public void setRowIndex(int rowIndex) {
if (0 <= rowIndex && rowIndex < rows.length) {
model.setRowIndex(rows[rowIndex]);
} else {
model.setRowIndex(rowIndex);
}
}
@Override
public boolean isRowAvailable() {
return model.isRowAvailable();
}
@Override
public int getRowCount() {
return model.getRowCount();
}
@Override
public E getRowData() {
return model.getRowData();
}
@Override
public int getRowIndex() {
return model.getRowIndex();
}
@Override
public Object getWrappedData() {
return model.getWrappedData();
}
@Override
public void setWrappedData(Object data) {
model.setWrappedData(data);
initRows();
}
}
檔案:table-style.css 的程式碼內容如下所示 -
.book-table-header{
bbook-bottom:1px solid #BBB;
padding:16px;
}
.book-table-odd-row{
bbook-top:1px solid #BBB;
}
.book-table-even-row{
bbook-top:1px solid #BBB;
}
右鍵執行工程:DataTableSortDataModel,如果沒有任何錯誤,開啟瀏覽器存取:
http://localhost:8084/DataTableSortDataModel/
應該會看到以下結果 -
在上圖中,您可以點選」Book No「,就可以看到排序情況了。