I would like to be able to enter the time in a javafx text field in the format hh:mm:ss. How would I go about formatting the text field? I already got the regex method so it only accepts numbers as inputs:
public void format(TextField t, String regex){
TextFormatter<String> formatter = new TextFormatter<String>( change -> {
change.setText(change.getText().replaceAll(regex, ""));
return change;
});
t.setTextFormatter(formatter);
}
and I also got a method that limits the amount of characters allowed in the textfield:
public void limitLength(int maxLength, TextField t){
t.lengthProperty().addListener(new ChangeListener<Number>() {
@Override
public void changed(ObservableValue<? extends Number> observable,
Number oldValue, Number newValue) {
if (newValue.intValue() > oldValue.intValue()) {
// Check if the new character is greater than LIMIT
if (t.getText().length() >= maxLength) {
t.setText(t.getText().substring(0, maxLength));
}
}
}
});
}
However none of this helps me get the time format I want. The ideal would be the initial text being 00:00:00 and the user ONLY being able to edit the digits, unable to touch the colons. It would also be awesome if I could be able to make sure that between each colon there are 2 digits, ie the user should be unable to move around the digits, like this 0:000:00.
Thanks for any help.
There is already a class that is designed for formatting dates that you can use with the TextField
's textFormatter
: SimpleDateFormat
TextField tf = new TextField();
SimpleDateFormat format = new SimpleDateFormat("HH:mm:ss");
tf.setTextFormatter(new TextFormatter<>(new DateTimeStringConverter(format), format.parse("00:00:00")));
See javadoc for SimpleDateFormat
for a more detailed decription of the meaning of the characters.
You could also use 3 different TextField
s and remove background and border and put them in a HBox
to get non-editable :
s:
TextField hours = new TextField();
TextField minutes = new TextField();
TextField seconds = new TextField();
StringConverter<Integer> minSecConverter = new IntRangeStringConverter(0, 59);
minutes.setTextFormatter(new TextFormatter<>(minSecConverter, 0));
seconds.setTextFormatter(new TextFormatter<>(minSecConverter, 0));
hours.setTextFormatter(new TextFormatter<>(new IntRangeStringConverter(0, 23), 0));
prepareTextField(hours);
prepareTextField(minutes);
prepareTextField(seconds);
HBox fields = new HBox(hours, createLabel(),minutes, createLabel(), seconds);
fields.setPadding(new Insets(4));
fields.setStyle("-fx-background-color: white;");
public static void prepareTextField(TextField tf) {
tf.setAlignment(Pos.CENTER);
tf.setBackground(Background.EMPTY);
tf.setBorder(Border.EMPTY);
tf.setPadding(Insets.EMPTY);
tf.setPrefColumnCount(2);
}
public static class IntRangeStringConverter extends StringConverter<Integer> {
private final int min;
private final int max;
public IntRangeStringConverter(int min, int max) {
this.min = min;
this.max = max;
}
@Override
public String toString(Integer object) {
return String.format("%02d", object);
}
@Override
public Integer fromString(String string) {
int integer = Integer.parseInt(string);
if (integer > max || integer < min) {
throw new IllegalArgumentException();
}
return integer;
}
}
public static Label createLabel() {
Label label = new Label(":");
label.setPrefWidth(3);
return label;
}