How to Use Material Design Buttons in Android (XML & Compose)

How to Use Material Design Buttons in Android (XML & Compose)


Material Design buttons are the simplest way to build clear, tappable actions in Android apps. In this step-by-step guide, you’ll learn exactly how to use Material Design buttons in Android using modern Jetpack Compose (recommended) and classic XML with MaterialButton. We’ll cover button types, styling (color, shape, size), adding icons, handling clicks in Kotlin and Java, accessibility tips, and when to choose each approach. By the end, you’ll know how to add and style Material buttons confidently in new or existing projects.

What are Material Design buttons, and when should you use them?

Android Material Design 3 button types and states on a phone mockup for beginners
Material 3 button types with enabled, pressed, and disabled states.

Material Design buttons are prebuilt, accessible components that follow Google’s Material 3 (M3) design system. They give your app consistent look, feel, and behavior with minimal code.

  • Jetpack Compose (recommended for new apps): Use Material 3 composables like Button, FilledTonalButton, ElevatedButton, OutlinedButton, and TextButton from androidx.compose.material3.
  • View system (XML, legacy or existing apps): Use com.google.android.material.button.MaterialButton and MaterialButtonToggleGroup with a Material 3 theme.

Pick Compose for new development (it’s the Compose-first path for Material on Android). Stick with Views in existing projects until you migrate.

Compose vs XML for Material 3 buttons

Approach Main APIs Dependency Theme requirement Best for
Jetpack Compose Button, FilledTonalButton, ElevatedButton, OutlinedButton, TextButton, SegmentedButton androidx.compose.material3:material3 via Compose BOM MaterialTheme (M3 colorScheme, shapes, typography) New apps, rapid UI iteration, Kotlin-first teams
Views (XML) MaterialButton, MaterialButtonToggleGroup com.google.android.material:material Theme.Material3.* parent in app theme Existing XML screens, incremental adoption, Java support

Tip: For “How to use Material Design buttons in Android” in 2026+—prefer Compose unless you must stay on XML.

Project setup

Light and dark theme Android screens showing Material 3 button hierarchy and FAB placement
Button hierarchy and theming: primary, secondary, tertiary, and FAB in light and dark mode.

If you’re using Jetpack Compose (recommended)

Add the Compose Bill of Materials (BOM) and Material 3 dependency. The BOM keeps all Compose versions aligned:

// app/build.gradle (Kotlin DSL)
android {
buildFeatures {
compose = true
}
composeOptions {
kotlinCompilerExtensionVersion = "latest" // Use AndroidX releases index for the latest
}
}

dependencies {
implementation(platform("androidx.compose:compose-bom:<latest>"))
implementation("androidx.compose.material3:material3")
implementation("androidx.compose.ui:ui")
implementation("androidx.compose.ui:ui-tooling-preview")
debugImplementation("androidx.compose.ui:ui-tooling")
implementation("androidx.activity:activity-compose:<latest>")
}

Use the latest versions from the AndroidX releases index. Wrap screens with MaterialTheme so buttons pick up your color scheme, typography, and shapes.

If you’re using the View system (XML)

Add the Material Components dependency and apply a Material 3 theme.

// app/build.gradle (Kotlin DSL)
dependencies {
implementation("com.google.android.material:material:<latest>")
}

Enable a Material 3 parent theme in themes.xml (or styles.xml):

<resources>
<style name="Theme.MyApp" parent="Theme.Material3.DayNight.NoActionBar">
<item name="colorPrimary">@color/your_primary</item>
<!-- Define your color scheme etc. -->
</style>
</resources>

Flow: From setup to your first Material button

Compose path
1. Add Compose BOM + material3
2. Wrap UI with MaterialTheme (M3)
3. Place Button { Text("Click") }
4. Handle onClick { ... } in Kotlin
5. Verify states: pressed, focused, disabled; min 48dp

XML (Views) path
1. Add com.google.android.material:material
2. Set Theme.Material3.* in app theme
3. Add MaterialButton in XML
4. Call setOnClickListener { ... }
5. Check ripple, elevation/tonal style, contrast

