0

カスタム配列アダプター上に構築された ListView にフィルターを実装しました。リストには、有名人の名前とその有名人の写真が表示されます。

public class Celebrities extends ListActivity {

private EditText filterText = null;
ArrayAdapter<CelebrityEntry> adapter = null;
private TextWatcher filterTextWatcher = new TextWatcher() {

    public void afterTextChanged(Editable s) {
    }

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

    public void onTextChanged(CharSequence s, int start, int before,
            int count) {
        adapter.getFilter().filter(s);
    }
};

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

     //disables the up button
     getActionBar().setDisplayHomeAsUpEnabled(true);

     filterText = (EditText) findViewById(R.id.search_box);
     filterText.addTextChangedListener(filterTextWatcher);

     adapter = new CelebrityEntryAdapter(this, getModel());
     setListAdapter(adapter); 
}

toString()そして、CelebrityEntry.java のメソッドをオーバーライドしました。

public final class CelebrityEntry {

private String name;
private int pic;

public CelebrityEntry(String name, int pic) {
    this.name = name;
    this.pic = pic;
}

/**
 * @return name of celebrity
 */
public String getName() {
    return name;
}
/**
 * override the toString function so filter will work
 */
public String toString() {
    return name;
}
/**
 * @return picture of celebrity
 */
public int getPic() {
    return pic;
}

}

ただし、アプリを起動してフィルタリングを開始すると、各リスト エントリには適切な画像が表示されますが、名前は元のリストにすぎず、フィルタを実際に満たした有名人の数に切り捨てられます。Kirsten Dunst がリストの最初のエントリで、Adam Savage が 2 番目のエントリであるとします。Adam Savage をフィルターすると、彼の写真が表示されますが、この 2 つの情報は 1 つのオブジェクトの要素であるにもかかわらず、名前は Kirsten Dunst のままです。

明らかに、これは望ましい結果ではありません。考え?

4

1 に答える 1

1

アダプターの使用方法がわからないので、遅延読み込みを使用して ListView をフィルター処理する方法を示します (スクロールすると新しいビューが膨らむのではなく、行ビューがリサイクルされます)。SlowAdapter 内部クラスを作成します。

private class SlowAdapter extends BaseAdapter {
    private LayoutInflater mInflater;

    public SlowAdapter(Context context) {
        mInflater = (LayoutInflater)context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
    }
    public int getCount() {
        if (filtered) {
            return filteredItems.length;
        } else {
            return unfilteredItems.length;
        }
    }
    public Object getItem(int position) {
        return position;
    }
    public long getItemId(int position) {
        return position;
    }
    public View getView(int position, View convertView, ViewGroup parent) {
        LinearLayout rowView;

        if (convertView == null) {
            rowView = (LinearLayout)mInflater.inflate(R.layout.row, parent, false);
        } else {
            rowView = (LinearLayout)convertView;
        }
        ImageView celebrity_image = rowView.findViewById(R.id.celebrity_image);
        TextView celebrity_name = rowView.findViewById(R.id.celebrity_name);

        if (!filtered) { // use position to get the filtered item.
            CelebrityEntry c = filteredItems[position];
             // do what you do to set the image and text for a celebrity.

        } else { // use position to get the unfiltered item.
            CelebrityEntry c = unfilteredItems[position];
             // do what you do to set the image and text for a celebrity.                 
        }   
        return rowView;
    }
}

次に、textWatcher で、文字列に基づいて有名人をフィルター処理して、filteredItems 配列に入れます。次に、filtered=true を設定して、新しい SlowAdapter を作成し、それを ListView に設定します。

unfilteredItems は、何もフィルタリングされていない場合に使用され、完全なソースからの将来のフィルタリングに使用されます。

于 2013-04-22T23:52:45.993 に答える