diff --git a/frontend/occupi-mobile4/screens/Booking/BookRoom.tsx b/frontend/occupi-mobile4/screens/Booking/BookRoom.tsx index 4deef071..0a1f8c9c 100644 --- a/frontend/occupi-mobile4/screens/Booking/BookRoom.tsx +++ b/frontend/occupi-mobile4/screens/Booking/BookRoom.tsx @@ -11,6 +11,7 @@ import { import Navbar from '../../components/NavBar'; import { widthPercentageToDP as wp, heightPercentageToDP as hp } from 'react-native-responsive-screen'; +import * as SecureStore from 'expo-secure-store'; const groupDataInPairs = (data) => { if (!data) return []; @@ -42,13 +43,23 @@ const BookRoom = () => { const toggleLayout = () => { setLayout((prevLayout) => (prevLayout === "row" ? "grid" : "row")); }; + const apiUrl = process.env.EXPO_PUBLIC_LOCAL_API_URL; + const viewroomsendpoint = process.env.EXPO_PUBLIC_VIEW_ROOMS; useEffect(() => { const fetchAllRooms = async () => { - console.log("heree"); + // console.log("heree"); + let authToken = await SecureStore.getItemAsync('Token'); try { - const response = await fetch('https://dev.occupi.tech/api/view-rooms') + const response = await fetch(`${apiUrl}${viewroomsendpoint}?floorNo=0`, { + method: 'GET', + headers: { + 'Content-Type': 'application/json', + 'Authorization': `${authToken}` + }, + }); const data = await response.json(); + // console.log(data); if (response.ok) { setRoomData(data.data || []); // Ensure data is an array // toast.show({ @@ -89,7 +100,7 @@ const BookRoom = () => { } }; fetchAllRooms(); - }, [toast]); + }, [toast, apiUrl, viewroomsendpoint]); useEffect(() => { setIsDarkMode(colorScheme === 'dark'); @@ -101,6 +112,11 @@ const BookRoom = () => { const roomPairs = groupDataInPairs(roomData); + const handleRoomSelect = async (room) => { + await SecureStore.setItemAsync('CurrentRoom', JSON.stringify(room)); + router.push('/office-details'); + } + return ( <> @@ -131,7 +147,7 @@ const BookRoom = () => { {roomPairs.map((pair, index) => ( {pair.map((room, idx) => ( - router.push({ pathname: '/office-details', params: { roomData: JSON.stringify(room) } })}> + handleRoomSelect(room)}> {room.roomName} @@ -160,7 +176,7 @@ const BookRoom = () => { ) : ( {roomData.map((room, idx) => ( - router.push({ pathname: '/office-details', params: { roomData: JSON.stringify(room) } })}> + handleRoomSelect(room)}> {room.roomName} diff --git a/frontend/occupi-mobile4/screens/Booking/ViewBookingDetails.tsx b/frontend/occupi-mobile4/screens/Booking/ViewBookingDetails.tsx index f918f6b4..5f990311 100644 --- a/frontend/occupi-mobile4/screens/Booking/ViewBookingDetails.tsx +++ b/frontend/occupi-mobile4/screens/Booking/ViewBookingDetails.tsx @@ -1,4 +1,4 @@ -import React, { useState } from 'react'; +import React, { useState, useEffect } from 'react'; import { Icon, ScrollView, @@ -18,46 +18,80 @@ import { MaterialIcons } from '@expo/vector-icons'; import { useColorScheme, StyleSheet, TouchableOpacity, ActivityIndicator } from 'react-native'; +import * as SecureStore from 'expo-secure-store'; import { widthPercentageToDP as wp } from 'react-native-responsive-screen'; import PagerView from 'react-native-pager-view'; -import { useRouter, useLocalSearchParams } from 'expo-router'; +import { useRouter } from 'expo-router'; +interface Room { + _id: string; + roomName: string; + roomId: string; + roomNo: number; + floorNo: number; + minOccupancy: number; + maxOccupancy: number; + description: string; + emails: string[]; + date: string; + start: string; + end: string; +} -const ViewBookingDetails = (bookingId, roomName) => { +const ViewBookingDetails = (bookingId:string, roomName:string) => { const colorScheme = useColorScheme(); const isDarkMode = colorScheme === 'dark'; - const roomParams = useLocalSearchParams(); - const roomData = roomParams.roomData; - const room = JSON.parse(roomData); + const [room, setRoom] = useState({}); const router = useRouter(); - const [checkedIn, setCheckedIn] = useState(room.checkedIn); + const [checkedIn, setCheckedIn] = useState(false); const [isLoading, setIsLoading] = useState(false); const toast = useToast(); - console.log("HERE:" + roomData); - console.log(checkedIn); + const apiUrl = process.env.EXPO_PUBLIC_LOCAL_API_URL; + const checkinendpoint = process.env.EXPO_PUBLIC_CHECK_IN; + const cancelbookingendpoint = process.env.EXPO_PUBLIC_CANCEL_BOOKING; + + // console.log("HERE:" + room); + + useEffect(() => { + const getCurrentRoom = async () => { + let result : string = await SecureStore.getItemAsync('CurrentRoom'); + // console.log("CurrentRoom:",result); + // setUserDetails(JSON.parse(result).data); + let jsonresult = JSON.parse(result); + console.log(jsonresult); + setRoom(jsonresult); + setCheckedIn(jsonresult.checkedIn); + }; + getCurrentRoom(); + }, []); + + // console.log("Room",room._id); + const checkin = async () => { const body = { "bookingId": room._id, - "creator": room.creator, - "roomId": room.roomId + "creator": room.creator }; setIsLoading(true); console.log(body); + // console.log(apiUrl+""+checkinendpoint); + let authToken = await SecureStore.getItemAsync('Token'); try { - const response = await fetch('https://dev.occupi.tech/api/check-in', { + const response = await fetch(`${apiUrl}${checkinendpoint}`, { method: 'POST', headers: { Accept: 'application/json', - 'Content-Type': 'application/json' + 'Content-Type': 'application/json', + 'Authorization': `${authToken}` }, body: JSON.stringify(body), credentials: "include" }); const data = await response.json(); - console.log(data); + // console.log(data); // const cookies = response.headers.get('Accept'); // console.log(cookies); if (response.ok) { @@ -94,17 +128,19 @@ const ViewBookingDetails = (bookingId, roomName) => { const cancelBooking = async () => { const body = { - "_id": room._id, + "bookingId": room._id, "creator": room.creator, }; setIsLoading(true); console.log(body); + let authToken = await SecureStore.getItemAsync('Token'); try { - const response = await fetch('https://dev.occupi.tech/api/cancel-booking', { + const response = await fetch(`${apiUrl}${cancelbookingendpoint}`, { method: 'POST', headers: { Accept: 'application/json', - 'Content-Type': 'application/json' + 'Content-Type': 'application/json', + 'Authorization': `${authToken}` }, body: JSON.stringify(body), credentials: "include" @@ -125,7 +161,7 @@ const ViewBookingDetails = (bookingId, roomName) => { }, }); setIsLoading(false); - router.push("/home"); + router.replace("/home"); } else { setIsLoading(false); console.log(data); @@ -177,10 +213,10 @@ const ViewBookingDetails = (bookingId, roomName) => { - Attendees: {room.emails.length} + Attendees: {room.emails?.length} - {room.emails.map((email, idx) => ( + {room.emails?.map((email, idx) => ( {idx + 1}. {email} ))} Description diff --git a/frontend/occupi-mobile4/screens/Booking/ViewBookings.tsx b/frontend/occupi-mobile4/screens/Booking/ViewBookings.tsx index 7e28223a..fb34d61f 100644 --- a/frontend/occupi-mobile4/screens/Booking/ViewBookings.tsx +++ b/frontend/occupi-mobile4/screens/Booking/ViewBookings.tsx @@ -11,6 +11,7 @@ import RNPickerSelect from 'react-native-picker-select'; import { Octicons } from '@expo/vector-icons'; import { Ionicons } from '@expo/vector-icons'; import Navbar from '../../components/NavBar'; +import * as SecureStore from 'expo-secure-store'; import { useRouter } from 'expo-router'; const groupDataInPairs = (data) => { @@ -31,61 +32,20 @@ interface Room { maxOccupancy: number; description: string; emails: string[]; + date: string; + start: string; + end: string; } -const getTimeForSlot = (slot) => { - let startTime, endTime; - switch (slot) { - case 1: - startTime = '07:00'; - endTime = '08:00'; - break; - case 2: - startTime = '08:00'; - endTime = '09:00'; - break; - case 3: - startTime = '09:00'; - endTime = '10:00'; - break; - case 4: - startTime = '10:00'; - endTime = '11:00'; - break; - case 5: - startTime = '11:00'; - endTime = '12:00'; - break; - case 6: - startTime = '12:00'; - endTime = '13:00'; - break; - case 7: - startTime = '13:00'; - endTime = '14:00'; - break; - case 8: - startTime = '14:00'; - endTime = '15:00'; - break; - case 9: - startTime = '15:00'; - endTime = '16:00'; - break; - case 10: - startTime = '16:00'; - endTime = '17:00'; - break; - default: - startTime = 'Invalid slot'; - endTime = 'Invalid slot'; - } - return { startTime, endTime }; -}; +function extractTimeFromDate(dateString: string): string { + const date = new Date(dateString); + date.setHours(date.getHours() - 2); + return date.toTimeString().substring(0, 5); +} -const slotToTime = (slot: number) => { - const { startTime, endTime } = getTimeForSlot(slot); - return `${startTime} - ${endTime}` +function extractDateFromDate(dateString: string): string { + const date = new Date(dateString); + return date.toDateString(); } const ViewBookings = () => { @@ -95,25 +55,30 @@ const ViewBookings = () => { const toast = useToast(); const [roomData, setRoomData] = useState([]); // const [selectedSort, setSelectedSort] = useState("newest"); - // const [email, setEmail] = useState('kamogelomoeketse@gmail.com'); + const [email, setEmail] = useState(''); const router = useRouter(); const [refreshing, setRefreshing] = useState(false); + const apiUrl = process.env.EXPO_PUBLIC_LOCAL_API_URL; + const viewbookingsendpoint = process.env.EXPO_PUBLIC_VIEW_BOOKINGS; const onRefresh = React.useCallback(() => { const fetchAllRooms = async () => { console.log("heree"); + let authToken = await SecureStore.getItemAsync('Token'); + console.log("Token:" + authToken); try { - const response = await fetch(`https://dev.occupi.tech/api/view-bookings?email=kamogelomoeketse@gmail.com`, { + const response = await fetch(`${apiUrl}${viewbookingsendpoint}?email=${email}`, { method: 'GET', headers: { 'Content-Type': 'application/json', + 'Authorization': `${authToken}` }, }); const data = await response.json(); if (response.ok) { setRoomData(data.data || []); // Ensure data is an array - console.log(data); + // console.log(data); // toast.show({ // placement: 'top', // render: ({ id }) => { @@ -156,7 +121,7 @@ const ViewBookings = () => { setRefreshing(false); fetchAllRooms(); }, 2000); - }, [toast]); + }, [toast, apiUrl, viewbookingsendpoint, email]); const toggleLayout = () => { setLayout((prevLayout) => (prevLayout === "row" ? "grid" : "row")); @@ -186,18 +151,29 @@ const ViewBookings = () => { useEffect(() => { const fetchAllRooms = async () => { - console.log("heree"); + let authToken = await SecureStore.getItemAsync('Token'); + let result = await SecureStore.getItemAsync('UserData'); + // console.log(result); + // if (result !== undefined) { + let jsonresult = JSON.parse(result); + setEmail(jsonresult?.data?.email); + // } + // console.log("Token:"+authToken); + // console.log("heree"); try { - const response = await fetch(`https://dev.occupi.tech/api/view-bookings?email=kamogelomoeketse@gmail.com`, { + // console.log(`${apiUrl}${viewbookingsendpoint}?email=${jsonresult?.data?.email}`); + const response = await fetch(`${apiUrl}${viewbookingsendpoint}?email=${jsonresult?.data?.email}`, { method: 'GET', headers: { 'Content-Type': 'application/json', + 'Authorization': `${authToken}` }, }); const data = await response.json(); + // console.log(data); if (response.ok) { setRoomData(data.data || []); // Ensure data is an array - console.log(data); + // console.log(data); // toast.show({ // placement: 'top', // render: ({ id }) => { @@ -236,10 +212,16 @@ const ViewBookings = () => { } }; fetchAllRooms(); - }, [toast]); + }, [toast, apiUrl, email, viewbookingsendpoint]); const roomPairs = groupDataInPairs(roomData); + const handleRoomClick = async (value: string) => { + await SecureStore.setItemAsync('CurrentRoom', value); + router.push('/viewbookingdetails'); + // console.log(value); + } + return ( @@ -326,7 +308,7 @@ const ViewBookings = () => { > {pair.map((room) => ( router.push({ pathname: '/viewbookingdetails', params: { roomData: JSON.stringify(room) } })} + onPress={() => handleRoomClick(JSON.stringify(room))} style={{ flex: 1, borderWidth: 1, @@ -358,10 +340,9 @@ const ViewBookings = () => { - {new Date().toDateString()} - {slotToTime(room.slot)} + {extractDateFromDate(room.date)} + {extractTimeFromDate(room.start)}-{extractTimeFromDate(room.end)} - @@ -380,7 +361,7 @@ const ViewBookings = () => { > {roomData.map((room) => ( router.push({ pathname: '/viewbookingdetails', params: { roomData: JSON.stringify(room) } })} + onPress={() => handleRoomClick(JSON.stringify(room))} style={{ flex: 1, borderWidth: 1, @@ -408,7 +389,7 @@ const ViewBookings = () => { justifyContent: "space-between" }} > - {room.roomName} + {room.roomName} Attendees: {room.emails.length} @@ -416,8 +397,8 @@ const ViewBookings = () => { Your booking time: - {new Date().toDateString()} - {slotToTime(room.slot)} + {extractDateFromDate(room.date)} + {extractTimeFromDate(room.start)}-{extractTimeFromDate(room.end)} @@ -433,16 +414,4 @@ const ViewBookings = () => { ); }; -const styles = StyleSheet.create({ - container: { - flex: 1, - }, - scrollView: { - flex: 1, - backgroundColor: 'pink', - alignItems: 'center', - justifyContent: 'center', - }, -}); - export default ViewBookings; diff --git a/frontend/occupi-mobile4/screens/Login/SignIn.tsx b/frontend/occupi-mobile4/screens/Login/SignIn.tsx index 2019a625..afbff9ff 100644 --- a/frontend/occupi-mobile4/screens/Login/SignIn.tsx +++ b/frontend/occupi-mobile4/screens/Login/SignIn.tsx @@ -68,10 +68,10 @@ const SignInForm = () => { } = useForm({ resolver: zodResolver(signInSchema), }); - const apiUrl = process.env.EXPO_PUBLIC_DEVELOP_API_URL; + const apiUrl = process.env.EXPO_PUBLIC_LOCAL_API_URL; const loginUrl = process.env.EXPO_PUBLIC_LOGIN; const getUserDetailsUrl= process.env.EXPO_PUBLIC_GET_USER_DETAILS; - console.log(apiUrl,loginUrl); + console.log(apiUrl + "" +loginUrl); const isEmailFocused = useState(false); const [loading, setLoading] = useState(false); const [showPassword, setShowPassword] = useState(false); diff --git a/frontend/occupi-mobile4/screens/Login/SplashScreen.tsx b/frontend/occupi-mobile4/screens/Login/SplashScreen.tsx index 1c5dce6c..d7bf7401 100644 --- a/frontend/occupi-mobile4/screens/Login/SplashScreen.tsx +++ b/frontend/occupi-mobile4/screens/Login/SplashScreen.tsx @@ -93,7 +93,7 @@ export default function SplashScreen() { useEffect(() => { const timer = setTimeout(() => { setSelectedIndex(1); // Assuming Onboarding1 is at index 1 - router.replace('/login'); // Navigate to Onboarding1 screen + router.replace('/bookings'); // Navigate to Onboarding1 screen }, 5000); // 8 seconds return () => clearTimeout(timer); // Clean up timer on component unmount diff --git a/frontend/occupi-mobile4/screens/Office/BookingDetails.tsx b/frontend/occupi-mobile4/screens/Office/BookingDetails.tsx index 559ad181..3d67a3e1 100644 --- a/frontend/occupi-mobile4/screens/Office/BookingDetails.tsx +++ b/frontend/occupi-mobile4/screens/Office/BookingDetails.tsx @@ -1,4 +1,4 @@ -import React, { useState } from "react"; +import React, { useState, useEffect } from "react"; import { Image, TouchableOpacity, @@ -24,84 +24,53 @@ import { LinearGradient } from "expo-linear-gradient"; import { useRouter, useLocalSearchParams } from 'expo-router'; import { ActivityIndicator } from 'react-native'; import * as LocalAuthentication from "expo-local-authentication"; +import * as SecureStore from 'expo-secure-store'; import GradientButton from '@/components/GradientButton'; -const getTimeForSlot = (slot) => { - console.log(slot); - let startTime, endTime; - switch (slot) { - case 1: - startTime = '07:00'; - endTime = '08:00'; - break; - case 2: - startTime = '08:00'; - endTime = '09:00'; - break; - case 3: - startTime = '09:00'; - endTime = '10:00'; - break; - case 4: - startTime = '10:00'; - endTime = '11:00'; - break; - case 5: - startTime = '11:00'; - endTime = '12:00'; - break; - case 6: - startTime = '12:00'; - endTime = '13:00'; - break; - case 7: - startTime = '13:00'; - endTime = '14:00'; - break; - case 8: - startTime = '14:00'; - endTime = '15:00'; - break; - case 9: - startTime = '15:00'; - endTime = '16:00'; - break; - case 10: - startTime = '16:00'; - endTime = '17:00'; - break; - default: - startTime = 'Invalid slot'; - endTime = 'Invalid slot'; - } - return { startTime, endTime }; -}; const BookingDetails = () => { const navigation = useNavigation(); const [currentStep, setCurrentStep] = useState(0); const [email, setEmail] = useState(""); const [loading, setLoading] = useState(false); + const [bookingInfo, setbookingInfo] = useState(); const colorScheme = useColorScheme(); const toast = useToast(); const router = useRouter(); - const roomParams = useLocalSearchParams(); - const creatorEmail = roomParams.email; - const slot = roomParams.slot || 0; - const { startTime, endTime } = getTimeForSlot(Number(roomParams.slot)); - const roomId = roomParams.roomId; - const floorNo = roomParams.floorNo; - const roomData = JSON.parse(roomParams.roomData); + const [creatorEmail, setCreatorEmail] = useState(''); + const [startTime, setStartTime] = useState(''); + const [endTime, setEndTime] = useState(''); const isDark = colorScheme === "dark"; - console.log(creatorEmail + slot + roomId + floorNo); - console.log(roomData); - console.log("slot: " + slot); - console.log(startTime); - const [attendees, setAttendees] = useState([creatorEmail]); - console.log(attendees); + // console.log(creatorEmail + roomId + floorNo); + // console.log(bookingInfo?); + // console.log(startTime); + const [attendees, setAttendees] = useState(['']); + // console.log(attendees); const cardBackgroundColor = isDark ? '#2C2C2E' : '#F3F3F3'; - const steps = ["Booking details", "Invite attendees", "Receipt"]; + const apiUrl = process.env.EXPO_PUBLIC_LOCAL_API_URL; + const bookroomendpoint = process.env.EXPO_PUBLIC_BOOK_ROOM; + + useEffect(() => { + const getbookingInfo = async () => { + let userinfo = await SecureStore.getItemAsync('UserData'); + // console.log(result); + // if (result !== undefined) { + let jsoninfo = JSON.parse(userinfo); + setCreatorEmail(jsoninfo?.data?.email); + let result: string = await SecureStore.getItemAsync('BookingInfo'); + console.log("CurrentRoom:", jsoninfo?.data?.email); + // setUserDetails(JSON.parse(result).data); + let jsonresult = JSON.parse(result); + console.log("BookingInfo", jsonresult); + setbookingInfo(jsonresult); + setStartTime(jsonresult.startTime); + setEndTime(jsonresult.endTime); + console.log(jsoninfo?.data?.email); + setAttendees([jsoninfo?.data?.email]); + }; + getbookingInfo(); + }, []); const addAttendee = () => { if (email && !attendees.includes(email)) { @@ -115,35 +84,32 @@ const BookingDetails = () => { }; const onSubmit = async () => { - const body = { - "roomId": roomParams.roomId, - "slot": parseInt(roomParams.slot, 10), + "roomId": bookingInfo?.roomId, "emails": attendees, - "roomName": roomData.roomName, + "roomName": bookingInfo?.roomName, "creator": creatorEmail, - "floorNo": parseInt(roomParams.floorNo, 10) + "floorNo": bookingInfo?.floorNo, + "date": `${bookingInfo?.date}T00:00:00.000+00:00`, + "start": `${bookingInfo?.date}T${startTime}:00.000+00:00`, + "end": `${bookingInfo?.date}T${endTime}:00.000+00:00` }; - console.log(body); + console.log("hereeeeee", body); + let authToken = await SecureStore.getItemAsync('Token'); try { setLoading(true); - const response = await fetch('https://dev.occupi.tech/api/book-room', { + const response = await fetch(`${apiUrl}${bookroomendpoint}`, { method: 'POST', headers: { Accept: 'application/json', - 'Content-Type': 'application/json' + 'Content-Type': 'application/json', + 'Authorization': `${authToken}` }, body: JSON.stringify(body), credentials: "include" }); const data = await response.json(); console.log(data); - const cookies = response.headers.get('Accept'); - // CookieManager.get('https://dev.occupi.tech') - // .then((cookies) => { - // console.log('CookieManager.get =>', cookies); - // }); - console.log(cookies); if (response.ok) { setCurrentStep(2); setLoading(false); @@ -340,7 +306,7 @@ const BookingDetails = () => { color: isDark ? "#fff" : "#000", }} > - {roomData.roomName} + {bookingInfo?.roomName} { > Fast OLED - {roomData.minOccupancy} - {roomData.maxOccupancy} - Floor: {roomData.floorNo === 0 ? 'G' : roomData.floorNo} + {bookingInfo?.minOccupancy} - {bookingInfo?.maxOccupancy} + Floor: {bookingInfo?.floorNo === "0" ? 'G' : bookingInfo?.floorNo} { {!loading ? ( onSubmit()} - text="Send invites" + text="Send invites" /> ) : ( { color: isDark ? "#fff" : "#000", }} > */} - + - HDMI Room + {bookingInfo?.roomName} Fast OLED - {roomData.minOccupancy} - {roomData.maxOccupancy} - Floor {roomData.floorNo === 0 ? 'G' : roomData.floorNo} + {bookingInfo?.minOccupancy} - {bookingInfo?.maxOccupancy} + Floor {bookingInfo?.floorNo === "0" ? 'G' : bookingInfo?.floorNo} @@ -536,7 +502,7 @@ const BookingDetails = () => { Attendees: - + {attendees.map((email, idx) => ( {idx + 1}. {email} ))} diff --git a/frontend/occupi-mobile4/screens/Office/OfficeDetails.tsx b/frontend/occupi-mobile4/screens/Office/OfficeDetails.tsx index d9b34feb..d6eca469 100644 --- a/frontend/occupi-mobile4/screens/Office/OfficeDetails.tsx +++ b/frontend/occupi-mobile4/screens/Office/OfficeDetails.tsx @@ -1,7 +1,6 @@ import React, { useState, useEffect, useRef } from 'react'; import { TouchableOpacity, - Modal, useColorScheme, StyleSheet, Animated, @@ -14,23 +13,20 @@ import { ChevronDownIcon, Feather } from '@expo/vector-icons'; -import AsyncStorage from '@react-native-async-storage/async-storage'; import { useRouter, useLocalSearchParams } from 'expo-router'; -import DateTimePickerModal from 'react-native-modal-datetime-picker'; import { LinearGradient } from 'expo-linear-gradient'; import RNPickerSelect from 'react-native-picker-select'; -import { Icon, ScrollView, View, Text, Image } from '@gluestack-ui/themed'; +import { Icon, ScrollView, View, Text, Image, Divider } from '@gluestack-ui/themed'; import { widthPercentageToDP as wp, heightPercentageToDP as hp, } from 'react-native-responsive-screen'; // import Carousel from 'react-native-snap-carousel'; +import * as SecureStore from 'expo-secure-store'; import { useNavigation, NavigationProp } from '@react-navigation/native'; import { Theme } from 'react-native-calendars/src/types'; -import slotsData from './availableSlots.json'; import { PageIndicator } from 'react-native-page-indicator'; - type RootStackParamList = { BookingDetails: undefined; }; @@ -61,87 +57,89 @@ type RootStackParamList = { const pages = ['Page 1', 'Page 2', 'Page 3']; const OfficeDetails = () => { - const [modalVisible, setModalVisible] = useState(false); - // const [date, setDate] = useState(new Date(2000, 6, 7)); - const [isDatePickerVisible, setDatePickerVisibility] = useState(false); - const [slot, setSlot] = useState(1); - const [userEmail, setUserEmail] = useState(''); + const [date, setDate] = useState(); + const [startTime, setStartTime] = useState(); + const [endTime, setEndTime] = useState(); const router = useRouter(); const colorScheme = useColorScheme(); const isDarkMode = colorScheme === 'dark'; - const roomParams = useLocalSearchParams(); - const roomData = roomParams.roomData; - const roomData2 = JSON.parse(roomData); + const [room, setRoom] = useState(); const navigation = useNavigation>(); - const [availableSlots, setAvailableSlots] = useState({}); const scrollX = useRef(new Animated.Value(0)).current; const { width } = useWindowDimensions(); const animatedCurrent = useRef(Animated.divide(scrollX, width)).current; + const getUpcomingDates = () => { + const dates = []; + for (let i = 1; i <= 4; i++) { + const date = new Date(); + date.setDate(date.getDate() + i); + dates.push(date.toISOString().split('T')[0]); + } + return dates; + }; + const upcomingDates = getUpcomingDates(); + useEffect(() => { - // Load the available slots from the JSON file - setAvailableSlots(slotsData.slots); - getData(); + const getCurrentRoom = async () => { + let result : string = await SecureStore.getItemAsync('CurrentRoom'); + console.log("CurrentRoom:",result); + // setUserDetails(JSON.parse(result).data); + let jsonresult = JSON.parse(result); + // console.log(jsonresult); + setRoom(jsonresult); + }; + getCurrentRoom(); }, []); - // const handleCheckAvailability = () => { - // setModalVisible(true); - // }; - - // const showDatePicker = () => { - // setDatePickerVisibility(true); - // }; - - const hideDatePicker = () => { - setDatePickerVisibility(false); - }; - - const handleConfirm = (selectedDate) => { - // setDate(selectedDate); - // setDate(selectedDate.toLocaleDateString()); - // console.log(date.toLocaleDateString()); - hideDatePicker(); - }; + const handleBookRoom = async () => { + // console.log('Booking Room'); + // console.log(date); + // console.log(startTime); + // console.log(endTime); + // console.log(room?.roomName); + // console.log(room?.roomId); + // console.log(room?.floorNo); - // const storeData = async (value) => { - // try { - // await AsyncStorage.setItem('email', value); - // } catch (e) { - // // saving error - // } - // }; + // Check if any of the required fields are blank + if (!date || !startTime || !endTime) { + alert('Please fill in all the information.'); + return; // Exit the function to prevent further execution + } - const getData = async () => { - try { - const value = await AsyncStorage.getItem('email'); - // console.log(value); - setUserEmail(value); - } catch (e) { - // error reading value - console.log(e); + // Compare startTime and endTime + const start = new Date(`1970-01-01T${startTime}Z`); + const end = new Date(`1970-01-01T${endTime}Z`); + if (end <= start) { + alert('End time cannot be before start time.'); + return; // Exit the function to prevent further execution } - }; - // storeData('kamogelomoeketse@gmail.com'); + let bookingInfo = { + date: date, + startTime: startTime, + endTime: endTime, + roomName: room?.roomName, + roomId: room?.roomId, + floorNo: room?.floorNo, + minOccupancy: room?.minOccupancy, + maxOccupancy: room?.maxOccupancy + }; - // const renderItem = ({ item }: { item: { uri: string } }) => ( - // - // - // - // ); + console.log(bookingInfo); + await SecureStore.setItemAsync('BookingInfo', JSON.stringify(bookingInfo)); + router.replace('/booking-details'); + } - const handleSlotClick = () => { - navigation.navigate('/booking-details'); - }; - console.log(roomData2); - console.log(userEmail); + // console.log(room?); + // console.log(userEmail); return ( <> {/* Top Section */} navigation.goBack()} /> - {roomData2.roomName} + {room?.roomName} @@ -152,18 +150,7 @@ const OfficeDetails = () => { - - {/* - - slide1 - - - slide2 - - - slide3 - - */} + { - - {roomData2.roomName} + + {room?.roomName} Fast OLED - {roomData2.minOccupancy} - {roomData2.maxOccupancy} - Floor: {roomData2.floorNo === 0 ? 'G' : roomData2.floorNo} + {room?.minOccupancy} - {room?.maxOccupancy} + Floor: {room?.floorNo === 0 ? 'G' : room?.floorNo} @@ -231,30 +218,27 @@ const OfficeDetails = () => { Description - {roomData2.description} + {room?.description} + + Date: setSlot(value)} + darkTheme={isDarkMode ? true : false} + onValueChange={(value) => { setDate(value) }} items={[ - { label: '07:00 - 08:00', value: '1' }, - { label: '08:00 - 09:00', value: '2' }, - { label: '09:00 - 10:00', value: '3' }, - { label: '10:00 - 11:00', value: '4' }, - { label: '11:00 - 12:00', value: '5' }, - { label: '12:00 - 13:00', value: '6' }, - { label: '13:00 - 14:00', value: '7' }, - { label: '14:00 - 15:00', value: '8' }, - { label: '15:00 - 16:00', value: '9' }, - { label: '16:00 - 17:00', value: '10' } + { label: upcomingDates[0], value: upcomingDates[0] }, + { label: upcomingDates[1], value: upcomingDates[1] }, + { label: upcomingDates[2], value: upcomingDates[2] }, + { label: upcomingDates[3], value: upcomingDates[3] }, ]} - placeholder={{ label: 'Select a slot', value: null, color: isDarkMode ? '#fff' : '#000' }} + placeholder={{ label: 'Select a date', value: null, color: isDarkMode ? '#fff' : '#000' }} style={{ inputIOS: { fontSize: 16, paddingVertical: 12, - marginVertical: 12, + marginVertical: 4, paddingHorizontal: 16, borderWidth: 1, borderColor: 'lightgrey', @@ -278,58 +262,112 @@ const OfficeDetails = () => { }} /> + + + Start Time: + setStartTime(value)} + items={[ + { label: '07:00', value: '07:00' }, + { label: '08:00', value: '08:00' }, + { label: '09:00', value: '09:00' }, + { label: '10:00', value: '10:00' }, + { label: '11:00', value: '11:00' }, + { label: '12:00', value: '12:00' }, + { label: '13:00', value: '13:00' }, + { label: '14:00', value: '14:00' }, + { label: '15:00', value: '15:00' }, + { label: '16:00', value: '16:00' } + ]} + placeholder={{ label: 'Select a time', value: null, color: isDarkMode ? '#fff' : '#000' }} + style={{ + inputIOS: { + fontSize: 16, + paddingVertical: 12, + marginVertical: 4, + paddingHorizontal: 16, + borderWidth: 1, + borderColor: 'lightgrey', + borderRadius: 10, + color: isDarkMode ? '#fff' : '#000', + paddingRight: 30, // to ensure the text is never behind the icon + }, + inputAndroid: { + fontSize: 16, + paddingVertical: 8, + paddingHorizontal: 16, + borderWidth: 1, + borderColor: 'lightgrey', + borderRadius: 4, + color: isDarkMode ? '#fff' : '#000', + paddingRight: 30, // to ensure the text is never behind the icon + }, + }} + Icon={() => { + return ; + }} + /> + + + End Time: + setEndTime(value)} + items={[ + { label: '08:00', value: '08:00' }, + { label: '09:00', value: '09:00' }, + { label: '10:00', value: '10:00' }, + { label: '11:00', value: '11:00' }, + { label: '12:00', value: '12:00' }, + { label: '13:00', value: '13:00' }, + { label: '14:00', value: '14:00' }, + { label: '15:00', value: '15:00' }, + { label: '16:00', value: '16:00' }, + { label: '17:00', value: '17:00' } + ]} + placeholder={{ label: 'Select a time', value: null, color: isDarkMode ? '#fff' : '#000' }} + style={{ + inputIOS: { + fontSize: 16, + paddingVertical: 12, + marginVertical: 4, + paddingHorizontal: 16, + borderWidth: 1, + borderColor: 'lightgrey', + borderRadius: 10, + color: isDarkMode ? '#fff' : '#000', + paddingRight: 30, // to ensure the text is never behind the icon + }, + inputAndroid: { + fontSize: 16, + paddingVertical: 8, + paddingHorizontal: 16, + borderWidth: 1, + borderColor: 'lightgrey', + borderRadius: 4, + color: isDarkMode ? '#fff' : '#000', + paddingRight: 30, // to ensure the text is never behind the icon + }, + }} + Icon={() => { + return ; + }} + /> + + + {/* Check Availability Button */} - router.push({ pathname: '/booking-details', params: { email: userEmail, slot: slot, roomId: roomData2.roomId, floorNo: roomData2.floorNo, roomData: roomData } })}> + handleBookRoom()}> - Check availability - - - {/* Modal for Calendar */} - { - setModalVisible(!modalVisible); - }} - > - - Available slots - {/* */} - - {Object.keys(availableSlots).map(date => ( - availableSlots[date].map((slot, index) => ( - - {date} at {slot} - - )) - ))} - - setModalVisible(!modalVisible)} - > - Close - - - ); @@ -344,8 +382,8 @@ const styles = StyleSheet.create({ alignItems: 'center', }, pageIndicator: { - left: 20, - right: 20, + // left: 20, + // right: 20, // bottom: 50, // position: 'absolute', marginTop: 20, diff --git a/frontend/occupi-mobile4/screens/Settings/Profile.tsx b/frontend/occupi-mobile4/screens/Settings/Profile.tsx index 30b03cac..a902d670 100644 --- a/frontend/occupi-mobile4/screens/Settings/Profile.tsx +++ b/frontend/occupi-mobile4/screens/Settings/Profile.tsx @@ -57,7 +57,7 @@ const Profile = () => { const [isLoading, setIsLoading] = useState(false); const [isDatePickerVisible, setDatePickerVisibility] = useState(false); let colorScheme = useColorScheme(); - const apiUrl = process.env.EXPO_PUBLIC_DEVELOP_API_URL; + const apiUrl = process.env.EXPO_PUBLIC_LOCAL_API_URL; const getUserDetailsUrl= process.env.EXPO_PUBLIC_GET_USER_DETAILS; const updateDetailsUrl = process.env.EXPO_PUBLIC_UPDATE_USER_DETAILS; console.log(apiUrl, getUserDetailsUrl, updateDetailsUrl); diff --git a/occupi-backend/pkg/router/router.go b/occupi-backend/pkg/router/router.go index 7457a2b0..840fa309 100644 --- a/occupi-backend/pkg/router/router.go +++ b/occupi-backend/pkg/router/router.go @@ -48,7 +48,7 @@ func OccupiRouter(router *gin.Engine, db *mongo.Client, cache *bigcache.BigCache api.POST("/check-in", middleware.ProtectedRoute, func(ctx *gin.Context) { handlers.CheckIn(ctx, appsession) }) api.POST("/cancel-booking", middleware.ProtectedRoute, func(ctx *gin.Context) { handlers.CancelBooking(ctx, appsession) }) api.GET(("/view-bookings"), middleware.ProtectedRoute, func(ctx *gin.Context) { handlers.ViewBookings(ctx, appsession) }) - api.GET("/view-rooms", middleware.UnProtectedRoute, func(ctx *gin.Context) { handlers.ViewRooms(ctx, appsession) }) + api.GET("/view-rooms", middleware.ProtectedRoute, func(ctx *gin.Context) { handlers.ViewRooms(ctx, appsession) }) api.GET("/user-details", middleware.ProtectedRoute, func(ctx *gin.Context) { handlers.GetUserDetails(ctx, appsession) }) api.PUT("/update-user", middleware.ProtectedRoute, func(ctx *gin.Context) { handlers.UpdateUserDetails(ctx, appsession) }) // api.GET("/filter-users", middleware.UnProtectedRoute, func(ctx *gin.Context) { handlers.FilterUsers(ctx, appsession) })