Skip to content

Commit

Permalink
feat: added detached bottom sheet (#487)
Browse files Browse the repository at this point in the history
* chore: fix background stylings

* chore: handle detached prop on the container

* chore: updated integrated view dynamic handling

* chore: updated dynamic snap point handling

* chore: update examples

* chore: added footer handling to bottom sheet view
  • Loading branch information
gorhom committed Jun 12, 2021
1 parent cbfb32d commit 3aa5fdb
Show file tree
Hide file tree
Showing 19 changed files with 270 additions and 80 deletions.
5 changes: 3 additions & 2 deletions example/src/components/contactList/ContactList.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -30,9 +30,10 @@ const handleGetCount = (data: any[]) => data.length;
const ContactList = ({
type,
count = 25,
onRefresh,
style,
onRefresh,
onItemPress,
...rest
}: ContactListProps) => {
// hooks
const { bottom: bottomSafeArea } = useSafeAreaInsets();
Expand Down Expand Up @@ -162,7 +163,7 @@ const ContactList = ({
);
} else if (type === 'View') {
return (
<BottomSheetView style={styles.contentContainer}>
<BottomSheetView style={styles.contentContainer} {...rest}>
{data.map(renderScrollViewItem)}
</BottomSheetView>
);
Expand Down
2 changes: 1 addition & 1 deletion example/src/components/headerHandle/HeaderHandle.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ const styles = StyleSheet.create({
paddingBottom: 12,
paddingHorizontal: 16,
borderBottomWidth: 1,
borderBottomColor: 'rgba(0,0,0,0.125)',
borderBottomColor: 'rgba(0,0,0,0.075)',
zIndex: 99999,
},
title: {
Expand Down
24 changes: 16 additions & 8 deletions example/src/screens/advanced/DynamicSnapPointExample.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -10,11 +10,16 @@ import Button from '../../components/button';
const DynamicSnapPointExample = () => {
// state
const [count, setCount] = useState(0);
const initialSnapPoints = useMemo(() => ['CONTENT_HEIGHT'], []);

// hooks
const bottomSheetRef = useRef<BottomSheet>(null);
const { animatedHandleHeight, animatedSnapPoints, contentProps } =
useBottomSheetDynamicSnapPoints(['CONTENT_HEIGHT']);
const {
animatedHandleHeight,
animatedSnapPoints,
animatedContentHeight,
handleContentLayout,
} = useBottomSheetDynamicSnapPoints(initialSnapPoints);
const { bottom: safeBottomArea } = useSafeAreaInsets();

// callbacks
Expand All @@ -33,10 +38,10 @@ const DynamicSnapPointExample = () => {

// styles
const contentContainerStyle = useMemo(
() => ({
...styles.contentContainerStyle,
paddingBottom: safeBottomArea || 6,
}),
() => [
styles.contentContainerStyle,
{ paddingBottom: safeBottomArea || 6 },
],
[safeBottomArea]
);
const emojiContainerStyle = useMemo(
Expand All @@ -56,10 +61,14 @@ const DynamicSnapPointExample = () => {
ref={bottomSheetRef}
snapPoints={animatedSnapPoints}
handleHeight={animatedHandleHeight}
contentHeight={animatedContentHeight}
enablePanDownToClose={true}
animateOnMount={true}
>
<BottomSheetView style={contentContainerStyle} {...contentProps}>
<BottomSheetView
style={contentContainerStyle}
onLayout={handleContentLayout}
>
<Text style={styles.message}>
Could this sheet resize to its content height ?
</Text>
Expand All @@ -83,7 +92,6 @@ const styles = StyleSheet.create({
paddingTop: 12,
paddingBottom: 6,
paddingHorizontal: 24,
backgroundColor: 'white',
},
message: {
fontSize: 24,
Expand Down
3 changes: 2 additions & 1 deletion example/src/screens/advanced/KeyboardHandlingExample.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -71,12 +71,13 @@ const KeyboardHandlingExample = () => {
<Button label="Close" onPress={handleClosePress} />
<BottomSheet
ref={bottomSheetRef}
index={1}
snapPoints={snapPoints}
keyboardBehavior={keyboardBehavior}
keyboardBlurBehavior={keyboardBlurBehavior}
handleComponent={SearchHandle}
>
<ContactList count={10} type="FlatList" />
<ContactList count={10} type="ScrollView" />
</BottomSheet>
</View>
);
Expand Down
132 changes: 132 additions & 0 deletions example/src/screens/modal/DetachedExample.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,132 @@
import React, { useCallback, useMemo, useRef } from 'react';
import { View, StyleSheet, Text } from 'react-native';
import { useSafeAreaInsets } from 'react-native-safe-area-context';
import {
BottomSheetModal,
BottomSheetView,
BottomSheetFooter,
useBottomSheetDynamicSnapPoints,
} from '@gorhom/bottom-sheet';
import Button from '../../components/button';
import ContactItem from '../../components/contactItem';
import HeaderHandle from '../../components/headerHandle';
import withModalProvider from '../withModalProvider';
import { createContactListMockData } from '../../utilities';

const DetachedExample = () => {
// refs
const bottomSheetRef = useRef<BottomSheetModal>(null);

// variables
const initialSnapPoints = useMemo(() => ['CONTENT_HEIGHT'], []);
const data = useMemo(() => createContactListMockData(2), []);

// hooks
const {
animatedHandleHeight,
animatedSnapPoints,
animatedContentHeight,
handleContentLayout,
} = useBottomSheetDynamicSnapPoints(initialSnapPoints);
const { bottom: safeBottomArea } = useSafeAreaInsets();

// callbacks
const handlePresentPress = useCallback(() => {
bottomSheetRef.current!.present();
}, []);
const handleDismissPress = useCallback(() => {
bottomSheetRef.current!.dismiss();
}, []);
const handleClosePress = useCallback(() => {
bottomSheetRef.current?.close();
}, []);

// renders
const renderHeaderHandle = useCallback(
props => <HeaderHandle {...props} children="Detached Example" />,
[]
);
const renderItem = useCallback(
(item, index) => (
<ContactItem
key={`${item.name}.${index}`}
title={`${index}: ${item.name}`}
subTitle={item.jobTitle}
/>
),
[]
);
return (
<View style={styles.container}>
<Button label="Present" onPress={handlePresentPress} />
<Button label="Dismiss" onPress={handleDismissPress} />
<Button label="Close" onPress={handleClosePress} />
<BottomSheetModal
ref={bottomSheetRef}
snapPoints={animatedSnapPoints}
handleHeight={animatedHandleHeight}
contentHeight={animatedContentHeight}
bottomInset={safeBottomArea + 34}
enablePanDownToClose={true}
style={styles.sheetContainer}
backgroundComponent={null}
handleComponent={renderHeaderHandle}
detached={true}
>
<BottomSheetView
style={styles.contentContainerStyle}
onLayout={handleContentLayout}
>
{data.map(renderItem)}
<BottomSheetFooter>
<View style={styles.footer}>
<Text style={styles.footerText}>this is a footer!</Text>
</View>
</BottomSheetFooter>
</BottomSheetView>
</BottomSheetModal>
</View>
);
};

const styles = StyleSheet.create({
container: {
flex: 1,
padding: 24,
},
sheetContainer: {
marginHorizontal: 16,
backgroundColor: 'white',
borderRadius: 16,
shadowColor: 'rgba(0,0,0,0.25)',
shadowOffset: {
width: 0,
height: 5,
},
shadowOpacity: 0.25,
shadowRadius: 16.0,

elevation: 24,
},
contentContainerStyle: {
paddingTop: 12,
paddingBottom: 12,
paddingHorizontal: 16,
},
footer: {
justifyContent: 'center',
alignItems: 'center',
marginHorizontal: 12,
padding: 12,
marginBottom: 12,
borderRadius: 24,
backgroundColor: '#80f',
},
footerText: {
fontSize: 16,
fontWeight: '600',
color: '#fff',
},
});

export default withModalProvider(DetachedExample);
14 changes: 11 additions & 3 deletions example/src/screens/modal/DynamicSnapPointExample.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -15,8 +15,12 @@ const DynamicSnapPointExample = () => {

// hooks
const bottomSheetRef = useRef<BottomSheetModal>(null);
const { animatedHandleHeight, animatedSnapPoints, contentProps } =
useBottomSheetDynamicSnapPoints(['CONTENT_HEIGHT']);
const {
animatedHandleHeight,
animatedSnapPoints,
animatedContentHeight,
handleContentLayout,
} = useBottomSheetDynamicSnapPoints(['CONTENT_HEIGHT']);
const { bottom: safeBottomArea } = useSafeAreaInsets();

// callbacks
Expand Down Expand Up @@ -59,9 +63,13 @@ const DynamicSnapPointExample = () => {
ref={bottomSheetRef}
snapPoints={animatedSnapPoints}
handleHeight={animatedHandleHeight}
contentHeight={animatedContentHeight}
enablePanDownToClose={true}
>
<BottomSheetView style={contentContainerStyle} {...contentProps}>
<BottomSheetView
style={contentContainerStyle}
onLayout={handleContentLayout}
>
<Text style={styles.message}>
Could this sheet modal resize to its content height ?
</Text>
Expand Down
5 changes: 5 additions & 0 deletions example/src/screens/screens.ts
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,11 @@ export const screens = [
slug: 'Modal/DynamicSnapPointExample',
getScreen: () => require('./modal/DynamicSnapPointExample').default,
},
{
name: 'Detached',
slug: 'Modal/DetachedExample',
getScreen: () => require('./modal/DetachedExample').default,
},
],
},
{
Expand Down
Loading

0 comments on commit 3aa5fdb

Please sign in to comment.