You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Fragment中用EditText实现ListView的名称与描述搜索(含自定义适配器)

Hey there! Let's work through your two search-related challenges for ListView in Android. I'll walk you through modifying your custom adapter to support filtering, then hooking it up to an EditText in your Fragment to search both names and descriptions.


Step 1: Modify Your Custom Adapter to Support Filtering

The core of ListView search functionality relies on implementing the Filterable interface in your adapter. We'll need to track two data sets: the original full dataset (used as the source for filtering) and the filtered dataset (what gets displayed in the ListView).

Here's a complete example of how to adjust your adapter (replace the Item class with your actual data model):

public class CustomAdapter extends BaseAdapter implements Filterable {
    private final Context context;
    private final List<Item> originalItems; // Stores the full, unfiltered data
    private List<Item> filteredItems; // Stores the results to display
    private ItemFilter itemFilter;

    public CustomAdapter(Context context, List<Item> items) {
        this.context = context;
        this.originalItems = new ArrayList<>(items);
        this.filteredItems = new ArrayList<>(items);
        this.itemFilter = new ItemFilter();
    }

    // --- BaseAdapter Overrides ---
    @Override
    public int getCount() {
        return filteredItems.size();
    }

    @Override
    public Item getItem(int position) {
        return filteredItems.get(position);
    }

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

    @Override
    public View getView(int position, View convertView, ViewGroup parent) {
        // Keep your existing getView implementation here
        // Make sure you use filteredItems.get(position) to bind data to the view
        ViewHolder holder;
        if (convertView == null) {
            convertView = LayoutInflater.from(context).inflate(R.layout.your_list_item_layout, parent, false);
            holder = new ViewHolder();
            holder.tvName = convertView.findViewById(R.id.tv_name);
            holder.tvDescription = convertView.findViewById(R.id.tv_description);
            convertView.setTag(holder);
        } else {
            holder = (ViewHolder) convertView.getTag();
        }

        Item currentItem = filteredItems.get(position);
        holder.tvName.setText(currentItem.getName());
        holder.tvDescription.setText(currentItem.getDescription());
        return convertView;
    }

    // --- Filterable Implementation ---
    @Override
    public Filter getFilter() {
        return itemFilter;
    }

    // Custom Filter class to handle search logic
    private class ItemFilter extends Filter {
        @Override
        protected FilterResults performFiltering(CharSequence constraint) {
            FilterResults results = new FilterResults();
            List<Item> tempFilteredList = new ArrayList<>();

            String searchQuery = constraint.toString().toLowerCase().trim();

            if (TextUtils.isEmpty(searchQuery)) {
                // If search is empty, show all original items
                tempFilteredList.addAll(originalItems);
            } else {
                // Check each item for matches in name OR description
                for (Item item : originalItems) {
                    boolean matchesName = item.getName().toLowerCase().contains(searchQuery);
                    boolean matchesDescription = item.getDescription().toLowerCase().contains(searchQuery);
                    if (matchesName || matchesDescription) {
                        tempFilteredList.add(item);
                    }
                }
            }

            results.values = tempFilteredList;
            results.count = tempFilteredList.size();
            return results;
        }

        @Override
        protected void publishResults(CharSequence constraint, FilterResults results) {
            filteredItems.clear();
            filteredItems.addAll((List<Item>) results.values);
            notifyDataSetChanged(); // Refresh the ListView with new results
        }
    }

    // --- Helper Classes ---
    private static class ViewHolder {
        TextView tvName;
        TextView tvDescription;
    }

    // Replace this with your actual data model class
    public static class Item {
        private final String name;
        private final String description;

        public Item(String name, String description) {
            this.name = name;
            this.description = description;
        }

        public String getName() {
            return name;
        }

        public String getDescription() {
            return description;
        }
    }
}

Step 2: Connect EditText to ListView in Your Fragment

Next, we'll set up the Fragment to listen for input in the EditText and trigger the adapter's filter.

1. Fragment Layout (e.g., fragment_search.xml)

Add an EditText and ListView to your layout:

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    android:padding="16dp">

    <EditText
        android:id="@+id/et_search"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:hint="Search by name or description..."
        android:inputType="text" />

    <ListView
        android:id="@+id/list_view"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:layout_marginTop="16dp" />

</LinearLayout>

2. Fragment Code

Initialize the adapter and attach a TextWatcher to the EditText to trigger filtering as the user types:

public class SearchFragment extends Fragment {
    private EditText etSearch;
    private ListView listView;
    private CustomAdapter adapter;

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
        return inflater.inflate(R.layout.fragment_search, container, false);
    }

    @Override
    public void onViewCreated(@NonNull View view, @Nullable Bundle savedInstanceState) {
        super.onViewCreated(view, savedInstanceState);

        // Initialize views
        etSearch = view.findViewById(R.id.et_search);
        listView = view.findViewById(R.id.list_view);

        // Load your actual data here (replace with your data source)
        List<CustomAdapter.Item> itemList = new ArrayList<>();
        itemList.add(new CustomAdapter.Item("Laptop", "Portable computing device"));
        itemList.add(new CustomAdapter.Item("Headphones", "Audio listening accessory"));
        itemList.add(new CustomAdapter.Item("Smartphone", "Mobile communication device"));

        // Set up the adapter
        adapter = new CustomAdapter(requireContext(), itemList);
        listView.setAdapter(adapter);

        // Listen for text changes to trigger search
        etSearch.addTextChangedListener(new TextWatcher() {
            @Override
            public void beforeTextChanged(CharSequence s, int start, int count, int after) {}

            @Override
            public void onTextChanged(CharSequence s, int start, int before, int count) {
                // Trigger filter with the current input text
                adapter.getFilter().filter(s);
            }

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

Key Notes

  • Case Insensitivity: The code converts both the search query and item fields to lowercase to ensure case-insensitive matching.
  • Data Source: If your data comes from a database or network call, initialize the adapter after the data is fully loaded.
  • Performance: For large datasets, consider optimizing the filtering logic (e.g., using background threads, though the performFiltering method already runs off the main thread by default).

内容的提问来源于stack exchange,提问作者Giuseppe Fontana

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.19 10:43:16