Reputation: 477
import javafx.scene.control.TableCell;
import javafx.scene.control.TableColumn;
import javafx.scene.control.cell.ComboBoxTableCell;
import javafx.util.Callback;
public class ComboBoxTableCellFactory<S, T> implements Callback<TableColumn<S, T>, TableCell<S, T>> {
private T[] nodes;
public void setNodes(T[] nodes) {
this.nodes = nodes;
}
public T[] getNodes() {
return nodes;
}
@Override
public TableCell<S, T> call(TableColumn<S, T> column) {
if (nodes == null) {
return new ComboBoxTableCell<S, T>();
}
return new ComboBoxTableCell<S, T>(nodes);
}
}
I've written this class for declaring ComboBoxTableCells in fxml. This is how I would declare a cell factory for a table cell:
<TableColumn prefWidth="50" text="Grade">
<cellFactory>
<ComboBoxTableCellFactory />
<nodes>
//How would i declare nodes?
</nodes>
</cellFactory>
</TableColumn>
My question is, how would I declare an array of nodes for the combo box. It will run with an empty array obviously but i want to be able to declare nodes in FXML. So what would I put in between the two nodes tags? An example would be a Grade column where a ComboBox would be populated with a number of single character strings from which you'd have to choose a grade.
EDIT: Changed the class to this:
import javafx.collections.ObservableList;
import javafx.scene.control.TableCell;
import javafx.scene.control.TableColumn;
import javafx.scene.control.cell.ComboBoxTableCell;
import javafx.util.Callback;
public class ComboBoxTableCellFactory<S, T> implements Callback<TableColumn<S, T>, TableCell<S, T>> {
private ObservableList<T> nodes;
public void setNodes(ObservableList<T> nodes) {
this.nodes = nodes;
}
public ObservableList<T> getNodes() {
return nodes;
}
@Override
public TableCell<S, T> call(TableColumn<S, T> column) {
if (nodes != null) {
return new ComboBoxTableCell<S, T>(nodes);
}
return new ComboBoxTableCell<S, T>();
}
}
And:
<TableColumn prefWidth="50" text="Grade">
<cellFactory>
<ui.view.ComboBoxTableCellFactory />
<nodes>
<FXCollections fx:factory="observableArrayList">
//don't know how to declare the nodes here!
</FXCollections>
</nodes>
</cellFactory>
</TableColumn>
I just don't know how to declare the nodes!
Essentially, I'm trying to do this:
ObservableList<String> values = FXCollections.observableArrayList("A", "B", "C");
TableColumn<String, String> gradeColumn = new TableColumn<>(tableView);
gradeColumn.setCellFactory(ComboBoxTableCell.forTableColumn(new DefaultStringConverter(), values));
In FXML.
Upvotes: 0
Views: 1230
Reputation: 477
Alright, I figured out why it wasn't working. By default the combo box doesn't show, you have to click for it to show. I didn't realize but the Table view wasn't editable and so when i clicked to edit, the combo box didn't show. Everything's working fine now! Thanks for the help.
Upvotes: 0
Reputation: 209245
If you are creating String
s, you can do
<TableColumn prefWidth="50" text="Grade">
<cellFactory>
<ui.view.ComboBoxTableCellFactory />
<nodes>
<FXCollections fx:factory="observableArrayList">
<String fx:value="A"/>
<String fx:value="B"/>
<String fx:value="C"/>
</FXCollections>
</nodes>
</cellFactory>
</TableColumn>
See the "Instance declarations" section of the Introduction to FXML for details. (And note, a little counter-intuitively, that you have to explicitly import String
with <?import java.lang.String?>
.)
Upvotes: 2