NullPointerException on dynamic AutoCompleteTextView

柔情痞子 提交于 2020-01-04 02:47:10

问题


Some users are reporting this error:

java.lang.NullPointerException
at android.widget.ArrayAdapter.getCount(ArrayAdapter.java:291)
at android.widget.AutoCompleteTextView$PopupDataSetObserver$1.run(AutoCompleteTextView.java:1670)
at android.os.Handler.handleCallback(Handler.java:587)
at android.os.Handler.dispatchMessage(Handler.java:92)
at android.os.Looper.loop(Looper.java:123)
at android.app.ActivityThread.main(ActivityThread.java:3687)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:507)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:842)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:600)
at dalvik.system.NativeStart.main(Native Method)

Here is my code snippet:

    private List<City> autoCompleteCities = new ArrayList<City>();
    private List<City> autoCompleteCitiesOld = new ArrayList<City>();
    private ArrayAdapter<String> autoCompleteAdapter;
    private AutoCompleteTextView cityView;

    ...

    autoCompleteAdapter = new ArrayAdapter<String>(this, android.R.layout.simple_dropdown_item_1line);
    autoCompleteAdapter.setNotifyOnChange(true);

    cityView = (AutoCompleteTextView) findViewById(R.id.city);      

    cityView.setAdapter(autoCompleteAdapter);
    cityView.addTextChangedListener(new TextWatcher() {

        @Override
        public void onTextChanged(CharSequence s, int start, int before, int count) {
            LogUtil.i("!!!!!!!!!!!!! ontextchanged", s.toString());
            autoCompleteAdapter.clear();
            autoCompleteCitiesOld = autoCompleteCities;
            if (s.toString().length() > 2) {
                autoCompleteCities = search(s.toString());
                for (City city : autoCompleteCities) {
                    autoCompleteAdapter.add(city.getDisplayName());
                }
            }
        }

        @Override
        public void beforeTextChanged(CharSequence s, int start, int count, int after) {
        }

        @Override
        public void afterTextChanged(Editable s) {
        }
    });

It doesnt happen for me, but I have enough error reports to know it happens for several users. Any idea what is wrong? Why does this happen to only a handful of users?

I found this post but putting the fetching of new autocomplete values in an AsyncTask meant that the results always were one character behind what the user had entered.


回答1:


Where are you passing the ArrayList to the ArrayAdapter. The NullPointerException throws while counting the list lenght in ArrayAdapter. But the list is not passed to Adapter, so the list object in default Adapter contains null.




回答2:


My hypothesis is that you are somewhere using static variables which are nulled after activity recreation. See my answer here: Public static variables and Android activity life cycle management

create android v.4 emulator, go to developer's settings, disable background tasks, disable multiple activities and then try to use your application - chances are it will fail.




回答3:


Where did u have added the array of String ,the reason of error may be the empty array list as: autoCompleteAdapter = new ArrayAdapter(this, android.R.layout.simple_dropdown_item_1line);

here u hav'nt assign any string array

And enter your full code it will help lot to the people to understand the problem




回答4:


Better do null check before using object like below and do it in search function also..

 if (s.toString().length() > 2) {
     autoCompleteCities = search(s.toString());
     if(autoCompeleteCities!=null){     
         for (City city : autoCompleteCities) {
              autoCompleteAdapter.add(city.getDisplayName());
         }
       }




回答5:


I had exactly the same problem with the same issue. In my case I have thousands of streets I dynamically add and remove from the list. In my case it was always reproducable when I enter some value into the AutoComplete field, let's say 3 characters (while threshold is set to 0), so the dropdown list appears, and then I delete those characters by delete button very quickly. That means I hit the delete button a lot of times. It always crashes then. I figured out that clear causes the crashes. I put the clear in beforeTextChanged and the crashes were gone:

public class StreetTextWatcher implements TextWatcher {

    private final StreetArrayAdapter adapter;
    private boolean alreadyAdded = false;

    public StreetTextWatcher(StreetArrayAdapter adapter) {
        this.adapter = adapter;
    }

    @Override
    public void afterTextChanged(Editable s) {
        //not used
    }

    @Override
    public void beforeTextChanged(CharSequence s, int start, int count, int after) {
        if (s.length() < 1)  {
            adapter.clear();

            alreadyAdded = false;
        }
    }

    @Override
    public void onTextChanged(CharSequence s, int start, int before, int count) {           
        if (s.length() == 1) {
            if (s.toString().toLowerCase(Locale.GERMAN).startsWith("a") && !alreadyAdded)  {
                adapter.addAll(StreetNames.STREETS_A);
                alreadyAdded = true;
            }

            if (s.toString().toLowerCase(Locale.GERMAN).startsWith("b") && !alreadyAdded)  {
                adapter.addAll(StreetNames.STREETS_B);
                alreadyAdded = true;
            }

            //more streets...
        }
    }
}

StreetArrayAdapter:

public class StreetArrayAdapter extends ArrayAdapter<String> {

    public StreetArrayAdapter(Context context, int textViewResourceId) {
        super(context, textViewResourceId);
    }

    public void addAll(String[] streets) {
        for (String street : streets) {
            add(street);
        }
    }
}


来源:https://stackoverflow.com/questions/12769552/nullpointerexception-on-dynamic-autocompletetextview

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!