To implement custom PhoneTextWatcher in android native for +1(xxx)-xxx-xxxx format. We have PhoneNumberFormattingTextWatcher default available in Telephony class. But it is not enough for me. I want set format like below :
So here is new TextWatcher class which can convert your input into above format:
import android.text.Editable; import android.text.TextWatcher; import android.widget.EditText; public class PhoneNumberTextWatcher implements TextWatcher { //This TextWatcher sub-class formats entered numbers as 1 (123) 456-7890 private boolean mFormatting; // this is a flag which prevents the // stack(onTextChanged) private boolean clearFlag; private int mLastStartLocation; private String mLastBeforeText; private EditText mWeakEditText; private int maxLength = 0; public PhoneNumberTextWatcher(EditText weakEditText, int length) { this.mWeakEditText = weakEditText; this.maxLength = length; } @Override public void beforeTextChanged(CharSequence s, int start, int count, int after) { clearFlag = after == 0 && s.toString().equals(Watchers.PHONE_COUNTRY_CODE + " "); mLastStartLocation = start; mLastBeforeText = s.toString(); } @Override public void onTextChanged(CharSequence s, int start, int before, int count) { // TODO: Do nothing } @Override public void afterTextChanged(Editable s) { // Make sure to ignore calls to afterTextChanged caused by the work // done below if(!s.toString().isEmpty() && Character.isAlphabetic(s.charAt(0))){ // mWeakEditText.removeTextChangedListener(this); return; } if (!mFormatting) { mFormatting = true; String formattedValue = formatNumber(s.toString(), clearFlag); mWeakEditText.removeTextChangedListener(this); int lengthBeforeUpdate = mWeakEditText.getText().length(); int lengthAfterUpdate = formattedValue.length(); int lastCursorPosition = mWeakEditText.getSelectionStart(); mWeakEditText.setText(formattedValue); int newPosition = 0; if(lengthAfterUpdate < lengthBeforeUpdate){ //It is deletion of character newPosition = lastCursorPosition - (lengthBeforeUpdate - lengthAfterUpdate); } else { newPosition = lastCursorPosition + (lengthAfterUpdate - lengthBeforeUpdate); } mWeakEditText.setSelection(Math.min(maxLength,Math.max(newPosition, 0))); mWeakEditText.addTextChangedListener(this); mFormatting = false; } } private String formatNumber(String currentInput, boolean clearFlag) { String clearedString = removeUnwantedCharacter(currentInput); StringBuilder outputString = new StringBuilder(); clearedString = addPlusSignIfNotExist(clearedString); int totalDigitCount = clearedString.length(); //if already entered 10 characters without country code then add country code if (totalDigitCount == 10 && !clearedString.startsWith(Watchers.PHONE_COUNTRY_CODE)) { outputString.append(Watchers.PHONE_COUNTRY_CODE + " "); } //Only country code then remove it if (clearedString.equals(Watchers.PHONE_COUNTRY_CODE) && clearFlag) { return ""; } int alreadyPlacedDigitCount = 0; if (clearedString.startsWith(Watchers.PHONE_COUNTRY_CODE)) { outputString.append(Watchers.PHONE_COUNTRY_CODE + " "); alreadyPlacedDigitCount = Watchers.PHONE_COUNTRY_CODE.length(); } if (totalDigitCount - alreadyPlacedDigitCount > 3) { outputString.append("(").append(clearedString.substring(alreadyPlacedDigitCount, alreadyPlacedDigitCount + 3)).append(") "); alreadyPlacedDigitCount += 3; } if (totalDigitCount - alreadyPlacedDigitCount > 3) { outputString.append(clearedString.substring( alreadyPlacedDigitCount, alreadyPlacedDigitCount + 3)).append("-"); alreadyPlacedDigitCount += 3; } // All the required formatting is done so we'll just copy the // remaining digits. if (totalDigitCount > alreadyPlacedDigitCount) { outputString.append(clearedString .substring(alreadyPlacedDigitCount)); if (outputString.length() > maxLength) { String fullLength = outputString.toString(); outputString.delete(0, outputString.length()); outputString.append(fullLength.substring(0, maxLength)); } } return outputString.toString(); } private String addPlusSignIfNotExist(String clearedString) { if (Watchers.PHONE_COUNTRY_CODE.contains("+") && !clearedString.contains("+") && clearedString.length() > 10) { clearedString = "+" + clearedString; } return clearedString; } private String removeUnwantedCharacter(String currentInput) { StringBuilder clearedString = new StringBuilder(); int p = 0; while (p < currentInput.length()) { char ch = currentInput.charAt(p); if (Character.isDigit(ch) || (ch == '+' && p == 0)) { clearedString.append(ch); } p++; } return clearedString.toString(); } }
Here is only one parameter is not available in code that is length, let me define it here so you will only get 10 digit mobile number with country code in pretty format.
int formattingSupporterLength = 5; //chracters which will be used in formatting number (, ,), ,-, int length = PHONE_COUNTRY_CODE.length() + 10 + formattingSupporterLength;
For country code I have used +1 you can also use any code here.
PHONE_COUNTRY_CODE = “+1”
Feel free to copy and paste code. Contribute your knowledge here so other can also copy and fasten their development.
I have added comment for each section, so you can better understand how code works and also modify according to your requirement.
????????*Posted In India* ????????
⌨️ Happy Coding ⌨️
Share this content: