一、概述:
javafx中是按列来创建表格的。首先生成一个TableColumn对象,其次设置TableColumn对象的属性,然后将TableColumn对象加入TableView对象,最后设置表格数据即可。
1、生成TableColumn:
可以通过构造函数直接生成TableColumn对象:
TableColumn<Document, Integer> idColumn = new TableColumn<>("文档ID");
2、设置TableColumn对象属性:
1)必须设置setCellValueFactory方法,如果不设置的话,^_^该列的值将为空。
2)此外,可以通过setMinWidth设置最小宽度,setCellFactory设置多样化表格,setSortable设置可否排序,setEditable是否可编辑等。
3、将TableColumn加入TableView对象:
调用以下语句即可:
tableView.getColumns().add(idColumn);
4、设置表格数据:
可通过以下方法实现:documentData为ObservableList对象。
tableView.setItems(documentData)
二、Demo展示
先看效果图:
(图一) |
(图二) |
(图三) |
(图四) |
(图五) |
说明:
(图一)是根据对象属性创建table:setCellValueFactory设置的是PropertyValueFactory对象
// 根据对象属性创建table public TableViewcreateTableByObject() { TableView<Document> tableView = new TableView<Document>(); addDocumentColumns(tableView); averageColumnsWidth(tableView); tableView.setItems(documentData); return tableView; } private void addDocumentColumns(TableView<Document> tableView) { TableColumn<Document, Integer> idColumn = new TableColumn<>("文档ID"); idColumn.setCellValueFactory(new PropertyValueFactory<Document, Integer>( "id")); idColumn.setMinWidth(50); tableView.getColumns().add(idColumn); TableColumn<Document, String> nameColumn = new TableColumn<>("文档名"); nameColumn .setCellValueFactory(new PropertyValueFactory<Document, String>( "name")); nameColumn.setMinWidth(50); tableView.getColumns().add(nameColumn); TableColumn<Document, String> remarkColumn = new TableColumn<>("备注"); remarkColumn .setCellValueFactory(new PropertyValueFactory<Document, String>( "remark")); remarkColumn.setMinWidth(50); tableView.getColumns().add(remarkColumn); }
(图二)是根据数组创建table:setCellValueFactory返回的是ReadOnlyStringWrapper对象;
// 根据数组创建table public TableViewcreateTableByStringArray() { TableView<String[]> tableView = new TableView<>(); for (final String name : columnNames) { TableColumn<String[], String> column = new TableColumn<>(name); column.setCellValueFactory(new Callback<TableColumn.CellDataFeatures<String[], String>, ObservableValue<String>>() { @Override public ObservableValue<String> call( CellDataFeatures<String[], String> param) { int index = columnNames.indexOf(name); String value = param.getValue()[index]; return new ReadOnlyStringWrapper(value); } }); tableView.getColumns().add(column); } tableView.setItems(stringArrayData); return tableView; }
(图三)是创建带checkbox的table:使用了setCellFactory方法 ,返回CheckBoxTableCell对象(javafx库中自带)。
// 创建带checkbox的table public TableViewcreateTableWithCheckBox() { initDocumentData(); TableView<Document> tableView = new TableView<Document>(); tableView.setEditable(true); TableColumn<Document, Boolean> selectColumn = new TableColumn<>("选择"); selectColumn .setCellValueFactory(new PropertyValueFactory<Document, Boolean>( "select")); selectColumn .setCellFactory(new Callback<TableColumn<Document, Boolean>, TableCell<Document, Boolean>>() { @Override public TableCell<Document, Boolean> call( TableColumn<Document, Boolean> param) { CheckBoxTableCell<Document, Boolean> cell = new CheckBoxTableCell<>(); cell.setAlignment(Pos.CENTER); return cell; } }); tableView.getColumns().add(selectColumn); addDocumentColumns(tableView); averageColumnsWidth(tableView); tableView.setItems(documentData); return tableView; }
(图四)是创建带单选按钮的table:使用了setCellFactory方法 ,返回RadioButtonTableCell对象。
// 创建带单选按钮的table public TableViewcreateTableWithRadioButton() { initDocumentData(); final TableView<Document> tableView = new TableView<Document>(); tableView.setEditable(true); TableColumn<Document, Boolean> selectColumn = new TableColumn<>("选择"); selectColumn .setCellValueFactory(new PropertyValueFactory<Document, Boolean>( "select")); selectColumn .setCellFactory(new Callback<TableColumn<Document, Boolean>, TableCell<Document, Boolean>>() { @Override public TableCell<Document, Boolean> call( TableColumn<Document, Boolean> param) { final RadioButtonTableCell<Document, Boolean> cell = new RadioButtonTableCell<>(); final RadioButton radio = (RadioButton) cell .getGraphic(); radio.setOnAction(new EventHandler<ActionEvent>() { @Override public void handle(ActionEvent event) { for (Document doc : tableView.getItems()) { doc.setSelect(false); } Document doc = documentData.get(cell.getIndex()); doc.setSelect(true); } }); return cell; } }); tableView.getColumns().add(selectColumn); addDocumentColumns(tableView); averageColumnsWidth(tableView); tableView.setItems(documentData); return tableView; }
RadioButtonTableCell类实现代码:RadioButtonTableCell继承TableCell类,覆盖updateItem方法
public class RadioButtonTableCell<S, T> extends TableCell<S, T> { private final RadioButton radio; private ObservableValue<T> ov; public RadioButtonTableCell() { this.radio = new RadioButton(); setAlignment(Pos.CENTER); setGraphic(radio); } @Override protected void updateItem(T item, boolean empty) { super.updateItem(item, empty); if (empty) { setText(null); setGraphic(null); } else { setGraphic(radio); if (ov instanceof BooleanProperty) { radio.selectedProperty().unbindBidirectional( (BooleanProperty) ov); } ov = getTableColumn().getCellObservableValue(getIndex()); if (ov instanceof BooleanProperty) { radio.selectedProperty() .bindBidirectional((BooleanProperty) ov); } } } }
(图五)是创建带图表的table:使用了setCellFactory方法 ,返回ChartTableCell对象。
// 创建带图表的table public TableViewcreateTableWithGraphic() { final TableView<Document> tableView = new TableView<Document>(); addDocumentColumns(tableView); TableColumn<Document, List<Double>> chartColumn = new TableColumn<>( "图形"); chartColumn .setCellValueFactory(new PropertyValueFactory<Document, List<Double>>( "charts")); chartColumn .setCellFactory(new Callback<TableColumn<Document, List<Double>>, TableCell<Document, List<Double>>>() { @Override public TableCell<Document, List<Double>> call( TableColumn<Document, List<Double>> param) { return new ChartTableCell(); } }); tableView.getColumns().add(chartColumn); chartColumn.setMinWidth(150); chartColumn.setPrefWidth(200); chartColumn.setMaxWidth(300); tableView.setItems(documentData); return tableView; }
ChartTableCell类类实现代码:ChartTableCell继承TableCell类,覆盖updateItem方法
package table;import java.util.List;import javafx.scene.chart.AreaChart;import javafx.scene.chart.NumberAxis;import javafx.scene.chart.XYChart;import javafx.scene.control.ContentDisplay;import javafx.scene.control.TableCell;import javafx.util.StringConverter;/** * @author hanxi * */ public class ChartTableCell extends TableCell<Document, List<Double>> { NumberAxis xAxis; NumberAxis yAxis; AreaChart<Number, Number> chart; public ChartTableCell() { super(); getStyleClass().add("table-chart-cell"); xAxis = new NumberAxis(); yAxis = new NumberAxis(); chart = new AreaChart<Number, Number>(xAxis, yAxis); chart.getStyleClass().add("table-chart"); chart.setLegendVisible(false); chart.setTitle(null); chart.setAnimated(false); xAxis.setLabel(null); xAxis.setTickMarkVisible(false); xAxis.setMinorTickVisible(false); xAxis.setTickLabelFormatter(new StringConverter<Number>() { @Override public String toString(Number t) { return ""; } @Override public Number fromString(String string) { return 0; } }); yAxis.setLabel(null); yAxis.setTickMarkVisible(false); yAxis.setMinorTickVisible(false); yAxis.setTickLabelFormatter(new StringConverter<Number>() { @Override public String toString(Number t) { return ""; } @Override public Number fromString(String string) { return 0; } }); chart.setMinSize(20, 35); chart.setPrefSize(150, 35); chart.setMaxSize(Double.MAX_VALUE, 35); setGraphic(chart); setContentDisplay(ContentDisplay.GRAPHIC_ONLY); } @Override public void updateItem(List<Double> item, boolean empty) { super.updateItem(item, empty); if (empty) { setGraphic(null); } else { XYChart.Series<Number, Number> salesSeries = new XYChart.Series<Number, Number>(); for (int i = 0; i < item.size(); i++) { salesSeries.getData().add( new XYChart.Data<Number, Number>(i, item.get(i))); } chart.getData().clear(); chart.getData().add(salesSeries); setContentDisplay(ContentDisplay.GRAPHIC_ONLY); } } }