I use java 8.0.45. I have implemented my first javafx application (very simple)
with data binding. However, biding from user input-> pojo seems to work with
bugs. I've checked about 200 times. I entered new values in text fields and
after that I checked model values. The same code, the same my behaviour.
Sometimes everything works fine (in most cases - about 80-90%) sometimes model
value!=textfield value. I've noticed the following. Data binding for some
certain text field works,works and then at some point of time that binding
stops working and all new values for this certain textfield are not passed to
model. Nor exceptions. Nor any warnings. Nothing. Just binding doesn't work.
I have 4 textfiled which are created via fxml. Two for string model type. One
for integer. One for bigdecimal. The problem happens to all these
fields(sometimes to one, sometimes to several). As my number fields can have
null values, I use for example PropertyObject but not IntegerProperty (people
from openjfx advised so).
So is this JavaFx bug or what? P.S. I use felix osgi, weld cdi, and pax - I
don't know if it matters...
My code is the following:
DTO - POJO Model
public class Task {
private String name;
private Integer order;
private BigDecimal weight;
private String comment;
private final PropertyChangeSupport propertyChangeSupport;
public Task() {
this.propertyChangeSupport = new PropertyChangeSupport(this);
}
public String getName() {
return name;
}
public void setName(String name) {
String pv = this.name ;
this.name = name;
propertyChangeSupport.firePropertyChange("name", pv, name);
}
public Integer getOrder() {
return order;
}
public void setOrder(Integer order) {
Integer pv = this.order;
this.order = order;
propertyChangeSupport.firePropertyChange("order", pv, this.order);
}
public BigDecimal getWeight() {
return weight;
}
public void setWeight(BigDecimal weight) {
BigDecimal pv = this.weight;
this.weight = weight;
propertyChangeSupport.firePropertyChange("weight", pv, weight);
}
public String getComment() {
return comment;
}
public void setComment(String comment) {
String pv = this.comment;
this.comment = comment;
propertyChangeSupport.firePropertyChange("comment", pv, this.comment);
}
public void addPropertyChangeListener(PropertyChangeListener listener) {
propertyChangeSupport.addPropertyChangeListener(listener);
}
}
Adapter
public class TaskAdapter {
private StringProperty nameProperty;
private ObjectProperty<Integer> orderProperty;
private ObjectProperty<BigDecimal> weightProperty;
private StringProperty commentProperty;
public TaskAdapter(Task task) {
try {
nameProperty=new
JavaBeanStringPropertyBuilder().bean(task).name("name").build();
orderProperty=new
JavaBeanObjectPropertyBuilder<Integer>().bean(task).name("order").build();
weightProperty=new
JavaBeanObjectPropertyBuilder<BigDecimal>().bean(task).name("weight").build();
commentProperty=new
JavaBeanStringPropertyBuilder().bean(task).name("comment").build();
} catch (NoSuchMethodException ex) {
Logger.getLogger(this.getClass().getName()).log(Level.SEVERE, null,
ex);
}
}
public StringProperty getNameProperty() {
return nameProperty;
}
public ObjectProperty<Integer> getOrderProperty() {
return orderProperty;
}
public ObjectProperty<BigDecimal> getWeightProperty() {
return weightProperty;
}
public StringProperty getCommentProperty() {
return commentProperty;
}
}
BigDecimal Converter
public class SimpleBigDecimalStringConverter extends
StringConverter<BigDecimal>{
@Override
public String toString(BigDecimal i) {
if (i == null) {
return "" ;
} else {
return i.toString();
}
}
@Override
public BigDecimal fromString(String string) {
if (string.trim().length() == 0) {
return null ;
} else {
try {
return new BigDecimal(string);
} catch (NumberFormatException nfe) {
return null ;
}
}
}
}
IntegerConverter
public class SimpleIntegerStringConverter extends StringConverter<Integer>{
@Override
public String toString(Integer i) {
if (i == null) {
return "" ;
} else {
return i.toString();
}
}
@Override
public Integer fromString(String string) {
if (string.trim().length() == 0) {
return null ;
} else {
try {
return Integer.valueOf(string);
} catch (NumberFormatException nfe) {
return null ;
}
}
}
}
Initializing code
Task task=new Task();
TaskAdapter adapter=new TaskAdapter(task);
nameTextField.textProperty().bindBidirectional(adapter.getNameProperty());
orderTextField.textProperty().bindBidirectional(adapter.getOrderProperty(),new
SimpleIntegerStringConverter());
weightTextField.textProperty().bindBidirectional(adapter.getWeightProperty(),new
BigDecimalStringConverter());
commentTextField.textProperty().bindBidirectional(adapter.getCommentProperty());