This flow is a quick memory aid for beginners learning how to use Material Design buttons in Android across Compose and XML.

Add your first Material button in Compose

Here’s a minimal Compose screen with the most common button variants.

import androidx.compose.foundation.layout.*
import androidx.compose.material.icons.Icons
import androidx.compose.material.icons.filled.Save
import androidx.compose.material3.*
import androidx.compose.runtime.*
import androidx.compose.ui.Modifier
import androidx.compose.ui.unit.dp

@Composable
fun ButtonsDemo() {
var clicks by remember { mutableStateOf(0) }

Column(
modifier = Modifier
.padding(16.dp)
.fillMaxSize(),
verticalArrangement = Arrangement.spacedBy(12.dp)
) {
Button(onClick = { clicks++ }, modifier = Modifier.fillMaxWidth()) {
Text("Primary action (Filled)")
}

FilledTonalButton(onClick = { clicks++ }, modifier = Modifier.fillMaxWidth()) {
Text("Secondary (Filled Tonal)")
}

ElevatedButton(onClick = { clicks++ }, modifier = Modifier.fillMaxWidth()) {
Text("Lower emphasis (Elevated)")
}

OutlinedButton(onClick = { clicks++ }, modifier = Modifier.fillMaxWidth()) {
Text("Secondary action (Outlined)")
}

TextButton(onClick = { clicks++ }, modifier = Modifier.fillMaxWidth()) {
Text("Tertiary action (TextButton)")
}

Button(onClick = {}, enabled = false, modifier = Modifier.fillMaxWidth()) {
Text("Disabled")
}

// Button with icon
Button(onClick = { clicks++ }, modifier = Modifier.fillMaxWidth()) {
Icon(Icons.Default.Save, contentDescription = null)
Spacer(Modifier.width(8.dp))
Text("Save")
}

Text("Total clicks: $clicks")
}
}

Guideline: use higher-emphasis buttons (Filled, FilledTonal, Elevated) for primary actions; use Outlined and Text buttons for secondary/tertiary actions.

Styling: change color, shape, and size (Compose)

You can override colors, shapes, and sizes at the button level or via your theme.

import androidx.compose.foundation.shape.RoundedCornerShape
import androidx.compose.ui.graphics.Color

@Composable
fun StyledButton() {
Button(
onClick = { /* TODO */ },
modifier = Modifier
.fillMaxWidth()
.height(56.dp), // Keep at least 48.dp for touch target
shape = RoundedCornerShape(24.dp),
colors = ButtonDefaults.buttonColors(
containerColor = Color(0xFF0061A5),
contentColor = Color.White,
disabledContainerColor = Color(0xFF0061A5).copy(alpha = 0.38f),
disabledContentColor = Color.White.copy(alpha = 0.38f)
),
elevation = ButtonDefaults.buttonElevation(defaultElevation = 0.dp)
) {
Text("Custom styled")
}
}

Compose Material 3 buttons include proper state layers and ripples by default, so you don’t need to add them manually.

Handle button clicks in Compose (Kotlin)

import android.widget.Toast
import androidx.compose.ui.platform.LocalContext

@Composable
fun ClickHandlerButton() {
val context = LocalContext.current
Button(onClick = {
Toast.makeText(context, "Button clicked!", Toast.LENGTH_SHORT).show()
}) {
Text("Click me")
}
}

Segmented buttons (Compose)

Use segmented buttons for mutually exclusive choices.

import androidx.compose.material3.*
import androidx.compose.runtime.*

@Composable
fun SegmentedExample() {
val options = listOf("Day", "Week", "Month")
var selectedIndex by remember { mutableStateOf(0) }

SingleChoiceSegmentedButtonRow {
options.forEachIndexed { index, label ->
SegmentedButton(
selected = index == selectedIndex,
onClick = { selectedIndex = index },
shape = SegmentedButtonDefaults.itemShape(index, options.size),
label = { Text(label) }
)
}
}
}

Using MaterialButton in XML (Views)

