在ListAdapter的Andr​​oid多的EditText领域 [英] Android Multiple EditText fields in a ListAdapter

查看:83
本文介绍了在ListAdapter的Andr​​oid多的EditText领域的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个屏幕(见图片)由一个GridView使用BaseAdapter的自定义扩展填充。

当用户输入一些文本到的EditText领域,他们输入的文本易于左右移位或完全消失。我假设这个,是因为有意见的回收利用,但我listadapters的理解很差。

本场表现优良最初得益于Manifest条目机器人:windowSoftInputMode =adjustPan,但他们游移如果您滚动混乱

所有我希望做的是从用户获得一些字符串数据。该字符串存储在一个全局字符串数组字符串[]。琴弦阵列由MyTextWatcher,这是TextWatcher的一个扩展更新。

在code(尝试),以确保TextWatchers总是知道自己的EditText字段的网格内的位置。这样一来,TextWatchers应该总是更新字符串[]正确的索引。

我有充分的理由相信,这个问题从我的getView方法导出():

 公共无效initList()
{
    ArrayAdapter<字符串> listAdapter =新的ArrayAdapter<字符串>(这一点,R.layout.shape,字符串)
    {
        @覆盖
        公共查看getView(最终诠释的立场,观点convertView,ViewGroup中父){
            最后ViewHolder持有人;

            如果(convertView == NULL || convertView.getTag()== NULL){
                convertView = LayoutInflater.from(的getContext())膨胀(R.layout.shape,空)。

                持有人=新ViewHolder();
                holder.text =(TextView中)convertView.findViewById(R.id.shape_text);
                holder.image =(ImageView的)convertView.findViewById(R.id.shape_image);
                holder.editText =(EditText上)convertView.findViewById(R.id.shape_edittext);

                holder.editText.addTextChangedListener(新TextWatcher(){
                    公共无效beforeTextChanged(CharSequence中的CharSequence,诠释我,诠释I1,I2 INT){}
                    公共无效onTextChanged(CharSequence中,诠释开始,诠释之前,诠释计数){
                        如果(游戏类型== SHAPES_ABSTRACT和放大器;&安培;&安培; == 0功放前数== 1){
                            InputMethodManager经理=(InputMethodManager)getSystemService(Context.INPUT_METHOD_SERVICE);
                            mgr.hideSoftInputFromWindow(holder.editText.getWindowToken(),0);
                        }
                    }
                    公共无效afterTextChanged(编辑S){
                        串[holder.ref] = s.toString();
                    }
                });

                convertView.setTag(保持器);
            }
            其他 {
                支架=(ViewHolder)convertView.getTag();
            }
            holder.ref =位置;
            holder.editText.setText(字符串[位置]);

            holder.image.setBackgroundResource(图片[位置]);

            如果(游戏类型== SHAPES_ABSTRACT)
                holder.text.setText(SEQ:);
            其他
                holder.text.setVisibility(View.GONE);

            返回convertView;
        }
    };

    grid.setAdapter(listAdapter);
}
 

解决方案

我要再次preface这一点,因为在其他的答案,说我不会实现这种方式。你做可怕的东西。携带大量引用各地。但是,我认为这应该帮助:

 地图< EditText上,MyTextWatcher>观察家=新的HashMap< EditText上,MyTextWatcher>();

公共查看getView(INT位置,查看convertView,父母的ViewGroup)
{
    查看MyView的= convertView;
    如果(MyView的== NULL)
    {
        LayoutInflater李= getLayoutInflater();
        MyView的= li.inflate(R.layout.shape,NULL);
    }

    的EditText文本框=(EditText上)MyView.findViewById(R.id.shape_edittext);

    textbox.setText(字符串[位置]);
    MyTextWatcher myTextWatcher = watchers.get(文本);

    如果(myTextWatcher == NULL)
    {
        myTextWatcher =新MyTextWatcher(位置,文本框);
        watchers.put(文本框,myTextWatcher);
    }

    myTextWatcher.setIndex(位置);

    ImageView的形象=(ImageView的)MyView.findViewById(R.id.shape_image);
    image.setBackgroundResource(图片[位置]);

    TextView的文字=(TextView的)MyView.findViewById(R.id.shape_text);
    text.setText(SEQ:);

    返回MyView的;
}
 

这里的问题是,你创建的TextWatcher,把它添加到一个EditText,但随后保持对它的引用在列表中的位置,这样的EditText和TextWatcher间引用被打破。

