我正在实施可扩展ListView 。每个子项都有一个文本视图和一个EditText。
问题是,假设一个组有10个项目/行。我在第1行和第2行输入了一个数据。当我向下滚动到第6行和第7行时。它们已经有一个文本(第6行包含第1行数据,第7行包含第2行数据)。
我明白为什么会发生这种情况。 这是因为,当我在第1行输入时,我当前可以看到第1行到第5行。当我向下滚动以查看剩余的行时。 自动调用getChildView()以显示剩余的行和其他数据,因为所有editTexts具有相同的ID 。因此,Next View具有与先前视图中相同的数据。 此处类似问题:ArrayAdapter's getView() method getting called automatically on load and while scrolling listview 我试过:
这是我的 ExpandableListAdapter.java :
package com.syapaa;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import android.content.Context;
import android.content.SharedPreferences;
import android.graphics.Typeface;
import android.text.Editable;
import android.text.TextUtils;
import android.text.TextWatcher;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.BaseExpandableListAdapter;
import android.widget.EditText;
import android.widget.TextView;
import android.widget.Toast;
import static android.content.Context.MODE_PRIVATE;
public class ExpandableListAdapter extends BaseExpandableListAdapter {
int j=1;
int neww=0;
EditText edt;
private Context _context;
private List<String> _listDataHeader; // header titles
// child data in format of header title, child title
private HashMap<String, List<String>> _listDataChild;
public ExpandableListAdapter(Context context, List<String> listDataHeader,
HashMap<String, List<String>> listChildData) {
this._context = context;
this._listDataHeader = listDataHeader;
this._listDataChild = listChildData;
}
@Override
public Object getChild(int groupPosition, int childPosititon) {
return this._listDataChild.get(this._listDataHeader.get(groupPosition))
.get(childPosititon);
}
@Override
public long getChildId(int groupPosition, int childPosition) {
return childPosition;
}
@Override
public View getChildView(int groupPosition, final int childPosition,
boolean isLastChild, View convertView, ViewGroup parent) {
//Don't change://///////////////////////////////-/////////////////////
final String childText = (String) getChild(groupPosition, childPosition);
if (convertView == null) {
LayoutInflater infalInflater = (LayoutInflater) this._context
.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
convertView = infalInflater.inflate(R.layout.list_item, null);
}
TextView txtListChild = (TextView) convertView.findViewById(R.id.lblListItem);
//////////////------------------------------------------------------------/////
//For Sharing my ID(I am Group PG):
SharedPreferences prefb = convertView.getContext().getSharedPreferences("my_prefb", MODE_PRIVATE);
SharedPreferences.Editor editb = prefb.edit();
editb.putInt("GR", groupPosition );
editb.commit();
if(childPosition==0){
//Receiving 1857 of OnClick
SharedPreferences phobjc = convertView.getContext().getSharedPreferences("my_prefd", 0);
neww = phobjc.getInt("BRNDM", 0);
phobjc.edit().clear().commit();
}
if(neww==1857){
edt=convertView.findViewById(R.id.marks);
String abc=edt.getText().toString();
j=childPosition+1;
//For Sharing data entered in list:
SharedPreferences prefa = convertView.getContext().getSharedPreferences("my_prefa", MODE_PRIVATE);
SharedPreferences.Editor edita = prefa.edit();
edita.putString("PH"+j, abc );
edita.commit();
Toast.makeText(convertView.getContext(),"Sharing "+ abc+"with "+"PH"+j,Toast.LENGTH_SHORT).show();
if(isLastChild==true){
int tellmaxitems=childPosition+1;
//Sharing No of Items in Group
SharedPreferences prefd = convertView.getContext().getSharedPreferences("noofitems", MODE_PRIVATE);
SharedPreferences.Editor editd = prefd.edit();
editd.putInt("NoItems", tellmaxitems );
editd.commit();
}
}
txtListChild.setText(childText);
return convertView;
}
@Override
public int getChildrenCount(int groupPosition) {
return this._listDataChild.get(this._listDataHeader.get(groupPosition)).size();
}
@Override
public Object getGroup(int groupPosition) {
return this._listDataHeader.get(groupPosition);
}
@Override
public int getGroupCount() {
return this._listDataHeader.size();
}
@Override
public long getGroupId(int groupPosition) {
return groupPosition;
}
@Override
public View getGroupView(int groupPosition, boolean isExpanded,
View convertView, ViewGroup parent) {
String headerTitle = (String) getGroup(groupPosition);
if (convertView == null) {
LayoutInflater infalInflater = (LayoutInflater) this._context
.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
convertView = infalInflater.inflate(R.layout.list_group, null);
}
TextView lblListHeader = (TextView) convertView
.findViewById(R.id.lblListHeader);
lblListHeader.setText(headerTitle);
return convertView;
}
@Override
public boolean hasStableIds() {
return false;
}
@Override
public boolean isChildSelectable(int groupPosition, int childPosition) {
return true;
}
}
这是 Tab1.Java ,我在列表/行中添加项目:
package com.syapaa;
import android.content.Context;
import android.content.Intent;
import android.content.SharedPreferences;
import android.os.CountDownTimer;
import android.support.v4.app.Fragment;
import android.os.Bundle;
import android.support.v4.widget.SwipeRefreshLayout;
import android.telephony.SmsManager;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.view.inputmethod.InputMethodManager;
import android.widget.Button;
import android.widget.EditText;
import android.widget.Toast;
import android.widget.ExpandableListView;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import static android.content.Context.MODE_PRIVATE;
public class Tab1 extends Fragment {
int grtoShow=0;
int prGroup=-1;
String last="ls.txt";
SwipeRefreshLayout rfrsh;
ExpandableListAdapter listAdapter;
ExpandableListView expListView;
List<String> listDataHeader;
HashMap<String, List<String>> listDataChild;
Button btn;
@Override
public View onCreateView(LayoutInflater inflater,ViewGroup container,Bundle savedInstanceState) {
final View v = inflater.inflate(R.layout.tab1, container, false);
// get the listview
expListView = v.findViewById(R.id.lvExp);
//Pull Down to Refresh ListView///////////////////////////////////////////////////////
rfrsh=v.findViewById(R.id.refresh);
rfrsh.setOnRefreshListener(new SwipeRefreshLayout.OnRefreshListener() {
@Override
public void onRefresh() {
Intent intent = getActivity().getIntent();
intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_NEW_TASK
| Intent.FLAG_ACTIVITY_NO_ANIMATION);
getActivity().overridePendingTransition(0, 0);
getActivity().finish();
getActivity().overridePendingTransition(0, 0);
startActivity(intent);
rfrsh.setRefreshing(false);
}
});
////-------Refresh Logic Ends here----------------------------------------/////////////
////////Expand Only One Group at a Time (collapse previously Expanded Gruop)///////////////
expListView.setOnGroupExpandListener(new ExpandableListView.OnGroupExpandListener() {
@Override
public void onGroupExpand(int i) {
new CountDownTimer(120, 1) {
public void onFinish() {
// When timer is finished
// Execute your code here
//Taking Group ID (which group was expanded last)
SharedPreferences phobjb = getContext().getSharedPreferences("my_prefb", 0);
final int i= phobjb.getInt("GR", 0);
}
public void onTick(long millisUntilFinished) {}
}.start();
if ((prGroup != -1) && (i != prGroup)) {
expListView.collapseGroup(prGroup);
InputMethodManager imm = (InputMethodManager)getActivity().getSystemService(Context.INPUT_METHOD_SERVICE);
try{imm.hideSoftInputFromWindow(v.getWindowToken(), 0);}
catch (Exception e){}
}
prGroup = i;
}
});
/////////////-----------Only One Expand at a time Ends here-------------------------/////////////////////
// preparing list data
prepareListData();
listAdapter = new ExpandableListAdapter(getContext(), listDataHeader, listDataChild);
// setting list adapter
expListView.setAdapter(listAdapter);
//Send Button OnClick Starts /////////////////////////////////////////////////////////////////
btn=v.findViewById(R.id.button);
btn.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
//Sharing Rndom to OnChildView
SharedPreferences prefd = getContext().getSharedPreferences("my_prefd", MODE_PRIVATE);
SharedPreferences.Editor editd = prefd.edit();
editd.putInt("BRNDM", 1857 );
editd.commit();
//Taking Group ID (which group was expanded last)
SharedPreferences phobjb = getContext().getSharedPreferences("my_prefb", 0);
int grID = phobjb.getInt("GR", 0);
expListView.collapseGroup(grID);
expListView.expandGroup(grID);
new CountDownTimer(1000, 1000) {
public void onFinish() {
// When timer is finished
// Execute your code here
//Receiving 1857 of OnClick
SharedPreferences phobjc = getContext().getSharedPreferences("noofitems", 0);
int j = phobjc.getInt("NoItems", 0);
phobjc.edit().clear().commit();
for(int i=1;i<=j;i++){
//Taking data entered in ETs
SharedPreferences phobja = getContext().getSharedPreferences("my_prefa", 0);
String data = phobja.getString("PH"+i, "");
Toast.makeText(getContext(),"Recving "+data+"from PH"+i,Toast.LENGTH_SHORT).show();
}
}
public void onTick(long millisUntilFinished) {
// millisUntilFinished The amount of time until finished.
}
}.start();
}
});
//-------On Click of button ends here----------------------////////////
return v;
}
//////----------------OnCreate ends here-----------------------------////////////////
private void prepareListData() {
listDataHeader = new ArrayList<String>();
listDataChild = new HashMap<String, List<String>>();
if(readFile("filePG1.txt").equals(null)||readFile("filePG1.txt").equals("")){
//pg.add("No Contacts Present");
}
else {
listDataHeader.add("PG");
List<String> pg = new ArrayList<String>();
int j=1;
int i = Integer.parseInt(readFile(last));
//Start reading from 1 to "How many files are saved"/////////////////
while (j <= i) {
try {
FileInputStream fis = getContext().openFileInput("filePG"+ j + ".txt");
pg.add(readFile("filePG"+ j + ".txt"));
//Add items to listView by reading all saved files/Contacts/////////////
int size = fis.available();
byte[] buffer = new byte[size];
fis.read(buffer);
fis.close();
} catch (Exception e) {
//If limit is reached , Break the Loop///////////////////////////
break;
}
j++;
}
listDataChild.put(listDataHeader.get(grtoShow), pg); // Header, Child data
grtoShow++;
}
if(readFile("fileNur1.txt").equals(null)||readFile("fileNur1.txt").equals("")){
//nur.add("No Contacts Present");
}
else {
listDataHeader.add("Nursery");
List<String> nur = new ArrayList<String>();
int j=1;
int i = Integer.parseInt(readFile(last));
//Start reading from 1 to "How many files are saved"/////////////////
while (j <= i) {
try {
FileInputStream fis = getContext().openFileInput("fileNur"+ j + ".txt");
nur.add(readFile("fileNur"+ j + ".txt"));
//Add items to listView by reading all saved files/Contacts/////////////
int size = fis.available();
byte[] buffer = new byte[size];
fis.read(buffer);
fis.close();
} catch (Exception e) {
//If limit is reached , Break the Loop///////////////////////////
break;
}
j++;
}
listDataChild.put(listDataHeader.get(grtoShow), nur);
grtoShow++;
}
if(readFile("filePrep1.txt").equals(null)||readFile("filePrep1.txt").equals("")){
//prep.add("No Contacts Present");
}
else {
listDataHeader.add("Prep");
List<String> prep = new ArrayList<String>();
int j=1;
int i = Integer.parseInt(readFile(last));
//Start reading from 1 to "How many files are saved"/////////////////
while (j <= i) {
try {
FileInputStream fis = getContext().openFileInput("filePrep"+ j + ".txt");
prep.add(readFile("filePrep"+ j + ".txt"));
//Add items to listView by reading all saved files/Contacts/////////////
int size = fis.available();
byte[] buffer = new byte[size];
fis.read(buffer);
fis.close();
} catch (Exception e) {
//If limit is reached , Break the Loop///////////////////////////
break;
}
j++;
}
listDataChild.put(listDataHeader.get(grtoShow), prep);
grtoShow++;
}
if(readFile("fileOne1.txt").equals(null)||readFile("fileOne1.txt").equals("")){
//one.add("No Contacts Present");
}
else {
listDataHeader.add("One");
List<String> one = new ArrayList<String>();
int j=1;
int i = Integer.parseInt(readFile(last));
//Start reading from 1 to "How many files are saved"/////////////////
while (j <= i) {
try {
FileInputStream fis = getContext().openFileInput("fileOne"+ j + ".txt");
one.add(readFile("fileOne"+ j + ".txt"));
//Add items to listView by reading all saved files/Contacts/////////////
int size = fis.available();
byte[] buffer = new byte[size];
fis.read(buffer);
fis.close();
} catch (Exception e) {
//If limit is reached , Break the Loop///////////////////////////
break;
}
j++;
}
listDataChild.put(listDataHeader.get(grtoShow), one);
grtoShow++;
}
if(readFile("fileTwo1.txt").equals(null)||readFile("fileTwo1.txt").equals("")){
//two.add("No Contacts Present");
}
else {
listDataHeader.add("Two");
List<String> two = new ArrayList<String>();
int j=1;
int i = Integer.parseInt(readFile(last));
//Start reading from 1 to "How many files are saved"/////////////////
while (j <= i) {
try {
FileInputStream fis = getContext().openFileInput("fileTwo"+ j + ".txt");
two.add(readFile("fileTwo"+ j + ".txt"));
//Add items to listView by reading all saved files/Contacts/////////////
int size = fis.available();
byte[] buffer = new byte[size];
fis.read(buffer);
fis.close();
} catch (Exception e) {
//If limit is reached , Break the Loop///////////////////////////
break;
}
j++;
}
listDataChild.put(listDataHeader.get(grtoShow), two);
grtoShow++;
}
if(readFile("fileThree1.txt").equals(null)||readFile("fileThree1.txt").equals("")){
//three.add("No Contacts Present");
}
else {
listDataHeader.add("Three");
List<String> three = new ArrayList<String>();
int j=1;
int i = Integer.parseInt(readFile(last));
//Start reading from 1 to "How many files are saved"/////////////////
while (j <= i) {
try {
FileInputStream fis = getContext().openFileInput("fileThree"+ j + ".txt");
three.add(readFile("fileThree"+ j + ".txt"));
//Add items to listView by reading all saved files/Contacts/////////////
int size = fis.available();
byte[] buffer = new byte[size];
fis.read(buffer);
fis.close();
} catch (Exception e) {
//If limit is reached , Break the Loop///////////////////////////
break;
}
j++;
}
listDataChild.put(listDataHeader.get(grtoShow), three);
grtoShow++;
}
}
public String readFile(String file){
String text="";
try {
FileInputStream fis=getContext().openFileInput(file);
int size=fis.available();
byte[] buffer=new byte[size];
fis.read(buffer);
fis.close();
text=new String(buffer);
}
catch (Exception e){
e.printStackTrace();
}
return text;
}
}
所以,如何限制onChildView()仅在扩展组时调用,而不是在滚动/更改视图时调用。
答案 0 :(得分:1)
问题在于您的视图正在被回收,这意味着Android采用滚动屏幕的相同视图,并重新使用它来绘制您正在滚动的下一个视图,因为您在此处编写了一些文本,使用相同的视图将具有相同的文本。
解决方案非常简单。
您应该让模型反映用户在视图中输入的数据。在任何时候你都应该知道每个孩子有什么文字,也许可以使用TextWatcher
。
对于每个孩子,您只需执行以下操作即可。
String text = getTextForThisChild();
if (!TextUtils.isEmpty(text) {
yourEditText.setText(text); // Sets correct text for view
} else {
yourEditText.setText(null); // Clears text of recycled view
}
您需要跟踪文字更改
edt.addTextChangedListener(new TextWatcher() {
@Override
public void beforeTextChanged(final CharSequence charSequence, final int i, final int i1, final int i2) {}
@Override
public void onTextChanged(final CharSequence charSequence, final int i, final int i1, final int i2) {
yourModelList.get(childPosition).setText(charSequence); // This is dummy, you should get the correct model for this child
}
@Override
public void afterTextChanged(final Editable editable) {}
});
然后在yourModelList.get(childPosition)
获得的同一模型中,您可以获得text
您检查的那个是否为空。
如果仍然不清楚,请告诉我
答案 1 :(得分:0)
getView()是Android自己的方法,你无法覆盖它。 你想要实现的唯一方法是:
你想要做的事情当然是可能的,但很复杂:
(第3步,进一步可选)
在ChildItem中为EditText添加TextWatcher(TextChangedListener)(它将输入getText&gt;将其保存在Array []&gt;用户离开当前EditText时单击Button本身)。为:
edt.addTextChangedListener(new TextWatcher() {
@Override
public void beforeTextChanged(CharSequence charSequence, int i, int i1, int i2) {}
@Override
public void onTextChanged(CharSequence charSequence, int i, int i1, int i2) {}
@Override
public void afterTextChanged(Editable editable) {
if(edt.getText().toString()==""&&edt.getText().toString().equals(null)){
}
else {
edt.setOnFocusChangeListener(new View.OnFocusChangeListener() {
@Override
public void onFocusChange(View v, boolean hasFocus) {
if (!hasFocus)//Perform Click when edt loses Focus {
btn.callOnClick();
}
}
});
}
}});
现在按钮点击将如下:
btn.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
if(edt.getText().toString().equals("")){
}
else {
Toast.makeText(view.getContext(),"Entered: "+edt.getText().toString(),Toast.LENGTH_SHORT).show();
myStringArray[childPosition]=edt.getText().toString();
edt.setText("");
}
}
});