Грешка на Android IndexOutOfBoundsException за изглед на списък за филтриране на търсене

Приложих филтър за търсене към моя SearchView в моята лента за действие Sherlock. Приложих персонализиран филтър. Когато пиша всяка буква, получавам грешка

public class PlacesListAdapter extends ArrayAdapter<Place> implements
        Filterable {

    public Context mContext;

    List<Place> mPlaces, orig;

    public PlacesListAdapter(Context context, List<Place> places) {
        super(context, R.layout.list_item_places, places);
        // TODO Auto-generated constructor stub
        this.mPlaces = places;
        this.mContext = context;

        orig = new ArrayList<Place>(places);

    }

    @Override
    public Place getItem(int position) {
        // TODO Auto-generated method stub
        return mPlaces.get(position);
    }

    @Override
    public long getItemId(int position) {
        return position;
    }

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

        ViewHolder holder;

        if (convertView == null) {
            LayoutInflater viewInflater;
            viewInflater = LayoutInflater.from(getContext());
            convertView = viewInflater.inflate(R.layout.list_item_places, null);

            holder = new ViewHolder();
            holder.placeTitle = (TextView) convertView
                    .findViewById(R.id.place_title);
            holder.placeDistance = (TextView) convertView
                    .findViewById(R.id.place_distance);
            holder.placeCategoryIcon = (ImageView) convertView
                    .findViewById(R.id.place_category_icon);

            convertView.setTag(holder);

        } else {
            holder = (ViewHolder) convertView.getTag();
        }

        holder.placeTitle.setText(mPlaces.get(position).getPlaceName());
        holder.placeDistance.setText(mPlaces.get(position).getPlaceDistance());
        holder.placeCategoryIcon
                .setImageResource(R.drawable.icon_category_hillstation);

        // // Setting Alternative Row Colors
        if (position % 2 == 0) {
            convertView
                    .setBackgroundResource(R.drawable.list_view_places_row_1);
        } else {
            convertView
                    .setBackgroundResource(R.drawable.list_view_places_row_2);
        }

        return convertView;
    }

    static class ViewHolder {
        TextView placeId;

        TextView placeTitle;

        TextView placeDistance;

        ImageView placeCategoryIcon;
    }

    @Override
    public Filter getFilter() {
        // TODO Auto-generated method stub
        return new PlaceFilter();
    }

    private class PlaceFilter extends Filter {

        @Override
        protected FilterResults performFiltering(CharSequence constraint){
            FilterResults oReturn = new FilterResults();
            ArrayList<Place> results = new ArrayList<Place>();
            if (orig == null)
                orig = mPlaces;
            if (constraint != null) {
                if (orig != null && orig.size() > 0) {
                    for (Place g : orig) {
                        if (g.getPlaceName()
                                .toLowerCase()
                                .startsWith(constraint.toString().toLowerCase()))
                            results.add(g);
                    }
                }
                oReturn.values = results;
            }
            return oReturn;
        }

        @Override
        protected void publishResults(CharSequence constraint,
                FilterResults results) {
            mPlaces = (ArrayList<Place>) results.values;
            notifyDataSetChanged();
        }

    }

}

ГРЕШКА

12-26 17:24:43.900: E/AndroidRuntime(18693): FATAL EXCEPTION: main
12-26 17:24:43.900: E/AndroidRuntime(18693): java.lang.IndexOutOfBoundsException: Invalid index 1, size is 1
12-26 17:24:43.900: E/AndroidRuntime(18693):    at java.util.ArrayList.throwIndexOutOfBoundsException(ArrayList.java:251)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at java.util.ArrayList.get(ArrayList.java:304)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at com.m7.nomad.PlacesListAdapter.getView(PlacesListAdapter.java:68)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.widget.AbsListView.obtainView(AbsListView.java:2193)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.widget.ListView.makeAndAddView(ListView.java:1774)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.widget.ListView.fillDown(ListView.java:672)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.widget.ListView.fillSpecific(ListView.java:1330)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.widget.ListView.layoutChildren(ListView.java:1603)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.widget.AbsListView.onLayout(AbsListView.java:2044)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.view.View.layout(View.java:11418)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.view.ViewGroup.layout(ViewGroup.java:4224)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.widget.RelativeLayout.onLayout(RelativeLayout.java:925)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.view.View.layout(View.java:11418)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.view.ViewGroup.layout(ViewGroup.java:4224)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.widget.FrameLayout.onLayout(FrameLayout.java:431)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.view.View.layout(View.java:11418)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.view.ViewGroup.layout(ViewGroup.java:4224)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.widget.LinearLayout.setChildFrame(LinearLayout.java:1628)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.widget.LinearLayout.layoutVertical(LinearLayout.java:1486)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.widget.LinearLayout.onLayout(LinearLayout.java:1399)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.view.View.layout(View.java:11418)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.view.ViewGroup.layout(ViewGroup.java:4224)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.widget.FrameLayout.onLayout(FrameLayout.java:431)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.view.View.layout(View.java:11418)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.view.ViewGroup.layout(ViewGroup.java:4224)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.view.ViewRootImpl.performTraversals(ViewRootImpl.java:1628)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.view.ViewRootImpl.handleMessage(ViewRootImpl.java:2585)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.os.Handler.dispatchMessage(Handler.java:99)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.os.Looper.loop(Looper.java:137)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at android.app.ActivityThread.main(ActivityThread.java:4507)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at java.lang.reflect.Method.invokeNative(Native Method)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at java.lang.reflect.Method.invoke(Method.java:511)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:790)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:557)
12-26 17:24:43.900: E/AndroidRuntime(18693):    at dalvik.system.NativeStart.main(Native Method)

