Skip to content

Commit deebf78

Browse files
feat(sample): Add bottom tabs navigation to the RN sample app (#3597)
1 parent 7c5a254 commit deebf78

File tree

8 files changed

+268
-79
lines changed

8 files changed

+268
-79
lines changed

samples/react-native/android/app/build.gradle

+6
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,12 @@ apply plugin: "org.jetbrains.kotlin.android"
33
apply plugin: "com.facebook.react"
44
apply plugin: "io.sentry.android.gradle"
55

6+
project.ext.vectoricons = [
7+
iconFontNames: [ 'Ionicons.ttf' ] // Specify font files
8+
]
9+
10+
apply from: file("../../node_modules/react-native-vector-icons/fonts.gradle")
11+
612
project.ext.sentryCli = [
713
collectModulesScript: "../../../../dist/js/tools/collectModules.js",
814
modulesPaths: [

samples/react-native/ios/sampleNewArchitecture.xcodeproj/project.pbxproj

+2-8
Original file line numberDiff line numberDiff line change
@@ -595,10 +595,7 @@
595595
);
596596
MTL_ENABLE_DEBUG_INFO = YES;
597597
ONLY_ACTIVE_ARCH = YES;
598-
OTHER_CFLAGS = (
599-
"$(inherited)",
600-
" ",
601-
);
598+
OTHER_CFLAGS = "$(inherited) ";
602599
OTHER_CPLUSPLUSFLAGS = (
603600
"$(OTHER_CFLAGS)",
604601
"-DFOLLY_NO_CONFIG",
@@ -670,10 +667,7 @@
670667
"\"$(inherited)\"",
671668
);
672669
MTL_ENABLE_DEBUG_INFO = NO;
673-
OTHER_CFLAGS = (
674-
"$(inherited)",
675-
" ",
676-
);
670+
OTHER_CFLAGS = "$(inherited) ";
677671
OTHER_CPLUSPLUSFLAGS = (
678672
"$(OTHER_CFLAGS)",
679673
"-DFOLLY_NO_CONFIG",

samples/react-native/ios/sampleNewArchitecture/Info.plist

+4
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,10 @@
22
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
33
<plist version="1.0">
44
<dict>
5+
<key>UIAppFonts</key>
6+
<array>
7+
<string>Ionicons.ttf</string>
8+
</array>
59
<key>CFBundleDevelopmentRegion</key>
610
<string>en</string>
711
<key>CFBundleDisplayName</key>

samples/react-native/package.json

+3
Original file line numberDiff line numberDiff line change
@@ -17,13 +17,15 @@
1717
"clean-watchman": "watchman watch-del-all"
1818
},
1919
"dependencies": {
20+
"@react-navigation/bottom-tabs": "^6.5.12",
2021
"@react-navigation/native": "^6.1.9",
2122
"@react-navigation/stack": "^6.3.20",
2223
"react": "18.2.0",
2324
"react-native": "0.73.2",
2425
"react-native-gesture-handler": "^2.14.0",
2526
"react-native-safe-area-context": "4.8.0",
2627
"react-native-screens": "3.29.0",
28+
"react-native-vector-icons": "^10.0.3",
2729
"react-redux": "^8.1.3",
2830
"redux": "^4.2.1"
2931
},
@@ -36,6 +38,7 @@
3638
"@react-native/metro-config": "^0.73.1",
3739
"@react-native/typescript-config": "^0.73.1",
3840
"@types/react": "^18.2.13",
41+
"@types/react-native-vector-icons": "^6.4.18",
3942
"@types/react-test-renderer": "^18.0.0",
4043
"@typescript-eslint/eslint-plugin": "^5.37.0",
4144
"@typescript-eslint/parser": "^5.37.0",

samples/react-native/src/App.tsx

+85-26
Original file line numberDiff line numberDiff line change
@@ -4,12 +4,14 @@ import {
44
NavigationContainerRef,
55
} from '@react-navigation/native';
66
import { createStackNavigator } from '@react-navigation/stack';
7+
import { createBottomTabNavigator } from '@react-navigation/bottom-tabs';
78

89
// Import the Sentry React Native SDK
910
import * as Sentry from '@sentry/react-native';
1011

1112
import { SENTRY_INTERNAL_DSN } from './dsn';
12-
import HomeScreen from './Screens/HomeScreen';
13+
import ErrorsScreen from './Screens/ErrorsScreen';
14+
import PerformanceScreen from './Screens/PerformanceScreen';
1315
import TrackerScreen from './Screens/TrackerScreen';
1416
import ManualTrackerScreen from './Screens/ManualTrackerScreen';
1517
import PerformanceTimingScreen from './Screens/PerformanceTimingScreen';
@@ -20,6 +22,7 @@ import { GestureHandlerRootView } from 'react-native-gesture-handler';
2022
import GesturesTracingScreen from './Screens/GesturesTracingScreen';
2123
import { StyleSheet } from 'react-native';
2224
import { HttpClient } from '@sentry/integrations';
25+
import Ionicons from 'react-native-vector-icons/Ionicons';
2326

2427
const reactNavigationInstrumentation =
2528
new Sentry.ReactNavigationInstrumentation({
@@ -98,44 +101,100 @@ Sentry.init({
98101
});
99102

100103
const Stack = createStackNavigator();
104+
const Tab = createBottomTabNavigator();
101105

102-
const App = () => {
103-
const navigation = React.useRef<NavigationContainerRef<{}>>(null);
106+
const TabOneStack = () => {
107+
return (
108+
<GestureHandlerRootView style={styles.wrapper}>
109+
<Provider store={store}>
110+
<Stack.Navigator>
111+
<Stack.Screen
112+
name="ErrorsScreen"
113+
component={ErrorsScreen}
114+
options={{ title: 'Errors' }}
115+
/>
116+
</Stack.Navigator>
117+
</Provider>
118+
</GestureHandlerRootView>
119+
);
120+
};
104121

122+
const TabTwoStack = () => {
105123
return (
106124
<GestureHandlerRootView style={styles.wrapper}>
107125
<Provider store={store}>
108-
<NavigationContainer
109-
ref={navigation}
110-
onReady={() => {
111-
reactNavigationInstrumentation.registerNavigationContainer(
112-
navigation,
113-
);
114-
}}>
115-
<Stack.Navigator>
116-
<Stack.Screen name="Home" component={HomeScreen} />
117-
<Stack.Screen name="Tracker" component={TrackerScreen} />
118-
<Stack.Screen
119-
name="ManualTracker"
120-
component={ManualTrackerScreen}
121-
/>
122-
<Stack.Screen
123-
name="PerformanceTiming"
124-
component={PerformanceTimingScreen}
125-
/>
126-
<Stack.Screen name="Redux" component={ReduxScreen} />
127-
<Stack.Screen name="Gestures" component={GesturesTracingScreen} />
128-
</Stack.Navigator>
129-
</NavigationContainer>
126+
<Stack.Navigator>
127+
<Stack.Screen
128+
name="PerformanceScreen"
129+
component={PerformanceScreen}
130+
options={{ title: 'Performance' }}
131+
/>
132+
<Stack.Screen name="Tracker" component={TrackerScreen} />
133+
<Stack.Screen name="ManualTracker" component={ManualTrackerScreen} />
134+
<Stack.Screen
135+
name="PerformanceTiming"
136+
component={PerformanceTimingScreen}
137+
/>
138+
<Stack.Screen name="Redux" component={ReduxScreen} />
139+
<Stack.Screen name="Gestures" component={GesturesTracingScreen} />
140+
</Stack.Navigator>
130141
</Provider>
131142
</GestureHandlerRootView>
132143
);
133144
};
134145

146+
function BottomTabs() {
147+
const navigation = React.useRef<NavigationContainerRef<{}>>(null);
148+
149+
return (
150+
<NavigationContainer
151+
ref={navigation}
152+
onReady={() => {
153+
reactNavigationInstrumentation.registerNavigationContainer(navigation);
154+
}}>
155+
<Tab.Navigator
156+
screenOptions={{
157+
headerShown: false,
158+
}}
159+
detachInactiveScreens={false} // workaround for https://github.com/react-navigation/react-navigation/issues/11384
160+
>
161+
<Tab.Screen
162+
name="ErrorsTab"
163+
component={TabOneStack}
164+
options={{
165+
tabBarLabel: 'Errors',
166+
tabBarIcon: ({ focused, color, size }) => (
167+
<Ionicons
168+
name={focused ? 'bug' : 'bug-outline'}
169+
size={size}
170+
color={color}
171+
/>
172+
),
173+
}}
174+
/>
175+
<Tab.Screen
176+
name="PerformanceTab"
177+
component={TabTwoStack}
178+
options={{
179+
tabBarLabel: 'Performance',
180+
tabBarIcon: ({ focused, color, size }) => (
181+
<Ionicons
182+
name={focused ? 'speedometer' : 'speedometer-outline'}
183+
size={size}
184+
color={color}
185+
/>
186+
),
187+
}}
188+
/>
189+
</Tab.Navigator>
190+
</NavigationContainer>
191+
);
192+
}
193+
135194
const styles = StyleSheet.create({
136195
wrapper: {
137196
flex: 1,
138197
},
139198
});
140199

141-
export default Sentry.wrap(App);
200+
export default Sentry.wrap(BottomTabs);

samples/react-native/src/Screens/HomeScreen.tsx renamed to samples/react-native/src/Screens/ErrorsScreen.tsx

+2-45
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,6 @@ import * as Sentry from '@sentry/react-native';
1515

1616
import { setScopeProperties } from '../setScopeProperties';
1717
import { StackNavigationProp } from '@react-navigation/stack';
18-
import { CommonActions } from '@react-navigation/native';
1918
import { UserFeedbackModal } from '../components/UserFeedbackModal';
2019
import { FallbackRender } from '@sentry/react';
2120
import NativeSampleModule from '../../tm/NativeSampleModule';
@@ -27,7 +26,7 @@ interface Props {
2726
navigation: StackNavigationProp<any, 'HomeScreen'>;
2827
}
2928

30-
const HomeScreen = (props: Props) => {
29+
const ErrorsScreen = (_props: Props) => {
3130
const [componentMountStartTimestamp] = React.useState<number>(() => {
3231
return timestampInSeconds();
3332
});
@@ -51,22 +50,6 @@ const HomeScreen = (props: Props) => {
5150
const [showBadCode, setShowBadCode] = React.useState(false);
5251
const [isFeedbackVisible, setFeedbackVisible] = React.useState(false);
5352

54-
const onPressPerformanceTiming = () => {
55-
// Navigate with a reset action just to test
56-
props.navigation.dispatch(
57-
CommonActions.reset({
58-
index: 1,
59-
routes: [
60-
{ name: 'Home' },
61-
{
62-
name: 'PerformanceTiming',
63-
params: { someParam: 'hello' },
64-
},
65-
],
66-
}),
67-
);
68-
};
69-
7053
const errorBoundaryFallback: FallbackRender = ({ eventId }) => (
7154
<Text>Error boundary caught with event id: {eventId}</Text>
7255
);
@@ -82,7 +65,6 @@ const HomeScreen = (props: Props) => {
8265
<>
8366
<StatusBar barStyle="dark-content" />
8467
<ScrollView style={styles.mainView}>
85-
<Text style={styles.welcomeTitle}>Hey there!</Text>
8668
<Button
8769
title="Capture message"
8870
onPress={() => {
@@ -218,31 +200,6 @@ const HomeScreen = (props: Props) => {
218200
}
219201
}}
220202
/>
221-
<Button
222-
title="Auto Tracing Example"
223-
onPress={() => {
224-
props.navigation.navigate('Tracker');
225-
}}
226-
/>
227-
<Button
228-
title="Manual Tracing Example"
229-
onPress={() => {
230-
props.navigation.navigate('ManualTracker');
231-
}}
232-
/>
233-
<Button
234-
title="Gestures Tracing Example"
235-
onPress={() => {
236-
props.navigation.navigate('Gestures');
237-
}}
238-
/>
239-
<Button title="Performance Timing" onPress={onPressPerformanceTiming} />
240-
<Button
241-
title="Redux Example"
242-
onPress={() => {
243-
props.navigation.navigate('Redux');
244-
}}
245-
/>
246203
<Button
247204
title="Send user feedback"
248205
onPress={() => {
@@ -296,4 +253,4 @@ const styles = StyleSheet.create({
296253
},
297254
});
298255

299-
export default HomeScreen;
256+
export default ErrorsScreen;

0 commit comments

Comments
 (0)