diff options
| author | Rafi Zadanly <zadanlyr@gmail.com> | 2024-01-18 12:08:37 +0700 |
|---|---|---|
| committer | Rafi Zadanly <zadanlyr@gmail.com> | 2024-01-18 12:08:37 +0700 |
| commit | f02511b103acce8d3fa4bc174a43be15c4cca052 (patch) | |
| tree | 08b01776038a9c44f0e21b85c3f776b22c342081 | |
| parent | f7a0be1407da7edab60f6cb2ca3f1ef97acf811a (diff) | |
Update add to wishlist in product detail
6 files changed, 81 insertions, 8 deletions
diff --git a/src-migrate/modules/product-card/components/ProductCard.tsx b/src-migrate/modules/product-card/components/ProductCard.tsx index c8a0b701..0a97b344 100644 --- a/src-migrate/modules/product-card/components/ProductCard.tsx +++ b/src-migrate/modules/product-card/components/ProductCard.tsx @@ -26,7 +26,7 @@ const ProductCard = ({ product, layout = 'vertical' }: Props) => { [style['wrapper-h']]: layout === 'horizontal', })} > - <div className={clsxm({ + <div className={clsxm('relative', { [style['image-v']]: layout === 'vertical', [style['image-h']]: layout === 'horizontal', })}> @@ -38,6 +38,9 @@ const ProductCard = ({ product, layout = 'vertical' }: Props) => { height={128} className='object-contain object-center h-full w-full' /> + {product.variant_total > 1 && ( + <div className={style['variant-badge']}>{product.variant_total} Varian</div> + )} </Link> </div> diff --git a/src-migrate/modules/product-card/styles/product-card.module.css b/src-migrate/modules/product-card/styles/product-card.module.css index aac27a84..653bf2ca 100644 --- a/src-migrate/modules/product-card/styles/product-card.module.css +++ b/src-migrate/modules/product-card/styles/product-card.module.css @@ -48,3 +48,7 @@ .sold { @apply text-gray-600 text-[11px]; } + +.variant-badge { + @apply bg-gray-500/20 backdrop-blur-md absolute rounded-md bottom-2 left-2 px-2 py-1 text-caption-2; +} diff --git a/src-migrate/modules/product-detail/components/AddToWishlist.tsx b/src-migrate/modules/product-detail/components/AddToWishlist.tsx index fccbdcf5..cb11e837 100644 --- a/src-migrate/modules/product-detail/components/AddToWishlist.tsx +++ b/src-migrate/modules/product-detail/components/AddToWishlist.tsx @@ -1,13 +1,56 @@ -import { Button } from '@chakra-ui/react' +import { Button, useToast } from '@chakra-ui/react' import { HeartIcon } from 'lucide-react' import React from 'react' +import { useQuery } from 'react-query' +import { getAuth } from '~/libs/auth' +import clsxm from '~/libs/clsxm' +import { getUserWishlist, upsertUserWishlist } from '~/services/wishlist' + +type Props = { + productId: number +} + +const AddToWishlist = ({ productId }: Props) => { + const auth = getAuth() + const toast = useToast({ + position: 'top', + isClosable: true + }) + + const searchParams = { product_id: productId.toString() } + const query = useQuery({ + queryKey: ['wishlist', searchParams, auth], + queryFn: () => { + if (typeof auth !== 'object') return null; + return getUserWishlist(auth.id, searchParams) + } + }) + + const isAdded = query.data?.product_total ? query.data.product_total > 0 : false; + + const toggleWishlist = async () => { + if (typeof auth !== 'object') return; + await upsertUserWishlist(auth.id, productId) + await query.refetch() + } + + const handleClick = async () => { + toast.promise(toggleWishlist(), { + loading: { title: 'Update Wishlist', description: 'Mohon tunggu...' }, + success: { title: 'Update Wishlist', description: 'Berhasil update wishlist' }, + error: { title: 'Update Wishlist', description: 'Gagal update wishlist' }, + }) + } -const AddToWishlist = () => { return ( <Button variant='link' colorScheme='gray' - leftIcon={<HeartIcon size={18} />} + onClick={handleClick} + leftIcon={<HeartIcon size={18} className={clsxm('transition-colors', { + 'text-danger-500 fill-danger-500': isAdded, + 'fill-transparent': !isAdded + })} />} > Wishlist </Button> diff --git a/src-migrate/modules/product-detail/components/Breadcrumb.tsx b/src-migrate/modules/product-detail/components/Breadcrumb.tsx index 0ee5b115..ec445b60 100644 --- a/src-migrate/modules/product-detail/components/Breadcrumb.tsx +++ b/src-migrate/modules/product-detail/components/Breadcrumb.tsx @@ -18,7 +18,7 @@ const Breadcrumb = ({ id, name }: Props) => { const breadcrumbs = query.data || [] return ( - <div className='line-clamp-3 md:line-clamp-1 leading-7'> + <div className='line-clamp-2 md:line-clamp-1 leading-7 text-caption-1'> <Link href='/' className='text-danger-500'>Home</Link> <span className='mx-2'>/</span> {breadcrumbs.map((category, index) => ( diff --git a/src-migrate/modules/product-detail/components/ProductDetail.tsx b/src-migrate/modules/product-detail/components/ProductDetail.tsx index 93fa7118..80f43aea 100644 --- a/src-migrate/modules/product-detail/components/ProductDetail.tsx +++ b/src-migrate/modules/product-detail/components/ProductDetail.tsx @@ -52,10 +52,10 @@ const ProductDetail = ({ product }: Props) => { return ( <> <div className='md:flex md:flex-wrap'> - <div className="w-full mb-4 md:mb-6 px-4 md:px-0"> + <div className="w-full mb-4 md:mb-0 px-4 md:px-0"> <Breadcrumb id={product.id} name={product.name} /> </div> - <div className='md:w-9/12 md:flex md:flex-col md:pr-4'> + <div className='md:w-9/12 md:flex md:flex-col md:pr-4 md:pt-6'> <div className='md:flex md:flex-wrap'> <div className="md:w-4/12"> <ProductImage product={product} /> @@ -86,7 +86,7 @@ const ProductDetail = ({ product }: Props) => { Ask Admin </Button> - <AddToWishlist /> + <AddToWishlist productId={product.id} /> <RWebShare data={{ diff --git a/src-migrate/services/wishlist.ts b/src-migrate/services/wishlist.ts new file mode 100644 index 00000000..6fb8cb2e --- /dev/null +++ b/src-migrate/services/wishlist.ts @@ -0,0 +1,23 @@ +import odooApi from '~/libs/odooApi'; + +export const getUserWishlist = async ( + userId: number, + searchParams: { + product_id?: string; + } = {} +): Promise<{ product_total: number }> => { + const url = `/api/v1/user/${userId}/wishlist`; + const searchParamsObj = new URLSearchParams(searchParams); + + return await odooApi('GET', url + '?' + searchParamsObj.toString()); +}; + +export const upsertUserWishlist = async ( + userId: number, + productId: number +): Promise<{ id: number }> => { + const url = `/api/v1/user/${userId}/wishlist/create-or-delete`; + const data = { product_id: productId }; + + return await odooApi('POST', url, data); +}; |
