Browse Source

Remember filter for album page

master
jeffvli 3 years ago
committed by Jeff
parent
commit
75b91b4fa6
  1. 8
      src/__tests__/App.test.tsx
  2. 23
      src/components/library/AlbumList.tsx
  3. 26
      src/redux/albumSlice.ts
  4. 2
      src/redux/store.ts

8
src/__tests__/App.test.tsx

@ -12,6 +12,7 @@ import { ConfigPage } from '../redux/configSlice';
import { FolderSelection } from '../redux/folderSlice'; import { FolderSelection } from '../redux/folderSlice';
import { FavoritePage } from '../redux/favoriteSlice'; import { FavoritePage } from '../redux/favoriteSlice';
import App from '../App'; import App from '../App';
import { AlbumPage } from '../redux/albumSlice';
const middlewares: Middleware<Record<string, unknown>, any, Dispatch<AnyAction>>[] | undefined = []; const middlewares: Middleware<Record<string, unknown>, any, Dispatch<AnyAction>>[] | undefined = [];
const mockStore = configureMockStore(middlewares); const mockStore = configureMockStore(middlewares);
@ -116,6 +117,12 @@ const favoriteState: FavoritePage = {
}, },
}; };
const albumState: AlbumPage = {
active: {
filter: 'random',
},
};
const mockInitialState = { const mockInitialState = {
player: playerState, player: playerState,
playQueue: playQueueState, playQueue: playQueueState,
@ -124,6 +131,7 @@ const mockInitialState = {
folder: folderState, folder: folderState,
config: configState, config: configState,
favorite: favoriteState, favorite: favoriteState,
album: albumState,
}; };
describe('App', () => { describe('App', () => {

23
src/components/library/AlbumList.tsx

@ -20,25 +20,24 @@ import {
} from '../../redux/multiSelectSlice'; } from '../../redux/multiSelectSlice';
import { StyledInputPicker } from '../shared/styled'; import { StyledInputPicker } from '../shared/styled';
import { RefreshButton } from '../shared/ToolbarButtons'; import { RefreshButton } from '../shared/ToolbarButtons';
import useRouterQuery from '../../hooks/useRouterQuery'; import { setActive } from '../../redux/albumSlice';
const ALBUM_SORT_TYPES = [ const ALBUM_SORT_TYPES = [
{ label: 'A-Z (Name)', value: 'alphabeticalByName', role: 'Default' }, { label: 'A-Z (Name)', value: 'alphabeticalByName', role: 'Default' },
{ label: 'A-Z (Artist)', value: 'alphabeticalByArtist', role: 'Default' }, { label: 'A-Z (Artist)', value: 'alphabeticalByArtist', role: 'Default' },
{ label: 'Most Played', value: 'frequent', role: 'Default' }, { label: 'Most Played', value: 'frequent', role: 'Default' },
{ label: 'Newly Added', value: 'newest', role: 'Default' },
{ label: 'Random', value: 'random', role: 'Default' }, { label: 'Random', value: 'random', role: 'Default' },
{ label: 'Recently Added', value: 'newest', role: 'Default' },
{ label: 'Recently Played', value: 'recent', role: 'Default' }, { label: 'Recently Played', value: 'recent', role: 'Default' },
]; ];
const AlbumList = () => { const AlbumList = () => {
const dispatch = useAppDispatch(); const dispatch = useAppDispatch();
const history = useHistory(); const history = useHistory();
const query = useRouterQuery();
const queryClient = useQueryClient(); const queryClient = useQueryClient();
const folder = useAppSelector((state) => state.folder); const folder = useAppSelector((state) => state.folder);
const album = useAppSelector((state) => state.album);
const [isRefreshing, setIsRefreshing] = useState(false); const [isRefreshing, setIsRefreshing] = useState(false);
const [sortBy, setSortBy] = useState(query.get('sortType') || 'random');
const [sortTypes, setSortTypes] = useState<any[]>(); const [sortTypes, setSortTypes] = useState<any[]>();
const [viewType, setViewType] = useState(settings.getSync('albumViewType')); const [viewType, setViewType] = useState(settings.getSync('albumViewType'));
const [musicFolder, setMusicFolder] = useState(undefined); const [musicFolder, setMusicFolder] = useState(undefined);
@ -50,16 +49,16 @@ const AlbumList = () => {
}, [folder]); }, [folder]);
const { isLoading, isError, data: albums, error }: any = useQuery( const { isLoading, isError, data: albums, error }: any = useQuery(
['albumList', sortBy, musicFolder], ['albumList', album.active.filter, musicFolder],
() => () =>
sortBy === 'random' album.active.filter === 'random'
? getAlbumsDirect({ ? getAlbumsDirect({
type: 'random', type: 'random',
size: Number(settings.getSync('gridCardSize')), size: Number(settings.getSync('gridCardSize')),
musicFolderId: musicFolder, musicFolderId: musicFolder,
}) })
: getAllAlbums({ : getAllAlbums({
type: sortBy, type: album.active.filter,
size: 500, size: 500,
offset: 0, offset: 0,
musicFolderId: musicFolder, musicFolderId: musicFolder,
@ -127,7 +126,7 @@ const AlbumList = () => {
const handleRowFavorite = async (rowData: any) => { const handleRowFavorite = async (rowData: any) => {
if (!rowData.starred) { if (!rowData.starred) {
await star(rowData.id, 'album'); await star(rowData.id, 'album');
queryClient.setQueryData(['albumList', sortBy, musicFolder], (oldData: any) => { queryClient.setQueryData(['albumList', album.active.filter, musicFolder], (oldData: any) => {
const starredIndices = _.keys(_.pickBy(oldData, { id: rowData.id })); const starredIndices = _.keys(_.pickBy(oldData, { id: rowData.id }));
starredIndices.forEach((index) => { starredIndices.forEach((index) => {
oldData[index].starred = Date.now(); oldData[index].starred = Date.now();
@ -137,7 +136,7 @@ const AlbumList = () => {
}); });
} else { } else {
await unstar(rowData.id, 'album'); await unstar(rowData.id, 'album');
queryClient.setQueryData(['albumList', sortBy, musicFolder], (oldData: any) => { queryClient.setQueryData(['albumList', album.active.filter, musicFolder], (oldData: any) => {
const starredIndices = _.keys(_.pickBy(oldData, { id: rowData.id })); const starredIndices = _.keys(_.pickBy(oldData, { id: rowData.id }));
starredIndices.forEach((index) => { starredIndices.forEach((index) => {
oldData[index].starred = undefined; oldData[index].starred = undefined;
@ -159,15 +158,15 @@ const AlbumList = () => {
<StyledInputPicker <StyledInputPicker
size="sm" size="sm"
width={180} width={180}
defaultValue={sortBy} defaultValue={album.active.filter}
groupBy="role" groupBy="role"
data={sortTypes} data={sortTypes}
cleanable={false} cleanable={false}
placeholder="Sort Type" placeholder="Sort Type"
onChange={async (value: string) => { onChange={async (value: string) => {
await queryClient.cancelQueries(['albumList', sortBy, musicFolder]); await queryClient.cancelQueries(['albumList', album.active.filter, musicFolder]);
setSearchQuery(''); setSearchQuery('');
setSortBy(value); dispatch(setActive({ filter: value }));
}} }}
/> />
<RefreshButton onClick={handleRefresh} size="sm" loading={isRefreshing} width={100} /> <RefreshButton onClick={handleRefresh} size="sm" loading={isRefreshing} width={100} />

26
src/redux/albumSlice.ts

@ -0,0 +1,26 @@
import { createSlice, PayloadAction } from '@reduxjs/toolkit';
export interface AlbumPage {
active: {
filter: string;
};
}
const initialState: AlbumPage = {
active: {
filter: 'random',
},
};
const albumSlice = createSlice({
name: 'album',
initialState,
reducers: {
setActive: (state, action: PayloadAction<{ filter: string }>) => {
state.active.filter = action.payload.filter;
},
},
});
export const { setActive } = albumSlice.actions;
export default albumSlice.reducer;

2
src/redux/store.ts

@ -8,6 +8,7 @@ import playlistReducer from './playlistSlice';
import folderReducer from './folderSlice'; import folderReducer from './folderSlice';
import configReducer from './configSlice'; import configReducer from './configSlice';
import favoriteReducer from './favoriteSlice'; import favoriteReducer from './favoriteSlice';
import albumReducer from './albumSlice';
export const store = configureStore<PlayQueue | any>({ export const store = configureStore<PlayQueue | any>({
reducer: { reducer: {
@ -19,6 +20,7 @@ export const store = configureStore<PlayQueue | any>({
folder: folderReducer, folder: folderReducer,
config: configReducer, config: configReducer,
favorite: favoriteReducer, favorite: favoriteReducer,
album: albumReducer,
}, },
middleware: [forwardToMain], middleware: [forwardToMain],
}); });

Loading…
Cancel
Save