Repository navigation
Overview
- addressed: #18, #46, #52, #55, #103
- external contributors: @dkulakov, @falcondpr, @NicholasBoccuzzi
Changes
-
Added web support for
BottomSheetandModalBottomSheet. Installreact-domandreact-native-webalongside the library to use sheets on the web. -
Added floating cards. Each detent can set
left,right, andbottomgaps throughinsets. The gaps change smoothly as the sheet moves between detents. Taps in the gaps reach the modal scrim or the view behind an inline sheet. -
Added
surfaceStylefor corner radii and shadows. The sheet clips its background and content to the same outline while allowing the shadow to extend beyond it.borderCurveis iOS-only, andelevationis Android-only. -
Added
lazyto both sheet components. When enabled, the sheet mounts before opening and unmounts after the closing animation finishes. Reopening mid-animation preserves content state. Reopening after a full close starts with fresh state. An unmounted sheet emits noonPositionChangeevents.lazydefaults tofalseand only applies when there is a closed detent. -
Added
settleDurationto both sheet components. It accepts a finite duration greater than0, in seconds. Animations that start from rest take the full duration. The default is0.45seconds on all platforms, up from about0.2seconds on Android. -
Improved snapping on all platforms. A gentle swipe can reach the next detent before crossing the midpoint. Pausing before release selects the nearest detent. A fast flick carries its speed into the animation and can reach the target before
settleDurationwithout overshooting. -
Added accessible dismissal for
ModalBottomSheet. When tapping the scrim would close the sheet, screen reader users can activate its Dismiss button, perform the VoiceOver escape gesture on iOS, or invoke the TalkBack Dismiss action on Android. These actions select the closed detent directly. UsescrimAccessibilityLabelto localize the button label. -
Changed modal stacking so the most recently opened or reopened sheet appears on top.
nativeOverlaysheets stay above portal sheets. Android back and Escape on Android and web route to the topmost eligible sheet. -
Fixed Android system back bypassing
onCloseRequeston portal sheets. This could send the app to the background on Android 10 while the sheet was open. -
Fixed drags that start sideways or diagonally inside a vertical scrollable on iOS and Android. They now respect
scrollCoordination. Horizontal scrollables still handle sideways gestures. -
Fixed scroll handoff on iOS when a drag reverses direction. With
handoffenabled for the new direction, the same touch can move the sheet after a bounce or pull-to-refresh clears. A touch that interrupts a snap without moving the sheet now lets the snap resume. -
Fixed an iOS issue where a modal sheet could reopen with the wrong scrim opacity.
Migrating from 0.17.1
-
Check the minimum versions:
0.18.0requires React Native0.82.0or later and React19.1.1or later. -
Move detent options into
detents: Remove theprogrammaticimport and replaceprogrammatic(value)with{ value, programmatic: true }. ReplacescrimOpacitieswithscrimOpacityon each corresponding modal detent. The old array reused its last entry for later detents, so repeat that value wherever you relied on it. An omitted opacity defaults to0for a closed detent and1for an open one. For explicitly typed arrays containingscrimOpacity, useModalDetent[].// 0.17.1 detents={[0, programmatic(320), '100%']} scrimOpacities={[0, 0.4]} // 0.18.0 detents={[ 0, { value: 320, programmatic: true, scrimOpacity: 0.4 }, { value: '100%', scrimOpacity: 0.4 }, ]}
-
Replace
extendUnderStatusBarwithtopInset: UsetopInset={0}where you previously passedextendUnderStatusBar={true}. If you passedfalse, omittopInsetto keep the default status-bar clearance. -
Move corner radii and shadows from
surfacetosurfaceStyle: Keep the background color, image, or gradient onsurface. -
Rename
scrollableNegotiationtoscrollCoordination: Keep your existing mode or{ expand, collapse }value. RenameScrollableNegotiationandScrollableNegotiationModetoScrollCoordinationandScrollCoordinationMode. If you useddisableScrollableNegotiation={true}, replace it withscrollCoordination="none". If you passedfalse, omit the prop.