日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 运维知识 > Android >内容正文

Android

android listview edittext 事件,Android ListView item中含有Edittext 中一些坑

發(fā)布時間:2023/12/15 Android 39 豆豆
生活随笔 收集整理的這篇文章主要介紹了 android listview edittext 事件,Android ListView item中含有Edittext 中一些坑 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

今天做一個界面. ?是?一個列表 .列表中有spinner,button,edittext等控件

首次打開需要展示,用戶可以修改,修改后數(shù)據(jù)保存.

??在保存Edittext控件上的值的時候,用的etRemark.addTextChangedListener(myTextWatcher)????????

注意?是addTextChangedListener

來監(jiān)聽Edittext的值,如果變化的話 就將變化的值直接存入數(shù)據(jù)集對象中.

這樣存在了幾個問題

1,我們改變了一個editext的值后通過logcat 發(fā)現(xiàn)?onTextChanged會被多次調用.

我們知道listview在第一次展示的時候會多次調用getView方法來確定itemView的高度.

多次調用就會給同一個editext控件 add多個TextChangedListener.

public?void?addTextChangedListener(TextWatcher?watcher)?{

if?(mListeners?==?null)?{

mListeners?=?new?ArrayList();

}

mListeners.add(watcher);

}

也就導致了為什么輸入一次 會多次調用TextChangedListener的方法.

2,listview滑動后發(fā)現(xiàn)editext的值會混亂.

如果一屏為3個item

具體混亂特征為首次加載完listview的時候.

第一次滑動,滑倒第二頁的時候第二屏的第一個(position=3)會把第一屏的第一個item(position=0)給覆蓋掉.如果position=3的這個item為空的話.再滑到頂部則發(fā)現(xiàn)position的item 也為空了.

這個時候在position=0的item中的editext的值改變的時候,往下滑發(fā)現(xiàn)position=3的也改變了.

我們都知道這是convertView復用的結果.

具體原因是,在加載第二屏第一個的item的時候調用的getView()方法,

EditText?et=?ViewHolder.get(convertView,?R.id.item_editText);

et.setText(datas.get(itemPosition).editTextValue);

et.addTextChangedListener(myTextWatcher);

我的代碼里有一個settext(value)方法,,因為和第一屏的item用的是同一個editext對象

這個時候會觸發(fā)TextChanged事件,因為用的是addTextChangedListener方法.所以這個editext中有多個listener

插入Textwatcher代碼.

class?MyTextWatcher?implements?TextWatcher{

private?int?position;

public?MyTextWatcher(int?position)?{

super();

this.position?=?position;

}

@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)?{

datas.get(position).editTextValue=?s.toString();

}

}

也會觸發(fā),所以這個時候,就會調用afterTextChanged()方法

因為我的TextWatcher對象中維護了一個position的全局變量,其實這個TextWatcher的position為0.則把position為3的edittext的值賦給了datas.get(0)editTextValue;所以存在了第一次滑動的時候會發(fā)現(xiàn)值會被覆蓋的問題.

等到多次滑動后一個editext控件就會add多個TextWatcher對象,這個時候一旦修改一個editext的值,就會調用多個TextWatcher的textChanged回調,也就是為什么改一個position為0的editext.怎么也把position為3的editext也改了.

其實修改的是datas中的值.

怎么解決呢.看了半天廢話終于到點子上了.

1 不復用converView,并且為listview的item指定高度阻止首次加載多次調用getView()方法.

但是這樣每次都去inflate布局文件實在太坑了.

2 不用addTextChangedListener 改用?setOnFocusChangeListener() .靠失去焦點來觸發(fā)保存數(shù)據(jù)

個人嘗試過后沒問題.但是失去焦點.總感覺有點不靠譜.不知道是不是web開發(fā)的后遺癥,怕如果用戶輸入完后直接點擊別的地方的按鈕,會不會不會觸發(fā),(經(jīng)過原生的android測試,發(fā)現(xiàn)無論是關閉輸入框,還是點擊別的地方的按鈕,都會觸發(fā)焦點丟失事件) ?應該可以放心使用

3. 還用addTextChangedListener()來觸發(fā)保存,不過在editext賦值之前先remov掉之前的TextWatcher

查看源碼removeTextChangedListener()方法 用的是

public?void?removeTextChangedListener(TextWatcher?watcher)?{

if?(mListeners?!=?null)?{

int?i?=?mListeners.indexOf(watcher);

if?(i?>=?0)?{

mListeners.remove(i);

}

}

}

list的indexOf()方法.

則需要重寫TextWatcher的 equals()方法.

見代碼

MyTextWatcher?myTextWatcher?=?new?MyTextWatcher(itemPosition);

et.removeTextChangedListener(myTextWatcher);

et.setText(datas.get(itemPosition).editTextValue);

et.addTextChangedListener(myTextWatcher);

MyTextWatcher類中重寫

@Override

public?boolean?equals(Object?o)?{

return?true;

}

這樣就可以完美解決了;

總結

以上是生活随笔為你收集整理的android listview edittext 事件,Android ListView item中含有Edittext 中一些坑的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內容還不錯,歡迎將生活随笔推薦給好友。