Griffon - restricting a textfield to numbers
With my latest Griffon+JavaFX application, I wasn't having any luck binding a textfield to a 'float' property in my model. So to work around it temporarily, I've added a change listener which will veto any input that isn't a number.
This example is basically using a very Java centric approach:
Now, we can simplify this by using the Groovy way:
See Groovy way to implement interfaces to understand how this is implementing the interface.
If we want to have several text fields using the same logic, we can define the closure in the Controller and reference that in many places:
Still, this is not optimal since I have to use Strings instead of Floats in my model - but it does let me continue with whats important right now. Hopefully the binding bug can be fixed soon.
This example is basically using a very Java centric approach:
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import javafx.beans.value.ChangeListener | |
import javafx.beans.value.ObservableValue | |
import org.apache.commons.lang.StringUtils | |
// model | |
@FXBindable String amount1 | |
// view | |
textField(id: 'amount1', text: bind(model.amount1Property)) | |
noparent { | |
amount1.textProperty().addListener(new ChangeListener<String>() { | |
@Override | |
public void changed(ObservableValue<? extends String> observable, | |
String oldValue, String newValue) { | |
try { | |
if (StringUtils.isNotBlank(newValue)) { | |
Integer.parseInt(newValue); | |
} | |
} catch (Exception e) { | |
observable.setValue(oldValue); | |
} | |
} | |
}); | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import javafx.beans.value.ChangeListener | |
import javafx.beans.value.ObservableValue | |
import org.apache.commons.lang.StringUtils | |
// model | |
@FXBindable String amount1 | |
// view | |
textField(id: 'amount1', text: bind(model.amount1Property)) | |
noparent { | |
amount1.textProperty().addListener({ ObservableValue<? extends String> observable, String oldValue, String newValue -> | |
try { | |
if (StringUtils.isNotBlank(newValue)) { | |
Integer.parseInt(newValue); | |
} | |
} catch (Exception e) { | |
observable.setValue(oldValue); | |
} | |
} as ChangeListener<String>) | |
} |
If we want to have several text fields using the same logic, we can define the closure in the Controller and reference that in many places:
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import javafx.beans.value.ChangeListener | |
import javafx.beans.value.ObservableValue | |
import org.apache.commons.lang.StringUtils | |
// model | |
@FXBindable String amount1 | |
@FXBindable String amount2 | |
// view | |
textField(id: 'amount1', text: bind(model.amount1Property)) | |
textField(id: 'amount2', text: bind(model.amount2Property)) | |
noparent { | |
amount1.textProperty().addListener(controller.restrictToNumber) | |
amount2.textProperty().addListener(controller.restrictToNumber) | |
} | |
// controller | |
def restrictToNumber = { ObservableValue<? extends String> observable, String oldValue, String newValue -> | |
try { | |
if (StringUtils.isNotBlank(newValue)) { | |
Integer.parseInt(newValue); | |
} | |
} catch (Exception e) { | |
observable.setValue(oldValue); | |
} | |
} as ChangeListener<String> |