0

I have created a custom TextField (by extending javafx.scene.control.TextField) which I use to store monetary values eg say $120,000. I have called this class CurrencyField and It has two constructors public CurrencyField() and public CurrencyField(String currency) I also have a public void setCurrency(String currency) method for setting the currency symbol. One can out rightly set the currency by using new CurrencyField(currency) or set it later using the Setter Method - setCurrency(currency)

Usually, I want to be able to use different currency symbols based on conditions (outside the scope of this questions) Eg. I may want to switch the currency from $ to £ by clicking a button. In this case, I want all the CurrencyFields to immediately display the amounts with the new currency symbol.

I have already learned that using Properties and Binding can be used to update one variable when another variable is updated without any extra methods. Now, in a more practical way, I want that if I call the setCurrency("$") method, a field with Rs2,000 will immediately display $2,000.

How can I go about this using Properties and/or Binding or any other way basically?

3
  • 1
    I think this can help you : stackoverflow.com/questions/35093145/… Commented Sep 6, 2017 at 12:32
  • Assuming you use the TextField's text property to display the number AND the currency symbol, I'm afraid this is not possible since any binding of the text property would render the TextField uneditable (bound properties cannot be set). You need to replace the currency symbols for all text fields without a binding. If the currency stored in a property you could do this from a listener though. Commented Sep 6, 2017 at 15:22
  • unrelated: no need for subclassing a textField, instead configure the textField with a TextFormatter. Apart from that: I don't quite understand the problem - what exactly are you stumbling across? And changing the currency will certainly change the value ... Please provide a SSCCE that demonstrates what you are after and how you can't reach it Commented Sep 7, 2017 at 12:37

1 Answer 1

0

Your CurrencyField class could have two properties: "amount" (DoubleProperty) and "currency" (StringProperty). If in your case "double" is not sufficient to store monetary values you can also use "ObjectProperty" or something similar.

Then you create a custom-binding based on these two properties which calculates the formatted string. This custom-binding can now be bound to the textProperty of the TextField.

This could look something like this (not tested):

public CurrencyField extends TextField { private StringProperty currency = new SimpleStringProperty(); private DoubleProperty amount = new SimpleDoubleProperty(0); public CurrencyField() { // this observable will be updated everytime either "currency" or "amount" is updated. ObservableStringValue formattedAmount = Bindings.createStringBinding(() -> { String currencyValue = currency.get(); double amountValue = amount.get(); return currencyValue + " " + amountValue; // your formatting logic here }, currency, amount); this.textProperty().bind(formattedAmount); } // getter/setter/property-accessors } 

There are two things to keep in mind with this solution:

  • textProperty of your class can't be set anymore from outside. If someone tries to set a value then an exception will be thrown indicating that textProperty is already bound.
  • Maybe it is possible that "formattedAmount" get's garbage collected. If this is the case you simply have to create a field in your class for formattedAmount. The initialization can still happen in the constructor.
Sign up to request clarification or add additional context in comments.

1 Comment

please don't re-invent the wheel ... core has extensive support for formatting (core classes like Format et al) and applying them to a fx TextField which has a TextFormatter property

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.