If you’re maintaining a Views-based app, you can add Material Design buttons with MaterialButton. Make sure your activity/theme uses a Theme.Material3.* parent.

Add a MaterialButton in a layout

<com.google.android.material.button.MaterialButton
android:id="@+id/btnPrimary"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Primary action"
style="@style/Widget.Material3.Button"
app:icon="@drawable/ic_save_24"
app:iconGravity="textStart"
app:iconPadding="8dp" />

<com.google.android.material.button.MaterialButton
android:id="@+id/btnOutlined"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Outlined"
style="@style/Widget.Material3.Button.OutlinedButton" />

<com.google.android.material.button.MaterialButton
android:id="@+id/btnText"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Text button"
style="@style/Widget.Material3.Button.TextButton" />

Common style options are Widget.Material3.Button, .FilledTonalButton, .ElevatedButton, .OutlinedButton, and .TextButton.

Change MaterialButton color and shape (XML)

For quick demos, you can customize directly on the view, but prefer theme-level colors for production.

<com.google.android.material.button.MaterialButton
android:id="@+id/btnCustom"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Custom styled"
style="@style/Widget.Material3.Button"
app:cornerRadius="24dp"
app:strokeWidth="1dp"
app:strokeColor="@color/teal_700"
android:backgroundTint="@color/blue_primary"
android:textColor="@android:color/white" />

In Material 3, it’s best to set your color scheme in the theme (e.g., colorPrimary, colorSecondary) so all buttons update consistently.

Handle MaterialButton clicks in Kotlin and Java

Kotlin:

Code
class MainActivity : AppCompatActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)

        val btn = findViewById<com.google.android.material.button.MaterialButton>(R.id.btnPrimary)
        btn.setOnClickListener {
            Toast.makeText(this, "Clicked!", Toast.LENGTH_SHORT).show()
        }
    }
}

Java:

Code
class="cd-keyword cd-access">public class MainActivity extends AppCompatActivity {
    class="cd-annotation">@Override
    class="cd-keyword cd-access">protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        MaterialButton btn = findViewById(R.id.btnPrimary);
        btn.setOnClickListener(v ->
            Toast.makeText(this, "Clicked!", Toast.LENGTH_SHORT).show()
        );
    }
}

Toggle groups with MaterialButtonToggleGroup (Views)

Use toggle groups for single or multiple selection.

<com.google.android.material.button.MaterialButtonToggleGroup
android:id="@+id/toggleGroup"
android:layout_width="match_parent"
android:layout_height="wrap_content"
app:singleSelection="true">

<com.google.android.material.button.MaterialButton
android:id="@+id/toggleDay"
style="@style/Widget.Material3.Button.OutlinedButton"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:text="Day" />

<com.google.android.material.button.MaterialButton
android:id="@+id/toggleWeek"
style="@style/Widget.Material3.Button.OutlinedButton"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:text="Week" />

<com.google.android.material.button.MaterialButton
android:id="@+id/toggleMonth"
style="@style/Widget.Material3.Button.OutlinedButton"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:text="Month" />
</com.google.android.material.button.MaterialButtonToggleGroup>

In code, you can observe checked states via addOnButtonCheckedListener.

Practical tips for Android button styles (Material 3)

  • Stick to one primary button per screen to reduce confusion.
  • Use icons sparingly; pair them with text unless the meaning is universally clear.
  • Keep minimum touch targets at least 48dp x 48dp.
  • Use content labels for icon-only controls and verify with Accessibility Scanner.
  • Respect contrast: text should meet accessible contrast against the container color.
  • Prefer theme-level styling for consistent appearance across the app.

Pre-release checklist: Material 3 buttons

  • Primary CTA appears once per screen; secondary actions use Outlined/Text.
  • Touch target ≥ 48dp height and width (Compose: set min height; XML: ensure padding).
  • Readable label using sentence case and localized strings.
  • Icon-only buttons have contentDescription (Compose) or android:contentDescription (XML).
  • Contrast checked for label vs. container across light/dark themes.
  • States verified: default, pressed, focused, disabled (ripple/state layers visible).
  • Keyboard focus works: tab to button and press Enter/Space activates it.
  • TalkBack/VoiceOver announces label and state correctly.
  • No hardcoded per-view colors unless intentionally overriding theme.
  • Click handlers are idempotent or debounce long operations to prevent double taps.

