summaryrefslogtreecommitdiff
path: root/src/core/components/elements/Navbar
diff options
context:
space:
mode:
Diffstat (limited to 'src/core/components/elements/Navbar')
-rw-r--r--src/core/components/elements/Navbar/NavbarDesktop.jsx161
-rw-r--r--src/core/components/elements/Navbar/NavbarMobile.jsx4
-rw-r--r--src/core/components/elements/Navbar/TopBanner.jsx40
-rw-r--r--src/core/components/elements/Navbar/style/NavbarDesktop.module.css14
4 files changed, 169 insertions, 50 deletions
diff --git a/src/core/components/elements/Navbar/NavbarDesktop.jsx b/src/core/components/elements/Navbar/NavbarDesktop.jsx
index 9de761a2..6454c414 100644
--- a/src/core/components/elements/Navbar/NavbarDesktop.jsx
+++ b/src/core/components/elements/Navbar/NavbarDesktop.jsx
@@ -5,16 +5,19 @@ import { createSlug } from '@/core/utils/slug';
import whatsappUrl from '@/core/utils/whatsappUrl';
import IndoteknikLogo from '@/images/logo.png';
import Cardheader from '@/lib/cart/components/Cartheader';
+import Quotationheader from "../../../../../src/lib/quotation/components/Quotationheader.jsx"
import Category from '@/lib/category/components/Category';
+import { useProductCartContext } from '@/contexts/ProductCartContext';
import {
ChevronDownIcon,
DocumentCheckIcon,
HeartIcon,
+ ArrowUpRightIcon,
} from '@heroicons/react/24/outline';
import dynamic from 'next/dynamic';
import Image from 'next/image';
import { useRouter } from 'next/router';
-import { useEffect, useState } from 'react';
+import { useCallback, useEffect, useState } from 'react';
import DesktopView from '../../views/DesktopView';
import Link from '../Link/Link';
import NavbarUserDropdown from './NavbarUserDropdown';
@@ -27,6 +30,8 @@ import {
MenuList,
useDisclosure,
} from '@chakra-ui/react';
+import style from "./style/NavbarDesktop.module.css";
+import useTransactions from '@/lib/transaction/hooks/useTransactions';
const Search = dynamic(() => import('./Search'), { ssr: false });
const TopBanner = dynamic(() => import('./TopBanner'), { ssr: false });
@@ -36,7 +41,8 @@ const NavbarDesktop = () => {
const auth = useAuth();
const [cartCount, setCartCount] = useState(0);
-
+ const [quotationCount, setQuotationCount] = useState(0);
+ const [pendingTransactions, setPendingTransactions] = useState([])
const [templateWA, setTemplateWA] = useState(null);
const [payloadWA, setPayloadWa] = useState(null);
const [urlPath, setUrlPath] = useState(null);
@@ -45,8 +51,64 @@ const NavbarDesktop = () => {
const { product } = useProductContext();
const { isOpen, onOpen, onClose } = useDisclosure();
+
+ const query = {
+ context: 'quotation',
+ site:
+ (auth?.webRole === null && auth?.site ? auth.site : null),
+ };
+
+ const { transactions } = useTransactions({ query });
+ const data = transactions?.data?.saleOrders.filter(
+ (transaction) => transaction.status === 'draft'
+ );
+
+ const [showPopup, setShowPopup] = useState(false);
+ const [isTop, setIsTop] = useState(true);
+
+ const handleTopBannerLoad = useCallback(() => {
+ const showTimer = setTimeout(() => {
+ setShowPopup(true);
+ }, 500);
+
+ const hideTimer = setTimeout(() => {
+ // setShowPopup(false);
+ }, 9500);
+
+ return () => {
+ clearTimeout(showTimer);
+ clearTimeout(hideTimer);
+ };
+ }, []);
+
+ useEffect(() => {
+ const handleScroll = () => {
+ setIsTop(window.scrollY < 100);
+ };
+
+ window.addEventListener('scroll', handleScroll);
+ return () => {
+ window.removeEventListener('scroll', handleScroll);
+ };
+ }, []);
+
+ useEffect(() => {
+ const handleScroll = () => {
+ setIsTop(window.scrollY < 100);
+ };
+
+ window.addEventListener('scroll', handleScroll);
+ return () => {
+ window.removeEventListener('scroll', handleScroll);
+ };
+ }, []);
useEffect(() => {
+ setPendingTransactions(data);
+ }, [transactions.data]);
+
+
+ useEffect(() => {
if (router.pathname === '/shop/product/[slug]') {
setPayloadWa({
name: product?.name,
@@ -54,11 +116,11 @@ const NavbarDesktop = () => {
url: createSlug('/shop/product/', product?.name, product?.id, true),
});
setTemplateWA('product');
-
+
setUrlPath(router.asPath);
}
}, [product, router]);
-
+
useEffect(() => {
const handleCartChange = () => {
const cart = async () => {
@@ -67,18 +129,34 @@ const NavbarDesktop = () => {
};
cart();
};
- handleCartChange();
-
+ handleCartChange();
+
window.addEventListener('localStorageChange', handleCartChange);
-
+
return () => {
window.removeEventListener('localStorageChange', handleCartChange);
};
}, []);
+ useEffect(() => {
+ const handleQuotationChange = () => {
+ const quotation = async () => {
+ setQuotationCount(pendingTransactions?.length);
+ };
+ quotation();
+ };
+ handleQuotationChange();
+
+ window.addEventListener('localStorageChange', handleQuotationChange);
+
+ return () => {
+ window.removeEventListener('localStorageChange', handleQuotationChange);
+ };
+ }, [pendingTransactions]);
+
return (
<DesktopView>
- <TopBanner />
+ <TopBanner onLoad={handleTopBannerLoad} />
<div className='py-2 bg-warning-400' id='desktop-nav-top'>
<div className='container mx-auto flex justify-between'>
<div className='flex items-start gap-5'>
@@ -138,17 +216,7 @@ const NavbarDesktop = () => {
<Search />
</div>
<div className='flex gap-x-4 items-center'>
- <Link
- href='/my/transactions'
- target='_blank'
- rel='noreferrer'
- className='flex items-center gap-x-2 !text-gray_r-12/80'
- >
- <DocumentCheckIcon className='w-7' />
- Daftar
- <br />
- Quotation
- </Link>
+ <Quotationheader quotationCount={quotationCount} data={pendingTransactions} />
<Cardheader cartCount={cartCount} />
@@ -203,45 +271,76 @@ const NavbarDesktop = () => {
</div>
</button>
<div className='w-6/12 flex px-1 divide-x divide-gray_r-6'>
+
+ <Link
+ href="/shop/promo"
+ className={`${
+ router.asPath === '/shop/promo' && 'bg-gray_r-3'
+ } flex-1 flex justify-center items-center !text-gray_r-12/80 hover:bg-gray_r-3 idt-transition group relative`} // Added relative position
+ target="_blank"
+ rel="noreferrer"
+ >
+ {showPopup && (
+ <div className='w-full h-full relative justify-end items-start'>
+ <Image
+ src='/images/penawaran-terbatas.jpg'
+ alt='penawaran terbatas'
+ width={1440}
+ height={160}
+ quality={100}
+ // className={`fixed ${isTop ? 'md:top-[145px] lg:top-[160px] ' : 'lg:top-[85px] top-[80px]'} rounded-3xl md:left-1/4 lg:left-1/4 xl:left-1/4 left-2/3 w-40 h-12 p-2 z-50 transition-all duration-300 animate-pulse`}
+ className={`inline-block relative -top-8 transition-all duration-300 z-20 animate-pulse`}
+ />
+ </div>
+ )}
+ <p className="absolute inset-0 flex justify-center items-center group-hover:scale-105 group-hover:text-red-500 transition-transform duration-200 z-10">Semua Promo</p>
+ </Link>
+ {/* {showPopup && router.pathname === '/' && (
+ <div className={`fixed ${isTop ? 'top-[170px]' : 'top-[90px]'} rounded-3xl left-[700px] w-fit object-center bg-green-50 text-xs font-medium text-green-700 ring-1 ring-inset ring-green-600/20 text-center p-2 z-50 transition-all duration-300`}>
+ <p className='w-36 h-3'>
+ Penawaran Terbatas
+ </p>
+ </div>
+ )} */}
+
+
<Link
href='/shop/brands'
- className={`${
+ className={`${
router.asPath === '/shop/brands' && 'bg-gray_r-3'
- } p-4 flex-1 flex justify-center items-center !text-gray_r-12/80 hover:bg-gray_r-3 idt-transition`}
+ } p-4 flex-1 flex justify-center items-center !text-gray_r-12/80 hover:bg-gray_r-3 idt-transition group`}
target='_blank'
rel='noreferrer'
>
- Semua Brand
+ <p className="group-hover:scale-105 group-hover:text-red-500 transition-transform duration-200">Semua Brand</p>
</Link>
<Link
href='/shop/search?orderBy=stock'
className={`${
router.asPath === '/shop/search?orderBy=stock' &&
'bg-gray_r-3'
- } p-4 flex-1 flex justify-center items-center !text-gray_r-12/80 hover:bg-gray_r-3 idt-transition`}
+ } p-4 flex-1 flex justify-center items-center !text-gray_r-12/80 hover:bg-gray_r-3 idt-transition group`}
target='_blank'
rel='noreferrer'
>
- Ready Stock
+ <p className="group-hover:scale-105 group-hover:text-red-500 transition-transform duration-200">Ready Stock</p>
</Link>
<Link
href='https://blog.indoteknik.com/'
- className='p-4 flex-1 flex justify-center items-center !text-gray_r-12/80 hover:bg-gray_r-3 idt-transition'
+ className='p-4 flex-1 flex justify-center items-center !text-gray_r-12/80 hover:bg-gray_r-3 idt-transition group'
target='_blank'
rel='noreferrer noopener'
>
- Blog Indoteknik
+ <p className="group-hover:scale-105 group-hover:text-red-500 transition-transform duration-200">Blog Indoteknik</p>
</Link>
- <Link
+ {/* <Link
href='/video'
- className={`${
- router.asPath === '/video' && 'bg-gray_r-3'
- } p-4 flex-1 flex justify-center items-center !text-gray_r-12/80 hover:bg-gray_r-3 idt-transition`}
+ className='p-4 flex-1 flex justify-center items-center !text-gray_r-12/80 hover:bg-gray_r-3 idt-transition'
target='_blank'
rel='noreferrer'
>
Indoteknik TV
- </Link>
+ </Link> */}
</div>
<div className='w-3/12 flex gap-x-1 relative'>
diff --git a/src/core/components/elements/Navbar/NavbarMobile.jsx b/src/core/components/elements/Navbar/NavbarMobile.jsx
index bcf45e0a..90314671 100644
--- a/src/core/components/elements/Navbar/NavbarMobile.jsx
+++ b/src/core/components/elements/Navbar/NavbarMobile.jsx
@@ -11,7 +11,7 @@ import Image from 'next/image';
import { useEffect, useState } from 'react';
import MobileView from '../../views/MobileView';
import Link from '../Link/Link';
-// import TopBanner from './TopBanner';
+import TopBanner from './TopBanner';
const Search = dynamic(() => import('./Search'));
@@ -39,7 +39,7 @@ const NavbarMobile = () => {
return (
<MobileView>
- {/* <TopBanner /> */}
+ <TopBanner />
<nav className='px-4 py-2 pb-3 sticky top-0 z-50 bg-white shadow'>
<div className='flex justify-between items-center mb-2'>
<Link href='/'>
diff --git a/src/core/components/elements/Navbar/TopBanner.jsx b/src/core/components/elements/Navbar/TopBanner.jsx
index 722a7501..b035eea4 100644
--- a/src/core/components/elements/Navbar/TopBanner.jsx
+++ b/src/core/components/elements/Navbar/TopBanner.jsx
@@ -1,39 +1,45 @@
import Image from 'next/image';
-import { useQuery } from 'react-query';
-
+import { useQuery } from 'react-query';import useDevice from '@/core/hooks/useDevice'
import odooApi from '@/core/api/odooApi';
import SmoothRender from '~/components/ui/smooth-render';
import Link from '../Link/Link';
+import { useEffect } from 'react';
-const TopBanner = () => {
+const TopBanner = ({ onLoad = () => {} }) => {
const topBanner = useQuery({
queryKey: 'topBanner',
queryFn: async () => await odooApi('GET', '/api/v1/banner?type=top-banner'),
refetchOnWindowFocus: false,
});
- const backgroundColor = topBanner.data?.[0]?.backgroundColor || 'transparent';
+ // const backgroundColor = topBanner.data?.[0]?.backgroundColor || 'transparent';
const hasData = topBanner.data?.length > 0;
const data = topBanner.data?.[0] || null;
+ useEffect(() => {
+ if (hasData) {
+ onLoad();
+ }
+ }, [hasData, onLoad]);
+
return (
<SmoothRender
isLoaded={hasData}
- height='36px'
+ // height='36px'
duration='700ms'
delay='300ms'
- style={{ backgroundColor }}
- >
- <Link href={data?.url}>
- <Image
- src={data?.image}
- alt={data?.name}
- width={1440}
- height={40}
- className='object-cover object-center h-full mx-auto'
- />
- </Link>
- </SmoothRender>
+ className='h-auto'
+ >
+ <Link
+ href={data?.url}
+ className="block bg-cover bg-center h-3 md:h-6 lg:h-[36px]"
+ style={{
+ backgroundImage: `url('${data?.image}')`,
+ }}
+ >
+ </Link>
+
+ </SmoothRender>
);
};
diff --git a/src/core/components/elements/Navbar/style/NavbarDesktop.module.css b/src/core/components/elements/Navbar/style/NavbarDesktop.module.css
new file mode 100644
index 00000000..9cddb127
--- /dev/null
+++ b/src/core/components/elements/Navbar/style/NavbarDesktop.module.css
@@ -0,0 +1,14 @@
+/* navbarDesktop.module.css */
+@keyframes blink {
+ 0%, 100% {
+ opacity: 1;
+ }
+ 50% {
+ opacity: 0;
+ }
+}
+
+.blink {
+ animation: blink 0.8s infinite;
+}
+