Drawer 作成
twitter-clone-example アプリでは Drawer をすべてのスクリーンで閲覧出来るようにしますので、Drawer が ルートナビゲーター となります。
Main.js に Drawer 設定を追加するため、Main.js を下記のように変更します。
- VSCode で
rnfcomp( 使用方法 ) と打ち込んで DrawerContent と HomeScreen を作成します。( コピぺ可能 ▼ )
src/Main.js
// Main.js
import React from "react";
import { Text, View } from "react-native";
import { createDrawerNavigator } from "@react-navigation/drawer";
const Drawer = createDrawerNavigator();
function DrawerContent() {
return (
<View style={{ flex: 1, alignItems: "center", justifyContent: "center" }}>
<Text>Drawer content</Text>
</View>
);
}
function HomeScreen() {
return (
<View style={{ flex: 1, alignItems: "center", justifyContent: "center" }}>
<Text>Home Screen</Text>
</View>
);
}
export const Main = () => {
return (
<Drawer.Navigator drawerContent={() => <DrawerContent />}>
<Drawer.Screen name="Home" component={HomeScreen} />
</Drawer.Navigator>
);
};
iOS シミュレータを再起動 ( ⌘ R ) して確認すると、▼ のように動作します。
最終的に Main.js にはテーマや RTL の切替の設定が入るので、DrawerContent と HomeScreen を含む Stack ナビケーターを別のファイルに分離します。
必要なファイルを作成します。▼
try🐶everything twitter-clone-example$ touch ./src/RootNavigator.js try🐶everything twitter-clone-example$ touch ./src/DrawerContent.js try🐶everything twitter-clone-example$ touch ./src/StackNavigator.js
StackNavigator と DrawerContent を RootNavigator にインポートして設定します。
※ NavigationContainer は App.js で設定しているのでここでは設定しません 。
src/RootNavigator.js ファイルを作成します。( VSCodeで imrnfc 実行 )
// RootNavigator.js
import React from "react";
import { createDrawerNavigator } from "@react-navigation/drawer";
import { StackNavigator } from "./StackNavigator";
import { DrawerContent } from "./DrawerContent";
const Drawer = createDrawerNavigator();
export const RootNavigator = () => {
return (
<Drawer.Navigator drawerContent={props => <DrawerContent {...props} />}>
<Drawer.Screen name="Home" component={StackNavigator} />
</Drawer.Navigator>
);
};
src/DrawerContent.js ファイルを作成します。
// DrawerContent
import React from "react";
import { View, Text, StyleSheet } from "react-native";
export const DrawerContent = props => {
return (
<View style={styles.container}>
<Text>DrawerContent</Text>
</View>
);
};
const styles = StyleSheet.create({
container: {
flex: 1,
alignItems: "center",
justifyContent: "center"
}
});
src/StackNavigator.js ファイルを作成します。
// StackNavigator.js
import React from "react";
import { View, Text, StyleSheet } from "react-native";
export const StackNavigator = props => {
return (
<View style={styles.container}>
<Text>StackNavigator</Text>
</View>
);
};
const styles = StyleSheet.create({
container: {
flex: 1,
alignItems: "center",
justifyContent: "center"
}
});
src/Main.js ファイルを変更します。
// Main.js
import React from "react";
import { Provider as PaperProvider } from "react-native-paper";
import { RootNavigator } from "./RootNavigator";
export const Main = () => {
return (
<PaperProvider>
<RootNavigator />
</PaperProvider>
);
};
iOS シミュレータを確認します。▼ のように動作すれば OK です。
次は、DrawerContent と StackNavigator の詳細を設定します。
現時点では何もない状態なので、DrawerContentScrollView と DrawerItem そして、Avatar、Text、Switch などを使用して設定します。
src/DrawerContent.js
下記のようにファイルを作成します。( コピぺ可能 ▼ )
// DrawerContent.js
import React from "react";
import { View, StyleSheet } from "react-native";
import { DrawerItem, DrawerContentScrollView } from "@react-navigation/drawer";
import {
Avatar,
Title,
Caption,
Paragraph,
Drawer,
Text,
TouchableRipple,
Switch
} from "react-native-paper";
import { MaterialCommunityIcons } from "@expo/vector-icons";
export function DrawerContent(props) {
return (
<DrawerContentScrollView {...props}>
<View style={styles.drawerContent}>
<View style={styles.userInfoSection}>
<Avatar.Image
source={{
uri:
"https://pbs.twimg.com/profile_images/952545910990495744/b59hSXUd_400x400.jpg"
}}
size={50}
/>
<Title style={styles.title}>Dawid Urbaniak</Title>
<Caption style={styles.caption}>@trensik</Caption>
<View style={styles.row}>
<View style={styles.section}>
<Paragraph style={[styles.paragraph, styles.caption]}>
202
</Paragraph>
<Caption style={styles.caption}>Following</Caption>
</View>
<View style={styles.section}>
<Paragraph style={[styles.paragraph, styles.caption]}>
159
</Paragraph>
<Caption style={styles.caption}>Followers</Caption>
</View>
</View>
</View>
<Drawer.Section style={styles.drawerSection}>
<DrawerItem
icon={({ color, size }) => (
<MaterialCommunityIcons
name="account-outline"
color={color}
size={size}
/>
)}
label="Profile"
onPress={() => {}}
/>
<DrawerItem
icon={({ color, size }) => (
<MaterialCommunityIcons name="tune" color={color} size={size} />
)}
label="Preferences"
onPress={() => {}}
/>
<DrawerItem
icon={({ color, size }) => (
<MaterialCommunityIcons
name="bookmark-outline"
color={color}
size={size}
/>
)}
label="Bookmarks"
onPress={() => {}}
/>
</Drawer.Section>
<Drawer.Section title="Preferences">
<TouchableRipple onPress={() => {}}>
<View style={styles.preference}>
<Text>Dark Theme</Text>
<View pointerEvents="none">
<Switch value={false} />
</View>
</View>
</TouchableRipple>
<TouchableRipple onPress={() => {}}>
<View style={styles.preference}>
<Text>RTL</Text>
<View pointerEvents="none">
<Switch value={false} />
</View>
</View>
</TouchableRipple>
</Drawer.Section>
</View>
</DrawerContentScrollView>
);
}
const styles = StyleSheet.create({
drawerContent: {
flex: 1
},
userInfoSection: {
paddingLeft: 20
},
title: {
marginTop: 20,
fontWeight: "bold"
},
caption: {
fontSize: 14,
lineHeight: 14
},
row: {
marginTop: 20,
flexDirection: "row",
alignItems: "center"
},
section: {
flexDirection: "row",
alignItems: "center",
marginRight: 15
},
paragraph: {
fontWeight: "bold",
marginRight: 3
},
drawerSection: {
marginTop: 15
},
preference: {
flexDirection: "row",
justifyContent: "space-between",
paddingVertical: 12,
paddingHorizontal: 16
}
});
ここまで、問題なければ下記のように動作します。
次は、Stack Navigator を設定しましょう。


コメント
参考になりました。ありがとうございます。
React NativeはネイティブアプリらしいUIが作りづらく苦労していたので参考になりました。
技術革新も早くコピペしてもまともに動かないサイトも多く非常に参考になりました。
動かない部分もありますが自分で調べてみようと思います。