该解决方案假定'等于'进行的EditText会做一个对象实例的比较,而不是一个值进行比较。如果不是的话,你需要不断的引用,所有的EditText情况下,做一个'=='比较每找到一个匹配。

我觉得有更安全的方法可以做到这一点,但给它一个镜头。

I have a screen (see picture) that is populated by a GridView using a custom extension of BaseAdapter.

When the user enters some text into the EditText fields, the text they entered is liable to shifting around or disappearing entirely. I'm assuming this has to do with the recycling of views, but my understanding of listadapters is poor.

The fields behave fine initially thanks to the Manifest entry android:windowSoftInputMode="adjustPan", but they shift around if you scroll chaotically.

All I am looking to do is get some String data from the user. The Strings are stored in a global String array "strings[]". The strings array is updated by MyTextWatcher, which is just an extension of TextWatcher.

The code (attempts) to ensure that the TextWatchers always know the position of their EditText field within the grid. That way, the TextWatchers should always be updating strings[] with the correct index.

I have every reason to believe that the issue derives from my getView method():

public void initList()
{
    ArrayAdapter<String> listAdapter = new ArrayAdapter<String>(this, R.layout.shape, strings)
    {
        @Override
        public View getView(final int position, View convertView, ViewGroup parent)  {
            final ViewHolder holder;

            if (convertView == null  || convertView.getTag() == null)  {
                convertView = LayoutInflater.from(getContext()).inflate(R.layout.shape, null);

                holder = new ViewHolder();
                holder.text = (TextView) convertView.findViewById(R.id.shape_text);
                holder.image = (ImageView) convertView.findViewById(R.id.shape_image);
                holder.editText = (EditText) convertView.findViewById(R.id.shape_edittext);

                holder.editText.addTextChangedListener(new TextWatcher() {                      
                    public void beforeTextChanged(CharSequence charSequence, int i, int i1, int i2){}
                    public void onTextChanged(CharSequence s, int start, int before, int count) {
                        if (gameType == SHAPES_ABSTRACT && before == 0 && count == 1) {
                            InputMethodManager mgr = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
                            mgr.hideSoftInputFromWindow(holder.editText.getWindowToken(), 0);                               
                        }    
                    }
                    public void afterTextChanged(Editable s) {
                        strings[holder.ref]= s.toString(); 
                    }
                });

                convertView.setTag(holder);                    
            }
            else {
                holder = (ViewHolder) convertView.getTag();
            }
            holder.ref = position;
            holder.editText.setText(strings[position]);                             

            holder.image.setBackgroundResource(images[position]);

            if (gameType == SHAPES_ABSTRACT)
                holder.text.setText("Seq:");
            else
                holder.text.setVisibility(View.GONE);   

            return convertView;
        }
    };

    grid.setAdapter(listAdapter);
}

解决方案

I would again preface this, as in the other answer, by saying I wouldn't implement it this way. You're doing scary stuff. Carrying lots of references around. However, I think this should help:

Map<EditText, MyTextWatcher> watchers = new HashMap<EditText, MyTextWatcher>();

public View getView(int position, View convertView, ViewGroup parent)
{
    View MyView = convertView;
    if (MyView == null)
    {
        LayoutInflater li = getLayoutInflater();
        MyView = li.inflate(R.layout.shape, null);
    }

    EditText textbox = (EditText) MyView.findViewById(R.id.shape_edittext);

    textbox.setText(strings[position]);
    MyTextWatcher myTextWatcher = watchers.get(textbox);

    if(myTextWatcher == null)
    {
        myTextWatcher = new MyTextWatcher(position, textbox);
        watchers.put(textbox, myTextWatcher);
    }

    myTextWatcher.setIndex(position);

    ImageView image = (ImageView) MyView.findViewById(R.id.shape_image);
    image.setBackgroundResource(images[position]);

    TextView text = (TextView) MyView.findViewById(R.id.shape_text);
    text.setText("Seq:");

    return MyView;
}

The problem here is that you created the TextWatcher, added it to an EditText, but then kept a reference to it in a list by position, so the references between EditText and the TextWatcher were broken.

This solution assumes that 'equals' for EditText will do an object instance compare and not a value compare. If that is NOT the case, you'd need to keep a reference to all EditText instances, and do an '==' compare to each and find a match.

I think there are safer ways to do this, but give it a shot.

这篇关于在ListAdapter的Andr​​oid多的EditText领域的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