menu: add open button with its bottom sheet
This commit is contained in:
@@ -122,6 +122,8 @@
|
||||
"carbs": "الكربوهيدرات",
|
||||
"fat": "الدهون",
|
||||
"viewCart": "عرض السلة",
|
||||
"open": "مفتوح",
|
||||
"close": "مغلق",
|
||||
"pay": "الدفع",
|
||||
"payDescription": "الدفع",
|
||||
"rating": "التقييم ",
|
||||
@@ -158,7 +160,9 @@
|
||||
"joinUs": "انضم إلى الولاء",
|
||||
"joinUsDescription": "لتحصل على هدية مجانية",
|
||||
"openingHours": "ساعات العمل: {{openingTime}} - {{closingTime}}",
|
||||
"restaurantIsClosed": "المطعم مغلق"
|
||||
"restaurantIsClosed": "المطعم مغلق",
|
||||
"address": "العنوان",
|
||||
"openingTimes": "ساعات العمل"
|
||||
},
|
||||
"cart": {
|
||||
"title": "السلة",
|
||||
|
||||
@@ -138,6 +138,8 @@
|
||||
"carbs": "Carbs",
|
||||
"fat": "Fat",
|
||||
"viewCart": "View Cart",
|
||||
"open": "Open",
|
||||
"close": "Close",
|
||||
"rating": "Rating ",
|
||||
"loyaltyPoints": "Loyalty Points",
|
||||
"loyaltyDescription": "Buy {{value}} meals and get 1 FREE",
|
||||
@@ -170,7 +172,9 @@
|
||||
"openingHours": "Opening Hours: {{openingTime}} - {{closingTime}}",
|
||||
"restaurantIsClosed": "Restaurant is closed",
|
||||
"pay": "Pay",
|
||||
"payDescription": "Pay for your order"
|
||||
"payDescription": "Pay for your order",
|
||||
"address": "Address",
|
||||
"openingTimes": "Opening Times"
|
||||
},
|
||||
"cart": {
|
||||
"title": "Cart",
|
||||
|
||||
214
src/components/CustomBottomSheet/OpeningTimesBottomSheet.tsx
Normal file
214
src/components/CustomBottomSheet/OpeningTimesBottomSheet.tsx
Normal file
@@ -0,0 +1,214 @@
|
||||
import { Button } from "antd";
|
||||
import { useTranslation } from "react-i18next";
|
||||
import { ProBottomSheet } from "../ProBottomSheet/ProBottomSheet";
|
||||
import ProText from "components/ProText";
|
||||
import ProTitle from "components/ProTitle";
|
||||
import { useAppSelector } from "redux/hooks";
|
||||
|
||||
interface OpeningTimesBottomSheetProps {
|
||||
isOpen: boolean;
|
||||
onClose: () => void;
|
||||
}
|
||||
|
||||
const textStyle: React.CSSProperties = {
|
||||
fontWeight: 400,
|
||||
fontStyle: "Regular",
|
||||
fontSize: 14,
|
||||
lineHeight: "140%",
|
||||
letterSpacing: "0%",
|
||||
};
|
||||
|
||||
export function OpeningTimesBottomSheet({
|
||||
isOpen,
|
||||
onClose,
|
||||
}: OpeningTimesBottomSheetProps) {
|
||||
const { t } = useTranslation();
|
||||
const { isRTL } = useAppSelector((state) => state.locale);
|
||||
const { restaurant } = useAppSelector((state) => state.order);
|
||||
|
||||
const days = [
|
||||
"sunday",
|
||||
"monday",
|
||||
"tuesday",
|
||||
"wednesday",
|
||||
"thursday",
|
||||
"friday",
|
||||
"saturday",
|
||||
];
|
||||
const todayIndex = new Date().getDay();
|
||||
const todayDay = days[todayIndex];
|
||||
|
||||
return (
|
||||
<ProBottomSheet
|
||||
isOpen={isOpen}
|
||||
onClose={onClose}
|
||||
title={t("menu.openingTimes")}
|
||||
showCloseButton={false}
|
||||
initialSnap={1}
|
||||
height={445}
|
||||
snapPoints={[445]}
|
||||
>
|
||||
<div
|
||||
style={{
|
||||
display: "flex",
|
||||
flexDirection: "column",
|
||||
padding: 20,
|
||||
}}
|
||||
>
|
||||
<ProTitle level={5}>{t("menu.address")}</ProTitle>
|
||||
<ProText type="secondary">
|
||||
{isRTL ? restaurant?.addressAR : restaurant?.address}
|
||||
</ProText>
|
||||
|
||||
<ProTitle level={5}>{t("menu.openingTimes")}</ProTitle>
|
||||
<div style={{ display: "flex", justifyContent: "space-between" }}>
|
||||
<ProText
|
||||
type="secondary"
|
||||
style={{
|
||||
...textStyle,
|
||||
fontWeight: todayDay === "sunday" ? 700 : 400,
|
||||
}}
|
||||
>
|
||||
sunday
|
||||
</ProText>
|
||||
<ProText
|
||||
type="secondary"
|
||||
style={{
|
||||
...textStyle,
|
||||
fontWeight: todayDay === "sunday" ? 700 : 400,
|
||||
}}
|
||||
>
|
||||
10:00 AM to 10:00 PM
|
||||
</ProText>
|
||||
</div>
|
||||
<div style={{ display: "flex", justifyContent: "space-between" }}>
|
||||
<ProText
|
||||
type="secondary"
|
||||
style={{
|
||||
...textStyle,
|
||||
fontWeight: todayDay === "monday" ? 700 : 400,
|
||||
}}
|
||||
>
|
||||
monday
|
||||
</ProText>
|
||||
<ProText
|
||||
type="secondary"
|
||||
style={{
|
||||
...textStyle,
|
||||
fontWeight: todayDay === "monday" ? 700 : 400,
|
||||
}}
|
||||
>
|
||||
10:00 AM to 10:00 PM
|
||||
</ProText>
|
||||
</div>
|
||||
<div style={{ display: "flex", justifyContent: "space-between" }}>
|
||||
<ProText
|
||||
type="secondary"
|
||||
style={{
|
||||
...textStyle,
|
||||
fontWeight: todayDay === "tuesday" ? 700 : 400,
|
||||
}}
|
||||
>
|
||||
tuesday
|
||||
</ProText>
|
||||
<ProText
|
||||
type="secondary"
|
||||
style={{
|
||||
...textStyle,
|
||||
fontWeight: todayDay === "tuesday" ? 700 : 400,
|
||||
}}
|
||||
>
|
||||
10:00 AM to 10:00 PM
|
||||
</ProText>
|
||||
</div>
|
||||
<div style={{ display: "flex", justifyContent: "space-between" }}>
|
||||
<ProText
|
||||
type="secondary"
|
||||
style={{
|
||||
...textStyle,
|
||||
fontWeight: todayDay === "wednesday" ? 700 : 400,
|
||||
}}
|
||||
>
|
||||
wednesday
|
||||
</ProText>
|
||||
<ProText
|
||||
type="secondary"
|
||||
style={{
|
||||
...textStyle,
|
||||
fontWeight: todayDay === "wednesday" ? 700 : 400,
|
||||
}}
|
||||
>
|
||||
10:00 AM to 10:00 PM
|
||||
</ProText>
|
||||
</div>
|
||||
<div style={{ display: "flex", justifyContent: "space-between" }}>
|
||||
<ProText
|
||||
type="secondary"
|
||||
style={{
|
||||
...textStyle,
|
||||
fontWeight: todayDay === "thursday" ? 700 : 400,
|
||||
}}
|
||||
>
|
||||
thursday
|
||||
</ProText>
|
||||
<ProText
|
||||
type="secondary"
|
||||
style={{
|
||||
...textStyle,
|
||||
fontWeight: todayDay === "thursday" ? 700 : 400,
|
||||
}}
|
||||
>
|
||||
10:00 AM to 10:00 PM
|
||||
</ProText>
|
||||
</div>
|
||||
<div style={{ display: "flex", justifyContent: "space-between" }}>
|
||||
<ProText
|
||||
type="secondary"
|
||||
style={{
|
||||
...textStyle,
|
||||
fontWeight: todayDay === "friday" ? 700 : 400,
|
||||
}}
|
||||
>
|
||||
friday
|
||||
</ProText>
|
||||
<ProText
|
||||
type="secondary"
|
||||
style={{
|
||||
...textStyle,
|
||||
fontWeight: todayDay === "friday" ? 700 : 400,
|
||||
}}
|
||||
>
|
||||
10:00 AM to 10:00 PM
|
||||
</ProText>
|
||||
</div>
|
||||
<div style={{ display: "flex", justifyContent: "space-between" }}>
|
||||
<ProText
|
||||
type="secondary"
|
||||
style={{
|
||||
...textStyle,
|
||||
fontWeight: todayDay === "saturday" ? 700 : 400,
|
||||
}}
|
||||
>
|
||||
saturday
|
||||
</ProText>
|
||||
<ProText
|
||||
type="secondary"
|
||||
style={{
|
||||
...textStyle,
|
||||
fontWeight: todayDay === "saturday" ? 700 : 400,
|
||||
}}
|
||||
>
|
||||
10:00 AM to 10:00 PM
|
||||
</ProText>
|
||||
</div>
|
||||
</div>
|
||||
<Button
|
||||
type="primary"
|
||||
style={{ width: "100%", height: 50 }}
|
||||
onClick={onClose}
|
||||
>
|
||||
{t("menu.close")}
|
||||
</Button>
|
||||
</ProBottomSheet>
|
||||
);
|
||||
}
|
||||
@@ -4,15 +4,17 @@ import { ProGray1 } from "ThemeConstants";
|
||||
interface NextIconType {
|
||||
className?: string;
|
||||
onClick?: () => void;
|
||||
iconColor?: string;
|
||||
iconSize?: number;
|
||||
}
|
||||
|
||||
const NextIcon = ({ className, onClick }: NextIconType) => {
|
||||
const NextIcon = ({ className, onClick, iconColor, iconSize }: NextIconType) => {
|
||||
const { themeName } = useAppSelector((state) => state.theme);
|
||||
const color = themeName === "dark" ? "white" : ProGray1;
|
||||
const color = iconColor || (themeName === "dark" ? "white" : ProGray1);
|
||||
return (
|
||||
<svg
|
||||
width="16"
|
||||
height="16"
|
||||
width={iconSize || 16}
|
||||
height={iconSize || 16}
|
||||
viewBox="0 0 16 16"
|
||||
fill="none"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
|
||||
@@ -14,6 +14,37 @@
|
||||
object-fit: cover;
|
||||
}
|
||||
|
||||
.restaurantHeaderTitleContainer {
|
||||
display: flex;
|
||||
justify-content: flex-start;
|
||||
align-items: center;
|
||||
gap: 16px;
|
||||
}
|
||||
|
||||
.openCloseButton {
|
||||
background: #9fffcc4d;
|
||||
color: #278655;
|
||||
width: 62px !important;
|
||||
height: 20px !important;
|
||||
border: none;
|
||||
box-shadow: none;
|
||||
overflow: hidden;
|
||||
font-family: Outfit;
|
||||
font-weight: 500;
|
||||
font-style: Medium;
|
||||
font-size: 12px;
|
||||
line-height: 140%;
|
||||
letter-spacing: 0%;
|
||||
|
||||
opacity: 1;
|
||||
border-radius: 2px;
|
||||
padding-top: 4px;
|
||||
padding-right: 9px;
|
||||
padding-bottom: 4px;
|
||||
padding-left: 9px;
|
||||
gap: 5px;
|
||||
}
|
||||
|
||||
/* .restaurantHeader {
|
||||
margin-bottom: 24px;
|
||||
} */
|
||||
@@ -131,7 +162,6 @@
|
||||
margin-left: 200px;
|
||||
}
|
||||
|
||||
|
||||
/* Enhanced Dark theme styles */
|
||||
:global(.darkApp) .itemName {
|
||||
color: rgba(255, 255, 255, 0.95) !important;
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
import { StarFilled } from "@ant-design/icons";
|
||||
import { Image, Select, Space } from "antd";
|
||||
import { Button, Image, Select, Space } from "antd";
|
||||
import { FloatingButton } from "components/FloatingButton/FloatingButton";
|
||||
import LogoContainerIcon from "components/Icons/LogoContainerIcon";
|
||||
import ImageWithFallback from "components/ImageWithFallback";
|
||||
@@ -29,7 +29,9 @@ import MenuSkeleton from "./components/MenuSkeleton/MenuSkeleton";
|
||||
import ScrollEventHandler from "./components/ScrollEventHandler";
|
||||
import SearchButton from "./components/SearchButton";
|
||||
import styles from "./menu.module.css";
|
||||
import TimeIcon from "components/Icons/order/TimeIcon";
|
||||
import NextIcon from "components/Icons/NextIcon";
|
||||
import { OpeningTimesBottomSheet } from "components/CustomBottomSheet/OpeningTimesBottomSheet";
|
||||
import { useState } from "react";
|
||||
|
||||
function MenuPage() {
|
||||
const { subdomain } = useParams();
|
||||
@@ -51,7 +53,7 @@ function MenuPage() {
|
||||
const { categoryRefs } = useScrollHandler();
|
||||
const { isMobile, isTablet, isDesktop } = useBreakPoint();
|
||||
const isLoading = isLoadingRestaurant || isLoadingMenu;
|
||||
|
||||
const [isOpeningTimesOpen, setIsOpeningTimesOpen] = useState(false);
|
||||
const orderTypeOptions = enumToSelectOptions(OrderType, t, "orderTypes");
|
||||
|
||||
// Automatically load restaurant taxes when restaurant data is available
|
||||
@@ -113,9 +115,19 @@ function MenuPage() {
|
||||
|
||||
<div className={`${styles.headerContainer}`}>
|
||||
<div className={styles.contentWrapper}>
|
||||
<ProTitle className={styles.restaurantTitle}>
|
||||
{isRTL ? restaurant?.nameAR : restaurant?.restautantName}
|
||||
</ProTitle>
|
||||
<div className={styles.restaurantHeaderTitleContainer}>
|
||||
<ProTitle className={styles.restaurantTitle}>
|
||||
{isRTL ? restaurant?.nameAR : restaurant?.restautantName}
|
||||
</ProTitle>
|
||||
<Button
|
||||
className={styles.openCloseButton}
|
||||
icon={<NextIcon className={styles.openCloseIcon} iconColor="#278655" iconSize={9} />}
|
||||
iconPosition="end"
|
||||
onClick={() => setIsOpeningTimesOpen(true)}
|
||||
>
|
||||
{restaurant?.isOpened ? t("menu.open") : t("menu.close")}
|
||||
</Button>
|
||||
</div>
|
||||
|
||||
<div className={styles.ratingContainer}>
|
||||
<StarFilled className={styles.ratingStar} />
|
||||
@@ -128,10 +140,10 @@ function MenuPage() {
|
||||
</ProText>
|
||||
</div>
|
||||
|
||||
<ProText className={styles.openingHours}>
|
||||
{/* <ProText className={styles.openingHours}>
|
||||
<TimeIcon className={styles.timeIcon} />
|
||||
{restaurant?.openingTime} - {restaurant?.closingTime}
|
||||
</ProText>
|
||||
</ProText> */}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@@ -152,6 +164,10 @@ function MenuPage() {
|
||||
<ScrollEventHandler />
|
||||
<FloatingButton />
|
||||
{isDesktop && <CartButton />}
|
||||
<OpeningTimesBottomSheet
|
||||
isOpen={isOpeningTimesOpen}
|
||||
onClose={() => setIsOpeningTimesOpen(false)}
|
||||
/>
|
||||
</div>
|
||||
)}
|
||||
</>
|
||||
|
||||
Reference in New Issue
Block a user