Przeglądaj źródła

new layout logic and user notification picker

master
azri 3 dni temu
rodzic
commit
e96eeb07c9

+ 0
- 148
app/(pages)/index.jsx Wyświetl plik

@@ -1,148 +0,0 @@
1
-import React, { useState } from 'react';
2
-import { View, StyleSheet, TextInput, Text, ScrollView } from 'react-native';
3
-import { Appbar, Menu, Avatar, useTheme } from 'react-native-paper';
4
-import Icon from 'react-native-vector-icons/MaterialIcons';
5
-import dpuser from "@/assets/images/userdp.png";
6
-
7
-const Home = () => {
8
-  const { colors, fonts } = useTheme();
9
-  const [menuVisible, setMenuVisible] = useState(false);
10
-  const [searchInput, setSearchInput] = useState("")
11
-
12
-  const renderNotification = () => {
13
-    return (
14
-      <View style={{marginBottom:30, borderBottomWidth:1, borderBottomColor:"rgba(57, 104, 104, 0.3)"}}>
15
-        <View style={{ flexDirection: "row", marginBottom: 10 }}>
16
-          <Avatar.Image size={60} source={dpuser}></Avatar.Image>
17
-          <View style={{ flex: 1, justifyContent: "center", paddingStart: 15, position:"relative", justifyContent:"space-evenly" }}>
18
-            <Text style={{ fontWeight: "700", position:"absolute", top:5, right:0, color:"rgba(0,0,0,0.3)" }}>7:55AM</Text>
19
-            <Text style={{ fontWeight: "700" }}>Invest Pahang</Text>
20
-            <Text style={{ fontWeight: "700" }}>ID No : Ariffudin@PSK</Text>
21
-          </View>
22
-        </View>
23
-        <Text style={{ fontWeight: "700", marginBottom:10 }}>Muhammad Ariffudin is working from home today</Text>
24
-      </View>
25
-    )
26
-  }
27
-
28
-  return (
29
-    <View style={[styles.container, { backgroundColor: colors.background }]}>
30
-      <Appbar.Header>
31
-
32
-        <Avatar.Image size={50} source={dpuser}></Avatar.Image>
33
-
34
-        <View style={styles.titleContainer}>
35
-          <Appbar.Content title="General" titleStyle={[fonts.titleLarge, styles.title]} />
36
-        </View>
37
-
38
-        {/* Menu Component */}
39
-        <Menu
40
-          visible={menuVisible}
41
-          onDismiss={() => setMenuVisible(false)}
42
-          anchor={
43
-            <Appbar.Action icon="dots-vertical" onPress={() => setMenuVisible(true)} />
44
-          }
45
-        >
46
-          <Menu.Item onPress={() => console.log('Profile Clicked')} title="Profile" />
47
-          <Menu.Item onPress={() => console.log('Settings Clicked')} title="Settings" />
48
-          <Menu.Item onPress={() => console.log('Logout Clicked')} title="Logout" />
49
-        </Menu>
50
-      </Appbar.Header>
51
-
52
-      <View style={styles.tabContainer}>
53
-        <Text style={[styles.tabButton, fonts.titleMedium, { fontWeight: "bold" }, { borderBottomWidth: 2, borderBottomColor: colors.secondary, color: colors.secondary }]}>General  </Text>
54
-        <Text style={[styles.tabButton, { fontWeight: "bold" }, fonts.titleMedium]}>Request <Text style={styles.badge}>1</Text></Text>
55
-      </View>
56
-
57
-
58
-      <View style={styles.searchSection}>
59
-        <TextInput
60
-          style={styles.input}
61
-          placeholder="Search"
62
-          onChangeText={setSearchInput}
63
-          value={searchInput}
64
-          underlineColorAndroid="transparent"
65
-          placeholderTextColor="#D9D9D9"
66
-        />
67
-        <Icon name="search" size={20} color="#888" style={styles.icon} />
68
-      </View>
69
-
70
-      <View style={{flex:1}}>
71
-        <ScrollView>
72
-          <Text style={[fonts.titleMedium, { fontWeight: "bold", marginBottom: 15 }]}>Today</Text>
73
-          {[1,2].map(() => renderNotification())}
74
-
75
-          <Text style={[fonts.titleMedium, { fontWeight: "bold", marginBottom: 15 }]}>Yesterday</Text>
76
-          {[1,2].map(() => renderNotification())}
77
-
78
-          <Text style={[fonts.titleMedium, { fontWeight: "bold", marginBottom: 15 }]}>Older</Text>
79
-          {[1,2].map(() => renderNotification())}
80
-
81
-        </ScrollView>
82
-      </View>
83
-
84
-    </View>
85
-  );
86
-};
87
-
88
-const styles = StyleSheet.create({
89
-  container: {
90
-    flex: 1,
91
-    padding: 20,
92
-    width: '100%',
93
-  },
94
-  badge: {
95
-    backgroundColor: "#BB5C3F",
96
-    color: "#FFF",
97
-    borderRadius: 100,
98
-    paddingVertical: 4,
99
-    paddingHorizontal: 6,
100
-    fontSize: 10,
101
-    fontWeight: "400",
102
-    verticalAlign: "middle",
103
-    marginStart: 5
104
-  },
105
-  tabContainer: {
106
-    flexDirection: "row",
107
-    marginBottom: 20
108
-  },
109
-  tabButton: {
110
-    fontWeight: "bold",
111
-    paddingVertical: 15,
112
-    width: "50%",
113
-    textAlign: "center",
114
-    active: {
115
-      borderBottomWidth: 2,
116
-    }
117
-  },
118
-  titleContainer: {
119
-    flex: 1,
120
-    alignItems: 'center',
121
-  },
122
-  title: {
123
-    fontWeight: 'bold',
124
-  },
125
-  searchSection: {
126
-    flexDirection: 'row',
127
-    justifyContent: 'center',
128
-    alignItems: 'center',
129
-    marginBottom: 20
130
-  },
131
-  icon: {
132
-    padding: 10,
133
-    position: "absolute",
134
-    right: 10,
135
-    color: "#D9D9D9"
136
-  },
137
-  input: {
138
-    height: 40,
139
-    flex: 1,
140
-    borderWidth: 1,
141
-    paddingVertical: 10,
142
-    paddingHorizontal: 20,
143
-    borderRadius: 100,
144
-    borderColor: "#C0CFD0"
145
-  }
146
-});
147
-
148
-export default Home;

+ 0
- 112
app/(pages)/profile.jsx Wyświetl plik

