summaryrefslogtreecommitdiff
path: root/src-migrate/modules/product-detail/components/ProductDetail.tsx
diff options
context:
space:
mode:
Diffstat (limited to 'src-migrate/modules/product-detail/components/ProductDetail.tsx')
-rw-r--r--src-migrate/modules/product-detail/components/ProductDetail.tsx126
1 files changed, 97 insertions, 29 deletions
diff --git a/src-migrate/modules/product-detail/components/ProductDetail.tsx b/src-migrate/modules/product-detail/components/ProductDetail.tsx
index f32bb38e..e4ba2b2f 100644
--- a/src-migrate/modules/product-detail/components/ProductDetail.tsx
+++ b/src-migrate/modules/product-detail/components/ProductDetail.tsx
@@ -5,7 +5,12 @@ import { useRouter } from 'next/router';
import { useEffect, useRef, useState, UIEvent } from 'react';
import { Button } from '@chakra-ui/react';
-import { MessageCircleIcon, Share2Icon } from 'lucide-react';
+import {
+ AlertCircle,
+ AlertTriangle,
+ MessageCircleIcon,
+ Share2Icon,
+} from 'lucide-react';
import { LazyLoadComponent } from 'react-lazy-load-image-component';
import useDevice from '@/core/hooks/useDevice';
@@ -23,7 +28,6 @@ import SimilarBottom from './SimilarBottom';
import SimilarSide from './SimilarSide';
import dynamic from 'next/dynamic';
-
import { gtagProductDetail } from '@/core/utils/googleTag';
type Props = {
@@ -31,7 +35,7 @@ type Props = {
};
const RWebShare = dynamic(
- () => import('react-web-share').then(m => m.RWebShare),
+ () => import('react-web-share').then((m) => m.RWebShare),
{ ssr: false }
);
@@ -42,7 +46,9 @@ const ProductDetail = ({ product }: Props) => {
const router = useRouter();
const [auth, setAuth] = useState<any>(null);
useEffect(() => {
- try { setAuth(getAuth() ?? null); } catch { }
+ try {
+ setAuth(getAuth() ?? null);
+ } catch {}
}, []);
const canShare =
@@ -87,7 +93,6 @@ const ProductDetail = ({ product }: Props) => {
setSelectedVariant(selectedVariant);
}, []);
-
const allImages = (() => {
const arr: string[] = [];
if (product?.image) arr.push(product.image);
@@ -95,7 +100,6 @@ const ProductDetail = ({ product }: Props) => {
Array.isArray(product?.image_carousel) &&
product.image_carousel.length
) {
-
const set = new Set(arr);
for (const img of product.image_carousel) {
if (!set.has(img)) {
@@ -108,15 +112,14 @@ const ProductDetail = ({ product }: Props) => {
})();
const [mainImage, setMainImage] = useState(allImages[0] || '');
+ const hasPrice = Number(product?.lowest_price?.price) > 0;
useEffect(() => {
-
if (!allImages.includes(mainImage)) {
setMainImage(allImages[0] || '');
}
}, [allImages]);
-
const sliderRef = useRef<HTMLDivElement | null>(null);
const [currentIdx, setCurrentIdx] = useState(0);
@@ -138,9 +141,32 @@ const ProductDetail = ({ product }: Props) => {
setMainImage(allImages[i] || '');
};
-
return (
<>
+ <div className='relative'>
+ {isDesktop && !hasPrice && (
+ <div className='absolute inset-0 z-[20] flex items-center justify-center pointer-events-none select-none'>
+ <img
+ src='/images/produk_tidak_tersedia.svg'
+ alt='Produk tidak tersedia'
+ className='w-[47%] opacity-50 -translate-x-[3%] -translate-y-[-70%]'
+ />
+ </div>
+ )}
+ </div>
+
+ <div className='relative'>
+ {isMobile && !hasPrice && (
+ <div className='absolute inset-0 z-[50] flex items-center justify-center pointer-events-none select-none'>
+ <img
+ src='/images/produk_tidak_tersedia.svg'
+ alt='Produk tidak tersedia'
+ className='w-[100%] opacity-[1000%] -translate-x-[0%] -translate-y-[-197%]'
+ />
+ </div>
+ )}
+ </div>
+
<div className='md:flex md:flex-wrap'>
<div className='w-full mb-4 md:mb-0 px-4 md:px-0'>
<Breadcrumb id={product.id} name={product.name} />
@@ -165,7 +191,6 @@ const ProductDetail = ({ product }: Props) => {
>
{allImages.length > 0 ? (
allImages.map((img, i) => (
-
<div
key={i}
className='w-full flex-shrink-0 snap-center flex justify-center items-center'
@@ -200,8 +225,9 @@ const ProductDetail = ({ product }: Props) => {
<button
key={i}
aria-label={`Ke slide ${i + 1}`}
- className={`w-2 h-2 rounded-full ${currentIdx === i ? 'bg-gray-800' : 'bg-gray-300'
- }`}
+ className={`w-2 h-2 rounded-full ${
+ currentIdx === i ? 'bg-gray-800' : 'bg-gray-300'
+ }`}
onClick={() => scrollToIndex(i)}
/>
))}
@@ -220,10 +246,11 @@ const ProductDetail = ({ product }: Props) => {
{allImages.map((img, index) => (
<div
key={index}
- className={`flex-shrink-0 w-16 h-16 cursor-pointer border-2 rounded-md transition-colors ${mainImage === img
- ? 'border-red-500 ring-2 ring-red-200'
- : 'border-gray-200 hover:border-gray-300'
- }`}
+ className={`flex-shrink-0 w-16 h-16 cursor-pointer border-2 rounded-md transition-colors ${
+ mainImage === img
+ ? 'border-red-500 ring-2 ring-red-200'
+ : 'border-gray-200 hover:border-gray-300'
+ }`}
onClick={() => setMainImage(img)}
>
<img
@@ -247,13 +274,45 @@ const ProductDetail = ({ product }: Props) => {
{/* <<=== TUTUP kolom kiri */}
{/* ===== Kolom kanan: info ===== */}
- <div className='md:w-8/12 px-4 md:pl-6'>
- <div className='h-6 md:h-0' />
- <h1 className={style['title']}>{product.name}</h1>
- <div className='h-3 md:h-0' />
- <Information product={product} />
- <div className='h-6' />
- </div>
+ {isDesktop && (
+ <div className='md:w-8/12 px-4 md:pl-6'>
+ {!hasPrice && (
+ <div className='bg-red-50 p-2 py-1.5 rounded-lg border border-red-500 flex gap-1 items-center '>
+ <AlertTriangle
+ size={18}
+ className='text-red-600 shrink-0 mx-2'
+ />
+ <h1 className='text-red-600 font-normal text-h-sm'>
+ Maaf untuk saat ini Produk yang anda cari tidak tersedia
+ </h1>
+ </div>
+ )}
+ <div className='h-6 md:h-0' />
+ <h1 className={style['title']}>{product.name}</h1>
+ <div className='h-3 md:h-0' />
+ <Information product={product} />
+ <div className='h-6' />
+ </div>
+ )}
+ {isMobile && (
+ <div className='md:w-8/12 px-4 md:pl-6 relative'>
+ {!hasPrice && (
+ <div className='bg-red-50 p-2 py-1.5 border-b border-red-500 flex gap-1 items-center w-screen relative left-1/2 right-1/2 -translate-x-1/2'>
+ <AlertTriangle
+ size={18}
+ className='text-red-600 shrink-0 mx-2'
+ />
+ <h1 className='text-red-600 font-normal text-h-sm'>
+ Maaf untuk saat ini Produk yang anda cari tidak tersedia
+ </h1>
+ </div>
+ )}
+ <h1 className={style['title']}>{product.name}</h1>
+ <div className='h-3 md:h-0' />
+ <Information product={product} />
+ <div className='h-6' />
+ </div>
+ )}
</div>
<div className='h-full'>
@@ -281,7 +340,8 @@ const ProductDetail = ({ product }: Props) => {
className={style['description']}
dangerouslySetInnerHTML={{
__html:
- !product.description || product.description == '<p><br></p>'
+ !product.description ||
+ product.description == '<p><br></p>'
? 'Belum ada deskripsi'
: product.description,
}}
@@ -302,13 +362,16 @@ const ProductDetail = ({ product }: Props) => {
target='_blank'
colorScheme='gray'
leftIcon={<MessageCircleIcon size={18} />}
+ isDisabled={!hasPrice}
>
Ask Admin
</Button>
<span>|</span>
- <AddToWishlist productId={product.id} />
+ <div className={hasPrice ? '' : 'opacity-40 pointer-events-none'}>
+ <AddToWishlist productId={product.id} />
+ </div>
<span>|</span>
@@ -317,10 +380,17 @@ const ProductDetail = ({ product }: Props) => {
data={{
text: 'Check out this product',
title: `${product.name} - Indoteknik.com`,
- url: (process.env.NEXT_PUBLIC_SELF_HOST || '') + (router?.asPath || '/'),
+ url:
+ (process.env.NEXT_PUBLIC_SELF_HOST || '') +
+ (router?.asPath || '/'),
}}
>
- <Button variant='link' colorScheme='gray' leftIcon={<Share2Icon size={18} />}>
+ <Button
+ variant='link'
+ colorScheme='gray'
+ leftIcon={<Share2Icon size={18} />}
+ isDisabled={!hasPrice}
+ >
Share
</Button>
</RWebShare>
@@ -350,8 +420,6 @@ const ProductDetail = ({ product }: Props) => {
</div>
</>
);
-
-
};
export default ProductDetail;