12

For this piece of code (JavaFX).

StringProperty sp;
DoubleProperty dp;

StringConverter<Double> converter = new DoubleStringConverter();    

Bindings.bindBidirectional(sp, dp, converter);

I get compilation error (in Eclipse IDE)

This is the method signature:

public static <T> void bindBidirectional(Property<String> stringProperty, Property<T> otherProperty, StringConverter<T> converter)

But if I remove parametrization (of StringConverter), then I get only warnings and code works.

StringConverter converter = new DoubleStringConverter();    

I am trying to avoid to use raw type of generics so that I don't have to suppress warnings in my IDE.

So the question is:
What is the right pattern to write this piece of code?

TheCodeArtist
  • 21,479
  • 4
  • 69
  • 130
TurboFx
  • 121
  • 1
  • 1
  • 3

2 Answers2

26

This is probably a small "trap" in JavaFX properties. If you look closely at the signature:

static <T> void bindBidirectional(Property<java.lang.String> stringProperty,
    Property<T> otherProperty, StringConverter<T> converter)

The parameter of the converter must match the parameter of the property. But (the surprize here) DoubleProperty implements Property<Number>, thus the mismatch in bindBidirectional. Luckily the solution is simple: use NumberStringConverter:

StringProperty sp = ...;
DoubleProperty dp = ...;
StringConverter<Number> converter = new NumberStringConverter();
Bindings.bindBidirectional(sp, dp, converter);

You get the extra benefit that you can specify the conversion format.

Nikos Paraskevopoulos
  • 39,514
  • 12
  • 85
  • 90
0

That is the answer of my solution:

    ArrayList<Pair<Slider,Label>> sliderList = new ArrayList<Pair<Slider,Label>>(
            Arrays.asList(
                    new Pair<Slider,Label>(soundSlider, soundLabel),
                    new Pair<Slider,Label>(videoSlider, videoLabel),

    sliderList.forEach(p->{
        Bindings.bindBidirectional(p.getValue().textProperty(), p.getKey().valueProperty(), new NumberStringConverter() {
            @Override
            public String toString(Number value) {
                return super.toString(Math.round((double) value));
            }
        }); 
    });
Light
  • 175
  • 1
  • 2
  • 11