Status Update
Comments
ro...@gmail.com <ro...@gmail.com> #3
Thanks for the report!
ke...@google.com <ke...@google.com>
ke...@google.com <ke...@google.com>
ke...@google.com <ke...@google.com>
ap...@google.com <ap...@google.com> #4
The release notes documentation has been edited to clarify this change in behavior for line height.
To support non-standard text sizes, we encourage users to follow the Material design system and use a different style = LocalTextStyle.current.copy(lineHeight = TextUnit.Unspecified)
, or create a custom Typography
entirely.
ru...@gmail.com <ru...@gmail.com> #5
ke...@payback.net <ke...@payback.net> #6
In my case, I have multiple font sizes in the same Text
(using SpanStyle
in AnnotatedString
). There are legitimate reasons for this. For example, when combining Chinese and English (phonetic) together (for language-learning purposes).
tf...@gmail.com <tf...@gmail.com> #7
There’s already a dedicated issue about the back not working when android:enableOnBackInvokedCallback=“true”
is set:
It seems like it’s blocked by a general lack of predictive back support in Compose, though:
sh...@navi.com <sh...@navi.com> #8
ar...@gmail.com <ar...@gmail.com> #9
I've tried androidx.compose.material3:material3:1.2.0-beta01
and I believe it's still not working. BackHandler {}
is not called inside ModalBottomSheet
, the sheet is closing instead.
ay...@gmail.com <ay...@gmail.com> #10
Any ideas on why this is marked as fixed?
el...@ur.se <el...@ur.se> #11
tf...@gmail.com <tf...@gmail.com> #12
The fix wasn't to support BackHandler {}
. They just added a new properties
arg that you can set whether the sheet should be dismissed on back or not:
ModalBottomSheet(
...
properties = ModalBottomSheetDefaults.properties(shouldDismissOnBackPress = /* boolean goes here */),
...
)
Since the sheet is in a separate window, I'm afraid this might be the best they can do. That's pretty similar to the API of dialogs, which also have their own window:
Dialog(
...
properties = DialogProperties(dismissOnBackPress = /* boolean goes here */),
...
)
But of course the APIs aren't super consistent 😅
as...@gmail.com <as...@gmail.com> #13
da...@tixr.com <da...@tixr.com> #14
The bug as it's stated in the title and the snippet still exists despite the "fix": it remains impossible to use a BackHandler
inside a ModalBottomSheet.
Some thoughts after looking at the code: somehow the ModalBottomSheetWindow
needs to implement a OnBackPressedDispatcherOwner
and delegate to it when back is pressed (in dispatchKeyEvent
), instead of directly calling onDismissRequest like it does today (material3 version 1.2.0).
I note that the "ModalBottomSheetWindow" is actually a View
, not a Window
-- perhaps that's why this is not trivial to fix.
Knowing the code doesn't give me a good idea for a workaround though...
da...@tixr.com <da...@tixr.com> #15
I have found a workaround. It consists in intercepting the key event, doing the same checks that ModalBottomSheetWindow.dispatchKeyEvent
would do, and then delegating that to the OnBackPressedDispatcherOwner
manually.
@Composable
fun ModalBottomSheetWithBackHandling(
onDismissRequest: () -> Unit,
modifier: Modifier = Modifier,
sheetState: SheetState = rememberModalBottomSheetState(),
properties: ModalBottomSheetProperties = ModalBottomSheetDefaults.properties(),
content: @Composable ColumnScope.() -> Unit,
) {
val scope = rememberCoroutineScope()
BackHandler(enabled = sheetState.targetValue != SheetValue.Hidden) {
// Always catch back here, but only let it dismiss if shouldDismissOnBackPress.
// If not, it will have no effect.
if (properties.shouldDismissOnBackPress) {
scope.launch { sheetState.hide() }.invokeOnCompletion {
if (!sheetState.isVisible) {
onDismissRequest()
}
}
}
}
val requester = remember { FocusRequester() }
val backPressedDispatcherOwner = LocalOnBackPressedDispatcherOwner.current
ModalBottomSheet(
onDismissRequest = onDismissRequest,
modifier = modifier
.focusRequester(requester)
.focusable()
.onPreviewKeyEvent {
if (it.key == Key.Back && it.type == KeyEventType.KeyUp && !it.nativeKeyEvent.isCanceled) {
backPressedDispatcherOwner?.onBackPressedDispatcher?.onBackPressed()
return@onPreviewKeyEvent true
}
return@onPreviewKeyEvent false
},
properties = ModalBottomSheetDefaults.properties(
securePolicy = properties.securePolicy,
isFocusable = properties.isFocusable,
// Set false otherwise the onPreviewKeyEvent doesn't work at all.
// The functionality of shouldDismissOnBackPress is achieved by the BackHandler.
shouldDismissOnBackPress = false,
),
content = content,
)
LaunchedEffect(Unit) {
requester.requestFocus()
}
}
ni...@gmail.com <ni...@gmail.com> #16
Thank you for your workaround code!
j6...@gmail.com <j6...@gmail.com> #17
The problem is if you're using focusManager.clearFocus()
anywhere in your code the ModalBottomSheet will lose focus.
da...@tixr.com <da...@tixr.com> #18
BackHandler seems to be working in androidx.compose.material3:material3:1.3.0-beta02 out of the box without the workaround I posted a couple of messages above.
de...@gmail.com <de...@gmail.com> #19
pb...@gmail.com <pb...@gmail.com> #20
jo...@gmail.com <jo...@gmail.com> #21
se...@gmail.com <se...@gmail.com> #22
The short version of this solution that worked for me:
Description
Given the code
Steps:
Expectation: BackHandler's lambda is called and snackbar appears on the screen.
Reality: modal bottom sheet closes.