Redo queue handler as hook

This commit is contained in:
jeffvli 2022-12-20 04:11:06 -08:00
parent 3dd9e620a8
commit c858479d57
12 changed files with 247 additions and 199 deletions

View file

@ -3,11 +3,13 @@ import { Group, Stack } from '@mantine/core';
import type { Variants } from 'framer-motion';
import { AnimatePresence, motion } from 'framer-motion';
import { RiArrowLeftSLine, RiArrowRightSLine } from 'react-icons/ri';
import { AlbumCard, Button } from '/@/renderer/components';
import { Button } from '/@/renderer/components/button';
import { AppRoute } from '/@/renderer/router/routes';
import type { CardRow } from '/@/renderer/types';
import { LibraryItem, Play } from '/@/renderer/types';
import styled from 'styled-components';
import { AlbumCard } from '/@/renderer/components/card';
import { useHandlePlayQueueAdd } from '/@/renderer/features/player/hooks/use-handle-playqueue-add';
interface GridCarouselProps {
cardRows: CardRow[];
@ -27,6 +29,99 @@ interface GridCarouselProps {
const GridCarouselContext = createContext<any>(null);
const GridContainer = styled(motion.div)<{ height: number; itemsPerPage: number }>`
display: grid;
grid-auto-rows: 0;
grid-gap: 18px;
grid-template-rows: 1fr;
grid-template-columns: repeat(${(props) => props.itemsPerPage || 4}, minmax(0, 1fr));
height: ${(props) => props.height}px;
overflow: hidden;
`;
const Wrapper = styled.div`
position: relative;
width: 100%;
height: 100%;
overflow: hidden;
`;
const variants: Variants = {
animate: (custom: { direction: number; loading: boolean }) => {
return {
opacity: custom.loading ? 0.5 : 1,
scale: custom.loading ? 0.95 : 1,
transition: {
opacity: { duration: 0.2 },
x: { damping: 30, stiffness: 300, type: 'spring' },
},
x: 0,
};
},
exit: (custom: { direction: number; loading: boolean }) => {
return {
opacity: 0,
transition: {
opacity: { duration: 0.2 },
x: { damping: 30, stiffness: 300, type: 'spring' },
},
x: custom.direction > 0 ? -1000 : 1000,
};
},
initial: (custom: { direction: number; loading: boolean }) => {
return {
opacity: 0,
x: custom.direction > 0 ? 1000 : -1000,
};
},
};
const Carousel = ({ data, cardRows }: any) => {
const { loading, pagination, gridHeight, imageSize, direction, uniqueId } =
useContext(GridCarouselContext);
const handlePlayQueueAdd = useHandlePlayQueueAdd();
return (
<Wrapper>
<AnimatePresence
custom={{ direction, loading }}
initial={false}
mode="popLayout"
>
<GridContainer
key={`carousel-${uniqueId}-${data[0].id}`}
animate="animate"
custom={{ direction, loading }}
exit="exit"
height={gridHeight}
initial="initial"
itemsPerPage={pagination.itemsPerPage}
variants={variants}
>
{data?.map((item: any, index: number) => (
<AlbumCard
key={`card-${uniqueId}-${index}`}
controls={{
cardRows,
itemType: LibraryItem.ALBUM,
playButtonBehavior: Play.NOW,
route: {
route: AppRoute.LIBRARY_ALBUMS_DETAIL,
slugs: [{ idProperty: 'id', slugProperty: 'albumId' }],
},
}}
data={item}
handlePlayQueueAdd={handlePlayQueueAdd}
size={imageSize}
/>
))}
</GridContainer>
</AnimatePresence>
</Wrapper>
);
};
export const GridCarousel = ({
data,
loading,
@ -75,96 +170,6 @@ export const GridCarousel = ({
);
};
const variants: Variants = {
animate: (custom: { direction: number; loading: boolean }) => {
return {
opacity: custom.loading ? 0.5 : 1,
scale: custom.loading ? 0.95 : 1,
transition: {
opacity: { duration: 0.2 },
x: { damping: 30, stiffness: 300, type: 'spring' },
},
x: 0,
};
},
exit: (custom: { direction: number; loading: boolean }) => {
return {
opacity: 0,
transition: {
opacity: { duration: 0.2 },
x: { damping: 30, stiffness: 300, type: 'spring' },
},
x: custom.direction > 0 ? -1000 : 1000,
};
},
initial: (custom: { direction: number; loading: boolean }) => {
return {
opacity: 0,
x: custom.direction > 0 ? 1000 : -1000,
};
},
};
const GridContainer = styled(motion.div)<{ height: number; itemsPerPage: number }>`
display: grid;
grid-auto-rows: 0;
grid-gap: 18px;
grid-template-rows: 1fr;
grid-template-columns: repeat(${(props) => props.itemsPerPage || 4}, minmax(0, 1fr));
height: ${(props) => props.height}px;
overflow: hidden;
`;
const Wrapper = styled.div`
position: relative;
width: 100%;
height: 100%;
overflow: hidden;
`;
const Carousel = ({ data, cardRows }: any) => {
const { loading, pagination, gridHeight, imageSize, direction, uniqueId } =
useContext(GridCarouselContext);
return (
<Wrapper>
<AnimatePresence
custom={{ direction, loading }}
initial={false}
mode="popLayout"
>
<GridContainer
key={`carousel-${uniqueId}-${data[0].id}`}
animate="animate"
custom={{ direction, loading }}
exit="exit"
height={gridHeight}
initial="initial"
itemsPerPage={pagination.itemsPerPage}
variants={variants}
>
{data?.map((item: any, index: number) => (
<AlbumCard
key={`card-${uniqueId}-${index}`}
controls={{
cardRows,
itemType: LibraryItem.ALBUM,
playButtonBehavior: Play.NOW,
route: {
route: AppRoute.LIBRARY_ALBUMS_DETAIL,
slugs: [{ idProperty: 'id', slugProperty: 'albumId' }],
},
}}
data={item}
size={imageSize}
/>
))}
</GridContainer>
</AnimatePresence>
</Wrapper>
);
};
interface TitleProps {
children?: React.ReactNode;
}