@@ -1,112 +0,0 @@
1
-import React, { useState } from 'react';
2
-import { View, StyleSheet, TextInput, Text, ScrollView } from 'react-native';
3
-import { Appbar, Menu, Avatar, useTheme, Button } from 'react-native-paper';
4
-import Icon from 'react-native-vector-icons/MaterialIcons';
5
-import dpuser from "@/assets/images/userdp.png";
6
-
7
-const Notification = () => {
8
-  const { colors, fonts } = useTheme();
9
-  const [menuVisible, setMenuVisible] = useState(false);
10
-  const [inputContent, setInputContent] = useState("");
11
-
12
-
13
-  const preTextClick = (pretext) => {
14
-    setInputContent(pretext)
15
-  }
16
-
17
-  return (
18
-    <View style={[styles.container, { backgroundColor: colors.background }]}>
19
-      <Appbar.Header>
20
-
21
-        <Avatar.Image size={50} source={dpuser}></Avatar.Image>
22
-
23
-        <View style={styles.titleContainer}>
24
-          <Appbar.Content title="Send Notification" titleStyle={[fonts.titleLarge, styles.title]} />
25
-        </View>
26
-
27
-        {/* Menu Component */}
28
-        <Menu
29
-          visible={menuVisible}
30
-          onDismiss={() => setMenuVisible(false)}
31
-          anchor={
32
-            <Appbar.Action icon="dots-vertical" onPress={() => setMenuVisible(true)} />
33
-          }
34
-        >
35
-          <Menu.Item onPress={() => console.log('Profile Clicked')} title="Profile" />
36
-          <Menu.Item onPress={() => console.log('Settings Clicked')} title="Settings" />
37
-          <Menu.Item onPress={() => console.log('Logout Clicked')} title="Logout" />
38
-        </Menu>
39
-      </Appbar.Header>
40
-
41
-
42
-      <View style={{ flex: 1, marginTop: 20 }}>
43
-        <View style={{ flexDirection: "row", gap: 20, marginBottom: 20 }}>
44
-          <Text style={[fonts.titleLarge, { fontWeight: "bold" }]}>To :</Text>
45
-          <TextInput value='asd' style={{ flex: 1, paddingHorizontal: 20, borderBottomColor: "rgba(0,0,0,0.2)", borderBottomWidth: 1, marginEnd: 20 }}></TextInput>
46
-        </View>
47
-        <TextInput
48
-          style={styles.textArea}
49
-          value={inputContent}
50
-          onChangeText={setInputContent}
51
-          multiline={true} // Enables multi-line input
52
-          numberOfLines={8} // Sets an initial number of visible lines
53
-        />
54
-        <Text style={[fonts.titleLarge, { fontWeight: "bold", marginBottom:20 }]}>Select Pretext</Text>
55
-        <View style={{flex:1}}>
56
-          {[
57
-            "Request to Work From Home",
58
-            "Request for late Check In",
59
-            "Request for early Check Out",
60
-            "Notify for Annual Leave",
61
-            "Notify for Emergency Leave"
62
-          ].map(text => <Text onPress={()=>{preTextClick(text)}} style={[fonts.titleMedium, {marginBottom:20, fontWeight:"bold", color:colors.secondary}]} >{text}</Text> )}
63
-        </View>
64
-      </View>
65
-
66
-    </View>
67
-  );
68
-};
69
-
70
-const styles = StyleSheet.create({
71
-  container: {
72
-    flex: 1,
73
-    padding: 20,
74
-    width: '100%',
75
-  },
76
-  textArea: {
77
-    height: 220,
78
-    borderColor: "#ccc",
79
-    borderWidth: 1,
80
-    padding: 10,
81
-    borderRadius: 8,
82
-    textAlignVertical: "top", // Makes text start from the top-left
83
-    backgroundColor: "#fff",
84
-    marginBottom:20
85
-  },
86
-  badge: {
87
-    backgroundColor: "#BB5C3F",
88
-    color: "#FFF",
89
-    borderRadius: 100,
90
-    paddingVertical: 4,
91
-    paddingHorizontal: 6,
92
-    fontSize: 10,
93
-    fontWeight: "400",
94
-    verticalAlign: "middle",
95
-    marginStart: 5
96
-  },
97
-  titleContainer: {
98
-    flex: 1,
99
-    alignItems: 'center',
100
-  },
101
-  title: {
102
-    fontWeight: 'bold',
103
-  },
104
-  icon: {
105
-    padding: 10,
106
-    position: "absolute",
107
-    right: 10,
108
-    color: "#D9D9D9"
109
-  }
110
-});
111
-
112
-export default Notification;

app/(pages)/_layout.tsx → app/(tabs)/_layout.tsx Wyświetl plik

@@ -36,7 +36,7 @@ export default function ScreenLayout() {
36 36
       }}
37 37
       >
38 38
       <Tabs.Screen
