From cd266c057cad5304e0099471241b97b153058bbb Mon Sep 17 00:00:00 2001 From: hamid zarghami Date: Sun, 19 Jul 2026 16:29:37 +0330 Subject: [PATCH] responsive home page and layout --- app/components/Carousel.tsx | 44 +++++++++++++++-- app/home/Home.tsx | 8 +-- app/home/components/BannerSection.tsx | 20 +++++--- app/home/components/BestSellerCategories.tsx | 20 ++++---- app/home/components/BlogsSection.tsx | 9 ++-- app/home/components/CategoryCard.tsx | 6 +-- app/home/components/CategorySection.tsx | 10 ++-- app/home/components/ContactCtaSection.tsx | 12 +++-- app/home/components/OrderByApplication.tsx | 12 ++--- .../components/OrderRegistrationSteps.tsx | 12 +++-- app/home/components/ProductSection.tsx | 10 ++-- app/home/components/StepSection.tsx | 41 +++++++--------- app/shared/Footer.tsx | 16 +++--- app/shared/Header.tsx | 49 +++++++++++++------ app/shared/components/AllProductsMenu.tsx | 44 +++++++++-------- app/shared/components/FooterContact.tsx | 2 +- app/shared/components/FooterNewsletter.tsx | 2 +- app/shared/components/FooterSocial.tsx | 4 +- app/shared/components/FooterTrustBadges.tsx | 4 +- app/shared/components/HeaderMenu.tsx | 10 ++-- 20 files changed, 198 insertions(+), 137 deletions(-) diff --git a/app/components/Carousel.tsx b/app/components/Carousel.tsx index 7df3fc1..e0d4388 100644 --- a/app/components/Carousel.tsx +++ b/app/components/Carousel.tsx @@ -35,11 +35,37 @@ function useCarousel() { return context; } +type ResponsiveNumber = number | { base: number; md?: number; lg?: number }; + +function useResponsiveNumber(value: ResponsiveNumber): number { + const base = typeof value === "number" ? value : value.base; + const md = typeof value === "number" ? undefined : value.md; + const lg = typeof value === "number" ? undefined : value.lg; + + const resolve = () => { + if (typeof window === "undefined") return base; + if (window.matchMedia("(min-width: 1024px)").matches) return lg ?? md ?? base; + if (window.matchMedia("(min-width: 768px)").matches) return md ?? base; + return base; + }; + + const [resolved, setResolved] = useState(base); + + useEffect(() => { + const update = () => setResolved(resolve()); + update(); + window.addEventListener("resize", update); + return () => window.removeEventListener("resize", update); + }, [base, md, lg]); + + return resolved; +} + type CarouselProps = { children: ReactNode; - slidesPerView?: number; + slidesPerView?: ResponsiveNumber; slidesToScroll?: number; - gap?: number; + gap?: ResponsiveNumber; direction?: "rtl" | "ltr"; className?: string; }; @@ -52,10 +78,14 @@ const Carousel: FC = ({ direction = "rtl", className, }) => { + const resolvedSlidesPerView = useResponsiveNumber(slidesPerView); + const resolvedGap = useResponsiveNumber(gap); + const scrollBy = slidesToScroll ?? Math.max(1, Math.floor(resolvedSlidesPerView)); + const [emblaRef, emblaApi] = useEmblaCarousel({ align: "start", direction, - slidesToScroll: slidesToScroll ?? slidesPerView, + slidesToScroll: scrollBy, containScroll: "trimSnaps", }); @@ -80,6 +110,10 @@ const Carousel: FC = ({ }; }, [emblaApi]); + useEffect(() => { + emblaApi?.reInit({ slidesToScroll: scrollBy }); + }, [emblaApi, scrollBy, resolvedSlidesPerView, resolvedGap]); + return ( = ({ scrollNext: () => emblaApi?.scrollNext(), canScrollPrev, canScrollNext, - slidesPerView, - gap, + slidesPerView: resolvedSlidesPerView, + gap: resolvedGap, }} > diff --git a/app/home/Home.tsx b/app/home/Home.tsx index 09c2b1e..65d09ee 100644 --- a/app/home/Home.tsx +++ b/app/home/Home.tsx @@ -20,10 +20,10 @@ const Home = () => { -
-
-
چاپ جعبه، بسته‌بندی و محصولات تبلیغاتی با طراحی اختصاصی
-
+
+
+
چاپ جعبه، بسته‌بندی و محصولات تبلیغاتی با طراحی اختصاصی
+
جعبه، اولین چیزی است که مشتری از برند شما می‌بیند. ما با ارائه خدمات چاپ جعبه، لیبل، استیکر، کارت ویزیت و سایر محصولات تبلیغاتی، به شما کمک می‌کنیم تا بسته‌بندی حرفه‌ای و ماندگاری برای محصولات خود داشته باشید. با استفاده از متریال باکیفیت، طراحی اختصاصی و چاپ دقیق، سفارش شما در کوتاه‌ترین زمان آماده و ارسال می‌شود.
diff --git a/app/home/components/BannerSection.tsx b/app/home/components/BannerSection.tsx index dea36e9..8440b74 100644 --- a/app/home/components/BannerSection.tsx +++ b/app/home/components/BannerSection.tsx @@ -8,20 +8,26 @@ const BannerSection: FC = () => { return (
- banner -
-
چاپ و بسته بندی به روش هوشمندانه
-
مجــتمع تخصصــــــی
-
+ banner +
+
چاپ و بسته بندی به روش هوشمندانه
+
مجــتمع تخصصــــــی
+
چــــــاپ و بستــــه بندی دستی و هوشمند{" "}
-
+
قیمت‌های عالی
خدمات مشتریان بی‌نظیر
سیستم سفارش‌گیری ساده
-
+
diff --git a/app/home/components/OrderByApplication.tsx b/app/home/components/OrderByApplication.tsx index 154e986..27f7463 100644 --- a/app/home/components/OrderByApplication.tsx +++ b/app/home/components/OrderByApplication.tsx @@ -5,11 +5,11 @@ import ProductCard from "./ProductCard"; const OrderByApplication: FC = () => { return ( -
-
سفارش بر اساس کاربرد
- -
-
+
+
سفارش بر اساس کاربرد
+ +
+
-
+ +
پیگیری سفارش
@@ -44,7 +62,7 @@ const Header = () => {
-
(30 خط) 02134782000
+
(30 خط) 02134782000
@@ -55,6 +73,7 @@ const Header = () => {
+
); diff --git a/app/shared/components/AllProductsMenu.tsx b/app/shared/components/AllProductsMenu.tsx index 5870c92..80fb88a 100644 --- a/app/shared/components/AllProductsMenu.tsx +++ b/app/shared/components/AllProductsMenu.tsx @@ -42,28 +42,30 @@ const columns: CategoryGroup[][] = [ const AllProductsMenu: FC = () => { return ( -
-
- {columns.map((groups) => ( -
- {groups.map((group) => ( -
-
{group.title}
- {group.items.map((item) => ( - - ))} -
- ))} -
- ))} +
+
+
+ {columns.map((groups) => ( +
+ {groups.map((group) => ( +
+
{group.title}
+ {group.items.map((item) => ( + + ))} +
+ ))} +
+ ))} +
-
+
کارت ویزیت
diff --git a/app/shared/components/FooterContact.tsx b/app/shared/components/FooterContact.tsx index e8fe8fe..67495d6 100644 --- a/app/shared/components/FooterContact.tsx +++ b/app/shared/components/FooterContact.tsx @@ -17,7 +17,7 @@ const ContactItem: FC = ({ icon, children }) => { const FooterContact: FC = () => { return ( -
+
}> جاده خاوران، شریف آباد، شهرک صنعتی شنزار، بعد از میدان چهارم، خیابان بوستان پنجم، خیابان گلبهار، پلاک ۱۲۲ diff --git a/app/shared/components/FooterNewsletter.tsx b/app/shared/components/FooterNewsletter.tsx index f4aae10..e85fcbb 100644 --- a/app/shared/components/FooterNewsletter.tsx +++ b/app/shared/components/FooterNewsletter.tsx @@ -3,7 +3,7 @@ import { type FC } from "react"; const FooterNewsletter: FC = () => { return ( -
+

برای دریافت آخرین پیشنهادها، اخبار و مطالب الهام‌بخش، در خبرنامه ما عضو شوید.

{ return ( -
+

ما را در شبکه‌های اجتماعی دنبال کنید

-
+
{socialLinks.map((item) => ( {item.icon} diff --git a/app/shared/components/FooterTrustBadges.tsx b/app/shared/components/FooterTrustBadges.tsx index 74cbaca..53755aa 100644 --- a/app/shared/components/FooterTrustBadges.tsx +++ b/app/shared/components/FooterTrustBadges.tsx @@ -6,9 +6,9 @@ const FooterTrustBadges: FC = () => { return (

نماد های اعتماد

-
+
{badges.map((badge) => ( -
+
{badge}
))} diff --git a/app/shared/components/HeaderMenu.tsx b/app/shared/components/HeaderMenu.tsx index 9d0ba09..57dfdcc 100644 --- a/app/shared/components/HeaderMenu.tsx +++ b/app/shared/components/HeaderMenu.tsx @@ -36,21 +36,21 @@ const HeaderMenu: FC = () => { }, [isAllProductsOpen]); return ( -
-
+
+
{menuItems.map((item) => ( -
+
{item}
))}