Грешка

Сочи към

holder.placeTitle.setText(mPlaces.get(position).getPlaceName());

person Harsha M V    schedule 26.12.2012    source източник


Отговори (4)


Ако отстраните грешки, ще видите, че mPlaces.getSize() е равно на 1 и се опитвате да получите достъп до елемента в позиция 1, ще получите изключение ArrayOutOfBounds.

има нещо нередно във вашия ArrayList и вероятно няма всички данни, които се опитвате да получите.

person thepoosh    schedule 26.12.2012
comment
откъде трябва да започна да разглеждам отстраняването на грешки? списъкът се попълва веднага при зареждане. случва се само когато се опитвам да въвеждам и да го филтрирам - person Harsha M V; 26.12.2012
comment
опитайте да поставите точка на прекъсване в началото на getView и вижте къде ще ви отведе - person thepoosh; 26.12.2012
comment
когато пиша нещо - директно няма резултати. pastebin.com/7q4dQC4B странно :( - person Harsha M V; 26.12.2012
comment
Ще се уверя, че в конструктора mPlaces.size() е по-голямо от 1, след което ще отстраня грешките в getView и ще видя какво се обърка. - person thepoosh; 26.12.2012
comment
освен това, след като разгледах вашите редакции в pastebin, забелязах, че вече не сравнявате ограничението с g.getPlaceName(), което беше намерението в оригиналната публикация, така че трябва да бъде item.getPlaceName(), ако следвате същите данни модел..благодаря за публикуването на всичко това! - person whyoz; 23.01.2014

Опитайте се да покриете тази линия

holder.placeTitle.setText(mPlaces.get(position).getPlaceName());

*със следното условие *

if(position < mPlaces.size() && holder.placeTitle != null)
  holder.placeTitle.setText(mPlaces.get(position).getPlaceName());

РЕДАКТИРАНЕ:

Ето моят малък внедрен фрагмент:

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

            ViewHolder holder;

            if (convertView == null) {
                LayoutInflater viewInflater;
                viewInflater = getLayoutInflater();
                convertView = viewInflater.inflate(R.layout.listview, null);

                holder = new ViewHolder();
                convertView.setTag(holder);

            } else {
                holder = (ViewHolder) convertView.getTag();

                // Try here first
                holder.textview = (TextView) convertView.findViewById(R.id.TextView01);
                holder.imageview = (ImageView) convertView.findViewById(R.id.ImageView01);
            }

            // Try here second
            // holder.textview = (TextView)convertView.findViewById(R.id.TextView01);
            // holder.imageview = (ImageView)convertView.findViewById(R.id.ImageView01);

            if (holder.textview != null && position < data_text.length)
                holder.textview.setText(data_text[position]);
            if (holder.imageview != null && position < data_image.length)
                holder.imageview.setImageResource(data_image[position]);

            return convertView;
        }

Можете да го замените с вашите променливи.

Благодаря.

person Pratik Sharma    schedule 26.12.2012
comment
опитах това. но сега получавам множество въвеждания на редовете в произволен ред - person Harsha M V; 26.12.2012
comment
@HarshaMV опитайте да извадите такива декларации holder.placeTitle = (TextView) convertView.findViewById(R.id.place_title); от if до else част в getView метод. И ако това не работи, извадете страната след if..else. - person Pratik Sharma; 26.12.2012
comment
не те разбрах. може ли да обясните - person Harsha M V; 26.12.2012
comment
@HarshaMV вижте редактираното решение, което публикувах. Показах на кои места е добре да се декларират държавни контроли. - person Pratik Sharma; 26.12.2012
comment
да бях пропуснал метода getCount. просто го добавих и работи :( - person Harsha M V; 26.12.2012

Опитайте този код за вашите приложения,

if (g.getPlaceName().toLowerCase().contains(constraint.toString().toLowerCase())){
    results.add(g);
}
person NAP Developer    schedule 26.12.2012
comment
искам да използвам по-специално .startsWith - person Harsha M V; 26.12.2012

Ако някой се нуждае от кода за SearchView в персонализирана лента за действие, която влиза във вашата дейност (или в този случай ListFragment), ето го:

    ActionBar actionBar = getActivity().getActionBar();
    actionBar.setDisplayOptions(ActionBar.DISPLAY_SHOW_CUSTOM | ActionBar.DISPLAY_SHOW_HOME);
    actionBar.setDisplayShowHomeEnabled(true);
    actionBar.setCustomView(R.layout.your_bar);
    SearchView groupSV = (SearchView)actionBar.getCustomView().findViewById(R.id.groupSV);
    groupSV.setOnQueryTextListener(new SearchView.OnQueryTextListener() {
        @Override
        public boolean onQueryTextChange(String newText) {
            Log.d(TAG,"onQueryTextChange");
            ListViewFragment.adapter.getFilter().filter(newText);
            return true;
        }
        @Override
        public boolean onQueryTextSubmit(String query) {
            Log.d(TAG,"onQueryTextSubmit");
            //ListViewFragment.adapter.getFilter().filter(query);
            return true;
        }
    });

Ще трябва да декларирате вашия адаптер като статичен по този начин във вашия ListViewFragment:

public static ArrayAdapter<Your_obj> adapter = null;

public class ListViewFragment extends ListFragment implements OnItemClickListener {
    //...//
}

Също така не забравяйте да проверите редактирания код на OP от неговата връзка: РЕДАКТИРИ НА PASTEBIN

person whyoz    schedule 23.01.2014