【问题标题】:EditText in ListView loses content in scrollingListView 中的 EditText 在滚动中丢失内容
【发布时间】:2016-08-16 01:48:24
【问题描述】:

我一直在寻找解决问题的方法来寻找答案,但没有一个对我有用。 :/ 我在每个列表项中都有一个带有 edittext 的列表视图,当向下滚动并再次向上滚动时,已编辑的 edittext 的内容已丢失或其他 edittext 已采用他的值。

请帮我一个

MainActivity:-

public class MainActivity extends AppCompatActivity {

    private ArrayList<Friend> friendArrayList;
    ListViewAdapter adapter;

    String[] countriessArray =  { "USA", "USA", "USA", "USA",
            "China", "Japan", "France", "USA","USA", "USA", "USA", "USA",
            "China", "Japan", "France", "USA"};

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main_layout);

        friendArrayList = new ArrayList<Friend>();
        for (int i = 0; i < countriessArray.length; i++) {

            Friend item = new Friend(countriessArray[i]);
            friendArrayList.add(item);
        }

        ListView listView = (ListView) findViewById(R.id.list);
        listView.setItemsCanFocus(true);

        adapter = new ListViewAdapter(this, R.layout.item_listview, friendArrayList);

        listView.setAdapter(adapter);
    }

ListViewAdaper:-

public class ListViewAdapter extends ArrayAdapter<Friend> {

    ViewHolder holder;
    private List<Friend> myFriends;
    private Activity activity;

    public static HashMap<Integer,String> myList=new HashMap<Integer,String>();

    public ListViewAdapter(Activity context, int resource, List<Friend> objects) {

        super(context, resource, objects);
        this.activity = context;
        this.myFriends = objects;
    }

    @Override
    public View getView(final int position, View convertView, ViewGroup parent) {

        LayoutInflater inflater = (LayoutInflater) activity.getSystemService(Activity.LAYOUT_INFLATER_SERVICE);
        final int viewpos = position;

        // If holder not exist then locate all view from UI file.
        if (convertView == null) {
            // inflate UI from XML file
            convertView = inflater.inflate(R.layout.item_listview, parent, false);
            // get all UI view
            holder = new ViewHolder(convertView);
            convertView.setTag(holder);

        } else {
            // if holder created, get tag from view
            holder = (ViewHolder) convertView.getTag();
        }

        holder.friendName.setText(getItem(position).getName());

        //Edit Text Listeners:-

        holder.editText.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) {
                myList.put(position,s.toString().trim());
            }
        });

        holder.editText.setText(myList.get(position));

        return convertView;
    }

    private static class ViewHolder {

        private TextView friendName;
        private EditText editText;

        public ViewHolder(View v) {
            friendName = (TextView) v.findViewById(R.id.name);
            editText = (EditText) v.findViewById(R.id.edit);
        }
    }
}

自定义对象:-

public class Friend {

    private String name,editText;
    private int selection = 0;

    public Friend(String name) {
        this.name = name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public String getName() {
        return name;
    }

    public void setSelection(int selection) {
        this.selection = selection;
    }

    public int getSelection() {
        return selection;
    }

    public void setEditText(String editText) {
        this.editText = editText;
    }

    public String getEditText() {
        return editText;
    }
}

【问题讨论】:

  • 试着把 myList.put(position,s.toString().trim()); textChanged 中的一行
  • 不,即使我将它保存在 textChanged 中,它也无法正常工作
  • 你如何在 getItem 中设置值?给我看那个代码
  • 试试这个扩展 getViewTypeCount() 和 getItemViewType() 方法并检查

标签: android listview android-edittext


【解决方案1】:

您需要将数据存储在 afterTextChanged 中,与您在文本中设置的对象相同

   holder.friendName.setText(myFriends.get(position).getName());

        //Edit Text Listeners:-

        holder.editText.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) {
                myFriends.get(position).setName(s.toString);
            }
        });

【讨论】:

  • 那has map有什么用呢?
  • 这完全不同,在这里你在两个地方都使用自定义对象。所以不需要使用地图
  • getItem.get(position).setName(s.toString);这里 .setName() 已经是另一个名称属性
  • 我想我需要在我的 pojo 类中为 editText 创建另一个 setter 和 getters 属性,对吗?
  • setname 方法将更新后的文本设置在当前对象的位置上,并且在 edittext 中得到相同的结果
【解决方案2】:

好的,首先 ListView 使用回收视图。这意味着当您上下滚动时,它们会再次充气,这就是文本消失的原因。我建议不要使用 ListView,而是只使用 LinearLayout,然后以编程方式添加 EditText 视图。现在,如果您固执并且不想更改当前的解决方案。当用户在字段中键入时,您可以做的一件事是基本上存储所有字符串值,然后在适配器中您可以将其设置为类型值。

例如..

String valueForEditTextOne = "";

//in the get view adapter you have to set a tag for each edittext to be able to identify them. 

String tagName = editTextOne.getTag();

   if (tagName == null) {
   //You need to set the tag name (use the passed position constructor)
   editTextOne.setTag(String.valueOf(position));
   } else {
     if(tagName.equals("1")) {
      textViewOne.setText(valueForEditTextOne);
     } else if (tagName.equals("2") {
      //etc...
     }
   } 

}

我不知道你有多少个 TextView,但这肯定行得通。您还必须添加一个文本更改侦听器来更新该文本视图的每个手动字符串。

【讨论】:

    【解决方案3】:

    已解决:

    当滚动列表视图时,所有 editText 项都设置为 SAME VALUE 并且如果处理程序代码像这样,则会失去其真实值,

     txtQuantityVal.addTextChangedListener(new TextWatcher() {
            @Override
            public void afterTextChanged(Editable s) {
                items.get(position).setStock(Double.parseDouble(s.toString()));
            }
    

    因为,所有元素的 textChangeEventListener 都会发生变化。

    避免这种情况的方法,将数据项对象添加到editText的Tag属性中,

      txtQuantityVal.setTag(item);
      txtQuantityVal.setText(String.valueOf(item.getStock()));
    

    然后,我们在 TextChange 事件中保持控制, 这里我的数据的唯一键是 item.productId , 解决方案的逻辑是, 通过检查两个值,我们应该检查正确的元素是否正在发生变化。

     txtQuantityVal.addTextChangedListener(new TextWatcher() {
                @Override
                public void afterTextChanged(Editable s) {
                        BarcodeItem bitem=items.get(position);
                        BarcodeItem xitem=((BarcodeItem)txtQuantityVal.getTag());
                        if(bitem.getProductId() == xitem.getProductId() ) { // match id, item change ?
                            items.get(position).setStock(Double.parseDouble(s.toString()));
                        }
                        else{
                            // data item ids different, item no changes
                            
                        }
                }
        
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-10-06
      • 2014-02-02
      • 1970-01-01
      相关资源
      最近更新 更多