Use this list whenever you add or restyle buttons to ensure quality and accessibility.

Putting it together: a simple screen (Compose)

@Composable
fun ButtonsScreen() {
MaterialTheme { // Provide your colorScheme, typography, shapes if customized
Scaffold(
topBar = { TopAppBar(title = { Text("Material Buttons") }) }
) { paddingValues ->
Column(
Modifier
.padding(paddingValues)
.padding(16.dp)
.fillMaxSize(),
verticalArrangement = Arrangement.spacedBy(12.dp)
) {
ButtonsDemo()
Divider()
StyledButton()
Divider()
SegmentedExample()
}
}
}
}

Output / Result

When you run the Compose sample, you’ll see a screen titled “Material Buttons” showing:

  • A vertical stack of buttons: Filled, FilledTonal, Elevated, Outlined, Text, Disabled, and one with an icon and label.
  • A custom-styled rounded button with a custom color.
  • A segmented control with “Day”, “Week”, “Month” where only one option can be active.
  • Each click updates a visible counter or shows a Toast, confirming that clicks are handled correctly.

Common mistakes to avoid

  • Using plain AppCompat Button and expecting Material 3 styling. Use Compose Material 3 buttons or MaterialButton with a Material 3 theme.
  • Overusing high-emphasis (filled) buttons on one screen. Match button emphasis to action importance.
  • Touch targets under 48dp or tiny icon-only buttons without labels.
  • Hardcoding colors on individual buttons instead of theming—this makes maintenance harder.

FAQ: People also ask

What is a MaterialButton in Android?

MaterialButton is the Material Components button for the View system (XML). It supports Material 3 styles, icons, strokes, and shape customization. In Jetpack Compose, the equivalent components are Button, FilledTonalButton, ElevatedButton, OutlinedButton, and TextButton from androidx.compose.material3.

How do I add Material Design buttons in Android Studio?

  • Compose: add the Compose BOM and androidx.compose.material3:material3, then use Button { Text("...") } in your composables.
  • Views: add com.google.android.material:material, set your app theme to Theme.Material3.*, then add MaterialButton in your XML layout.

How do I change the color and shape of a MaterialButton?

  • Compose: use ButtonDefaults.buttonColors(...) and the shape parameter (e.g., RoundedCornerShape(24.dp)).
  • Views: use theme-level colors or view attributes like android:backgroundTint, app:cornerRadius, and app:strokeColor; or apply a Widget.Material3.Button.* style variant.

Do I need the Material Components library to use MaterialButton?

Yes. For XML-based apps, add com.google.android.material:material. For Compose, use the Material 3 Compose library androidx.compose.material3:material3 managed by the Compose BOM.

How do I handle MaterialButton clicks in Kotlin or Java?

  • Compose: pass an onClick lambda to the button.
  • Views: call setOnClickListener { ... } in Kotlin or setOnClickListener(...) in Java.

Recap: How to use Material Design buttons in Android

  • Use Jetpack Compose Material 3 buttons for new apps; use MaterialButton in existing XML apps.
  • Add dependencies via the Compose BOM (Compose) or Material Components (Views).
  • Choose the right emphasis: Filled for primary, Tonal/Elevated for supporting, Outlined/Text for secondary/tertiary.
  • Style via theme first; override per-button only when needed.
  • Ensure accessibility: 48dp targets, good contrast, clear labels.

Sources / Further reading

That’s it! You’ve learned how to use Material Design buttons in Android with both Jetpack Compose and the classic View system, including how to add them, style them, and handle clicks in Kotlin and Java. Try these patterns in your next screen and keep your UI consistent, accessible, and modern.

Subscribe
Notify of
guest
0 Comments
Oldest
Newest Most Voted