viewcontent fix
This commit is contained in:
parent
3b31c4e6cb
commit
61b50df864
|
|
@ -52,9 +52,22 @@ export const ViewContentPage = () => {
|
|||
}
|
||||
}, [statusState]);
|
||||
|
||||
const haveLicense = useMemo(() => (
|
||||
content?.data?.have_licenses?.includes('listen') ||
|
||||
content?.data?.have_licenses?.includes('resale')
|
||||
), [content]);
|
||||
|
||||
const contentMime = content?.data?.content_mime ?? null;
|
||||
const contentKind = content?.data?.display_options?.content_kind ?? null;
|
||||
const mediaUrl = content?.data?.display_options?.content_url ?? null;
|
||||
const isAudio = Boolean(content?.data?.content_type?.startsWith('audio'));
|
||||
const isReady = Boolean(mediaUrl);
|
||||
const isAudio = contentKind === 'audio' || Boolean(content?.data?.content_type?.startsWith('audio'));
|
||||
const isVideo = contentKind === 'video' || Boolean(content?.data?.content_type?.startsWith('video'));
|
||||
const isBinary = contentKind === 'binary' || (!isAudio && !isVideo);
|
||||
const hasInlinePlayer = Boolean(mediaUrl) && (isAudio || isVideo);
|
||||
const binaryDownloadReady = Boolean(mediaUrl) && isBinary;
|
||||
const isReadyState = statusState === "ready";
|
||||
const previewAvailable = Boolean(content?.data?.display_options?.has_preview);
|
||||
const coverImage = content?.data?.display_options?.metadata?.image ?? null;
|
||||
const metadataName = content?.data?.display_options?.metadata?.name;
|
||||
const contentTitle = metadataName || content?.data?.encrypted?.title || 'Контент';
|
||||
const processingDetails = useMemo(() => {
|
||||
|
|
@ -67,6 +80,10 @@ export const ViewContentPage = () => {
|
|||
};
|
||||
}, [conversionState, statusMessage, uploadState]);
|
||||
|
||||
const canDownload = Boolean(mediaUrl) && haveLicense && ((content?.data?.downloadable ?? false) || isBinary);
|
||||
const binaryAwaitingAccess = isBinary && !binaryDownloadReady;
|
||||
const isFailed = statusState === "failed";
|
||||
|
||||
const handleBuyContentTON = useCallback(async () => {
|
||||
if (!contentId) {
|
||||
console.error('No content identifier available for purchase');
|
||||
|
|
@ -185,11 +202,6 @@ export const ViewContentPage = () => {
|
|||
}
|
||||
}, [content, refetchContent]);
|
||||
|
||||
const haveLicense = useMemo(() => (
|
||||
content?.data?.have_licenses?.includes('listen') ||
|
||||
content?.data?.have_licenses?.includes('resale')
|
||||
), [content]);
|
||||
|
||||
const hadLicenseRef = useRef<boolean>(haveLicense);
|
||||
|
||||
useEffect(() => {
|
||||
|
|
@ -230,11 +242,15 @@ export const ViewContentPage = () => {
|
|||
const handleDwnldContent = async () => {
|
||||
try {
|
||||
const fileUrl = content?.data?.display_options?.content_url;
|
||||
if (!fileUrl) {
|
||||
return;
|
||||
}
|
||||
const fileName = content?.data?.display_options?.metadata?.name || 'content';
|
||||
const fileFormat = content?.data?.content_ext || '.raw';
|
||||
const rawExt = content?.data?.content_ext ?? 'bin';
|
||||
const normalizedExt = rawExt.replace(/^\.+/, '');
|
||||
await WebApp.downloadFile({
|
||||
url: fileUrl,
|
||||
file_name: fileName + '.' + fileFormat,
|
||||
file_name: `${fileName}.${normalizedExt}`,
|
||||
});
|
||||
} catch (error) {
|
||||
console.error('Error downloading content:', error);
|
||||
|
|
@ -242,40 +258,56 @@ export const ViewContentPage = () => {
|
|||
};
|
||||
|
||||
return (
|
||||
<main className={'min-h-screen flex w-full flex-col gap-[50px] px-4 '}>
|
||||
<main className={'min-h-screen flex w-full flex-col gap-[40px] px-4 '}>
|
||||
{isCongratsModal && <CongratsModal onConfirm={handleConfirmCongrats} />}
|
||||
{isErrorModal && <ErrorModal onConfirm={handleErrorModal} />}
|
||||
{isReady && isAudio &&
|
||||
content?.data?.display_options?.metadata?.image && (
|
||||
<div className={'mt-[30px] h-[314px] w-full'}>
|
||||
<img
|
||||
alt={'content_image'}
|
||||
className={'h-full w-full object-cover object-center'}
|
||||
src={content?.data?.display_options?.metadata?.image}
|
||||
/>
|
||||
{coverImage && (
|
||||
<div className="mt-[30px] flex w-full justify-center">
|
||||
<div className="relative aspect-square w-full max-w-[320px] rounded-3xl border border-slate-900/60 bg-transparent">
|
||||
<div className="absolute inset-0 flex items-center justify-center overflow-hidden">
|
||||
<img
|
||||
alt={'content cover'}
|
||||
className={'max-h-full max-w-full object-contain'}
|
||||
src={coverImage}
|
||||
loading="lazy"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
)}
|
||||
|
||||
{isReady ? (
|
||||
{isReadyState ? (
|
||||
<>
|
||||
{isAudio ? (
|
||||
<AudioPlayer src={mediaUrl ?? ''} />
|
||||
) : (
|
||||
<ReactPlayer
|
||||
playsinline={true}
|
||||
controls={true}
|
||||
width="100%"
|
||||
config={{
|
||||
file: {
|
||||
attributes: {
|
||||
playsInline: true,
|
||||
autoPlay: true,
|
||||
poster: content?.data?.display_options?.metadata?.image || undefined,
|
||||
{hasInlinePlayer && (
|
||||
isAudio ? (
|
||||
<AudioPlayer src={mediaUrl ?? ''} />
|
||||
) : (
|
||||
<ReactPlayer
|
||||
playsinline={true}
|
||||
controls={true}
|
||||
width="100%"
|
||||
config={{
|
||||
file: {
|
||||
attributes: {
|
||||
playsInline: true,
|
||||
autoPlay: true,
|
||||
poster: content?.data?.display_options?.metadata?.image || undefined,
|
||||
},
|
||||
},
|
||||
},
|
||||
}}
|
||||
url={mediaUrl}
|
||||
/>
|
||||
}}
|
||||
url={mediaUrl ?? ''}
|
||||
light={coverImage || undefined}
|
||||
/>
|
||||
)
|
||||
)}
|
||||
|
||||
{binaryDownloadReady && (
|
||||
<div className="rounded-2xl border border-slate-800 bg-slate-950/70 px-6 py-5 shadow-inner shadow-black/20">
|
||||
<h2 className="text-base font-semibold text-slate-100">Файл готов к скачиванию</h2>
|
||||
<p className="mt-2 text-sm text-slate-300">
|
||||
{contentMime ? `Тип файла: ${contentMime}` : 'Скачайте оригинальные данные на устройство.'}
|
||||
</p>
|
||||
</div>
|
||||
)}
|
||||
|
||||
<section className={'flex flex-col'}>
|
||||
|
|
@ -285,26 +317,40 @@ export const ViewContentPage = () => {
|
|||
</p>
|
||||
</section>
|
||||
|
||||
{binaryAwaitingAccess && (
|
||||
<div className="rounded-2xl border border-slate-800 bg-slate-950/70 px-6 py-5 text-sm text-slate-300">
|
||||
<h2 className="text-base font-semibold text-slate-100">Предпросмотр недоступен</h2>
|
||||
<p className="mt-2">
|
||||
Этот файл нельзя открыть в браузере. Получите доступ, чтобы скачать оригинал на устройство.
|
||||
</p>
|
||||
{!previewAvailable && (
|
||||
<p className="mt-2 text-xs text-slate-500">
|
||||
Предпросмотр не формируется для бинарных данных.
|
||||
</p>
|
||||
)}
|
||||
</div>
|
||||
)}
|
||||
|
||||
<div className="mt-auto pb-2">
|
||||
{content?.data?.downloadable && (
|
||||
{canDownload && (
|
||||
<Button
|
||||
onClick={() => handleDwnldContent()}
|
||||
className={'h-[48px] mb-4'}
|
||||
label={`Скачать контент`}
|
||||
label={`Скачать ${isBinary ? 'файл' : 'контент'}`}
|
||||
/>
|
||||
)}
|
||||
{!haveLicense && (
|
||||
<div className="flex flex-row gap-4">
|
||||
<div className="flex gap-4 pb-2">
|
||||
<Button
|
||||
onClick={handleBuyContentTON}
|
||||
className={'mb-4 h-[48px] px-2'}
|
||||
className={'mb-4 h-[48px] px-2 flex-1 min-w-[140px] w-auto'}
|
||||
label={`Купить за ${fromNanoTON(content?.data?.encrypted?.license?.resale?.price)} ТОН`}
|
||||
includeArrows={content?.data?.invoice ? false : true}
|
||||
/>
|
||||
{content?.data?.invoice && (
|
||||
<Button
|
||||
onClick={handleBuyContentStars}
|
||||
className={'mb-4 h-[48px] px-2'}
|
||||
className={'mb-4 h-[48px] px-2 flex-1 min-w-[140px] w-auto'}
|
||||
label={`Купить за ${content?.data?.invoice?.amount} ⭐️`}
|
||||
/>
|
||||
)}
|
||||
|
|
@ -332,10 +378,12 @@ export const ViewContentPage = () => {
|
|||
<div className="flex flex-1 flex-col items-center justify-center py-16">
|
||||
<div className="max-w-md rounded-2xl border border-slate-800 bg-slate-950/70 px-6 py-8 text-center shadow-lg shadow-black/30">
|
||||
<h1 className="text-lg font-semibold text-slate-100">
|
||||
Контент скоро будет здесь
|
||||
{isFailed ? 'Не удалось подготовить контент' : 'Контент скоро будет здесь'}
|
||||
</h1>
|
||||
<p className="mt-3 text-sm text-slate-300">
|
||||
Мы уже обрабатываем загруженный файл и обновим страницу автоматически, как только появится доступ к полному контенту.
|
||||
{isFailed
|
||||
? 'При обработке файла произошла ошибка. Попробуйте обновить страницу или повторно загрузить контент.'
|
||||
: 'Мы уже обрабатываем загруженный файл и обновим страницу автоматически, как только появится доступ к полному контенту.'}
|
||||
</p>
|
||||
{statusMessage && (
|
||||
<p className="mt-4 text-[12px] text-slate-500">
|
||||
|
|
|
|||
Loading…
Reference in New Issue