Migrating to v3
This guide will help you migrate from TrueSheet v2 to v3. Version 3 brings full Fabric (New Architecture) support and several improvements.
Breaking Changes
1. Fabric Architecture Required
Version 3 is built exclusively for React Native's New Architecture (Fabric). The old Paper architecture is no longer supported.
Requirements:
- React Native 0.74+ (recommended 0.81+ for edge-to-edge support)
- New Architecture must be enabled
What you need to do:
Enable the New Architecture in your app if you haven't already:
iOS
use_frameworks! :linkage => :static
$RNNewArchEnabled = true
Then run:
cd ios && pod install
Android
newArchEnabled=true
Check out the React Native New Architecture guide for more details.
2. Prop Renames
Several props have been renamed for better clarity:
| v2 Prop | v3 Prop |
|---|---|
initialIndex | initialDetentIndex |
initialIndexAnimated | initialDetentAnimated |
Migration:
// ❌ v2
<TrueSheet
initialIndex={1}
initialIndexAnimated={false}
>
<View />
</TrueSheet>
// ✅ v3
<TrueSheet
initialDetentIndex={1}
initialDetentAnimated={false}
>
<View />
</TrueSheet>
3. Removed Props
scrollRef (iOS)
The scrollRef prop has been removed. Scroll views are now automatically detected on iOS.
Migration:
// ❌ v2
const scrollView = useRef<ScrollView>(null)
<TrueSheet ref={sheet} scrollRef={scrollView}>
<ScrollView ref={scrollView} nestedScrollEnabled>
<View />
</ScrollView>
</TrueSheet>
// ✅ v3
<TrueSheet ref={sheet}>
<ScrollView nestedScrollEnabled>
<View />
</ScrollView>
</TrueSheet>
See the Scrolling guide for more information.
4. Detent Value Changes
Detent values now use fractional values (0-1) instead of percentage strings.
Migration:
// ❌ v2
<TrueSheet detents={["50%", "80%", "100%"]}>
<View />
</TrueSheet>
// ✅ v3
<TrueSheet detents={[0.5, 0.8, 1]}>
<View />
</TrueSheet>
The "auto" detent still works the same way!
New Features in v3
1. Automatic Edge-to-Edge Detection (Android)
TrueSheet now automatically detects and adapts to Android's edge-to-edge display mode. By default, the sheet respects the status bar when fully expanded.
For a true full-screen experience where the sheet extends behind the status bar, use the new edgeToEdgeFullScreen prop:
<TrueSheet edgeToEdgeFullScreen>
<View />
</TrueSheet>
This feature is Android-only and requires React Native 0.81+ with edgeToEdgeEnabled=true in your android/gradle.properties.
See the Edge-to-Edge guide for details.
2. Enhanced Event System
Version 3 introduces new lifecycle and interaction events for better control:
New Events:
onMount- Called when the sheet's content is mounted and readyonWillPresent- Called when the sheet is about to be presentedonDidPresent- Called when the sheet has been presentedonWillDismiss- Called when the sheet is about to be dismissedonDidDismiss- Called when the sheet has been dismissedonDragBegin- Called when the sheet begins draggingonDragChange- Called continuously while the sheet is being draggedonDragEnd- Called when sheet dragging has endedonPositionChange- Called continuously when the sheet's position changes
These events provide more granular control over the sheet's lifecycle and user interactions.
See the Events documentation for detailed usage and examples.
3. Improved Performance
- Faster rendering with Fabric architecture
- Built-in lazy loading by default
- Smoother animations and transitions
4. First-Class Reanimated v4 Support
Version 3 introduces dedicated components for seamless integration with react-native-reanimated v4:
New Components:
ReanimatedTrueSheetProvider- Context provider for managing shared valuesReanimatedTrueSheet- Drop-in replacement forTrueSheetwith automatic position trackinguseReanimatedTrueSheet- Hook to access the sheet's animated position
Example:
import {
ReanimatedTrueSheetProvider,
ReanimatedTrueSheet,
useReanimatedTrueSheet,
} from '@lodev09/react-native-true-sheet'
import Animated, { useAnimatedStyle } from 'react-native-reanimated'
// 1. Wrap your app with the provider
function App() {
return (
<ReanimatedTrueSheetProvider>
<YourApp />
</ReanimatedTrueSheetProvider>
)
}
// 2. Use ReanimatedTrueSheet instead of TrueSheet
function MyScreen() {
const sheetRef = useRef<TrueSheet>(null)
return (
<ReanimatedTrueSheet
ref={sheetRef}
detents={[0.3, 0.6, 1]}
initialDetentIndex={1}
>
<Text>Sheet Content</Text>
</ReanimatedTrueSheet>
)
}
// 3. Access the sheet's position for custom animations
function MyAnimatedComponent() {
const { animatedPosition } = useReanimatedTrueSheet()
const animatedStyle = useAnimatedStyle(() => ({
transform: [{ translateY: -animatedPosition.value }],
}))
return (
<Animated.View style={animatedStyle}>
<Text>This moves with the sheet</Text>
</Animated.View>
)
}
The onPositionChange event now runs on the UI thread (worklet) when using ReanimatedTrueSheet. Make sure to add the 'worklet' directive to your handler if you override it.
See the Reanimated Integration guide for complete examples.
Step-by-Step Migration
-
Enable New Architecture in your React Native app (see above)
-
Update the package:
yarn add @lodev09/react-native-true-sheet@^3.0.0npm install @lodev09/react-native-true-sheet@^3.0.0 -
Clean and reinstall iOS dependencies:
cd ios
rm -rf Pods Podfile.lock build
pod install
cd .. -
Clean Android build:
cd android
./gradlew clean
cd .. -
Update your code:
- Replace
initialIndexwithinitialDetentIndex - Replace
initialIndexAnimatedwithinitialDetentAnimated - Remove
scrollRefprop (iOS) - Change detent percentage strings to fractional numbers
- Replace
-
Test your app:
npx react-native run-ios
npx react-native run-android
Need Help?
If you encounter any issues during migration:
- Check the Troubleshooting guide
- Open an issue on GitHub
- Review the example app for reference implementations