Hitungan karakter langsung untuk EditText

101

Saya bertanya-tanya apa cara terbaik untuk melakukan penghitungan karakter langsung dari kotak teks edit di Android. Saya melihat ini tetapi sepertinya saya tidak bisa memahaminya.

Untuk menjelaskan masalahnya, saya memiliki EditText dan saya mencoba membatasi karakter menjadi 150. Saya dapat melakukan ini dengan filter input, namun saya ingin menunjukkan tepat di bawah kotak teks jumlah karakter yang telah dimasukkan pengguna (Hampir seperti yang dilakukan stack overflow sekarang).

Jika seseorang dapat menulis potongan kecil kode contoh atau mengarahkan saya ke arah yang benar, saya akan sangat menghargainya.

Taylor Perkins
sumber

Jawaban:

153

Anda dapat menggunakan TextWatcher untuk melihat kapan teks telah berubah

private TextView mTextView;
private EditText mEditText;
private final TextWatcher mTextEditorWatcher = new TextWatcher() {
        public void beforeTextChanged(CharSequence s, int start, int count, int after) {
        }

        public void onTextChanged(CharSequence s, int start, int before, int count) {
           //This sets a textview to the current length
           mTextView.setText(String.valueOf(s.length()));
        }

        public void afterTextChanged(Editable s) {
        }
};

Anda menyetel TextWatcher untuk teks editan dengan

mEditText.addTextChangedListener(mTextEditorWatcher);
Cameron Ketcham
sumber
5
mencoba ini, bekerja dengan baik! harus dipilih sebagai jawaban yang benar!
Patrick Boos
2
cara terbaik untuk menambahkan hitungan, katakan di kanan bawah kotak teks. Perpanjang edit teks dan gambar string secara manual?
Beruang
1
Terima kasih, saya juga mengerti, tetapi cara menghitung mundur dalam urutan terbalik seperti 150.149.148.147 .... saat memasukkan teks.
vinay Maneti
6
Ini diselesaikan dengan mengganti dengan baris ini mTextView.setText (String.valueOf (150-s.length ())); sebagai ganti mTextView.setText (String.valueOf (s.length ()));
vinay Maneti
Masalah saya mirip dengan @ Bear. Saya perlu menunjukkan teks hitung mundur ini tepat di bawah teks edit. Setiap orang memiliki sesuatu untuk dibagikan dalam referensi ini. Terima kasih.
Suresh Sharma
107

Anda dapat melakukan penghitungan karakter dari xml itu sendiri menggunakan pembungkus TextInputLayout untuk EditText yang diperkenalkan di SupportLibrary v23.1

Cukup bungkus EditText Anda dengan TextInputLayout dan setel CounterEnabled menjadi true dan Setel counterMaxLength.

<android.support.design.widget.TextInputLayout
    android:id="@+id/textContainer"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    app:counterEnabled="true"
    app:counterMaxLength="20"
    >
    <EditText
        android:id="@+id/text"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:hint="Text Hint"
        />
</android.support.design.widget.TextInputLayout>

Anda akan mendapatkan efek material seperti ini

Anda dapat menggunakan counterOverflowTextAppearance , counterTextAppearance untuk mengatur gaya penghitung.

EDIT

Dari dokumentasi Android.

Kelas TextInputEditText disediakan untuk digunakan sebagai turunan dari tata letak ini. Menggunakan TextInputEditText memungkinkan TextInputLayout memiliki kontrol yang lebih besar atas aspek visual dari input teks apa pun. Contoh penggunaannya adalah sebagai berikut:

     <android.support.design.widget.TextInputLayout
         android:layout_width="match_parent"
         android:layout_height="wrap_content">

     <android.support.design.widget.TextInputEditText
             android:layout_width="match_parent"
             android:layout_height="wrap_content"
             android:hint="@string/form_username"/>

 </android.support.design.widget.TextInputLayout>

TextInputLayout TextInputEditText

Midhun Vijayakumar
sumber
3
ini persis seperti yang saya cari :) a clean, support-library impl. terima kasih
VPZ
3
Harus menjadi jawaban yang Diterima! Saya benar-benar merindukan atribut itu!
sud007
24

Anda dapat melakukannya dengan TextInputLayoutdan perpustakaan compat dengan:

app:counterEnabled="true"
app:counterMaxLength="420"

dan selesai:

