import { List as ImmutableList } from 'immutable'; import React, { useEffect, useRef } from 'react'; import { FormattedMessage } from 'react-intl'; import { useParams } from 'react-router-dom'; import { openModal } from 'pl-fe/actions/modals'; import { fetchAccountTimeline } from 'pl-fe/actions/timelines'; import { useAccountLookup } from 'pl-fe/api/hooks'; import LoadMore from 'pl-fe/components/load-more'; import MissingIndicator from 'pl-fe/components/missing-indicator'; import { Column, Spinner } from 'pl-fe/components/ui'; import { useAppDispatch, useAppSelector } from 'pl-fe/hooks'; import { type AccountGalleryAttachment, getAccountGallery } from 'pl-fe/selectors'; import MediaItem from './components/media-item'; interface ILoadMoreMedia { maxId: string | null; onLoadMore: (value: string | null) => void; } const LoadMoreMedia: React.FC = ({ maxId, onLoadMore }) => { const handleLoadMore = () => { onLoadMore(maxId); }; return ( ); }; const AccountGallery = () => { const dispatch = useAppDispatch(); const { username } = useParams<{ username: string }>(); const { account, isLoading: accountLoading, isUnavailable, } = useAccountLookup(username, { withRelationship: true }); const attachments: ImmutableList = useAppSelector((state) => account ? getAccountGallery(state, account.id) : ImmutableList()); const isLoading = useAppSelector((state) => state.timelines.get(`account:${account?.id}:with_replies:media`)?.isLoading); const hasMore = useAppSelector((state) => state.timelines.get(`account:${account?.id}:with_replies:media`)?.hasMore); const node = useRef(null); const handleScrollToBottom = () => { if (hasMore) { handleLoadMore(); } }; const handleLoadMore = () => { if (account) { dispatch(fetchAccountTimeline(account.id, { only_media: true }, true)); } }; const handleLoadOlder: React.MouseEventHandler = e => { e.preventDefault(); handleScrollToBottom(); }; const handleOpenMedia = (attachment: AccountGalleryAttachment) => { if (attachment.type === 'video') { dispatch(openModal('VIDEO', { media: attachment, statusId: attachment.status.id, account: attachment.account })); } else { const media = attachment.status.media_attachments; const index = media.findIndex((x) => x.id === attachment.id); dispatch(openModal('MEDIA', { media, index, statusId: attachment.status.id })); } }; useEffect(() => { if (account) { dispatch(fetchAccountTimeline(account.id, { only_media: true, limit: 40 })); } }, [account?.id]); if (accountLoading || (!attachments && isLoading)) { return ( ); } if (!account) { return ( ); } let loadOlder = null; if (hasMore && !(isLoading && attachments.size === 0)) { loadOlder = ; } if (isUnavailable) { return (
); } return (
{attachments.map((attachment, index) => attachment === null ? ( 0 ? (attachments.get(index - 1)?.id || null) : null} onLoadMore={handleLoadMore} /> ) : ( ))} {!isLoading && attachments.size === 0 && (
)} {loadOlder}
{isLoading && attachments.size === 0 && (
)}
); }; export { AccountGallery as default };