一:重写ListView使其默认不可滑动。这样解决了条目中的EditText与键盘冲突的问题,冲突是指弹出键盘后EditText光标消失;关闭键盘后ListView默认是会刷新使你输入的内容又消失了。
二:用ScrollView包裹重写的NoScrollListView,使其获得滑动效果。
三:有多少个item,在adapter中就viewType就分多少泪。这样使得各个条目是独立的,方便afterTextChanged方法将你编辑的EditText的内容重新存入集合对应位置,同时不出现各个item的editText内容重复的问题。
代码如下:
public class Person {
String name;
String age;
String desc;
public Person(String age, String desc, String name) {
this.age = age;
this.desc = desc;
this.name = name;
}
public String getAge() {
return age;
}
public void setAge(String age) {
this.age = age;
}
public String getDesc() {
return desc;
}
public void setDesc(String desc) {
this.desc = desc;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
@Override
public String toString() {
return "Person{" +
"age='" + age + '\'' +
", name='" + name + '\'' +
", desc='" + desc + '\'' +
'}';
}
}
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context="com.dev.think.testlistview.MainActivity">
<Button
android:id="@+id/bt_save"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="保存" />
<ScrollView
android:layout_width="match_parent"
android:layout_height="match_parent">
<com.dev.think.testlistview.NoScrollListView
android:id="@+id/lv"
android:layout_width="match_parent"
android:layout_height="match_parent">
</com.dev.think.testlistview.NoScrollListView>
</ScrollView>
</LinearLayout>
条目布局:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="50dp"
android:orientation="horizontal"
android:gravity="center_vertical">
<TextView
android:id="@+id/tv_name"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_weight="1"
android:gravity="center"
android:text="名字"/>
<EditText
android:id="@+id/et_age"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_weight="1"
android:gravity="center"
android:text="12"/>
<TextView
android:id="@+id/tv_desc"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_weight="1"
android:gravity="center"
android:text="描述"/>
<Button
android:id="@+id/bt_delete"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="DEL"/>
</LinearLayout>
MainActivity
public class MainActivity extends AppCompatActivity implements View.OnClickListener,PersonAdapter.IListChangeListener {
private NoScrollListView lv;
private List<Person> mlist;
private PersonAdapter adapter;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
initView();
initData();
}
private void initData() {
mlist.add(new Person("21","对方答复","各个"));
mlist.add(new Person("26","地方","少的地方"));
mlist.add(new Person("34","地是","到的"));
mlist.add(new Person("76","爽肤水","就"));
mlist.add(new Person("46","发","好的"));
mlist.add(new Person("28","阿怪","同条件"));
mlist.add(new Person("90","啥随访","日日日"));
mlist.add(new Person("93","预约","恩恩"));
mlist.add(new Person("35","已一","不能"));
mlist.add(new Person("11","成都","地方"));
mlist.add(new Person("19","水电费","但是"));
mlist.add(new Person("23","啊啊","密码"));
mlist.add(new Person("29","匹配","澎湃"));
mlist.add(new Person("39","圈圈","请求"));
mlist.add(new Person("59","热天","荣耀"));
mlist.add(new Person("69","如医","人员"));
lv.setAdapter(adapter);
}
private void initView() {
findViewById(R.id.bt_save).setOnClickListener(this);
mlist = new ArrayList<Person>();
lv = (NoScrollListView) findViewById(R.id.lv);
adapter = new PersonAdapter(this,mlist,this);
}
/**
* 模拟保存集合数据
* @param v
*/
@Override
public void onClick(View v) {
Log.i("yin","输出:"+mlist.toString());
}
@Override
public void onDelete(int position) {
mlist.remove(position);
adapter.notifyDataSetChanged();
}
@Override
public void afterTextChanged(int position, String content) {
mlist.get(position).setAge(content);
}
}
adapter:
public class PersonAdapter extends BaseAdapter {
private List<Person> mlist;
private Context context;
private IListChangeListener listener;
public PersonAdapter(Context context, List<Person> mlist, IListChangeListener listener) {
this.context = context;
this.mlist = mlist;
this.listener = listener;
}
@Override
public int getCount() {
return mlist.size();
}
@Override
public Object getItem(int position) {
return mlist.get(position);
}
@Override
public long getItemId(int position) {
return position;
}
@Override
public int getItemViewType(int position) {
return position;
}
/**
* 因为我想使用TextWatcher将条目中的EditText编辑后的内容重新赋值到集合中,
* 如果不这样给viewType分类,赋值后会出现每一个条目的EditText的值重复的问题,
* 所以想到有多少个条目就分多少类viewType
*
* @return
*/
@Override
public int getViewTypeCount() {
return mlist.size();
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
//循环处理所有ViewType
for (int i = 0; i < mlist.size(); i++) {
if (i == getItemViewType(position)) {
ViewHolder viewHolder = null;
if (convertView == null) {
convertView = View.inflate(context, R.layout.list_item, null);
viewHolder = new ViewHolder(convertView);
convertView.setTag(viewHolder);
} else {
viewHolder = (ViewHolder) convertView.getTag();
}
bindData(viewHolder, position);
}
}
return convertView;
}
private void bindData(final ViewHolder viewHolder, final int position) {
final Person vo = mlist.get(position);
viewHolder.name.setText(vo.getName());
viewHolder.age.setText(vo.getAge());
viewHolder.desc.setText(vo.getDesc());
viewHolder.age.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) {
//内容变化后重新赋值给集合
listener.afterTextChanged(position, s.toString());
}
});
viewHolder.delete.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
listener.onDelete(position);
}
});
}
static class ViewHolder {
TextView name;
EditText age;
TextView desc;
Button delete;
public ViewHolder(View view) {
name = (TextView) view.findViewById(R.id.tv_name);
age = (EditText) view.findViewById(R.id.et_age);
desc = (TextView) view.findViewById(R.id.tv_desc);
delete = (Button) view.findViewById(R.id.bt_delete);
}
}
public interface IListChangeListener {
void onDelete(int position);//删除条目
void afterTextChanged(int position, String content);//重新给对应位置的集合元素赋值
}
}
不可滚动的ListView
/**
* 不可滚动的ListView,一般用ScrollView包裹
*/
public class NoScrollListView extends ListView {
public NoScrollListView(Context context) {
super(context);
}
public NoScrollListView(Context context, AttributeSet attrs) {
super(context, attrs);
}
public NoScrollListView(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
}
@TargetApi(Build.VERSION_CODES.LOLLIPOP)
public NoScrollListView(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) {
super(context, attrs, defStyleAttr, defStyleRes);
}
@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
int expandSpec = MeasureSpec.makeMeasureSpec(Integer.MAX_VALUE >> 2,MeasureSpec.AT_MOST);
super.onMeasure(widthMeasureSpec, expandSpec);
}
}