mirror of
https://github.com/jeffvli/feishin.git
synced 2026-05-07 04:20:12 +02:00
refactor playlist route component organization
This commit is contained in:
@@ -1,6 +1,9 @@
|
||||
import { lazy, Suspense } from 'react';
|
||||
import { useSuspenseQuery } from '@tanstack/react-query';
|
||||
import { lazy, Suspense, useEffect } from 'react';
|
||||
import { useParams } from 'react-router';
|
||||
|
||||
import { useListContext } from '/@/renderer/context/list-context';
|
||||
import { playlistsQueries } from '/@/renderer/features/playlists/api/playlists-api';
|
||||
import { ItemListSettings, useCurrentServer, useListSettings } from '/@/renderer/store';
|
||||
import { Spinner } from '/@/shared/components/spinner/spinner';
|
||||
import { PlaylistSongListQuery } from '/@/shared/types/domain-types';
|
||||
@@ -19,10 +22,31 @@ export const PlaylistDetailSongListContent = () => {
|
||||
ItemListKey.PLAYLIST_SONG,
|
||||
);
|
||||
const { playlistId } = useParams() as { playlistId: string };
|
||||
const server = useCurrentServer();
|
||||
const { setItemCount } = useListContext();
|
||||
|
||||
const playlistSongsQuery = useSuspenseQuery(
|
||||
playlistsQueries.songList({
|
||||
query: {
|
||||
id: playlistId,
|
||||
},
|
||||
serverId: server?.id,
|
||||
}),
|
||||
);
|
||||
|
||||
useEffect(() => {
|
||||
if (
|
||||
playlistSongsQuery.data?.totalRecordCount !== undefined &&
|
||||
playlistSongsQuery.data.totalRecordCount !== null
|
||||
) {
|
||||
setItemCount?.(playlistSongsQuery.data.totalRecordCount);
|
||||
}
|
||||
}, [playlistSongsQuery.data?.totalRecordCount, setItemCount]);
|
||||
|
||||
return (
|
||||
<Suspense fallback={<Spinner container />}>
|
||||
<PlaylistDetailSongListView
|
||||
data={playlistSongsQuery.data}
|
||||
display={display}
|
||||
grid={grid}
|
||||
itemsPerPage={itemsPerPage}
|
||||
@@ -37,10 +61,12 @@ export const PlaylistDetailSongListContent = () => {
|
||||
export type OverridePlaylistSongListQuery = Omit<Partial<PlaylistSongListQuery>, 'id'>;
|
||||
|
||||
export const PlaylistDetailSongListView = ({
|
||||
data,
|
||||
display,
|
||||
playlistId,
|
||||
table,
|
||||
}: ItemListSettings & {
|
||||
data: any;
|
||||
playlistId: string;
|
||||
}) => {
|
||||
const server = useCurrentServer();
|
||||
@@ -51,6 +77,7 @@ export const PlaylistDetailSongListView = ({
|
||||
<PlaylistDetailSongListTable
|
||||
autoFitColumns={table.autoFitColumns}
|
||||
columns={table.columns}
|
||||
data={data}
|
||||
enableAlternateRowColors={table.enableAlternateRowColors}
|
||||
enableHorizontalBorders={table.enableHorizontalBorders}
|
||||
enableRowHoverHighlight={table.enableRowHoverHighlight}
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
import { useQuery } from '@tanstack/react-query';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
import { useParams } from 'react-router';
|
||||
import { useLocation, useParams } from 'react-router';
|
||||
|
||||
import { PageHeader } from '/@/renderer/components/page-header/page-header';
|
||||
import { useListContext } from '/@/renderer/context/list-context';
|
||||
@@ -28,11 +28,13 @@ export const PlaylistDetailSongListHeader = ({
|
||||
const { playlistId } = useParams() as { playlistId: string };
|
||||
const { itemCount } = useListContext();
|
||||
const server = useCurrentServer();
|
||||
const detailQuery = useQuery(
|
||||
playlistsQueries.detail({ query: { id: playlistId }, serverId: server?.id }),
|
||||
);
|
||||
const location = useLocation();
|
||||
|
||||
const detailQuery = useQuery({
|
||||
...playlistsQueries.detail({ query: { id: playlistId }, serverId: server?.id }),
|
||||
initialData: location.state?.item,
|
||||
});
|
||||
|
||||
if (detailQuery.isLoading) return null;
|
||||
const isSmartPlaylist = isSmartPlaylistProp ?? detailQuery?.data?.rules;
|
||||
const playlistDuration = detailQuery?.data?.duration;
|
||||
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
import { useQuery } from '@tanstack/react-query';
|
||||
import { forwardRef, useMemo } from 'react';
|
||||
|
||||
import { useItemListColumnReorder } from '/@/renderer/components/item-list/helpers/use-item-list-column-reorder';
|
||||
@@ -8,7 +7,6 @@ import { ItemTableList } from '/@/renderer/components/item-list/item-table-list/
|
||||
import { ItemTableListColumn } from '/@/renderer/components/item-list/item-table-list/item-table-list-column';
|
||||
import { ItemControls, ItemListTableComponentProps } from '/@/renderer/components/item-list/types';
|
||||
import { usePlayer } from '/@/renderer/features/player/context/player-context';
|
||||
import { playlistsQueries } from '/@/renderer/features/playlists/api/playlists-api';
|
||||
import { usePlaylistSongListFilters } from '/@/renderer/features/playlists/hooks/use-playlist-song-list-filters';
|
||||
import { useSearchTermFilter } from '/@/renderer/features/shared/hooks/use-search-term-filter';
|
||||
import { searchLibraryItems } from '/@/renderer/features/shared/utils';
|
||||
@@ -19,6 +17,7 @@ import { ItemListKey, Play } from '/@/shared/types/types';
|
||||
|
||||
interface PlaylistDetailSongListTableProps
|
||||
extends Omit<ItemListTableComponentProps<PlaylistSongListQuery>, 'query'> {
|
||||
data: any;
|
||||
playlistId: string;
|
||||
}
|
||||
|
||||
@@ -27,6 +26,7 @@ export const PlaylistDetailSongListTable = forwardRef<any, PlaylistDetailSongLis
|
||||
{
|
||||
autoFitColumns = false,
|
||||
columns,
|
||||
data,
|
||||
enableAlternateRowColors = false,
|
||||
enableHorizontalBorders = false,
|
||||
enableRowHoverHighlight = true,
|
||||
@@ -39,12 +39,6 @@ export const PlaylistDetailSongListTable = forwardRef<any, PlaylistDetailSongLis
|
||||
},
|
||||
ref,
|
||||
) => {
|
||||
const playlistSongs = useQuery(
|
||||
playlistsQueries.songList({
|
||||
query: { id: playlistId },
|
||||
serverId: serverId,
|
||||
}),
|
||||
);
|
||||
|
||||
const { handleOnScrollEnd, scrollOffset } = useItemListScrollPersist({
|
||||
enabled: saveScrollOffset,
|
||||
@@ -62,7 +56,7 @@ export const PlaylistDetailSongListTable = forwardRef<any, PlaylistDetailSongLis
|
||||
const { query } = usePlaylistSongListFilters();
|
||||
|
||||
const filterSortedSongs = useMemo(() => {
|
||||
let items = playlistSongs.data?.items || [];
|
||||
let items = data?.items || [];
|
||||
|
||||
if (searchTerm) {
|
||||
if (searchTerm) {
|
||||
@@ -73,7 +67,7 @@ export const PlaylistDetailSongListTable = forwardRef<any, PlaylistDetailSongLis
|
||||
}
|
||||
|
||||
return sortSongList(items, query.sortBy, query.sortOrder);
|
||||
}, [playlistSongs.data?.items, searchTerm, query.sortBy, query.sortOrder]);
|
||||
}, [data?.items, searchTerm, query.sortBy, query.sortOrder]);
|
||||
|
||||
const player = usePlayer();
|
||||
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
import { closeAllModals, openModal } from '@mantine/modals';
|
||||
import { useQuery } from '@tanstack/react-query';
|
||||
import { useCallback, useEffect, useMemo, useRef, useState } from 'react';
|
||||
import { Suspense, useCallback, useMemo, useRef, useState } from 'react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
import { generatePath, useNavigate, useParams } from 'react-router';
|
||||
import { generatePath, useLocation, useNavigate, useParams } from 'react-router';
|
||||
|
||||
import { ListContext } from '/@/renderer/context/list-context';
|
||||
import { playlistsQueries } from '/@/renderer/features/playlists/api/playlists-api';
|
||||
@@ -26,6 +26,7 @@ import { Button } from '/@/shared/components/button/button';
|
||||
import { Group } from '/@/shared/components/group/group';
|
||||
import { Icon } from '/@/shared/components/icon/icon';
|
||||
import { ConfirmModal } from '/@/shared/components/modal/modal';
|
||||
import { Spinner } from '/@/shared/components/spinner/spinner';
|
||||
import { Stack } from '/@/shared/components/stack/stack';
|
||||
import { Text } from '/@/shared/components/text/text';
|
||||
import { toast } from '/@/shared/components/toast/toast';
|
||||
@@ -243,12 +244,15 @@ const PlaylistQueryEditor = ({
|
||||
const PlaylistDetailSongListRoute = () => {
|
||||
const { t } = useTranslation();
|
||||
const navigate = useNavigate();
|
||||
const location = useLocation();
|
||||
const { playlistId } = useParams() as { playlistId: string };
|
||||
const server = useCurrentServer();
|
||||
|
||||
const detailQuery = useQuery(
|
||||
playlistsQueries.detail({ query: { id: playlistId }, serverId: server?.id }),
|
||||
);
|
||||
const detailQuery = useQuery({
|
||||
...playlistsQueries.detail({ query: { id: playlistId }, serverId: server?.id }),
|
||||
initialData: location.state?.item,
|
||||
staleTime: 0,
|
||||
});
|
||||
const createPlaylistMutation = useCreatePlaylist({});
|
||||
const deletePlaylistMutation = useDeletePlaylist({});
|
||||
|
||||
@@ -410,15 +414,6 @@ const PlaylistDetailSongListRoute = () => {
|
||||
setIsQueryBuilderExpanded(true);
|
||||
};
|
||||
|
||||
const playlistSongs = useQuery(
|
||||
playlistsQueries.songList({
|
||||
query: {
|
||||
id: playlistId,
|
||||
},
|
||||
serverId: server?.id,
|
||||
}),
|
||||
);
|
||||
|
||||
const [itemCount, setItemCount] = useState<number | undefined>(undefined);
|
||||
|
||||
const providerValue = useMemo(() => {
|
||||
@@ -431,15 +426,6 @@ const PlaylistDetailSongListRoute = () => {
|
||||
};
|
||||
}, [playlistId, itemCount]);
|
||||
|
||||
useEffect(() => {
|
||||
if (
|
||||
playlistSongs.data?.totalRecordCount !== undefined &&
|
||||
playlistSongs.data.totalRecordCount !== null
|
||||
) {
|
||||
setItemCount(playlistSongs.data.totalRecordCount);
|
||||
}
|
||||
}, [playlistSongs.data?.totalRecordCount]);
|
||||
|
||||
return (
|
||||
<AnimatedPage key={`playlist-detail-songList-${playlistId}`}>
|
||||
<ListContext.Provider value={providerValue}>
|
||||
@@ -466,7 +452,9 @@ const PlaylistDetailSongListRoute = () => {
|
||||
queryBuilderRef={queryBuilderRef}
|
||||
/>
|
||||
)}
|
||||
<PlaylistDetailSongListContent />
|
||||
<Suspense fallback={<Spinner container />}>
|
||||
<PlaylistDetailSongListContent />
|
||||
</Suspense>
|
||||
</ListContext.Provider>
|
||||
</AnimatedPage>
|
||||
);
|
||||
|
||||
@@ -41,7 +41,10 @@ interface PlaylistRowButtonProps extends Omit<ButtonProps, 'onContextMenu' | 'on
|
||||
}
|
||||
|
||||
const PlaylistRowButton = ({ item, name, onContextMenu, onPlay, to }: PlaylistRowButtonProps) => {
|
||||
const url = generatePath(AppRoute.PLAYLISTS_DETAIL_SONGS, { playlistId: to });
|
||||
const url = {
|
||||
pathname: generatePath(AppRoute.PLAYLISTS_DETAIL_SONGS, { playlistId: to }),
|
||||
state: { item },
|
||||
};
|
||||
const { t } = useTranslation();
|
||||
|
||||
const [isHovered, setIsHovered] = useState(false);
|
||||
|
||||
Reference in New Issue
Block a user