Android compose material3 dropdown menu bug on landscape?


Is this behaviour a bug with the experimental material3 features on Android 16?

When the app is portrait mode everything works correctly on Android 15 and 16.

When the app is in landscape mode Android 15 works correctly but Android 16 does not.

e.g. DropMenu on Android 15 Landscape is aligned with the Button
enter image description here

DropMenu on Android 16 Landscape is Not aligned with the Button

enter image description here

Compose Code

import android.os.Bundle
import androidx.activity.ComponentActivity
import androidx.activity.compose.setContent
import androidx.activity.enableEdgeToEdge
import androidx.compose.foundation.layout.padding
import androidx.compose.foundation.layout.safeDrawingPadding
import androidx.compose.material.icons.Icons
import androidx.compose.material.icons.filled.MoreVert
import androidx.compose.material3.DropdownMenu
import androidx.compose.material3.DropdownMenuItem
import androidx.compose.material3.ExperimentalMaterial3Api
import androidx.compose.material3.ExposedDropdownMenuBox
import androidx.compose.material3.Icon
import androidx.compose.material3.IconButton
import androidx.compose.material3.MaterialTheme
import androidx.compose.material3.Scaffold
import androidx.compose.material3.Text
import androidx.compose.material3.TopAppBar
import androidx.compose.material3.TopAppBarDefaults.topAppBarColors
import androidx.compose.runtime.Composable
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.remember
import androidx.compose.runtime.setValue
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.tooling.preview.Preview
import com.github.zardozz.material3scafold.ui.theme.Material3ScafoldTheme


class MainActivity : ComponentActivity() {
    @OptIn(ExperimentalMaterial3Api::class)
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        enableEdgeToEdge()
        setContent {
            Material3ScafoldTheme {
                Scaffold(modifier = Modifier.safeDrawingPadding(),
                    topBar = {
                    TopAppBar(
                        colors = topAppBarColors(
                            containerColor = MaterialTheme.colorScheme.primary,
                            titleContentColor = MaterialTheme.colorScheme.onSecondary,
                        ),
                        title = {
                            Text("Top app bar")
                        },
                        actions = {
                            ActionDropdownMenu()
                        },
                    )
                },
                ) { innerPadding ->
                    Greeting(
                        name = "Android",
                        modifier = Modifier.padding(innerPadding)
                    )
                }
            }
        }
    }
}

@Composable
fun ActionDropdownMenu() {
    var expanded by remember { mutableStateOf(false) }
    IconButton(onClick = { expanded = !expanded }) {
        Icon(Icons.Filled.MoreVert,
            contentDescription = "More options",
            tint = Color.White)
    }
    DropdownMenu(
        expanded = expanded,
        onDismissRequest = { expanded = false }
    ) {
        DropdownMenuItem(
            text = { Text("Option 1") },
            onClick = { /* Do something... */ }
        )
        DropdownMenuItem(
            text = { Text("Option 2") },
            onClick = { /* Do something... */ }
        )
    }
}

@Composable
fun Greeting(name: String, modifier: Modifier = Modifier) {
    Text(
        text = "Hello $name!",
        modifier = modifier
    )
}

@Preview(showBackground = true)
@Composable
fun GreetingPreview() {
    Material3ScafoldTheme {
        Greeting("Android")
    }
}

Or have I done something wrong?

1
Mar 19 at 12:06 AM
User AvatarAndrew
#android#android-jetpack-compose#android-jetpack-compose-material3

Accepted Answer

So I tried the scenario on different devices and emulators and noticed that the additional padding given to the DropDownMenu was equivalent to the size of the Camera cutout.

A simple way to check this would be:

  1. Go to Settings > System > Developer options.

  2. Look for "Display cutout" (sometimes called "Simulate a display with a cutout").

  3. Select "Waterfall cutout". This will force the system to remove insets even in portrait, and especially in landscape.

And that gives you something like this:

Issue fixed without cutout

With the Device default cutout, you get back to the original issue you had:

Issue with default device cutout

Manipulating insets doesn't seem to work in this situation so your best bet would be to report this as an issue on Google.

User AvatarMofe Ejegi
Mar 19 at 11:00 AM
1