关于ListView中包含EditText数据复用引起异常的解决方案详解手机开发
2023-06-13 09:20:13 时间
前几天测试提了一个bug,在ListView中添加留言信息,导致错乱的问题。实际上就是ListView需要添加一个EditText,复用导致错乱的问题,这个问题以前也遇到过。诸如,ListView嵌套EditText、CheckBox等焦点问题都会出现复用的错乱,其根源就是ViewHolder的复用问题。
说说上面的问题吧,保存item中EditText中的数据,导致数据复用的时候都给设置了值。我们在最外层存了一个Map
Map Integer, String edItem;
监听每个Item的输入(OnTextChangedListener),并在afterTextChanged()将值保存到Map中去。
holder.editText.setOnEditorActionListener(new TextView.OnEditorActionListener() { @Override public boolean onEditorAction(TextView textView, int i, KeyEvent keyEvent) { if ((edItem.size() == inputContainer.size())) { // 添加一项控件 edItem.put(edindex, "edindex"); return false; });
但是这里出现了一个问题,由于复用,导致,每一个Item都被赋值了,所以我们要解决这个问题得从源头阻断给EditText赋值,也就是在OnTextChange方法里面,我们判断一下,如果用户操作的是当前的Item,我们就给Map赋值,否则不赋值,或者赋值为空值。
所以这个时候我们要对EditText的触摸事件做监听:
editText.setOnTouchListener(new View.OnTouchListener() { public boolean onTouch(View view, MotionEvent event) { if (event.getAction() == MotionEvent.ACTION_UP) { index = position; return false; });
然后我们在TextWatcher的onTextChanged判断一下:
public void onTextChanged(CharSequence text, int start, int before, int count) { //如果该edittext有默认内容,还要在if那里进行过滤 if (index =0 text.length() 0 index== position) { mData.get(index).put("input", text.toString()); }
这样就解决了复用的问题,完整代码:
public class ListViewTestAdapter extends BaseAdapter { private List Map String, String mData; private LayoutInflater mInflater; private Context mContext; private int index = -1; public ListViewTestAdapter(Context context, List Map String, String data) { this.mContext = context; this.mData = data; this.mInflater = LayoutInflater.from(context); @Override public int getCount() { return mData.size(); @Override public Object getItem(int position) { return mData.get(position); @Override public long getItemId(int position) { return position; @Override public View getView(final int position, View convertView, ViewGroup parent) { ViewHolder holder = new ViewHolder(); if (convertView == null) { convertView = mInflater.inflate(R.layout.main_function_listitem3, null); holder.title = (TextView) convertView.findViewById(R.id.txtTitle); holder.editText = (EditText) convertView.findViewById(R.id.input); convertView.setTag(holder); } else { holder = (ViewHolder) convertView.getTag();
public void beforeTextChanged(CharSequence text, int start, int count, int after) { public void onTextChanged(CharSequence text, int start, int before, int count) { //如果该edittext有默认内容,还要在if那里进行过滤 if (index =0 text.length() 0 index == position ) { mData.get(index).put("input", text.toString()); }); holder.title.setText(mData.get(position).get("title")); holder.editText.setText(mData.get(position).get("input")); editText.clearFocus(); if (index != -1 index == position) { editText.requestFocus(); final ViewHolder finalHolder = holder; convertView.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { Toast.makeText(mContext, finalHolder.title.getText(), Toast.LENGTH_SHORT).show(); }); return convertView; public final class ViewHolder { public TextView title; public EditText editText; }
5663.html
app程序应用开发手机开发无线开发移动端开发相关文章
- SPL工业智能:发现时序数据的异常
- 无监督域适应、人体解析、视频异常检测和水果成熟度分类,推荐本周那些有意思的CV综述
- springboot validated注解数据校验 异常处理
- mysql分组和排序同时使用时查询数据异常
- AI视频大数据智能分析平台EasyCVR因通道达到上限出现播放异常的排查
- 震惊!Linux调用C Main,居然使用的缺页异常
- 捕获其他线程的异常详解编程语言
- Linux系统异常信号及其处理方法(linux异常信号)
- 异MySQL 月份数据异常分析(mysql月份差)
- 处理解决Redis异常:从原因到解决方案(redis异常)
- MySQL异常频繁,数据操作受阻(mysql一直出错)
- 异常解决Oracle语句异常的尝试(oracle中的语句出现)
- MySQL同步异常,疑似数据不一致,及时报警(mysql不同步了 报警)
- Oracle主键数据异常分析与处理(oracle主键数据异常)
- Redis队列处理异常情况(redis 队列异常)
- php5编程中的异常处理详细方法介绍
- Spring事务管理只对出现运行期异常进行回滚