Material Search Bar in Android
Last Updated :
18 Feb, 2025
A Material Search Bar is an essential component in modern Android applications, enhancing the user experience by allowing quick searches. Google’s Material Design provides sleek, user-friendly search bars that blend well with UI/UX standards. This guide will help you integrate a Material Search Bar in your Android app.
Anatomy of the Material Search Bar
In the below anatomy taking the example of an basic application, one can see the primary action here is search and on tap it opens the Search View.
Steps for Creating Search Bar
Step 1: Create a new Android Studio project
To create a new project in Android Studio please refer to How to Create/Start a New Project in Android Studio.
Step 2: Adding the dependency to the build.gradle(:app) file
We will be using Android’s Material Design Library so we need to import it in the build.gradle.kts (Module :app) file . Here’s the dependency we need to add:
implementation("com.google.android.material:material:1.12.0")
Step 3: Working with activity_main.xml file
We are going to create a SearchBar and a SearchView, which work together to let users type in their search. There is also a ListView that shows a list of names. When the user taps on the SearchBar, the SearchView pops up so they can type in a name to search. The whole layout is inside an AppBarLayout to make sure everything looks neat and follows Material Design rules.
activity_main.xml:
XML
<androidx.coordinatorlayout.widget.CoordinatorLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".MainActivity">
<com.google.android.material.appbar.AppBarLayout
android:layout_width="match_parent"
android:layout_height="wrap_content">
<com.google.android.material.search.SearchBar
android:id="@+id/search_bar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:hint="Search name" />
</com.google.android.material.appbar.AppBarLayout>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
app:layout_behavior="@string/appbar_scrolling_view_behavior">
<ListView
android:id="@+id/listView"
android:layout_width="match_parent"
android:layout_height="match_parent"/>
</LinearLayout>
<com.google.android.material.search.SearchView
android:id="@+id/search_view"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:hint="Search name"
app:layout_anchor="@id/search_bar"/>
</androidx.coordinatorlayout.widget.CoordinatorLayout>
Layout Design:
Step : Working with the MainActivity file
First, let's set up the SearchBar, SearchView, and ListView with a list of names. When the user taps on the SearchBar, the SearchView appears so they can start searching. As they type, a TextWatcher listens for changes and updates the list to only show names that match the search. This way, the list filters in real-time, making it easy for users to find what they are looking for. The code for the MainActivity file is given below in both Java and Kotlin.
MainActivity.java
package org.geeksforgeeks.demo;
import android.os.Bundle;
import android.text.Editable;
import android.text.TextWatcher;
import android.widget.ArrayAdapter;
import android.widget.ListView;
import androidx.annotation.Nullable;
import androidx.appcompat.app.AppCompatActivity;
import com.google.android.material.search.SearchBar;
import com.google.android.material.search.SearchView;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
public class MainActivity extends AppCompatActivity {
private SearchView searchView;
private SearchBar searchBar;
private ListView listView;
private ArrayAdapter<String> adapter;
private final List<String> dataList = Arrays.asList("Alice", "Bob", "Charlie", "David", "Eve", "Frank");
private final List<String> filteredList = new ArrayList<>();
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
searchView = findViewById(R.id.search_view);
searchBar = findViewById(R.id.search_bar);
listView = findViewById(R.id.listView);
// Hide search on submit and carry the text to search bar
searchView.getEditText().setOnEditorActionListener((v, actionId, event) -> {
searchBar.setText(searchView.getText().toString());
searchView.hide();
return false;
});
// Initialize ListView with data
filteredList.addAll(dataList);
adapter = new ArrayAdapter<>(this, android.R.layout.simple_list_item_1, filteredList);
listView.setAdapter(adapter);
// Show searchView when searchBar is clicked
searchBar.setOnClickListener(v -> searchView.show());
// Handle text change in SearchView input
searchView.getEditText().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) {
filterList(s.toString());
}
@Override
public void afterTextChanged(Editable s) {}
});
}
private void filterList(String query) {
filteredList.clear();
if (query == null || query.isEmpty()) {
filteredList.addAll(dataList);
} else {
for (String item : dataList) {
if (item.toLowerCase().contains(query.toLowerCase())) {
filteredList.add(item);
}
}
}
adapter.notifyDataSetChanged();
}
}
MainActivity.kt
package org.geeksforgeeks.demo
import android.os.Bundle
import android.text.Editable
import android.text.TextWatcher
import android.widget.ArrayAdapter
import android.widget.ListView
import androidx.appcompat.app.AppCompatActivity
import com.google.android.material.search.SearchBar
import com.google.android.material.search.SearchView
class MainActivity : AppCompatActivity() {
private lateinit var searchView: SearchView
private lateinit var searchBar: SearchBar
private lateinit var listView: ListView
private lateinit var adapter: ArrayAdapter<String>
private val dataList = listOf("Alice", "Bob", "Charlie", "David", "Eve", "Frank")
private val filteredList = mutableListOf<String>()
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
searchView = findViewById(R.id.search_view)
searchBar = findViewById(R.id.search_bar)
listView = findViewById(R.id.listView)
// Hide search on submit and carry the text to search bar
searchView.editText
.setOnEditorActionListener { _, _, _ ->
searchBar.setText(searchView.text)
searchView.hide()
false
}
// Initialize ListView with data
filteredList.addAll(dataList)
adapter = ArrayAdapter(this, android.R.layout.simple_list_item_1, filteredList)
listView.adapter = adapter
// Show searchView when searchBar is clicked
searchBar.setOnClickListener {
searchView.show()
}
// Handle text change in SearchView input
searchView.editText.addTextChangedListener(object : TextWatcher {
override fun beforeTextChanged(s: CharSequence?, start: Int, count: Int, after: Int) {}
override fun onTextChanged(s: CharSequence?, start: Int, before: Int, count: Int) {
filterList(s.toString())
}
override fun afterTextChanged(s: Editable?) {}
})
}
private fun filterList(query: String?) {
filteredList.clear()
if (query.isNullOrEmpty()) {
filteredList.addAll(dataList)
} else {
filteredList.addAll(dataList.filter { it.contains(query, ignoreCase = true) })
}
adapter.notifyDataSetChanged()
}
}
Output: