This question goes further where JavaFX: Disable multiple rows in TableView based on other TableView stops. I want to generate a more general topic, of which other people could also benefit.
I also have the two tableviews. I also want to disable a row in table2 when table1 contains the same object. This is achieved with the code below:
//Check if a row needs to be disabled: this is achieved with a rowfactory
ObservableList<String> listOfSKUs = EasyBind.map(table1.getItems(),Product::getSKU);
table2.setRowFactory(tv -> {
TableRow<Product> row = new TableRow<>();
//The row doesnt need to be checked when it is empty, thats the first part
//The second part is a big OR: the row is a gift card OR the listOfSkus contains the row. In this last one, the amount also needs to be checked.
row.disableProperty().bind(Bindings.createBooleanBinding( () ->
row.getItem() != null &&
(row.getItem().getProductName().equals("Kadobon") ||
(listOfSKUs.contains(row.getItem().getSKU()) //&& some part to check for the amount)
), listOfSKUs, row.itemProperty() ));
return row;
});
Now I only want the row to be disabled when:
- The SKU of the product from table1 is also in table2 (this works now)
- The amount of the product in table2 is negative
I do not know how to check on the amount, because I need the amount that is associated with the certain SKU. How can I create this with multiple maps in one BooleanBinding?
Any help is greatly appreciated!
This sounds to me that you might benefit from reconsidering your object model. It seems that your
Product
has two different values you refer to asamount
: one that's displayed in table1, and one that's displayed in table2. If you make those two different fields of theProduct
class, then all this becomes much easier, as you can represent the items in both tables with the same actual objects (just with different properties displayed in the columns); and then the criteria for disabling a row becomes just a function of the object you're looking at (along withtable2.getItems().contains(...)
).Another option might be an
SKU
class:Then both tables can be
TableView<SKU>
s with the cell value factories on the columns just looking at the properties from the correct product. That wayrow.getItem()
in table1's row factory returns theSKU
object, and can look at the table2 properties as needed.If you really can't do that, then one way to do this would be to maintain an
ObservableMap<String, Double>
which maps SKUs to the amount displayed in table2. This is a bit of work, but not too bad:Now you need to keep the map updated when the table contents change:
And then the disable criteria can be something like
I haven't tried any of this, but it should work. There are two assumptions here: