Skip to content

Instantly share code, notes, and snippets.

@wakim
Created August 22, 2017 13:26
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save wakim/da29dc52d331802538cb29fb9c0c49f7 to your computer and use it in GitHub Desktop.
Save wakim/da29dc52d331802538cb29fb9c0c49f7 to your computer and use it in GitHub Desktop.
import android.text.Editable
import android.text.TextWatcher
import android.text.method.DigitsKeyListener
import android.widget.EditText
import java.lang.ref.WeakReference
import java.math.BigDecimal
import java.text.NumberFormat
import java.util.*
class MoneyTextWatcher(editText: EditText, locale: Locale, val maxLength: Int = 14, val maxFractionDigits: Int = 0) : TextWatcher {
private val editTextWeakReference = WeakReference<EditText>(editText)
val punctuationRegex = "[,.]".toRegex()
val letterRegex = "[^\\d.]".toRegex()
val currency: String = Currency.getInstance(locale).symbol
val numberFormatter: NumberFormat = NumberFormat.getNumberInstance(locale)
.also {
it.maximumFractionDigits = maxFractionDigits
}
init {
editText.keyListener = DigitsKeyListener.getInstance("0123456789 $currency")
}
override fun beforeTextChanged(s: CharSequence, start: Int, count: Int, after: Int) {}
override fun onTextChanged(s: CharSequence, start: Int, before: Int, count: Int) {}
override fun afterTextChanged(editable: Editable) {
val editText = editTextWeakReference.get() ?: return
val cleanString = editable.toString().replace(currency, "").replace(letterRegex, "").replace(punctuationRegex, "").trim()
val parsed = if (cleanString.isNullOrEmpty()) null else BigDecimal(cleanString)
.apply {
if (maxFractionDigits > 0) {
setScale(2, BigDecimal.ROUND_FLOOR)
divide(BigDecimal(100), BigDecimal.ROUND_FLOOR)
}
}
val formatted = parsed?.let { "$currency ${numberFormatter.format(it)}".let { it.substring(0, minOf(maxLength - 1, it.length)) } } ?: ""
with (editText) {
removeTextChangedListener(this@MoneyTextWatcher)
editable.replace(0, editable.length, formatted)
addTextChangedListener(this@MoneyTextWatcher)
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment