众所周知,使用listview时,出现大量数据的时候都会采用复用的写法,而recyclerView里已经有了复用的机制了。而因为复用的关系,如果item布局当中涉及到edittext等一些控件时,就会出现因为复用而产生的数据错乱。
特别是在item设置数据的时候,如果你的edittext有加入TextWatcher事件监听,而且有在afterTextChanged对文本进行操作的话,这时候,你没办法给edittext设置文本,因为一设置文本,就会触发afterTextChanged方法进行操作,然后就会出现一系列问题。
解决方式是,在加入TextWatcher事件之前,先判断edittext是否已经加入了TextWatcher事件,如果有,就先移除,然后给edittext设置文本之后再加入TextWatcher事件,这里可以通过tag标签来处理,具体实现方法如下:
(java写法)
//判断是否有TextWatcher监听事件,有的话先移除
if (holder.editText.getTag(R.id.search_key) instanceof TextWatcher){
holder.editText.removeTextChangedListener(((TextWatcher) holder.editText.getTag(R.id.search_key)));
}
//移除了TextWatcher事件后设置item对应的文本
holder.editText.setText("新文本");
TextWatcher textWatcher=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) {
beans.get(i).setValue(s.toString());
}
};
//设置tag为TextWatcher
holder.editText.addTextChangedListener(textWatcher);
holder.editText.setTag(R.id.search_key,textWatcher);
(kotlin写法)
if (editText.getTag(R.id.item_add_inputs) is TextWatcher){
editText.removeTextChangedListener(editText.getTag(R.id.item_add_inputs) as TextWatcher)
}
editText.setText(data.content)
var textWatcher:TextWatcher = object : TextWatcher{
override fun afterTextChanged(s: Editable?) {
data.content = s.toString()
}
override fun beforeTextChanged(s: CharSequence?, start: Int, count: Int, after: Int) {
}
override fun onTextChanged(s: CharSequence?, start: Int, before: Int, count: Int) {
}
}
editText.addTextChangedListener(textWatcher)
editText.setTag(R.id.item_add_inputs,textWatcher)
已经第二次遇到这个问题了,所以做一下记录。
QQ:361561789
可直接加Q联系