mirror of
https://github.com/invoke-ai/InvokeAI
synced 2024-08-30 20:32:17 +00:00
feat(ui): update right arrow gallery load more
- add hotkey support - add loading state - only show if there are more images to load
This commit is contained in:
parent
2c956806d7
commit
3001e4c947
@ -57,6 +57,7 @@ const selector = createSelector(
|
||||
images,
|
||||
allImagesTotal,
|
||||
isLoading,
|
||||
isFetching,
|
||||
categories,
|
||||
selectedBoardId,
|
||||
};
|
||||
@ -82,8 +83,14 @@ const ImageGalleryGrid = () => {
|
||||
},
|
||||
});
|
||||
|
||||
const { images, isLoading, allImagesTotal, categories, selectedBoardId } =
|
||||
useAppSelector(selector);
|
||||
const {
|
||||
images,
|
||||
isLoading,
|
||||
isFetching,
|
||||
allImagesTotal,
|
||||
categories,
|
||||
selectedBoardId,
|
||||
} = useAppSelector(selector);
|
||||
|
||||
const { selectedBoard } = useListAllBoardsQuery(undefined, {
|
||||
selectFromResult: ({ data }) => ({
|
||||
@ -176,7 +183,7 @@ const ImageGalleryGrid = () => {
|
||||
<IAIButton
|
||||
onClick={handleLoadMoreImages}
|
||||
isDisabled={!areMoreAvailable}
|
||||
isLoading={isLoading}
|
||||
isLoading={isFetching}
|
||||
loadingText="Loading"
|
||||
flexShrink={0}
|
||||
>
|
||||
|
@ -1,17 +1,17 @@
|
||||
import { ChakraProps, Flex, Grid, IconButton } from '@chakra-ui/react';
|
||||
import { ChakraProps, Flex, Grid, IconButton, Spinner } from '@chakra-ui/react';
|
||||
import { createSelector } from '@reduxjs/toolkit';
|
||||
import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
import { clamp, isEqual } from 'lodash-es';
|
||||
import { useCallback, useState } from 'react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
import { FaAngleLeft, FaAngleRight, FaRedo } from 'react-icons/fa';
|
||||
import { stateSelector } from 'app/store/store';
|
||||
import { useAppDispatch, useAppSelector } from 'app/store/storeHooks';
|
||||
import {
|
||||
imageSelected,
|
||||
selectFilteredImages,
|
||||
selectImagesById,
|
||||
} from 'features/gallery/store/gallerySlice';
|
||||
import { clamp, isEqual } from 'lodash-es';
|
||||
import { useCallback, useState } from 'react';
|
||||
import { useHotkeys } from 'react-hotkeys-hook';
|
||||
import { selectFilteredImages } from 'features/gallery/store/gallerySlice';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
import { FaAngleDoubleRight, FaAngleLeft, FaAngleRight } from 'react-icons/fa';
|
||||
import { receivedPageOfImages } from 'services/api/thunks/image';
|
||||
|
||||
const nextPrevButtonTriggerAreaStyles: ChakraProps['sx'] = {
|
||||
@ -27,6 +27,7 @@ const nextPrevButtonStyles: ChakraProps['sx'] = {
|
||||
export const nextPrevImageButtonsSelector = createSelector(
|
||||
[stateSelector, selectFilteredImages],
|
||||
(state, filteredImages) => {
|
||||
const { total, isFetching } = state.gallery;
|
||||
const lastSelectedImage =
|
||||
state.gallery.selection[state.gallery.selection.length - 1];
|
||||
|
||||
@ -64,6 +65,8 @@ export const nextPrevImageButtonsSelector = createSelector(
|
||||
isOnFirstImage: currentImageIndex === 0,
|
||||
isOnLastImage:
|
||||
!isNaN(currentImageIndex) && currentImageIndex === imagesLength - 1,
|
||||
areMoreImagesAvailable: total > imagesLength,
|
||||
isFetching,
|
||||
nextImage,
|
||||
prevImage,
|
||||
nextImageId,
|
||||
@ -81,8 +84,14 @@ const NextPrevImageButtons = () => {
|
||||
const dispatch = useAppDispatch();
|
||||
const { t } = useTranslation();
|
||||
|
||||
const { isOnFirstImage, isOnLastImage, nextImageId, prevImageId } =
|
||||
useAppSelector(nextPrevImageButtonsSelector);
|
||||
const {
|
||||
isOnFirstImage,
|
||||
isOnLastImage,
|
||||
nextImageId,
|
||||
prevImageId,
|
||||
areMoreImagesAvailable,
|
||||
isFetching,
|
||||
} = useAppSelector(nextPrevImageButtonsSelector);
|
||||
|
||||
const [shouldShowNextPrevButtons, setShouldShowNextPrevButtons] =
|
||||
useState<boolean>(false);
|
||||
@ -122,9 +131,21 @@ const NextPrevImageButtons = () => {
|
||||
useHotkeys(
|
||||
'right',
|
||||
() => {
|
||||
handleNextImage();
|
||||
if (isOnLastImage && areMoreImagesAvailable && !isFetching) {
|
||||
handleLoadMoreImages();
|
||||
return;
|
||||
}
|
||||
if (!isOnLastImage) {
|
||||
handleNextImage();
|
||||
}
|
||||
},
|
||||
[nextImageId]
|
||||
[
|
||||
nextImageId,
|
||||
isOnLastImage,
|
||||
areMoreImagesAvailable,
|
||||
handleLoadMoreImages,
|
||||
isFetching,
|
||||
]
|
||||
);
|
||||
|
||||
return (
|
||||
@ -173,16 +194,34 @@ const NextPrevImageButtons = () => {
|
||||
sx={nextPrevButtonStyles}
|
||||
/>
|
||||
)}
|
||||
{shouldShowNextPrevButtons && isOnLastImage && (
|
||||
<IconButton
|
||||
aria-label={t('accessibility.loadMore')}
|
||||
icon={<FaRedo size={42} />}
|
||||
variant="unstyled"
|
||||
onClick={handleLoadMoreImages}
|
||||
boxSize={16}
|
||||
sx={nextPrevButtonStyles}
|
||||
/>
|
||||
)}
|
||||
{shouldShowNextPrevButtons &&
|
||||
isOnLastImage &&
|
||||
areMoreImagesAvailable &&
|
||||
!isFetching && (
|
||||
<IconButton
|
||||
aria-label={t('accessibility.loadMore')}
|
||||
icon={<FaAngleDoubleRight size={64} />}
|
||||
variant="unstyled"
|
||||
onClick={handleLoadMoreImages}
|
||||
boxSize={16}
|
||||
sx={nextPrevButtonStyles}
|
||||
/>
|
||||
)}
|
||||
{shouldShowNextPrevButtons &&
|
||||
isOnLastImage &&
|
||||
areMoreImagesAvailable &&
|
||||
isFetching && (
|
||||
<Flex
|
||||
sx={{
|
||||
w: 16,
|
||||
h: 16,
|
||||
alignItems: 'center',
|
||||
justifyContent: 'center',
|
||||
}}
|
||||
>
|
||||
<Spinner opacity={0.5} size="xl" />
|
||||
</Flex>
|
||||
)}
|
||||
</Grid>
|
||||
</Flex>
|
||||
);
|
||||
|
Loading…
Reference in New Issue
Block a user