Skill: Safe Areas
Description
Use this reference when content or scroll containers must avoid notches, system bars, home indicators, and other system UI.
React Navigation already handles safe areas for its built-in UI such as headers, tab bars, and drawers. Apply insets manually only for your own screen content or when you replace the built-in navigation UI with custom components.
When to Use
- Content is hidden behind the status bar, navigation bar, notch, or home indicator
- A screen uses a custom header, custom tab bar, or custom drawer content
- Fixed UI such as hero media, floating actions, or bottom actions needs selective safe-area padding
Edge-to-Edge on Android
Edge-to-edge makes the app content extend behind translucent system bars on Android, similar to how it works on iOS. Enable edge-to-edge for consistent safe area handling across platforms.
Android enables edge-to-edge by default from Android 15 (API level 35) for apps targeting API level 35. Edge-to-edge cannot be disabled from Android 16 (API level 36). For older Android versions, edge-to-edge can be enabled from React Native 0.81 onwards in android/gradle.properties:
edgeToEdgeEnabled=trueUsing contentInsetAdjustmentBehavior for ScrollView
When the main screen content scrolls (such as a ScrollView, FlatList, SectionList etc.) on iOS, prefer contentInsetAdjustmentBehavior="automatic" so the scroll view adjusts for safe areas while still allowing edge-to-edge scrolling behavior.
import { ScrollView } from 'react-native';
function ArticleScreen() {
return (
<ScrollView contentInsetAdjustmentBehavior="automatic">
{/* content */}
</ScrollView>
);
}On Android, conditionally use the useSafeAreaInsets hook from react-native-safe-area-context to apply paddings.
Using useSafeAreaInsets
Use the useSafeAreaInsets hook from react-native-safe-area-context for custom layouts. It gives precise control over which edges should receive padding.
import { View } from 'react-native';
import { useSafeAreaInsets } from 'react-native-safe-area-context';
function ScreenContent() {
const insets = useSafeAreaInsets();
return (
<View
style={{
flex: 1,
paddingTop: insets.top,
paddingBottom: insets.bottom,
paddingLeft: insets.left,
paddingRight: insets.right,
}}
>
{/* content */}
</View>
);
}- Prefer the hook over
SafeAreaView, asSafeAreaViewcan behave poorly during animations, and mixingSafeAreaViewwith the hook can cause flicker. - It is usually not necessary to wrap the app in
SafeAreaProvideras it's done internally by React Navigation. Only add it when using in components not in stack, bottom tabs or drawer navigators. - Apply insets to only the specific edges that extend to the screen edge
- Keep landscape orientation in mind, as the top and bottom insets become left and right insets
- Do not wrap the whole app in a
SafeAreaViewto avoid wasting space.
Canonical Docs
- React Navigation: Supporting safe areas
- React Native: ScrollView
- React Navigation: Native Stack Navigator
- React Native 0.81: Android 16 support and edge-to-edge
- react-native-safe-area-context