<android.support.design.widget.TextInputLayout
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    app:counterEnabled="true"
    app:counterMaxLength="420">

    <EditText
      android:layout_width="match_parent"
      android:layout_height="wrap_content"
      android:maxLength="420" />

</android.support.design.widget.TextInputLayout>
Daniel Gomez Rico
sumber
Bagus ini berhasil untuk saya, tetapi bagaimana saya mengubah warna penghitung?
Erich García
14

di xml tambahkan atribut ini untuk editText

    android:maxLength="80"

di java tambahkan pendengar ini

  ed_caption.addTextChangedListener(new TextWatcher() {
        @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) {
            tv_counter.setText(80 - s.toString().length() + "/80");

        }
    });
Amal Kronz
sumber
7

Sangat Sederhana Ikuti petunjuk di bawah ini:

==== Tambahkan ke Impor Anda ===

import android.text.Editable;
import android.text.TextWatcher;

===== Tentukan ini =====

private TextView sms_count;

========== Inside On Create =====

sms_count = (TextView) findViewById(R.id.textView2);


final TextWatcher txwatcher = new TextWatcher() {
   public void beforeTextChanged(CharSequence s, int start, int count, int after) {
   }

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

      sms_count.setText(String.valueOf(s.length()));
   }

   public void afterTextChanged(Editable s) {
   }
};

sms_message.addTextChangedListener(txwatcher);
Depinder Bharti
sumber
5
    You can use TextWatcher class to see text has changed and how much number of character remains.Here i have set counter of 140 characters.

    EditText typeMessageToPost;
    TextView number_of_character;
public void onCreate(Bundle savedBundleInstance) {
        super.onCreate(savedBundleInstance);
setContentView(R.layout.post_activity);
typeMessageToPost.addTextChangedListener(mTextEditorWatcher);
}
private final TextWatcher mTextEditorWatcher=new TextWatcher() {

        @Override
        public void onTextChanged(CharSequence s, int start, int before, int count) {
            // TODO Auto-generated method stub

        }

        @Override
        public void beforeTextChanged(CharSequence s, int start, int count,
                int after) {
            // TODO Auto-generated method stub

        }

        @Override
        public void afterTextChanged(Editable s) {
            // TODO Auto-generated method stub
            number_of_character.setText(String.valueOf(140-s.length()));
        }
    };
Rana Pratap Singh
sumber
Terima kasih @RavishSharma :) Saya menghargai komentar Anda.
Rana Pratap Singh
4

Cukup setel 2 baris ini di TextInputLayoutfile XML Anda:

app:counterEnabled="true"
app:counterMaxLength="200"
mortezahosseini
sumber
Great tidak tahu tentang itu. Tampaknya selalu menjadi solusi yang lebih baik untuk menggabungkan Edittext ke dalam TextInputLayout.
Stefan Sprenger
3

Solusi ini menggunakan Kotlindan menunjukkan jumlah karakter yang tersisa. Selain itu, jika jumlah karakter saat ini melebihi batas 50, warna teks akan berubah menjadi merah.

Kotlin

private val mTitleTextWatcher = object : TextWatcher {
    override fun beforeTextChanged(s: CharSequence, start: Int, count: Int, after: Int) {}

    override fun onTextChanged(s: CharSequence, start: Int, before: Int, count: Int) {
        if(YOUR_EDIT_TEXT_ID.text.toString().trim().length < 51){
            YOUR_CHAR_LEFT_TEXTVIEW_ID.text = (50 - YOUR_EDIT_TEXT_ID.text.toString().trim().length).toString()
            YOUR_CHAR_LEFT_TEXTVIEW_ID.setTextColor(Color.BLACK)
        }
        else{
            YOUR_CHAR_LEFT_TEXTVIEW_ID.text = "0"
            YOUR_CHAR_LEFT_TEXTVIEW_ID.setTextColor(Color.RED)
        }
    }

    override fun afterTextChanged(s: Editable) {}
}

Juga, jangan lupa untuk menambahkan TextWatcherke AndaEditText

YOUR_EDIT_TEXT_ID.addTextChangedListener(mTitleTextWatcher)
grantespo
sumber
3

Anda dapat menambahkan penghitung ke TextInputEditText yang dibungkus dalam TextInputLayout. Seperti yang Anda lihat di contoh, counterEnabledmengaktifkan fitur ini dan counterMaxLenghmenentukan jumlah karakternya.

