This commit is contained in:
@@ -1,16 +1,15 @@
|
||||
import { type FC } from 'react'
|
||||
import { useGetCatalog } from '../home/hooks/useHomeData'
|
||||
import GridWrapper from '@/components/GridWrapper'
|
||||
import CatalogueItem from './components/CatalogueItem'
|
||||
import ButtonAddCatalogue from './components/ButtonAddCatalogue'
|
||||
import GridWrapper from "@/components/GridWrapper";
|
||||
import { type FC } from "react";
|
||||
import { useGetCatalog } from "../home/hooks/useHomeData";
|
||||
import ButtonAddCatalogue from "./components/ButtonAddCatalogue";
|
||||
import CatalogueItem from "./components/CatalogueItem";
|
||||
|
||||
const CatalogueList: FC = () => {
|
||||
const { data, refetch } = useGetCatalog();
|
||||
|
||||
const { data, refetch } = useGetCatalog()
|
||||
|
||||
return (
|
||||
<div className='w-full mt-5'>
|
||||
{/* {
|
||||
return (
|
||||
<div className="w-full mt-5">
|
||||
{/* {
|
||||
!isPending && !data?.data?.length &&
|
||||
<div className='flex flex-col items-center gap-5'>
|
||||
<div className='text-gray-500'>
|
||||
@@ -24,18 +23,14 @@ const CatalogueList: FC = () => {
|
||||
</Link>
|
||||
</div>
|
||||
} */}
|
||||
<GridWrapper desktop={4} gapDesktop={40} mobile={1}>
|
||||
{
|
||||
data?.data?.map((item) => {
|
||||
return (
|
||||
<CatalogueItem refetch={refetch} key={item.id} item={item} />
|
||||
)
|
||||
})
|
||||
}
|
||||
<ButtonAddCatalogue isFirst={data?.data?.length === 0} />
|
||||
</GridWrapper>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
<GridWrapper desktop={4} gapDesktop={40} mobile={1}>
|
||||
{data?.data?.map((item) => {
|
||||
return <CatalogueItem refetch={refetch} key={item.id} item={item} />;
|
||||
})}
|
||||
<ButtonAddCatalogue isFirst={data?.data?.length === 0} />
|
||||
</GridWrapper>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
|
||||
export default CatalogueList
|
||||
export default CatalogueList;
|
||||
|
||||
@@ -1,103 +1,103 @@
|
||||
import { type FC } from 'react'
|
||||
import { Edit, Eye, Share } from 'iconsax-react'
|
||||
import type { CatalogItemType } from '../types/Types'
|
||||
import moment from 'moment-jalaali'
|
||||
import { Link } from 'react-router-dom'
|
||||
import { Paths } from '@/config/Paths'
|
||||
import CatalogPreview from './CatalogPreview'
|
||||
import TrashWithConfrim from '@/components/TrashWithConfrim'
|
||||
import { useDleteCatalog } from '@/pages/home/hooks/useHomeData'
|
||||
import { toast } from '@/components/Toast'
|
||||
import { extractErrorMessage } from '@/helpers/utils'
|
||||
import { requestViewerFullscreen } from '@/pages/viewer/utils/viewerFullscreen'
|
||||
import { toast } from "@/components/Toast";
|
||||
import TrashWithConfrim from "@/components/TrashWithConfrim";
|
||||
import { Paths } from "@/config/Paths";
|
||||
import { extractErrorMessage } from "@/helpers/utils";
|
||||
import { useDleteCatalog } from "@/pages/home/hooks/useHomeData";
|
||||
import { requestViewerFullscreen } from "@/pages/viewer/utils/viewerFullscreen";
|
||||
import { Edit, Eye, Share } from "iconsax-react";
|
||||
import moment from "moment-jalaali";
|
||||
import { type FC } from "react";
|
||||
import { Link } from "react-router-dom";
|
||||
import type { CatalogItemType } from "../types/Types";
|
||||
import CatalogPreview from "./CatalogPreview";
|
||||
|
||||
type Props = {
|
||||
item: CatalogItemType,
|
||||
refetch: () => void,
|
||||
}
|
||||
item: CatalogItemType;
|
||||
refetch: () => void;
|
||||
};
|
||||
|
||||
const CatalogueItem: FC<Props> = ({ item, refetch }) => {
|
||||
const deleteCatalog = useDleteCatalog();
|
||||
|
||||
const deleteCatalog = useDleteCatalog()
|
||||
const shareUrl = `${window.location.origin}${Paths.viewer}/${item.id}`;
|
||||
|
||||
const shareUrl = `${window.location.origin}${Paths.viewer}/${item.id}`
|
||||
|
||||
const handleShare = async () => {
|
||||
try {
|
||||
if (typeof navigator.share === 'function') {
|
||||
await navigator.share({
|
||||
title: item.name,
|
||||
text: item.name,
|
||||
url: shareUrl,
|
||||
})
|
||||
return
|
||||
}
|
||||
await navigator.clipboard.writeText(shareUrl)
|
||||
toast('لینک در کلیپبورد کپی شد', 'success')
|
||||
} catch (err) {
|
||||
const isAbort =
|
||||
err instanceof DOMException
|
||||
? err.name === 'AbortError'
|
||||
: err instanceof Error && err.name === 'AbortError'
|
||||
if (isAbort) return
|
||||
toast(extractErrorMessage(err, 'امکان اشتراکگذاری وجود ندارد'), 'error')
|
||||
}
|
||||
const handleShare = async () => {
|
||||
try {
|
||||
if (typeof navigator.share === "function") {
|
||||
await navigator.share({
|
||||
title: item.name,
|
||||
text: item.name,
|
||||
url: shareUrl,
|
||||
});
|
||||
return;
|
||||
}
|
||||
await navigator.clipboard.writeText(shareUrl);
|
||||
toast("لینک در کلیپبورد کپی شد", "success");
|
||||
} catch (err) {
|
||||
const isAbort =
|
||||
err instanceof DOMException
|
||||
? err.name === "AbortError"
|
||||
: err instanceof Error && err.name === "AbortError";
|
||||
if (isAbort) return;
|
||||
toast(extractErrorMessage(err, "امکان اشتراکگذاری وجود ندارد"), "error");
|
||||
}
|
||||
};
|
||||
|
||||
const handleDelete = () => {
|
||||
deleteCatalog.mutate(item.id, {
|
||||
onSuccess: () => {
|
||||
toast('با موفقیت حذف شد', 'success')
|
||||
refetch()
|
||||
},
|
||||
onError: (error) => {
|
||||
toast(extractErrorMessage(error, 'error'))
|
||||
}
|
||||
})
|
||||
}
|
||||
const handleDelete = () => {
|
||||
deleteCatalog.mutate(item.id, {
|
||||
onSuccess: () => {
|
||||
toast("با موفقیت حذف شد", "success");
|
||||
refetch();
|
||||
},
|
||||
onError: (error) => {
|
||||
toast(extractErrorMessage(error, "error"));
|
||||
},
|
||||
});
|
||||
};
|
||||
|
||||
return (
|
||||
<div className='bg-white p-6 rounded-3xl w-full'>
|
||||
<div className='flex gap-4 items-center'>
|
||||
<CatalogPreview item={item} />
|
||||
<div>
|
||||
<h6>
|
||||
{item.name}
|
||||
</h6>
|
||||
<div className='mt-2 text-[#999999] text-xs'>
|
||||
{moment(item.createdAt).format('jYYYY/jMM/jDD')}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div className='flex justify-end gap-1 items-center mt-1'>
|
||||
<Link to={Paths.viewer + `/${item.id}`} onClick={requestViewerFullscreen}>
|
||||
<div className='size-6 bg-[#EAECF4] rounded-md flex justify-center items-center'>
|
||||
<Eye size={18} color='#0047FF' />
|
||||
</div>
|
||||
</Link>
|
||||
<Link to={Paths.editor + `/${item.id}`}>
|
||||
<div className='size-6 bg-[#EAECF4] rounded-md flex justify-center items-center'>
|
||||
<Edit size={18} color='#0047FF' />
|
||||
</div>
|
||||
</Link>
|
||||
<button
|
||||
type='button'
|
||||
onClick={handleShare}
|
||||
className='size-6 bg-[#EAECF4] rounded-md flex justify-center items-center border-0 p-0 cursor-pointer shrink-0'
|
||||
aria-label='اشتراکگذاری'
|
||||
>
|
||||
<Share size={18} color='#000' />
|
||||
</button>
|
||||
<div className='size-6 bg-[#EAECF4] rounded-md flex justify-center items-center'>
|
||||
<TrashWithConfrim
|
||||
onDelete={handleDelete}
|
||||
colorIcon='red'
|
||||
isloading={deleteCatalog.isPending}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
return (
|
||||
<div className="bg-white p-6 rounded-3xl w-full">
|
||||
<div className="flex gap-4 items-center">
|
||||
<CatalogPreview item={item} />
|
||||
<div>
|
||||
<h6>{item.name}</h6>
|
||||
<div className="mt-2 text-[#999999] text-xs">
|
||||
{moment(item.createdAt).format("jYYYY/jMM/jDD")}
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
</div>
|
||||
<div className="flex justify-end gap-1 items-center mt-1">
|
||||
<Link
|
||||
to={Paths.viewer + `/${item.slug}`}
|
||||
onClick={requestViewerFullscreen}
|
||||
>
|
||||
<div className="size-6 bg-[#EAECF4] rounded-md flex justify-center items-center">
|
||||
<Eye size={18} color="#0047FF" />
|
||||
</div>
|
||||
</Link>
|
||||
<Link to={Paths.editor + `/${item.slug}`}>
|
||||
<div className="size-6 bg-[#EAECF4] rounded-md flex justify-center items-center">
|
||||
<Edit size={18} color="#0047FF" />
|
||||
</div>
|
||||
</Link>
|
||||
<button
|
||||
type="button"
|
||||
onClick={handleShare}
|
||||
className="size-6 bg-[#EAECF4] rounded-md flex justify-center items-center border-0 p-0 cursor-pointer shrink-0"
|
||||
aria-label="اشتراکگذاری"
|
||||
>
|
||||
<Share size={18} color="#000" />
|
||||
</button>
|
||||
<div className="size-6 bg-[#EAECF4] rounded-md flex justify-center items-center">
|
||||
<TrashWithConfrim
|
||||
onDelete={handleDelete}
|
||||
colorIcon="red"
|
||||
isloading={deleteCatalog.isPending}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
|
||||
export default CatalogueItem
|
||||
export default CatalogueItem;
|
||||
|
||||
@@ -7,6 +7,7 @@ export type CatalogItemType = {
|
||||
size: string;
|
||||
status: string;
|
||||
createdAt: string;
|
||||
slug: string;
|
||||
};
|
||||
|
||||
export type CatalogResponseType = BaseResponse<CatalogItemType[]>;
|
||||
|
||||
@@ -20,7 +20,7 @@ export const getCatalogs = async () => {
|
||||
|
||||
export const getCatalogById = async (id: string) => {
|
||||
const { data } = await axios.get<CatalogByIdResponseType>(
|
||||
`/public/catalogue/${id}`,
|
||||
`/public/catalogue/slug/${id}`,
|
||||
);
|
||||
return data;
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user