NOTE: This seems to only be happening in Android 12 (SDK 31)
I have a pretty complex use case for a TextWatcher in which I need to change text as the user types, however I may need to change more than just the character they just typed. For that reason I cannot use a InputFilter.
For this example to highlight the error I am seeing I have simplified my use case. I would just like to add a space after every character typed.
In my TextWatcher:
override fun onTextChanged(s: CharSequence?, start: Int, before: Int, count: Int) {
editText.removeTextChangedListener(this)
addSpace(s, start, before, count)
editText.addTextChangedListener(this)
}
private fun addSpace(s: CharSequence?, start: Int, before: Int, count: Int) {
val text = s ?: return
val spaced = "$text "
editText.text.clear()
editText.text.append(spaced)
}
Note: I am using clear() and append() to avoid the keyboard from switching. If I use setText(), will switch back to the default keyboard.
This works just fine when adding letters:
However when adding numbers, it will duplicate each number. Adding some logging, it seems onTextChanged is being called again after my changes are complete and I re-add the listener.
Again this works just fine on SDK 30, and SDK 32, so it seems Android fixed the regression, but does not yet have a patch for SDK 31. Has anyone run into this? Know if there is an existing ticket I can follow? Having trouble finding any reference to this.
UPDATE: Running into the same issue using afterTextChanged(...)
override fun afterTextChanged(s: Editable?) {
editText.removeTextChangedListener(this)
addSpace(s)
editText.addTextChangedListener(this)
}
private fun addSpace(s: Editable?) {
val text = s ?: return
val spaced = "$text "
s.clear()
s.append(spaced)
}