Skip to main content
Version: 1.x

Consumer scroll handlers

Header Motion internally uses an animated scroll handler to track scroll position and drive header animations. Your own scroll callbacks still work alongside it — you don't have to choose between the library's behavior and your own logic.

Standard React Native callbacks​

You can pass the familiar React Native scroll callbacks directly. These are bridged via scheduleOnRN so they fire on the JS thread:

<HeaderMotion.ScrollView
onScroll={(e) => console.log('offset:', e.nativeEvent.contentOffset.y)}
onScrollBeginDrag={(e) => console.log('drag started')}
onScrollEndDrag={(e) => console.log('drag ended')}
onMomentumScrollBegin={(e) => console.log('momentum started')}
onMomentumScrollEnd={(e) => console.log('momentum ended')}
>
{/* content */}
</HeaderMotion.ScrollView>

Reanimated animated scroll handler​

If you need worklet-based scroll handling, pass a useAnimatedScrollHandler as the onScroll prop. Header Motion composes it with its internal handler via useComposedEventHandler, so both run on the UI thread:

const onScroll = useAnimatedScrollHandler({
onScroll: () => {
'worklet';
console.log('consumer onScroll worklet');
},
});

<HeaderMotion.ScrollView onScroll={onScroll}>
{/* content */}
</HeaderMotion.ScrollView>;

Mixing approaches​

Both approaches are compatible. Header Motion detects whether your onScroll is a standard callback or an animated handler and handles each accordingly. The library's internal scroll tracking continues to work regardless of which approach you use.


One more edge case to cover: learn how to handle screens where the content is too short to fully collapse the header in Short scrollable content.