我有一张RecyclerView
,其中有许多牌可容纳4 EditText
。当我在一张卡的EditText
中输入值时,它会在随机卡中填充相同的值。令人惊讶的是,它不会跳转EditText
例如:
如果我在edittext1
的{{1}}中输入值,则会将相同的值填入card1
中的edittext1
,如果我更改card8
中的值将更改card8
中的值。有人可以告诉我为什么会这样。
提前感谢
这是我的代码:
card1
这是我的卡片xml
public class MyAdapter extends RecyclerView.Adapter<MyAdapter.ViewHolder> {
private String[] mDataset;
public String[][] data = new String[30][4];
public static class ViewHolder extends RecyclerView.ViewHolder {
// each data item is just a string in this case
public LinearLayout mCardView;
public ViewHolder(LinearLayout v) {
super(v);
mCardView = v;
}
}
// Provide a suitable constructor (depends on the kind of dataset)
public MyAdapter(String[] myDataset) {
mDataset = myDataset;
}
// Create new views (invoked by the layout manager)
@Override
public MyAdapter.ViewHolder onCreateViewHolder(ViewGroup parent,
int viewType) {
LinearLayout v = (LinearLayout) LayoutInflater.from(parent.getContext())
.inflate(R.layout.cards, parent, false);
ViewHolder vh = new ViewHolder(v);
return vh;
}
// Replace the contents of a view (invoked by the layout manager)
@Override
public void onBindViewHolder(ViewHolder holder, final int position) {
// - get element from your dataset at this position
// - replace the contents of the view with that element
final EditText txt = (EditText) holder.mCardView.findViewById(R.id.ip1_text);
final EditText txt2 = (EditText) holder.mCardView.findViewById(R.id.ip2_text);
final EditText txt3 = (EditText) holder.mCardView.findViewById(R.id.ip3_text);
final EditText txt4 = (EditText) holder.mCardView.findViewById(R.id.ip4_text);
txt.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) {
data[position][0] = s.toString();
Log.d("DATA" + position + "0", s.toString());
}
});
txt2.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) {
data[position][1] = s.toString();
Log.d("DATA" + position + "1", s.toString());
}
});
txt3.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) {
data[position][2] = s.toString();
Log.d("DATA" + position + "2", s.toString());
}
});
txt4.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) {
data[position][3] = s.toString();
Log.d("DATA" + position + "3", s.toString());
}
});
TextView t = (TextView) holder.mCardView.findViewById(R.id.serNo);
t.setText(mDataset[position]);
}
// Return the size of your dataset (invoked by the layout manager)
@Override
public int getItemCount() {
return mDataset.length;
}
public String[][] getData() {
return data;
}
答案 0 :(得分:6)
这是因为RecyclerView
内的观点正在被回收。在onBindViewHolder
内,您需要将特定文本设置为特定位置的EditTexts。
在ViewHolder
内初始化您的视图并在其中添加TextWatchers,因为RecyclerView
的整个原则是重用视图:
public static class ViewHolder extends RecyclerView.ViewHolder {
EditText txt;
EditText txt2;
EditText txt3;
EditText txt4;
TextView serNoTxt;
public ViewHolder(LinearLayout mCardView) {
super(mCardView);
txt = (EditText) mCardView.findViewById(R.id.ip1_text);
txt2 = (EditText) mCardView.findViewById(R.id.ip2_text);
txt3 = (EditText) mCardView.findViewById(R.id.ip3_text);
txt4 = (EditText) mCardView.findViewById(R.id.ip4_text);
setNoTxt = (TextView) mCardView.findViewById(R.id.serNo);
txt.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) {
data[getAdapterPosition()][0] = s.toString();
Log.d("DATA" + getAdapterPosition() + "0", s.toString());
}
});
txt2.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) {
data[getAdapterPosition()][1] = s.toString();
Log.d("DATA" + getAdapterPosition() + "1", s.toString());
}
});
txt3.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) {
data[getAdapterPosition()][2] = s.toString();
Log.d("DATA" + getAdapterPosition() + "2", s.toString());
}
});
txt4.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) {
data[getAdapterPosition()][3] = s.toString();
Log.d("DATA" + getAdapterPosition() + "3", s.toString());
}
});
}
}
将相应的文本设置为onBindViewHolder
:
@Override
public void onBindViewHolder(ViewHolder holder, final int position) {
holder.txt1.setText(data[position][0]);
holder.txt2.setText(data[position][1]);
holder.txt3.setText(data[position][2]);
holder.txt4.setText(data[position][3]);
holder.setNoTxt.setText(mDataset[position]);
}
答案 1 :(得分:0)
您在未通知适配器的情况下更新了数据。这可能会造成不一致。因此,在更改数据后,您应该致电notifyItemChanged()
。
例如:
@Override
public void afterTextChanged(Editable s) {
data[position][3] = s.toString();
Log.d("DATA" + position + "3", s.toString());
notifyItemChanged(position);
}
我还有一个建议是重用代码,这样就不必复制粘贴这么多并在很多地方修复(例如,所有的TextWatcher对象基本相同)。
答案 2 :(得分:0)
我以前在onBindViewHolder中使用OnFocusChangeListener作为适配器
editText.setText(mValues.get(position).getValue());
editText.setOnFocusChangeListener(new View.OnFocusChangeListener() {
@Override
public void onFocusChange(View v, boolean hasFocus) {
if (!hasFocus)
mValues.get(position).setValue(editText.getText().toString());
}
});
答案 3 :(得分:0)
设置数据时,应使用getAdapterPosition()代替position。 这是因为,当recyclerview滚动时,它将被回收并且该位置将无法获得正确的值。
data[getAdapterPosition()][1] = s.toString();
答案 4 :(得分:0)
这是 Recycler View Recycle 的问题,只需覆盖这些功能
@Override
public long getItemId(int position) {
return position;
}
@Override public int getItemViewType(int position) {
return position;
}