android edittext onchange listener

115

Eu sei um pouco sobre, TextWatchermas isso dispara em cada caractere que você entra. Quero um ouvinte que seja acionado sempre que o usuário terminar a edição. É possível? Também TextWatcherrecebo uma instância de, Editablemas preciso de uma instância de EditText. Como faço para conseguir isso?

EDIT : a segunda pergunta é mais importante. Por favor, responda isso.

pinos
fonte
1
tente adicionar o ouvinte de foco, quando o editText toma o foco, isso significa que o usuário começou a editá-lo, e quando o editText perde o foco, significa que a edição está concluída
Houcine

Respostas:

214

Primeiro, você pode ver se o usuário terminou de editar o texto, se ele EditTextperde o foco ou se o usuário pressiona o botão Concluído (isso depende da sua implementação e do que é melhor para você). Em segundo lugar, você não pode obter uma EditTextinstância dentro de TextWatcherapenas se tiver declarado o EditTextcomo um objeto de instância. Mesmo que você não deva editar o EditTextdentro do TextWatcherporque não é seguro.

EDITAR:

Para conseguir colocar a EditTextinstância em sua TextWatcherimplementação, você deve tentar algo assim:

public class YourClass extends Activity {

    private EditText yourEditText;

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        setContentView(R.layout.main);
        yourEditText = (EditText) findViewById(R.id.yourEditTextId);

        yourEditText.addTextChangedListener(new TextWatcher() {

            public void afterTextChanged(Editable s) {

                // you can call or do what you want with your EditText here

                // yourEditText... 
            }

            public void beforeTextChanged(CharSequence s, int start, int count, int after) {}

            public void onTextChanged(CharSequence s, int start, int before, int count) {}
        });
    }
}

Observe que o exemplo acima pode ter alguns erros, mas eu só queria mostrar um exemplo.

Cata
fonte
17

Estava me incomodando que a implementação de um ouvinte para todos os meus campos EditText exigisse que eu tivesse um código feio e prolixo, então escrevi a classe abaixo. Pode ser útil para qualquer pessoa que tropece nisso.

public abstract class TextChangedListener<T> implements TextWatcher {
    private T target;

    public TextChangedListener(T target) {
        this.target = target;
    }

    @Override
    public void beforeTextChanged(CharSequence s, int start, int count, int after) {}

    @Override
    public void onTextChanged(CharSequence s, int start, int before, int count) {}

    @Override
    public void afterTextChanged(Editable s) {
        this.onTextChanged(target, s);
    }

    public abstract void onTextChanged(T target, Editable s);
}

Agora, implementar um ouvinte é um pouco mais limpo.

editText.addTextChangedListener(new TextChangedListener<EditText>(editText) {
            @Override
            public void onTextChanged(EditText target, Editable s) {
                //Do stuff
            }
        });

Quanto à frequência de disparo, talvez seja possível implementar uma verificação para executar o código desejado //Do stuffapós um determinado

RNGuy
fonte
Isso funciona muito bem para mim, economiza muitas linhas de código! Você é um gênio!
huypham99
12

Qualquer pessoa usando ButterKnife . Você pode usar como:

@OnTextChanged(R.id.zip_code)
void onZipCodeTextChanged(CharSequence zipCode, int start, int count, int after) {

}
Prakash
fonte
6

Eu fiz isso usando AutotextView:

AutotextView textView = (AutotextView) findViewById(R.id.autotextview);
textView.addTextChangedListener(new TextWatcher() {

    @Override
    public void onTextChanged(CharSequence cs, int arg1, int arg2, int arg3) {
        seq = cs;
    }

    @Override
    public void beforeTextChanged(CharSequence s, int arg1, int arg2, int arg3) {

    }

    @Override
    public void afterTextChanged(Editable arg0) {
        new SearchTask().execute(seq.toString().trim());
    }

});
Zar E Ahmer
fonte
3
 myTextBox.addTextChangedListener(new TextWatcher() {  

    public void afterTextChanged(Editable s) {}  

    public void beforeTextChanged(CharSequence s, int start, int count, int after) {} 

    public void onTextChanged(CharSequence s, int start, int before, int count) {  

    TextView myOutputBox = (TextView) findViewById(R.id.myOutputBox);  
    myOutputBox.setText(s);  

    }  
});  
Ramesh sambu
fonte
2
Há um desnecessário} no final
Howard
2

TextWatchernão funcionou para mim, pois continuou disparando para todos EditTexte bagunçando os valores uns dos outros.

Aqui está minha solução:

public class ConsultantTSView extends Activity {
    .....

    //Submit is called when I push submit button.
    //I wanted to retrieve all EditText(tsHours) values in my HoursList

    public void submit(View view){

        ListView TSDateListView = (ListView) findViewById(R.id.hoursList);
        String value = ((EditText) TSDateListView.getChildAt(0).findViewById(R.id.tsHours)).getText().toString();
    }
}

Portanto, usando o getChildAt(xx)método, você pode recuperar qualquer item no ListViewe obter o item individual usando findViewById. E então fornecerá o valor mais recente.

user2566490
fonte
1

Pelo que eu posso pensar sobre isso, há apenas duas maneiras de fazer isso. Como você pode saber se o usuário terminou de escrever uma palavra? Ou na perda de foco ou clicando em um botão "ok". Não tenho como saber se o usuário pressionou o último caractere ...

Portanto, chame onFocusChange(View v, boolean hasFocus)ou adicione um botão e um ouvinte de clique a ele.

Nuno Gonçalves
fonte
0

O método Watcher é acionado em cada entrada de caractere. Então, eu construí este código com base no método onFocusChange:

public static boolean comS(String s1,String s2){
    if (s1.length()==s2.length()){
        int l=s1.length();
        for (int i=0;i<l;i++){
            if (s1.charAt(i)!=s2.charAt(i))return false;
        }
        return true;
    }
    return false;
}

public void onChange(final EditText EdTe, final Runnable FRun){
    class finalS{String s="";}
    final finalS dat=new finalS();  
    EdTe.setOnFocusChangeListener(new OnFocusChangeListener() {          
        @Override
        public void onFocusChange(View v, boolean hasFocus) {
            if (hasFocus) {dat.s=""+EdTe.getText();}
            else if (!comS(dat.s,""+EdTe.getText())){(new Handler()).post(FRun);}       
        }
    });
}

Para usá-lo, basta chamar assim:

onChange(YourEditText, new Runnable(){public void run(){
    // V  V    YOUR WORK HERE

    }}
);

Você pode ignorar a função comS substituindo! ComS (dat.s, "" + EdTe.getText ()) pela função! Equal. No entanto, a própria função igual às vezes não funciona corretamente em tempo de execução.

O ouvinte onChange se lembrará de dados antigos de EditText quando o usuário focalizar a digitação e, em seguida, comparar os novos dados quando o usuário perder o foco ou pular para outra entrada. Se comparar a String antiga e não a mesma nova, ele dispara o trabalho.

Se você tiver apenas 1 EditText, então você precisará fazer uma função ClearFocus criando um Ultimate Secret Transparent Micro EditText 😸 fora das janelas 😽 e solicitar o foco para ele e, em seguida, ocultar o teclado através do Import Method Manager.

phnghue
fonte