Android odbiornik edittext onchange

116

Wiem trochę o TextWatchertym, ale to działa na każdą postać, którą wchodzisz. Chcę odbiornika, który uruchamia się za każdym razem, gdy użytkownik kończy edycję. Czy to możliwe? Również w TextWatcherotrzymuję instancję Editableale muszę instancję EditText. Jak to osiągnąć?

EDYCJA : drugie pytanie jest ważniejsze. Proszę, odpowiedz na to.

zęby
źródło
1
spróbuj dodać fokus słuchacza, gdy editText zajmie fokus, to znaczy, że użytkownik zaczął go edytować, a gdy editText straci fokus, oznacza to, że edycja jest zakończona
Houcine

Odpowiedzi:

216

Po pierwsze, możesz sprawdzić, czy użytkownik zakończył edycję tekstu, jeśli EditTextutraci fokus lub jeśli naciśnie przycisk Gotowe (zależy to od implementacji i tego, co jest dla Ciebie najlepsze). Po drugie, nie możesz uzyskać EditTextinstancji w ramach TextWatchertylko wtedy, gdy zadeklarowałeś EditTextjako obiekt instancji. Nawet jeśli nie powinieneś edytować pliku EditTextwewnątrz, TextWatcherponieważ nie jest to bezpieczne.

EDYTOWAĆ:

Aby móc wprowadzić EditTextinstancję do swojej TextWatcherimplementacji, powinieneś spróbować czegoś takiego:

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) {}
        });
    }
}

Zauważ, że powyższy przykład może zawierać błędy, ale chciałem tylko pokazać przykład.

Cata
źródło
18

Martwiło mnie, że zaimplementowanie odbiornika dla wszystkich moich pól EditText wymagało posiadania brzydkiego, rozwlekłego kodu, więc napisałem poniższą klasę. Może się przydać każdemu, kto się na to natknie.

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);
}

Wdrożenie słuchacza jest teraz trochę czystsze.

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

Jeśli chodzi o to, jak często się uruchamia, można by zaimplementować sprawdzenie, aby uruchomić żądany kod //Do stuffpo określonym a

RNGuy
źródło
U mnie działa to bardzo dobrze, oszczędza wiele linii kodu! Jesteś geniuszem!
huypham99
12

Każdy, kto używa ButterKnife . Możesz użyć takich jak:

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

}
Prakash
źródło
6

Zrobiłem to używając 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
źródło
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
źródło
2
Na koniec jest jeden niepotrzebny}
Howard
2

TextWatchernie zadziałało dla mnie, ponieważ ciągle strzelało do każdego EditTexti nawzajem zepsuło wartości.

Oto moje rozwiązanie:

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();
    }
}

W związku z tym, używając tej getChildAt(xx)metody, możesz pobrać dowolny element w ListViewi uzyskać pojedynczy element za pomocą findViewById. Następnie poda najnowszą wartość.

user2566490
źródło
1

O ile mogę o tym myśleć, są tylko dwa sposoby, aby to zrobić. Skąd możesz wiedzieć, że użytkownik skończył pisać słowo? Albo po utracie fokusu, albo po kliknięciu przycisku „OK”. Nie sądzę, żebyś wiedział, że użytkownik nacisnął ostatnią postać ...

Więc zadzwoń onFocusChange(View v, boolean hasFocus)lub dodaj do niego przycisk i odbiornik kliknięć.

Nuno Gonçalves
źródło
0

Metoda Watcher odpala przy każdym wprowadzeniu znaku. Tak więc zbudowałem ten kod w oparciu o metodę 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);}       
        }
    });
}

Aby z niego skorzystać, po prostu zadzwoń w ten sposób:

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

    }}
);

Możesz zignorować funkcję comS, zastępując! ComS (dat.s, "" + EdTe.getText ()) funkcją! Equal. Jednak sama funkcja równości czasami nie działa poprawnie w czasie wykonywania.

Odbiornik onChange zapamięta stare dane EditText, gdy użytkownik fokusuje pisanie, a następnie porówna nowe dane, gdy użytkownik straci fokus lub przeskoczy do innego wejścia. Jeśli porównując stary ciąg, a nie ten sam nowy ciąg, uruchamia pracę.

Jeśli masz tylko 1 EditText, będziesz musiał stworzyć funkcję ClearFocus, tworząc Ultimate Secret Transparent Micro EditText 😸 poza oknami 😽 i zażądaj skupienia się na nim, a następnie ukryj klawiaturę za pomocą Import Method Manager.

phnghue
źródło