Фильтрация с помощью пользовательского ArrayAdapter - PullRequest
2 голосов
/ 20 апреля 2011

Я боролся с этим некоторое время и не могу найти ответ, несмотря на то, что некоторое время искал.У меня есть собственный arrayAdapter, который заполняет мой список представления пользовательским POI объекта.

package com.WasserSportLotse;

import java.util.ArrayList;

import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ArrayAdapter;
import android.widget.Filter;
import android.widget.ImageView;
import android.widget.TextView;

class poiAdapter extends ArrayAdapter<POI>{


    private ArrayList<POI> items;
    private Context mContext;
    public ArrayList<POI> allItems;
    private Filter filter;
    public ArrayList<POI> filtered;

    public poiAdapter(Context context, int textViewResourceId, ArrayList<POI> items){
        super(context, textViewResourceId, items);
        mContext = context;
        this.items = items;


}

    @Override
    public View getView(int position, View convertView, ViewGroup parent) {
            View v = convertView;
            if (v == null) {
                LayoutInflater vi = (LayoutInflater)mContext.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
                v = vi.inflate(R.layout.list_items, null);
            }
            POI poi = items.get(position);
            if (poi != null) {
                    TextView mDistanceTextView = (TextView) v.findViewById(R.id.listitems_distancetxt);
                    TextView mNameTextView = (TextView) v.findViewById(R.id.listitems_nametxt);
                    TextView mCategoryTextView = (TextView) v.findViewById(R.id.listitems_categorytxt);
                    if (mDistanceTextView != null) {
                        mDistanceTextView.setText(poi.getDistance()+"km");                            
                        }
                    if(mNameTextView != null){
                        mNameTextView.setText(poi.getName());
                    }
                    if(mCategoryTextView != null){
                        mCategoryTextView.setText(poi.getType());
                        setImage(poi.getType(), v);

                    }
            }
            return v;
    }

    private void setImage(String type, View v) {
        if ("shopping".equals(type)){
            ImageView mImage = (ImageView) v.findViewById(R.id.imageView1);
            mImage.setImageResource(R.drawable.shopping);
        }
        if ("liegestelle".equals(type)){
            ImageView mImage = (ImageView) v.findViewById(R.id.imageView1);
            mImage.setImageResource(R.drawable.liegestelle);
        }
        if ("restaurant".equals(type)){
            ImageView mImage = (ImageView) v.findViewById(R.id.imageView1);
            mImage.setImageResource(R.drawable.restaurant);
        }
        if ("schleuse".equals(type)){
            ImageView mImage = (ImageView) v.findViewById(R.id.imageView1);
            mImage.setImageResource(R.drawable.schleuse);
        }
        if ("verein".equals(type)){
            ImageView mImage = (ImageView) v.findViewById(R.id.imageView1);
            mImage.setImageResource(R.drawable.verein);
        }
        if ("tankstelle".equals(type)){
            ImageView mImage = (ImageView) v.findViewById(R.id.imageView1);
            mImage.setImageResource(R.drawable.tankstelle);
        }
        if ("faekalien".equals(type)){
            ImageView mImage = (ImageView) v.findViewById(R.id.imageView1);
            mImage.setImageResource(R.drawable.faekalien);
        }
        if ("werkstatt".equals(type)){
            ImageView mImage = (ImageView) v.findViewById(R.id.imageView1);
            mImage.setImageResource(R.drawable.werkstatt);
        }
        if ("uebernachtung".equals(type)){
            ImageView mImage = (ImageView) v.findViewById(R.id.imageView1);
            mImage.setImageResource(R.drawable.uebernachtung);
        }

    }



   @Override
    public Filter getFilter()
    {
        if(filter == null)
            filter = new POITypeFilter();
        return filter;
    }

    private class POITypeFilter extends Filter
    {

        @Override
        protected FilterResults performFiltering(CharSequence constraint) {
            // NOTE: this function is *always* called from a background thread, and
            // not the UI thread.
            constraint = constraint.toString().toLowerCase();
            FilterResults result = new FilterResults();
            if(constraint != null && constraint.toString().length() > 0)
            {
                ArrayList<POI> filt = new ArrayList<POI>();
                ArrayList<POI> lItems = new ArrayList<POI>();
                synchronized (this)
                {
                    lItems.addAll(items);
                }
                for(int i = 0, l = lItems.size(); i < l; i++)
                {
                    POI m = lItems.get(i);
                    if(m.getType().toLowerCase().contains(constraint))
                        filt.add(m);
                }
                result.count = filt.size();
                result.values = filt;
            }
            else
            {
                synchronized(this)
                {
                    result.values = items;
                    result.count = items.size();
                }
            }
            return result;
        }

        @SuppressWarnings("unchecked")
        @Override
        protected void publishResults(CharSequence constraint, FilterResults results) {
            // NOTE: this function is *always* called from the UI thread.
            filtered = (ArrayList<POI>)results.values;
            notifyDataSetChanged();
            clear();
            for(int i = 0, l = filtered.size(); i < l; i++)
                add(filtered.get(i));
            notifyDataSetInvalidated();
        }

    }


}

Я пытаюсь переопределить метод getFilter, чтобы я мог фильтровать каждый POI по POI.type и обновлять listView.Я называю getFilter следующим образом:

    @Override
protected void onRestart() {
    super.onRestart();
    mAdapter.getFilter().filter(getFilterSettings());
    mAdapter.notifyDataSetChanged();
}

Это просто возвращает черный экран, как будто все отфильтровано.Я поставил точки останова над getFilter, но приложение действительно входит в него, поэтому я не уверен, что приложение использует этот код.Есть что-то очевидное, чего мне не хватает?

ОБНОВЛЕНИЕ - На полпути туда

У меня была пара проблем здесь.Выглядело так, как будто приложение не вызывает getFilter как точки останова, где не останавливаться на достигнутом.На самом деле виртуальная машина Davlik может использовать только столько точек останова (это не так много, чтобы помнить об этом).Он прекратил использовать точки останова в тот момент, когда я использую код, который хотел проанализировать.Я думаю, что мне не повезло.

Тогда где некоторые проблемы с кодом. Я изменил

 private ArrayList<POI> items; 

на public.Таким образом, он может быть прочитан в новый массив, который фильтрует результаты.Теперь просто чтобы выяснить, как заставить arrayAdapter фильтровать снова, но на исходном массиве.Ничего себе, это оказывается длительным процессом.

1 Ответ

2 голосов
/ 07 августа 2011

Если вы хотите создать пользовательский фильтр, все, что вам нужно сделать, это создать метод toString () в вашем классе POI, который возвращает значение, по которому вы хотите фильтровать.

...