Changeset f5b256e for my-react-app/src/components/Restaurants.js
- Timestamp:
- 04/28/25 14:20:18 (3 weeks ago)
- Branches:
- main
- Children:
- deea3c4
- Parents:
- 8ca35dc
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
my-react-app/src/components/Restaurants.js
r8ca35dc rf5b256e 4 4 import { useNavigate } from 'react-router-dom'; 5 5 import {RestaurantContext} from "./RestaurantContext"; 6 import {Alert} from "bootstrap"; 7 8 const parseTime = (timeString) => { 9 const [hours, minutes] = timeString.trim().split(':').map(Number); 10 return new Date().setHours(hours, minutes, 0, 0); 11 }; 12 13 const roundToNextQuarter = (date) => { 14 const minutes = date.getMinutes(); 15 const roundedMinutes = Math.floor(minutes / 15) * 15; 16 date.setMinutes(roundedMinutes, 0, 0); 17 return date; 18 }; 19 20 const shouldMoveToNextDay = (currentTime, endTime) => { 21 return (endTime - currentTime) <= 2 * 60 * 60 * 1000; 22 }; 6 23 7 24 const Restaurants = () => { … … 14 31 }, [restaurantContext]); 15 32 33 34 const generateTimeSlots = (operatingHours) => { 35 const timeSlots = []; 36 const [startTimeStr, endTimeStr] = operatingHours.split('-').map((time) => time.trim()); 37 38 const startTime = parseTime(startTimeStr); 39 let endTime = parseTime(endTimeStr); 40 41 const currentTime = new Date().getTime(); 42 if (shouldMoveToNextDay(currentTime, endTime)) { 43 endTime += 24 * 60 * 60 * 1000; 44 } 45 46 let currentTimeSlot = new Date(startTime); 47 currentTimeSlot = roundToNextQuarter(currentTimeSlot); 48 49 while (currentTimeSlot.getTime() < endTime) { 50 timeSlots.push(currentTimeSlot.toISOString()); 51 currentTimeSlot.setMinutes(currentTimeSlot.getMinutes() + 15); 52 } 53 54 return timeSlots; 55 }; 56 16 57 const handleDetailClick = (restaurantId) => { 17 58 navigate(`/restaurants/${restaurantId}`); 18 } 59 }; 19 60 20 61 const handleTimeSlotClick = (table, timeSlot, restaurant) => { … … 23 64 const restaurantId = restaurant.restaurantId; 24 65 25 const encodedTableNumber = encodeURI (tableNumber);66 const encodedTableNumber = encodeURIComponent(tableNumber); 26 67 const encodedTimeSlot = encodeURIComponent(formattedTimeSlot); 27 68 const encodedRestaurantId = encodeURIComponent(restaurantId); 28 69 29 70 navigate(`/reservationConfirmation/${encodedTableNumber}/${encodedTimeSlot}/${encodedRestaurantId}`); 30 } 71 }; 31 72 32 73 const renderTimeSlots = (tablesList, restaurant) => { 33 74 const currentTime = new Date().getTime(); 34 let renderedTimeSlots = {}; // Object to store rendered slots for each table capacity75 let renderedTimeSlots = {}; 35 76 36 return tablesList.flatMap(table => { 37 // Render capacity header when encountering a new capacity 77 if (tablesList.length === 0) { 78 return <p>No tables available for reservations at this restaurant.</p>; 79 } 80 81 return tablesList.flatMap((table) => { 82 const tableTimeSlots = generateTimeSlots(restaurant.operatingHours); 83 38 84 if (!renderedTimeSlots[table.capacity]) { 39 85 renderedTimeSlots[table.capacity] = 0; 40 86 return ( 41 87 <div key={table.capacity}> 42 <h3>Table for : {table.capacity}</h3>43 {table .timeSlots.map((timeSlot, index) => {88 <h3>Table for {table.capacity} guests</h3> 89 {tableTimeSlots.map((timeSlot, index) => { 44 90 const timeSlotTime = new Date(timeSlot).getTime(); 45 const tableCapacity = table.capacity;46 91 47 // Check if the time slot is after the current time and limit to 3 slots 48 if (timeSlotTime > currentTime && renderedTimeSlots[tableCapacity] < 3) { 49 renderedTimeSlots[tableCapacity]++; 92 if (timeSlotTime > currentTime && renderedTimeSlots[table.capacity] < 3) { 93 renderedTimeSlots[table.capacity]++; 50 94 const timeSlotDateTime = new Date(timeSlot); 51 const formattedTime = timeSlotDateTime.toLocaleTimeString(); 52 const formattedDateTime = timeSlotDateTime.toLocaleString(); // Format for both date and time 95 const formattedTime = timeSlotDateTime.toLocaleTimeString([], { 96 hour: '2-digit', 97 minute: '2-digit' 98 }); 53 99 54 100 return ( 55 <button key={index} className="btn btn-primary me-2 mb-2" onClick={() => handleTimeSlotClick(table, timeSlot, restaurant)}> 56 {formattedDateTime} {/* Display both date and time */} 101 <button 102 key={index} 103 className="btn btn-primary me-2 mb-2" 104 onClick={() => handleTimeSlotClick(table, timeSlot, restaurant)} 105 > 106 {formattedTime} {} 57 107 </button> 58 108 ); 59 109 } else { 60 return null; // Render nothing if the condition is not met110 return null; 61 111 } 62 112 })} … … 64 114 ); 65 115 } else { 66 // If capacity has been rendered, return null to avoid duplicate rendering67 116 return null; 68 117 } 69 118 }); 70 71 } 72 119 }; 73 120 74 121 return ( … … 77 124 <div className="row"> 78 125 {restaurants.map((restaurant) => ( 79 <div key={restaurant. id} className="col-md-4 mb-4">126 <div key={restaurant.restaurantId} className="col-md-4 mb-4"> 80 127 <div className="card"> 81 128 <div className="card-body"> 82 129 <h5 className="card-title"> 83 {restaurant.name} <StarRating key={restaurant.id} rating={restaurant.rating}/>130 {restaurant.name} 84 131 </h5> 85 132 <p className="card-text">{restaurant.cuisineType}</p> 86 133 <p className="card-text">{restaurant.operatingHours}</p> 87 134 <p className="card-text">Ul. {restaurant.address}</p> 88 <div className="d-flex flex-wrap"> 89 {renderTimeSlots(restaurant.tablesList.flatMap((table) => table), restaurant)} 90 </div> 135 136 {restaurant.tablesList && restaurant.tablesList.length > 0 ? ( 137 <div className="d-flex flex-wrap"> 138 {renderTimeSlots(restaurant.tablesList, restaurant)} 139 </div> 140 ) : ( 141 <p>No tables available for reservations at this restaurant.</p> 142 )} 91 143 </div> 92 <button onClick={() => handleDetailClick(restaurant.restaurantId)} 93 className="btn btn-primary">View Details144 <button onClick={() => handleDetailClick(restaurant.restaurantId)} className="btn btn-primary"> 145 View Details 94 146 </button> 95 147 </div>
Note:
See TracChangeset
for help on using the changeset viewer.