ClaimList: add default page-load indicator | Apply for Search and Following-Manage

Clients can still choose to roll their own way of showing "is fetching", like how ClaimListDiscover displays a whole bunch of placeholder tiles. This just serves as a default.
This commit is contained in:
infinite-persistence 2022-03-02 21:07:35 +08:00 committed by Thomas Zarebczan
parent 06f7cdbe25
commit f839e0c35d
4 changed files with 21 additions and 1 deletions

View file

@ -25,6 +25,7 @@ type Props = {
header: Node | boolean, header: Node | boolean,
headerAltControls: Node, headerAltControls: Node,
loading: boolean, loading: boolean,
useLoadingSpinner?: boolean, // use built-in spinner when 'loading' is true. Else, roll your own at client-side.
type: string, type: string,
activeUri?: string, activeUri?: string,
empty?: string, empty?: string,
@ -65,6 +66,7 @@ export default function ClaimList(props: Props) {
prefixUris, prefixUris,
headerAltControls, headerAltControls,
loading, loading,
useLoadingSpinner,
persistedStorageKey, persistedStorageKey,
empty, empty,
defaultSort, defaultSort,
@ -200,6 +202,7 @@ export default function ClaimList(props: Props) {
swipeLayout={swipeLayout} swipeLayout={swipeLayout}
/> />
))} ))}
{loading && useLoadingSpinner && <ClaimPreviewTile placeholder="loading" swipeLayout={swipeLayout} />}
{!timedOut && urisLength === 0 && !loading && <div className="empty main--empty">{empty || noResultMsg}</div>} {!timedOut && urisLength === 0 && !loading && <div className="empty main--empty">{empty || noResultMsg}</div>}
{timedOut && timedOutMessage && <div className="empty main--empty">{timedOutMessage}</div>} {timedOut && timedOutMessage && <div className="empty main--empty">{timedOutMessage}</div>}
</section> </section>
@ -289,6 +292,11 @@ export default function ClaimList(props: Props) {
{!timedOut && urisLength === 0 && !loading && <div className="empty empty--centered">{empty || noResultMsg}</div>} {!timedOut && urisLength === 0 && !loading && <div className="empty empty--centered">{empty || noResultMsg}</div>}
{!loading && timedOut && timedOutMessage && <div className="empty empty--centered">{timedOutMessage}</div>} {!loading && timedOut && timedOutMessage && <div className="empty empty--centered">{timedOutMessage}</div>}
{loading && useLoadingSpinner && (
<div className="spinnerArea--centered">
<Spinner type="small" />
</div>
)}
</section> </section>
); );
} }

View file

@ -39,6 +39,7 @@ export default function ChannelsFollowingManage(props: Props) {
// Infinite-scroll handling. 'page' is 0-indexed. // Infinite-scroll handling. 'page' is 0-indexed.
const [page, setPage] = React.useState(-1); const [page, setPage] = React.useState(-1);
const lastPage = Math.max(0, Math.ceil(uris.length / FOLLOW_PAGE_SIZE) - 1); const lastPage = Math.max(0, Math.ceil(uris.length / FOLLOW_PAGE_SIZE) - 1);
const [loadingPage, setLoadingPage] = React.useState(false);
async function resolveUris(uris) { async function resolveUris(uris) {
return doResolveUris(uris, true, false); return doResolveUris(uris, true, false);
@ -52,7 +53,11 @@ export default function ChannelsFollowingManage(props: Props) {
function bumpPage() { function bumpPage() {
if (page < lastPage) { if (page < lastPage) {
resolveNextPage(uris, page).finally(() => setPage(page + 1)); setLoadingPage(true);
resolveNextPage(uris, page).finally(() => {
setLoadingPage(false);
setPage(page + 1);
});
} }
} }
@ -96,6 +101,8 @@ export default function ChannelsFollowingManage(props: Props) {
onScrollBottom={bumpPage} onScrollBottom={bumpPage}
page={page + 1} page={page + 1}
pageSize={FOLLOW_PAGE_SIZE} pageSize={FOLLOW_PAGE_SIZE}
loading={loadingPage}
useLoadingSpinner
/> />
)} )}
</> </>

View file

@ -90,6 +90,7 @@ export default function SearchPage(props: Props) {
<ClaimList <ClaimList
uris={uris} uris={uris}
loading={isSearching} loading={isSearching}
useLoadingSpinner
onScrollBottom={loadMore} onScrollBottom={loadMore}
// 'page' is 1-indexed; It's not the same as 'from', but it just // 'page' is 1-indexed; It's not the same as 'from', but it just
// needs to be unique to indicate when a fetch is needed. // needs to be unique to indicate when a fetch is needed.

View file

@ -52,3 +52,7 @@
width: 3px; width: 3px;
} }
} }
.spinnerArea--centered {
text-align: center;
}