39
-        name="index"
39
+        name="home"
40 40
         options={{
41 41
           title: 'Home',
42 42
           tabBarIcon: ({ color }) => <Icon name="home" size={25} color={color} />,

+ 10
- 0
app/(tabs)/home/_layout.jsx Wyświetl plik

@@ -0,0 +1,10 @@
1
+import { Stack } from 'expo-router';
2
+
3
+export default function HomeLayout() {
4
+  return (
5
+    <Stack>
6
+        <Stack.Screen name="index" options={{headerShown:false}} />
7
+        <Stack.Screen name="status" options={{headerShown:false}} />
8
+    </Stack>
9
+  );
10
+}

+ 210
- 0
app/(tabs)/home/index.jsx Wyświetl plik

@@ -0,0 +1,210 @@
1
+import React, { useState } from 'react';
2
+import { View, StyleSheet, TextInput, Text, ScrollView, Pressable } from 'react-native';
3
+import { Appbar, Menu, Avatar, useTheme, Button } from 'react-native-paper';
4
+
5
+import Icon from 'react-native-vector-icons/MaterialIcons';
6
+import dpuser from "@/assets/images/userdp.png";
7
+import { Link } from 'expo-router';
8
+
9
+const Home = () => {
10
+  const { colors, fonts } = useTheme();
11
+  const [menuVisible, setMenuVisible] = useState(false);
12
+  const [searchInput, setSearchInput] = useState("")
13
+  const [showRequest, setshowRequest] = useState(false)
14
+  const [activeTab, setActiveTab] = useState('General');
15
+
16
+  const renderNotification = () => {
17
+    return (
18
+      <Link href={"/home/status"} asChild>
19
+        <View style={{ marginBottom: 30, borderBottomWidth: 1, borderBottomColor: "rgba(57, 104, 104, 0.3)" }}>
20
+          <View style={{ flexDirection: "row", marginBottom: 10 }}>
21
+            <Avatar.Image size={60} source={dpuser}></Avatar.Image>
22
+            <View style={{ flex: 1, justifyContent: "center", paddingStart: 15, position: "relative", justifyContent: "space-evenly" }}>
23
+              <Text style={{ fontWeight: "700", position: "absolute", top: 5, right: 0, color: "rgba(0,0,0,0.3)" }}>7:55AM</Text>
24
+              <Text style={{ fontWeight: "700" }}>Invest Pahang</Text>
25
+              <Text style={{ fontWeight: "700" }}>ID No : Ariffudin@PSK</Text>
26
+            </View>
27
+          </View>
28
+          <Text style={{ fontWeight: "700", marginBottom: 10 }}>Muhammad Ariffudin is working from home today</Text>
29
+        </View>
30
+      </Link>
31
+    )
32
+  }
33
+
34
+  const renderNotificationAction = () => {
35
+    return (
36
+      <View style={{ marginBottom: 30, borderBottomWidth: 1, paddingBottom: 15, borderBottomColor: "rgba(57, 104, 104, 0.3)" }}>
37
+        <View style={{ flexDirection: "row", marginBottom: 10 }}>
38
+          <Avatar.Image size={60} source={dpuser}></Avatar.Image>
39
+          <View style={{ flex: 1, justifyContent: "center", paddingStart: 15, position: "relative", justifyContent: "space-evenly" }}>
40
+            <Text style={{ fontWeight: "700", position: "absolute", top: 5, right: 0, color: "rgba(0,0,0,0.3)" }}>7:55AM</Text>
41
+            <Text style={{ fontWeight: "700" }}>Invest Pahang</Text>
42
+            <Text style={{ fontWeight: "700" }}>ID No : Ariffudin@PSK</Text>
43
+          </View>
44
+        </View>
45
+        <Text style={{ fontWeight: "700", marginBottom: 10 }}>Muhammad Ariffudin is working from home today</Text>
46
+        <View style={{ flexDirection: "row", justifyContent: "space-evenly", gap: 10 }}>
47
+          <Button mode='outlined' style={{ paddingHorizontal: 35, borderColor: colors.primary }} onPress={() => { console.log("click") }}>Reject</Button>
48
+          <Button mode='contained' style={{ paddingHorizontal: 35 }} onPress={() => { console.log("click") }}>Accept</Button>
49
+        </View>
50
+      </View>
51
+    )
52
+  }
53
+
54
+  const renderNotificationResult = (result) => {
55
+    return (
56
+      <View style={{ marginBottom: 30, borderBottomWidth: 1, paddingBottom: 15, borderBottomColor: "rgba(57, 104, 104, 0.3)" }}>
57
+        <View style={{ flexDirection: "row", marginBottom: 10 }}>
58
+          <Avatar.Image size={60} source={dpuser}></Avatar.Image>
59
+          <View style={{ flex: 1, justifyContent: "center", paddingStart: 15, position: "relative", justifyContent: "space-evenly" }}>
60
+            <Text style={{ fontWeight: "700", position: "absolute", top: 5, right: 0, color: "rgba(0,0,0,0.3)" }}>7:55AM</Text>
61
+            <Text style={{ fontWeight: "700" }}>Invest Pahang</Text>
62
+            <Text style={{ fontWeight: "700" }}>ID No : Ariffudin@PSK</Text>
63
+          </View>
64
+        </View>
65
+        <Text style={{ fontWeight: "700", marginBottom: 10 }}>Muhammad Ariffudin is working from home today</Text>
66
+        <View style={{ flexDirection: "row" }}>
67
+          {(result) ?
68
+            <Text style={[fonts.titleSmall, { color: colors.primary }]}><Icon name="done" size={20} style={{ verticalAlign: "middle", marginEnd: 10 }} />Request Accepted</Text> :
69
+            <Text style={[fonts.titleSmall, { color: colors.error }]}><Icon name="close" size={20} style={{ verticalAlign: "middle", marginEnd: 10 }} />Request Decline</Text>
70
+          }
71
+        </View>
72
+      </View>
73
+    )
74
+  }
75
+
76
+  return (
77
+    <View style={[styles.container, { backgroundColor: colors.background }]}>
78
+      <Appbar.Header>
79
+
80
+        <Avatar.Image size={50} source={dpuser}></Avatar.Image>
81
+
82
+        <View style={styles.titleContainer}>
83
+          <Appbar.Content title="General" titleStyle={[fonts.titleLarge, styles.title]} />
84
+        </View>
85
+
86
+        {/* Menu Component */}
87
+        <Menu
88
+          visible={menuVisible}
89
+          onDismiss={() => setMenuVisible(false)}
90
+          anchor={
91
+            <Appbar.Action icon="dots-vertical" onPress={() => setMenuVisible(true)} />
92
+          }
93
+        >
94
+          <Menu.Item onPress={() => console.log('Profile Clicked')} title="Profile" />
95
+          <Menu.Item onPress={() => console.log('Settings Clicked')} title="Settings" />
96
+          <Menu.Item onPress={() => console.log('Logout Clicked')} title="Logout" />
97
+        </Menu>
98
+      </Appbar.Header>
99
+
100
+      <View style={styles.tabContainer}>
101
+        <Text style={[styles.tabButton, fonts.titleMedium, activeTab === 'General' && styles.activeTab]} onPress={() => { setActiveTab('General') }}>General</Text>
102
+        <Text style={[styles.tabButton, fonts.titleMedium, activeTab === 'Request' && styles.activeTab]} onPress={() => { setActiveTab('Request') }}>Request <Text style={styles.badge}>1</Text></Text>
103
+      </View>
104
+
105
+
106
+      <View style={styles.searchSection}>
107
+        <TextInput
108
+          style={styles.input}
109
+          placeholder="Search"
110
+          onChangeText={setSearchInput}
111
+          value={searchInput}
112
+          underlineColorAndroid="transparent"
113
+          placeholderTextColor="#D9D9D9"
114
+        />
115
+        <Icon name="search" size={20} color="#888" style={styles.icon} />
116
+      </View>
117
+
118
+      {(activeTab == 'General') && <View style={{ flex: 1 }}>
119
+        <ScrollView>
120
+          <Text style={[fonts.titleMedium, { fontWeight: "bold", marginBottom: 15 }]}>Today</Text>
121
+          {[1, 2].map(() => renderNotification())}
122
+
123
+          <Text style={[fonts.titleMedium, { fontWeight: "bold", marginBottom: 15 }]}>Yesterday</Text>
124
+          {[1, 2].map(() => renderNotification())}
125
+
126
+          <Text style={[fonts.titleMedium, { fontWeight: "bold", marginBottom: 15 }]}>Older</Text>
127
+          {[1, 2].map(() => renderNotification())}
128
+
129
+        </ScrollView>
130
+      </View>}
131
+
132
+      {(activeTab == 'Request') && <View style={{ flex: 1 }}>
133
+        <ScrollView>
134
+          {[1, 2].map(() => renderNotificationAction())}
135
+          {[1].map(() => renderNotificationResult(true))}
136
+          {[1].map(() => renderNotificationResult(false))}
137
+        </ScrollView>
138
+      </View>}
139
+
140
+    </View>
141
+  );
142
+};
143
+
144
+const styles = StyleSheet.create({
145
+  container: {
146
+    flex: 1,
147
+    padding: 20,
148
+    width: '100%',
149
+  },
150
+  badge: {
151
+    backgroundColor: "#BB5C3F",
152
+    color: "#FFF",
153
+    borderRadius: 100,
154
+    paddingVertical: 4,
155
+    paddingHorizontal: 6,
156
+    fontSize: 10,
157
+    fontWeight: "400",
158
+    verticalAlign: "middle",
159
+    marginStart: 5
160
+  },
161
+  activeTab: {
162
+    borderBottomWidth: 2,
163
+    borderBottomColor: "#396868",
164
+    color: "#396868",
165
+    fontWeight: "bold"
166
+  },
167
+  tabContainer: {
168
+    flexDirection: "row",
169
+    marginBottom: 20
170
+  },
171
+  tabButton: {
172
+    fontWeight: "bold",
173
+    paddingVertical: 15,
174
+    width: "50%",
175
+    textAlign: "center",
176
+    active: {
177
+      borderBottomWidth: 2,
178
+    }
179
+  },
180
+  titleContainer: {
181
+    flex: 1,
182
+    alignItems: 'center',
183
+  },
184
+  title: {
185
+    fontWeight: 'bold',
186
+  },
187
+  searchSection: {
188
+    flexDirection: 'row',
189
+    justifyContent: 'center',
190
+    alignItems: 'center',
191
+    marginBottom: 20
192
+  },
193
+  icon: {
194
+    padding: 10,
195
+    position: "absolute",
196
+    right: 10,
197
+    color: "#D9D9D9"
198
+  },
199
+  input: {
200
+    height: 40,
201
+    flex: 1,
202
+    borderWidth: 1,
203
+    paddingVertical: 10,
204
+    paddingHorizontal: 20,
205
+    borderRadius: 100,
206
+    borderColor: "#C0CFD0"
207
+  }
208
+});
209
+
210
+export default Home;

app/screens/Status.jsx → app/(tabs)/home/status.jsx Wyświetl plik


+ 9
- 0
app/(tabs)/notify/_layout.jsx Wyświetl plik

@@ -0,0 +1,9 @@
1
+import { Stack } from "expo-router";
2
+
3
+export default function NotifyLayout() {
4
+    return(
5
+        <Stack>
6
+            <Stack.Screen name="index" options={{headerShown:false}}></Stack.Screen>
7
+        </Stack>
8
+    )
9
+}

+ 231
- 0
app/(tabs)/notify/index.jsx Wyświetl plik

@@ -0,0 +1,231 @@
1
+import React, { useEffect, useState } from 'react';
2
+import { View, StyleSheet, TextInput, Text, ScrollView, FlatList, Pressable } from 'react-native';
3
+import BootstrapModal from '@/components/BootstrapModal';
4
+import { Appbar, Menu, Avatar, useTheme, Button } from 'react-native-paper';
5
+import Icon from 'react-native-vector-icons/MaterialIcons';
6
+import dpuser from "@/assets/images/userdp.png";
7
+
8
+/** Some Temp Bullshits */
9
+const dummyUserDataName = [
10
+  {
11
+    id: 1,
12
+    name: "AzmanHadi@PSK",
13
+    user_img: "https://t4.ftcdn.net/jpg/03/64/21/11/360_F_364211147_1qgLVxv1Tcq0Ohz3FawUfrtONzz8nq3e.jpg"
14
+  },
15
+  {
16
+    id: 2,
17
+    name: "NorMelati@PSK",
18
+    user_img: "https://www.shutterstock.com/image-photo/head-shot-portrait-millennial-beautiful-260nw-1893951241.jpg"
19
+  },
20
+  {
21
+    id: 3,
22
+    name: "RazuanKhan@PSK",
23
+    user_img: "https://plus.unsplash.com/premium_photo-1689568126014-06fea9d5d341?fm=jpg&q=60&w=3000&ixlib=rb-4.0.3&ixid=M3wxMjA3fDB8MHxzZWFyY2h8MXx8cHJvZmlsZXxlbnwwfHwwfHx8MA%3D%3D"
24
+  }
25
+]
26
+
27
+const Notification = () => {
28
+  const { colors, fonts } = useTheme();
29
+  const [menuVisible, setMenuVisible] = useState(false);
30
+  const [inputContent, setInputContent] = useState("");
31
+  const [pickedUser, setPickedUser] = useState(null);
32
+  const [userNameSearch, setUserNameSearch] = useState('');
33
+  const [visible, setVisible] = useState(false);
34
+  const [nameSuggestion, setNameSuggestion] = useState([])
35
+
36
+
37
+  const preTextClick = (pretext) => {
38
+    setInputContent(pretext)
39
+  }
40
+
41
+  const handleOnSearchUser = (e) => {
42
+
43
+    const value = e.target.value;
44
+    setUserNameSearch(value)
45
+
46
+  }
47
+
48
+  useEffect(() => {
49
+
50
+    if (userNameSearch.length > 0) {
51
+
52
+      let filteredData = dummyUserDataName.filter(
53
+        ({ name }) => name.toLowerCase().includes(userNameSearch?.toLowerCase())
54
+      )
55
+      setNameSuggestion(filteredData);
56
+    } else {
57
+      setNameSuggestion([]);
58
+    }
59
+
60
+  }, [userNameSearch])
61
+
62
+  const renderUser = ({ item }) => (
63
+    <Pressable onPress={() => { 
64
+      setPickedUser(item);
65
+      setNameSuggestion([]);
66
+      setUserNameSearch("");
67
+     }}>
68
+      <View style={styles.nameItem} >
69
+        <Avatar.Image size={25} source={item.user_img}></Avatar.Image>
70
+        <Text style={styles.nameText}>{item.name}</Text>
71
+      </View>
72
+    </Pressable>
73
+  );
74
+
75
+  const renderUserBadge = (pickedUser) => {
76
+    return (
77
+      <View style={{ flexDirection: "row", backgroundColor: "#396868", padding: 5, borderRadius: 20, paddingRight: 10 }}>
78
+        <Avatar.Image size={35} source={pickedUser?.user_img}></Avatar.Image>
79
+        <Text style={{ marginTop: "auto", marginBottom: "auto", marginLeft: 10, fontWeight: "500", color: "#FFF", marginRight: 5 }}>{pickedUser?.name}</Text>
80
+        <Pressable onPress={()=>{setPickedUser(null)}}>
81
+          <Icon name="cancel" size={25} color={"#FFF"} style={{ marginTop: "auto", marginBottom: "auto" }} />
82
+        </Pressable>
83
+      </View>
84
+    )
85
+  }
86
+
87
+  return (
88
+    <View style={[styles.container, { backgroundColor: colors.background }]}>
89
+
90
+      <BootstrapModal visible={visible} setVisible={setVisible} />
91
+
92
+      <Appbar.Header>
93
+
94
+        <Avatar.Image size={50} source={dpuser}></Avatar.Image>
95
+
96
+        <View style={styles.titleContainer}>
97
+          <Appbar.Content title="Send Notification" titleStyle={[fonts.titleLarge, styles.title]} />
98
+        </View>
99
+
100
+        {/* Menu Component */}
101
+        <Menu
102
+          visible={menuVisible}
103
+          onDismiss={() => setMenuVisible(false)}
104
+          anchor={
105
+            <Appbar.Action icon="dots-vertical" onPress={() => setMenuVisible(true)} />
106
+          }
107
+        >
108
+          <Menu.Item onPress={() => console.log('Profile Clicked')} title="Profile" />
109
+          <Menu.Item onPress={() => console.log('Settings Clicked')} title="Settings" />
110
+          <Menu.Item onPress={() => console.log('Logout Clicked')} title="Logout" />
111
+        </Menu>
112
+      </Appbar.Header>
113
+
114
+      <View style={{ flex: 1, marginTop: 20 }}>
115
+        <View style={{ flexDirection: "row", gap: 20, marginBottom: 20 }}>
116
+          <Text style={[fonts.titleMedium, { fontWeight: "bold", marginTop: "auto", marginBottom: "auto" }]}>To :</Text>
117
+
118
+          {pickedUser ? renderUserBadge(pickedUser) : <View style={{ flex: 1 }}>
119
+            <TextInput
120
+              value={userNameSearch}
121
+              onChange={(e) => {
122
+                handleOnSearchUser(e)
123
+              }}
124
+              style={styles.userSearchInput}
125
+            />
126
+            {(nameSuggestion.length > 0) && <View style={styles.nameListContainer}>
127
+              <FlatList
128
+                data={nameSuggestion}
129
+                renderItem={renderUser}
130
+                keyExtractor={(item) => `${item?.id}`}
131
+                contentContainerStyle={styles.listContent}
132
+              />
133
+            </View>}
134
+          </View>}
135
+        </View>
136
+        <TextInput
137
+          style={styles.textArea}
138
+          value={inputContent}
139
+          onChangeText={setInputContent}
140
+          multiline={true} // Enables multi-line input
141
+          numberOfLines={8} // Sets an initial number of visible lines
142
+        />
143
+        <Text style={[fonts.titleLarge, { fontWeight: "bold", marginBottom: 20 }]}>Select Pretext</Text>
144
+        <View style={{ flex: 1 }}>
145
+          {[
146
+            "Request to Work From Home",
147
+            "Request for late Check In",
148
+            "Request for early Check Out",
149
+            "Notify for Annual Leave",
150
+            "Notify for Emergency Leave"
151
+          ].map(text => <Text onPress={() => { preTextClick(text) }} style={[fonts.titleMedium, { marginBottom: 20, fontWeight: "bold", color: colors.secondary }]} >{text}</Text>)}
152
+        </View>
153
+      </View>
154
+
155
+    </View>
156
+  );
157
+};
158
+
159
+const styles = StyleSheet.create({
160
+  container: {
161
+    flex: 1,
162
+    padding: 20,
163
+    width: '100%',
164
+  },
165
+  textArea: {
166
+    height: 220,
167
+    borderColor: "#ccc",
168
+    borderWidth: 1,
169
+    padding: 10,
170
+    borderRadius: 8,
171
+    textAlignVertical: "top", // Makes text start from the top-left
172
+    backgroundColor: "#fff",
173
+    marginBottom: 20
174
+  },
175
+  badge: {
176
+    backgroundColor: "#BB5C3F",
177
+    color: "#FFF",
178
+    borderRadius: 100,
179
+    paddingVertical: 4,
180
+    paddingHorizontal: 6,
181
+    fontSize: 10,
182
+    fontWeight: "400",
183
+    verticalAlign: "middle",
184
+    marginStart: 5
185
+  },
186
+  userSearchInput: {
187
+    flex: 1,
188
+    paddingHorizontal: 20,
189
+    borderBottomColor: "rgba(0,0,0,0.2)",
190
+    borderBottomWidth: 1,
191
+    marginEnd: 20
192
+  },
193
+  nameListContainer: {
194
+    position: "absolute",
195
+    top: 25,
196
+    left: 0,
197
+    backgroundColor: "#FFF",
198
+    width: "100%",
199
+    paddingHorizontal: 10,
200
+    borderWidth: 2,
201
+    borderColor: "#CFCFCF"
202
+  },
203
+  listContent: {
204
+    paddingBottom: 10,
205
+  },
206
+  nameItem: {
207
+    paddingVertical: 6,
208
+    flex: 1,
209
+    flexDirection: "row"
210
+  },
211
+  nameText: {
212
+    marginLeft: 10,
213
+    fontSize: 16,
214
+    color: '#555',
215
+  },
216
+  titleContainer: {
217
+    flex: 1,
218
+    alignItems: 'center',
219
+  },
220
+  title: {
221
+    fontWeight: 'bold',
222
+  },
223
+  icon: {
224
+    padding: 10,
225
+    position: "absolute",
226
+    right: 10,
227
+    color: "#D9D9D9"
228
+  }
229
+});
230
+
231
+export default Notification;

+ 9
- 0
app/(tabs)/profile/_layout.jsx Wyświetl plik

@@ -0,0 +1,9 @@
1
+import { Stack } from "expo-router";
2
+
3
+export default function ProfileLayout() {
4
+    return(
5
+        <Stack>
6
+            <Stack.Screen name="index" options={{headerShown:false}}></Stack.Screen>
7
+        </Stack>
8
+    )
9
+}

app/(pages)/notify.jsx → app/(tabs)/profile/index.jsx Wyświetl plik


+ 2
- 1
app/_layout.tsx Wyświetl plik

@@ -27,7 +27,8 @@ export default function RootLayout() {
27 27
 
28 28
   return (
29 29
     <Stack>
30
-      <Stack.Screen name="(pages)" options={{ headerShown: false }} />
30
+      <Stack.Screen name="index" options={{ headerShown: false }} />
31
+      <Stack.Screen name="(tabs)" options={{ headerShown: false }} />
31 32
       <Stack.Screen name="+not-found" />
32 33
     </Stack>
33 34
   );

+ 0
- 38
app/bak__layout.tsx Wyświetl plik

@@ -1,38 +0,0 @@
1
-import { DarkTheme, DefaultTheme, ThemeProvider } from '@react-navigation/native';
2
-import { useFonts } from 'expo-font';
3
-import { Stack } from 'expo-router';
4
-import * as SplashScreen from 'expo-splash-screen';
5
-import { StatusBar } from 'expo-status-bar';
6
-import { useEffect } from 'react';
7
-import 'react-native-reanimated';
8
-
9
-import { useColorScheme } from '@/hooks/useColorScheme';
10
-
11
-// Prevent the splash screen from auto-hiding before asset loading is complete.
12
-SplashScreen.preventAutoHideAsync();
13
-
14
-export default function RootLayout() {
15
-  const colorScheme = useColorScheme();
16
-  const [loaded] = useFonts({
17
-    SpaceMono: require('../assets/fonts/SpaceMono-Regular.ttf'),
18
-  });
19
-
20
-  useEffect(() => {
21
-    if (loaded) {
22
-      SplashScreen.hideAsync();
23
-    }
24
-  }, [loaded]);
25
-
26
-  if (!loaded) {
27
-    return null;
28
-  }
29
-
30
-  return (
31
-    <ThemeProvider value={colorScheme === 'dark' ? DarkTheme : DefaultTheme}>
32
-      <Stack>
33
-        <Stack.Screen name="(screen)" options={{ headerShown: false }} />
34
-        <Stack.Screen name="+not-found" />
35
-      </Stack>
36
-    </ThemeProvider>
37
-  );
38
-}

app/screens/Welcome.jsx → app/index.jsx Wyświetl plik

@@ -1,5 +1,6 @@
1 1
 import React from 'react';
2
-import { View, Text, StyleSheet, Image } from 'react-native';
2
+import { View, Text, StyleSheet, Image, Pressable } from 'react-native';
3
+import { Link } from 'expo-router';
3 4
 import { Button, useTheme } from 'react-native-paper';
4 5
 import text4uLogo from '@/assets/images/text4ulogo.png'
5 6
 import text4uTitle from '@/assets/images/text4utitle.png'
@@ -26,13 +27,11 @@ const Welcome = () => {
26 27
                 <Text style={[fonts.titleSmall, styles.subHeading]}>
27 28
                     Empowering you with instant alerts for every important moment!
28 29
                 </Text>
29
-                <Button
30
-                    mode="contained"
31
-                    style={[button, styles.button]}
32
-                    labelStyle={{ ...fonts.titleMedium, ...styles.buttonLabel }}
33
-                >
34
-                    Get Started
35
-                </Button>
30
+                <Pressable style={[button, styles.button]}>
31
+                    <Link href={"/home"}>
32
+                        <Text style={styles.buttonLabel}>Get Started</Text>
33
+                    </Link>
34
+                </Pressable>
36 35
                 <Text style={{ ...fonts.titleMedium, ...styles.loginInfo }}>
37 36
                     Already have an account?
38 37
                     <Text style={styles.loginText} onPress={goToLogin}>
@@ -79,10 +78,17 @@ const styles = StyleSheet.create({
79 78
     button: {
80 79
         marginBottom: 36,
81 80
         marginLeft:"auto",
82
-        marginRight:"auto"
81
+        marginRight:"auto",
82
+        backgroundColor:"#DD9C47",
83
+        paddingVertical:12,
84
+        paddingHorizontal:25,
85
+        borderRadius:30
83 86
     },
84 87
     buttonLabel: {
85
-        fontWeight: "bold"
88
+        fontWeight: "700",
89
+        color: "#FFF",
90
+        fontSize: 16,
91
+
86 92
     },
87 93
     loginInfo: {
88 94
         marginBottom: 20,

+ 0
- 112
app/screens/Notification.jsx Wyświetl plik

@@ -1,112 +0,0 @@
1
-import React, { useState } from 'react';
2
-import { View, StyleSheet, TextInput, Text, ScrollView } from 'react-native';
3
-import { Appbar, Menu, Avatar, useTheme, Button } from 'react-native-paper';
4
-import Icon from 'react-native-vector-icons/MaterialIcons';
5
-import dpuser from "@/assets/images/userdp.png";
6
-
7
-const Notification = () => {
8
-  const { colors, fonts } = useTheme();
9
-  const [menuVisible, setMenuVisible] = useState(false);
10
-  const [inputContent, setInputContent] = useState("");
11
-
12
-
13
-  const preTextClick = (pretext) => {
14
-    setInputContent(pretext)
15
-  }
16
-
17
-  return (
18
-    <View style={[styles.container, { backgroundColor: colors.background }]}>
19
-      <Appbar.Header>
20
-
21
-        <Avatar.Image size={50} source={dpuser}></Avatar.Image>
22
-
23
-        <View style={styles.titleContainer}>
24
-          <Appbar.Content title="Send Notification" titleStyle={[fonts.titleLarge, styles.title]} />
25
-        </View>
26
-
27
-        {/* Menu Component */}
28
-        <Menu
29
-          visible={menuVisible}
30
-          onDismiss={() => setMenuVisible(false)}
31
-          anchor={
32
-            <Appbar.Action icon="dots-vertical" onPress={() => setMenuVisible(true)} />
33
-          }
34
-        >
35
-          <Menu.Item onPress={() => console.log('Profile Clicked')} title="Profile" />
36
-          <Menu.Item onPress={() => console.log('Settings Clicked')} title="Settings" />
37
-          <Menu.Item onPress={() => console.log('Logout Clicked')} title="Logout" />
38
-        </Menu>
39
-      </Appbar.Header>
40
-
41
-
42
-      <View style={{ flex: 1, marginTop: 20 }}>
43
-        <View style={{ flexDirection: "row", gap: 20, marginBottom: 20 }}>
44
-          <Text style={[fonts.titleLarge, { fontWeight: "bold" }]}>To :</Text>
45
-          <TextInput value='asd' style={{ flex: 1, paddingHorizontal: 20, borderBottomColor: "rgba(0,0,0,0.2)", borderBottomWidth: 1, marginEnd: 20 }}></TextInput>
46
-        </View>
47
-        <TextInput
48
-          style={styles.textArea}
49
-          value={inputContent}
50
-          onChangeText={setInputContent}
51
-          multiline={true} // Enables multi-line input
52
-          numberOfLines={8} // Sets an initial number of visible lines
53
-        />
54
-        <Text style={[fonts.titleLarge, { fontWeight: "bold", marginBottom:20 }]}>Select Pretext</Text>
55
-        <View style={{flex:1}}>
56
-          {[
57
-            "Request to Work From Home",
58
-            "Request for late Check In",
59
-            "Request for early Check Out",
60
-            "Notify for Annual Leave",
61
-            "Notify for Emergency Leave"
62
-          ].map(text => <Text onPress={()=>{preTextClick(text)}} style={[fonts.titleMedium, {marginBottom:20, fontWeight:"bold", color:colors.secondary}]} >{text}</Text> )}
63
-        </View>
64
-      </View>
65
-
66
-    </View>
67
-  );
68
-};
69
-
70
-const styles = StyleSheet.create({
71
-  container: {
72
-    flex: 1,
73
-    padding: 20,
74
-    width: '100%',
75
-  },
76
-  textArea: {
77
-    height: 220,
78
-    borderColor: "#ccc",
79
-    borderWidth: 1,
80
-    padding: 10,
81
-    borderRadius: 8,
82
-    textAlignVertical: "top", // Makes text start from the top-left
83
-    backgroundColor: "#fff",
84
-    marginBottom:20
85
-  },
86
-  badge: {
87
-    backgroundColor: "#BB5C3F",
88
-    color: "#FFF",
89
-    borderRadius: 100,
90
-    paddingVertical: 4,
91
-    paddingHorizontal: 6,
92
-    fontSize: 10,
93
-    fontWeight: "400",
94
-    verticalAlign: "middle",
95
-    marginStart: 5
96
-  },
97
-  titleContainer: {
98
-    flex: 1,
99
-    alignItems: 'center',
100
-  },
101
-  title: {
102
-    fontWeight: 'bold',
103
-  },
104
-  icon: {
105
-    padding: 10,
106
-    position: "absolute",
107
-    right: 10,
108
-    color: "#D9D9D9"
109
-  }
110
-});
111
-
112
-export default Notification;

+ 0
- 168
app/screens/Request.jsx Wyświetl plik

@@ -1,168 +0,0 @@
1
-import React, { useState } from 'react';
2
-import { View, StyleSheet, TextInput, Text, ScrollView } from 'react-native';
3
-import { Appbar, Menu, Avatar, useTheme, Button } from 'react-native-paper';
4
-import Icon from 'react-native-vector-icons/MaterialIcons';
5
-import dpuser from "@/assets/images/userdp.png";
6
-
7
-const Request = () => {
8
-  const { colors, fonts } = useTheme();
9
-  const [menuVisible, setMenuVisible] = useState(false);
10
-  const [searchInput, setSearchInput] = useState("")
11
-
12
-  const renderNotificationAction = () => {
13
-    return (
14
-      <View style={{marginBottom:30, borderBottomWidth:1, paddingBottom:15, borderBottomColor:"rgba(57, 104, 104, 0.3)"}}>
15
-        <View style={{ flexDirection: "row", marginBottom: 10 }}>
16
-          <Avatar.Image size={60} source={dpuser}></Avatar.Image>
17
-          <View style={{ flex: 1, justifyContent: "center", paddingStart: 15, position:"relative", justifyContent:"space-evenly" }}>
18
-            <Text style={{ fontWeight: "700", position:"absolute", top:5, right:0, color:"rgba(0,0,0,0.3)" }}>7:55AM</Text>
19
-            <Text style={{ fontWeight: "700" }}>Invest Pahang</Text>
20
-            <Text style={{ fontWeight: "700" }}>ID No : Ariffudin@PSK</Text>
21
-          </View>
22
-        </View>
23
-        <Text style={{ fontWeight: "700", marginBottom:10 }}>Muhammad Ariffudin is working from home today</Text>
24
-        <View style={{flexDirection:"row", justifyContent:"space-evenly", gap:10}}>
25
-          <Button mode='outlined' style={{paddingHorizontal:35, borderColor:colors.primary }} onPress={()=>{console.log("click")}}>Reject</Button>
26
-          <Button mode='contained' style={{paddingHorizontal:35}} onPress={()=>{console.log("click")}}>Accept</Button>
27
-        </View>
28
-      </View>
29
-    )
30
-  }
31
-
32
-  const renderNotificationResult = (result) => {
33
-    return (
34
-      <View style={{marginBottom:30, borderBottomWidth:1, paddingBottom:15, borderBottomColor:"rgba(57, 104, 104, 0.3)"}}>
35
-        <View style={{ flexDirection: "row", marginBottom: 10 }}>
36
-          <Avatar.Image size={60} source={dpuser}></Avatar.Image>
37
-          <View style={{ flex: 1, justifyContent: "center", paddingStart: 15, position:"relative", justifyContent:"space-evenly" }}>
38
-            <Text style={{ fontWeight: "700", position:"absolute", top:5, right:0, color:"rgba(0,0,0,0.3)" }}>7:55AM</Text>
39
-            <Text style={{ fontWeight: "700" }}>Invest Pahang</Text>
40
-            <Text style={{ fontWeight: "700" }}>ID No : Ariffudin@PSK</Text>
41
-          </View>
42
-        </View>
43
-        <Text style={{ fontWeight: "700", marginBottom:10 }}>Muhammad Ariffudin is working from home today</Text>
44
-        <View style={{flexDirection:"row"}}>
45
-          {(result) ?
46
-          <Text style={[fonts.titleSmall, {color:colors.primary}]}><Icon name="done" size={20} style={{verticalAlign:"middle", marginEnd:10}} />Request Accepted</Text> : 
47
-          <Text style={[fonts.titleSmall, {color:colors.error}]}><Icon name="close" size={20} style={{verticalAlign:"middle", marginEnd:10}} />Request Decline</Text>
48
-          }
49
-        </View>
50
-      </View>
51
-    )
52
-  }
53
-
54
-  return (
55
-    <View style={[styles.container, { backgroundColor: colors.background }]}>
56
-      <Appbar.Header>
57
-
58
-        <Avatar.Image size={50} source={dpuser}></Avatar.Image>
59
-
60
-        <View style={styles.titleContainer}>
61
-          <Appbar.Content title="Request" titleStyle={[fonts.titleLarge, styles.title]} />
62
-        </View>
63
-
64
-        {/* Menu Component */}
65
-        <Menu
66
-          visible={menuVisible}
67
-          onDismiss={() => setMenuVisible(false)}
68
-          anchor={
69
-            <Appbar.Action icon="dots-vertical" onPress={() => setMenuVisible(true)} />
70
-          }
71
-        >
72
-          <Menu.Item onPress={() => console.log('Profile Clicked')} title="Profile" />
73
-          <Menu.Item onPress={() => console.log('Settings Clicked')} title="Settings" />
74
-          <Menu.Item onPress={() => console.log('Logout Clicked')} title="Logout" />
75
-        </Menu>
76
-      </Appbar.Header>
77
-
78
-      <View style={styles.tabContainer}>
79
-        <Text style={[styles.tabButton, fonts.titleMedium, { fontWeight: "bold" }]}>General  </Text>
80
-        <Text style={[styles.tabButton, fonts.titleMedium, { fontWeight: "bold" }, { borderBottomWidth: 2, borderBottomColor: colors.secondary, color: colors.secondary }]}>Request <Text style={styles.badge}>1</Text></Text>
81
-      </View>
82
-
83
-
84
-      <View style={styles.searchSection}>
85
-        <TextInput
86
-          style={styles.input}
87
-          placeholder="Search"
88
-          onChangeText={setSearchInput}
89
-          value={searchInput}
90
-          underlineColorAndroid="transparent"
91
-          placeholderTextColor="#D9D9D9"
92
-        />
93
-        <Icon name="search" size={20} color="#888" style={styles.icon} />
94
-      </View>
95
-
96
-      <View style={{flex:1}}>
97
-        <ScrollView>
98
-          {[1,2].map(() => renderNotificationAction())}
99
-          {[1].map(() => renderNotificationResult(true))}
100
-          {[1].map(() => renderNotificationResult(false))}
101
-        </ScrollView>
102
-      </View>
103
-
104
-    </View>
105
-  );
106
-};
107
-
108
-const styles = StyleSheet.create({
109
-  container: {
110
-    flex: 1,
111
-    padding: 20,
112
-    width: '100%',
113
-  },
114
-  badge: {
115
-    backgroundColor: "#BB5C3F",
116
-    color: "#FFF",
117
-    borderRadius: 100,
118
-    paddingVertical: 4,
119
-    paddingHorizontal: 6,
120
-    fontSize: 10,
121
-    fontWeight: "400",
122
-    verticalAlign: "middle",
123
-    marginStart: 5
124
-  },
125
-  tabContainer: {
126
-    flexDirection: "row",
127
-    marginBottom: 20
128
-  },
129
-  tabButton: {
130
-    fontWeight: "bold",
131
-    paddingVertical: 15,
132
-    width: "50%",
133
-    textAlign: "center",
134
-    active: {
135
-      borderBottomWidth: 2,
136
-    }
137
-  },
138
-  titleContainer: {
139
-    flex: 1,
140
-    alignItems: 'center',
141
-  },
142
-  title: {
143
-    fontWeight: 'bold',
144
-  },
145
-  searchSection: {
146
-    flexDirection: 'row',
147
-    justifyContent: 'center',
148
-    alignItems: 'center',
149
-    marginBottom: 20
150
-  },
151
-  icon: {
152
-    padding: 10,
153
-    position: "absolute",
154
-    right: 10,
155
-    color: "#D9D9D9"
156
-  },
157
-  input: {
158
-    height: 40,
159
-    flex: 1,
160
-    borderWidth: 1,
161
-    paddingVertical: 10,
162
-    paddingHorizontal: 20,
163
-    borderRadius: 100,
164
-    borderColor: "#C0CFD0"
165
-  }
166
-});
167
-
168
-export default Request;

+ 86
- 0
components/BootstrapModal.jsx Wyświetl plik

@@ -0,0 +1,86 @@
1
+import React, { useState } from 'react';
2
+import {
3
+  Modal,
4
+  View,
5
+  Text,
6
+  Pressable,
7
+  StyleSheet,
8
+  TouchableWithoutFeedback
9
+} from 'react-native';
10
+
11
+const BootstrapModal = ({ visible, setVisible }) => {
12
+
13
+  return (
14
+    <Modal
15
+      transparent
16
+      animationType="fade"
17
+      visible={visible}
18
+      onRequestClose={() => setVisible(false)}
19
+    >
20
+      <TouchableWithoutFeedback onPress={() => setVisible(false)}>
21
+        <View style={styles.backdrop} />
22
+      </TouchableWithoutFeedback>
23
+
24
+      <View style={styles.centeredView}>
25
+        <View style={styles.modalView}>
26
+          <Text style={styles.modalText}>This is a Bootstrap-like Modal!</Text>
27
+          <Pressable
28
+            style={[styles.button, styles.buttonClose]}
29
+            onPress={() => setVisible(false)}
30
+          >
31
+            <Text style={styles.textStyle}>Close</Text>
32
+          </Pressable>
33
+        </View>
34
+      </View>
35
+    </Modal>
36
+  );
37
+};
38
+
39
+const styles = StyleSheet.create({
40
+  centeredView: {
41
+    flex: 1,
42
+    justifyContent: 'center',
43
+    alignItems: 'center',
44
+    zIndex: 10,
45
+  },
46
+  backdrop: {
47
+    ...StyleSheet.absoluteFillObject,
48
+    backgroundColor: 'rgba(0,0,0,0.5)',
49
+  },
50
+  modalView: {
51
+    width: '80%',
52
+    backgroundColor: 'white',
53
+    borderRadius: 12,
54
+    padding: 20,
55
+    alignItems: 'center',
56
+    shadowColor: '#000',
57
+    shadowOpacity: 0.3,
58
+    shadowRadius: 4,
59
+    elevation: 5,
60
+  },
61
+  openButton: {
62
+    backgroundColor: '#007bff',
63
+    borderRadius: 6,
64
+    padding: 10,
65
+    elevation: 2,
66
+  },
67
+  button: {
68
+    marginTop: 15,
69
+    padding: 10,
70
+    borderRadius: 6,
71
+  },
72
+  buttonClose: {
73
+    backgroundColor: '#dc3545',
74
+  },
75
+  textStyle: {
76
+    color: 'white',
77
+    fontWeight: '600',
78
+    textAlign: 'center',
79
+  },
80
+  modalText: {
81
+    fontSize: 18,
82
+    textAlign: 'center',
83
+  },
84
+});
85
+
86
+export default BootstrapModal;

Ładowanie…
Anuluj
Zapisz