3

I want to have a button enabled or disabled based on whether a text field contains anything, and I want to implement this by using property binding.

So at first I used the isEmpty() method on the text field's text property to create a boolean binding for the button's disabled property:

startSearchButton.disableProperty().bind(searchField.textProperty().isEmpty());

While the binding works, my definition of "text field contains anything" is different to what the isEmpty() method does, namely just checking if the text's length is > 0. However, I'm interested in whether there is "real" text, i.e. whether the text field is blank (not just not empty, but actually not only whitespace).

Unfortunately there is no method isBlank(), and I also couldn't find anything appropriate in the Bindings utility class. Now I saw that you can implement any custom boolean property you like via the Bindings.createBooleanProperty method, but I'm not yet familiar with the concept of defining custom bindings. How would I have to implement such a boolean property for my case?

user3237736
  • 845
  • 1
  • 9
  • 24

3 Answers3

9

You can create a custom binding using (among many methods) Bindings.createBooleanBinding(...). The first argument is a function that computes the value of the binding (you can trim whitespace from the text with trim() and then check if the result is empty); the remaining arguments are a list of observables that trigger recomputation of the binding. You want to recompute the binding when the text in the text field changes, so just specify the text property:

startSearchButton.disableProperty().bind(Bindings.createBooleanBinding(() -> 
    searchField.getText().trim().isEmpty(),
    searchField.textProperty());
James_D
  • 201,275
  • 16
  • 291
  • 322
  • Ah, your answer gave me even a better understanding of the Observable parameter! Thank you – user3237736 Mar 11 '16 at 19:33
  • oh, just a quick follow-up question please: Is it not required to check if the getText() is null first? Or is it not possible for a (text field's) text property to be null? – user3237736 Mar 11 '16 at 19:34
  • 1
    Yes, [`Property`](http://docs.oracle.com/javase/8/javafx/api/javafx/beans/property/Property.html) is a subinterface of [`Observable`](http://docs.oracle.com/javase/8/javafx/api/javafx/beans/Observable.html), so all properties are `Observable`s. I *believe* `getText()` never returns `null`, but there is little harm in adding in a null check. – James_D Mar 11 '16 at 19:36
1

As for 2022

 public static BooleanBinding isBlank(StringProperty stringProperty) {
        return Bindings.createBooleanBinding(() -> stringProperty.get().isBlank(), stringProperty);
    }

    public static BooleanBinding isNotBlank(StringProperty stringProperty) {
        return isBlank(stringProperty).not();
    }

(idk why didn't nobody suggest String::isBlank, perhaps it was added in Java later)

Vadim
  • 125
  • 7
-1

You can do this too:

  1. With Apache StringUtils.isBlank()

    startSearchButton.disableProperty().bind(Bindings.createBooleanBinding(() -> 
        StringUtils.isBlank(searchField.getText()),
        searchField.textProperty());
    
  2. Create you own method

    public static boolean IsNullOrWhitespace(String s) {
            if(s == null) {
                return true;
            }
    
            for(int i = 0; i < s.length(); ++i) {
                if(!Character.isWhitespace(s.charAt(i))) {
                    return false;
                }
    
            }
            return true;
        }
    

and then:

    startSearchButton.disableProperty().bind(Bindings.createBooleanBinding(() -> 
            IsNullOrWhitespace(searchField.getText()),
            searchField.textProperty());
dani
  • 41
  • 7
  • Of course you could do that, you could go even further and define a utility method for the whole thing of setting up such a binding for a given property. But this is irrelevant to the question, which has been already answered by the way. so I don't really know why you are digging out this old question to post this. – user3237736 Sep 18 '18 at 20:17