<com.google.android.material.textfield.TextInputLayout
        android:id="@+id/til_title"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        app:counterEnabled="true"
        app:counterMaxLength="50">
    <com.google.android.material.textfield.TextInputEditText
            android:id="@+id/et_title"
            android:layout_width="match_parent"
            android:layout_height="match_parent"/>
</com.google.android.material.textfield.TextInputLayout>
Sathish
sumber
1

Saya menemui masalah yang sama dan saya mencoba metode Cameron. Ini berfungsi tetapi ada bug kecil: Jika pengguna menggunakan salin dan tempel, maka gagal menghitung karakter. Jadi saya sarankan untuk dilakukan setelah teks diubah, seperti di bawah ini:

    private final TextWatcher mTextEditorWatcher = new TextWatcher() {
         public void beforeTextChanged(CharSequence s, int start, int count, int after) {

         }

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

         }

          public void afterTextChanged(Editable s) {
             //This sets a textview to the current length
             mTextView.setText(String.valueOf(s.length()));
         }
    };
GilbertLee
sumber
1

Gunakan android: maxLength = "140"

Seharusnya itu berhasil. :)

Semoga membantu

Alireza Ghanbarinia
sumber
0

Coba lakukan sesuatu seperti ini.

Solusi ini mungkin lebih berkinerja dibandingkan dengan mendapatkan CharSequence.length. Setiap kali Anda mengetuk soft keyboard, acara akan menyala; oleh karena itu, jika Anda melakukan panjang, itu akan menghitung CharSequence setiap kali, yang mungkin melambat jika Anda mulai masuk ke CharSequnce besar. Pendengar acara pada perubahan teks menyesuaikan hitungan sebelum dan sesudah. Ini berfungsi dengan baik untuk nilai kenaikan dan penurunan

@Override
        public void beforeTextChanged(CharSequence charSequence, int start, int count, int after) {
            int tick = start + after;
            if(tick < mMessageMax) {
                int remaining = mMessageMax - tick;
                ((TextView)findViewById(R.id.contact_us_chars)).setText(String.valueOf(remaining));
            }
        }
Victor J. Garcia
sumber
Ini adalah permosrmatce efek, TextWatcher adalah Pendekatan terbaik untuk ini
Naveed Ahmad
0

coba ini

private TextWatcher textWatcher = new TextWatcher() {
    @Override
    public void beforeTextChanged(final CharSequence s, final int start, final int count, final int after) {
        editText.post(new Runnable() {
            @Override
            public void run() {
                if (length < 100) {
                    if (count > 0 && after <= 0)/*remove emoij*/ {
                        length--;
                    } else if (count > after)/*remove text*/ {
                        length--;
                    } else if (count == 0 && after > 1)/*emoij*/ {
                        ++length;
                    } else if (count == 0 && after == 1)/*Text*/ {
                        ++length;
                    } else if (count > 0 && after > 1) {
                        ++length;
                    }
                    if (s.length() <= 0)
                        length = 0;
                    Log.w("MainActivity", " Length: " + length);
                } else {
                    if (count > 0 && after <= 0)/*remove emoij*/ {
                        length--;
                    } else if (count > after)/*remove text*/ {
                        length--;
                    }
                    Log.w("MainActivity", " Length: " + length);
                }

                if (length == 100) {
                    editText.setFilters(new InputFilter[]{new InputFilter.LengthFilter(s.length())});
                } else {
                    editText.setFilters(new InputFilter[]{});
                }
            }
        });
    }

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

    }

    @Override
    public void afterTextChanged(Editable s) {

    }
};

`

Nankai
sumber
0

Cara yang jelas;

abstract class CharacterWatcher : TextWatcher {
    override fun afterTextChanged(text: Editable?) {
        afterCharacterChanged(text?.lastOrNull(), text?.length)
    }

    override fun beforeTextChanged(text: CharSequence?, start: Int, count: Int, before: Int) {}

    override fun onTextChanged(text: CharSequence?, start: Int, before: Int, count: Int) {}

    abstract fun afterCharacterChanged(char: Char?, count: Int?)
}



 editText.addTextChangedListener(new CharacterWatcher() {
            @Override
            public void afterCharacterChanged(@Nullable Character character, @Nullable Integer count) {
                action()
            }
        });
Cafer Mert Ceyhan
sumber