I have a TableView and two text fields. When the user write numbers into textfields and push the button. All tablerows should be painted as a percentage. For exmaple 30% should be yellow and 70% should be green.
I tried to use lookup method to look for TableView objects. Adding new css class changed the colour of tablerows. But this solution is not good. Lookup can find only visible elements.
@FXML
void confirmPercentage(ActionEvent event) {
clearSelectionsOfTestingTbaleView();
TableRow[] tableRows = selectTrainingDataTableView.lookupAll(".table-row-cell").toArray(new TableRow[0]);
double percent = Double.parseDouble(this.trainingSetPercentageTextField.getText());
percent = percent > 1 ? percent / 100 : percent;
int trainIndexes = (int) (Math.round(tableRows.length * percent));
for (int i = 0 ; i < trainIndexes; i++){
tableRows[i].getStyleClass().add("selected-as-train");
}
}
I have 15 notes, but there are only 13...
So what is the way to paint ALL tablerows?
SOLUTION
Finally, I received my sight!
So i created two sets to keep selected indexes. And, i just set PseudoClass according this indexes...
void init()
Set<Integer> testSetIndexes = new HashSet<>();
Set<Integer> trainSetIndexes = new HashSet<>();
tableView.setRowFactory( tableView2 -> {
PseudoClass train = PseudoClass.getPseudoClass("train");
PseudoClass test = PseudoClass.getPseudoClass("test");
PseudoClass trainAndTest = PseudoClass.getPseudoClass("train-and-test");
/*Percentage selection with button*/
final TableRow<List<Double>> row = new TableRow<List<Double>>(){
@Override
public void updateItem(List<Double> item, boolean empty){
if (item != null) {
int index = dataInsideTableView.indexOf(item);
this.pseudoClassStateChanged(train, trainSetIndexes.contains(index));
this.pseudoClassStateChanged(test, testSetIndexes.contains(index));
this.pseudoClassStateChanged(trainAndTest, trainSetIndexes.contains(index) && testSetIndexes.contains(index));
} else {
this.pseudoClassStateChanged(train, false);
this.pseudoClassStateChanged(test, false);
this.pseudoClassStateChanged(trainAndTest, false);
}
}
};
/*Mouse selection*/
row.addEventFilter(MouseEvent.MOUSE_PRESSED, new EventHandler<MouseEvent>() {
@Override
public void handle(MouseEvent event) {
if (manualSelectionCheckBox.isSelected()) {
if (event.isPrimaryButtonDown()) {
int index = dataInsideTableView.indexOf(row.getTableView().getItems().get(row.getIndex()));
if(trainSetIndexes.contains(index)){
trainSetIndexes.remove(index);
} else {
trainSetIndexes.add(index);
}
selectTrainingDataTableView.refresh(); //call update
} else if (event.isSecondaryButtonDown()) {
int index = dataInsideTableView.indexOf(row.getTableView().getItems().get(row.getIndex()));
if(testSetIndexes.contains(index)){
testSetIndexes.remove(index);
} else {
testSetIndexes.add(index);
}
tableView.refresh();
}
}
}
});
return row;
});
I click "Refresh" button, confirmPercentage method just recount indexes and refresh the table.
@FXML
void confirmPercentage(ActionEvent event) {
trainSetIndexes.clean();
testSetIndexes.clean();
double percent = Double.parseDouble(this.trainingSetPercentageTextField.getText());
percent = percent > 1 ? percent / 100 : percent;
trainSize = (int) (Math.floor(usedData.size() * percent));
percent = Double.parseDouble(this.testingSetPercentageTextField .getText());
percent = percent > 1 ? percent / 100 : percent;
testSize = (int) (Math.floor(usedData.size() * percent));
//put indexes
for (int i = 0 ; i < trainSize; i++){
trainSetIndexes.add(i);
}
for (int i = usedData.size()-1 ; i >= usedData.size()-1-testSize; i--){
testSetIndexes.add(i);
}
this.tableView.refresh();
}