Major UI improvements

This commit is contained in:
luke-hagar-sp
2022-08-01 16:07:34 -05:00
parent 5cad4e9526
commit 4d1ffbfe9a
5 changed files with 118 additions and 17 deletions

27
package-lock.json generated
View File

@@ -35,6 +35,7 @@
"qs": "^6.11.0", "qs": "^6.11.0",
"react": "^18.2.0", "react": "^18.2.0",
"react-dom": "^18.1.0", "react-dom": "^18.1.0",
"react-icons": "^4.4.0",
"react-infinite-scroller": "^1.2.6", "react-infinite-scroller": "^1.2.6",
"react-intl": "^6.0.5", "react-intl": "^6.0.5",
"react-jinke-music-player": "^4.24.2", "react-jinke-music-player": "^4.24.2",
@@ -14119,9 +14120,9 @@
} }
}, },
"node_modules/plex-api-oauth": { "node_modules/plex-api-oauth": {
"version": "1.1.114", "version": "1.1.116",
"resolved": "https://registry.npmjs.org/plex-api-oauth/-/plex-api-oauth-1.1.114.tgz", "resolved": "https://registry.npmjs.org/plex-api-oauth/-/plex-api-oauth-1.1.116.tgz",
"integrity": "sha512-oru0+xa/65fVQNJrt236VhYacGO2y5o8dgkqVhR2yf79txNESVIP+5We/HLeaRflEV+kuP5O2zuUg8tyZQ0IWQ==", "integrity": "sha512-bj509pQ4YVvkn1kytMUd8bvMqOAn7Q1VunGn+abX/yDCTjF7z9H3qyDLNBRNy2VhQ7lGSSFQE4LHJ//NXJZxDA==",
"dependencies": { "dependencies": {
"axios": "^0.27.2", "axios": "^0.27.2",
"plex-oauth": "^2.0.2", "plex-oauth": "^2.0.2",
@@ -15186,6 +15187,14 @@
"react-dom": ">= 16.3.0" "react-dom": ">= 16.3.0"
} }
}, },
"node_modules/react-icons": {
"version": "4.4.0",
"resolved": "https://registry.npmjs.org/react-icons/-/react-icons-4.4.0.tgz",
"integrity": "sha512-fSbvHeVYo/B5/L4VhB7sBA1i2tS8MkT0Hb9t2H1AVPkwGfVHLJCqyr2Py9dKMxsyM63Eng1GkdZfbWj+Fmv8Rg==",
"peerDependencies": {
"react": "*"
}
},
"node_modules/react-infinite-scroller": { "node_modules/react-infinite-scroller": {
"version": "1.2.6", "version": "1.2.6",
"resolved": "https://registry.npmjs.org/react-infinite-scroller/-/react-infinite-scroller-1.2.6.tgz", "resolved": "https://registry.npmjs.org/react-infinite-scroller/-/react-infinite-scroller-1.2.6.tgz",
@@ -29230,9 +29239,9 @@
"integrity": "sha512-Igl37++MSa+4H8LNP3Ene9GU0e1YypmXvFVNvVUwoAx44e74jbUlJXy4Q5rLSBisn0O2lBKdE6VkFIwrDl+UnQ==" "integrity": "sha512-Igl37++MSa+4H8LNP3Ene9GU0e1YypmXvFVNvVUwoAx44e74jbUlJXy4Q5rLSBisn0O2lBKdE6VkFIwrDl+UnQ=="
}, },
"plex-api-oauth": { "plex-api-oauth": {
"version": "1.1.114", "version": "1.1.116",
"resolved": "https://registry.npmjs.org/plex-api-oauth/-/plex-api-oauth-1.1.114.tgz", "resolved": "https://registry.npmjs.org/plex-api-oauth/-/plex-api-oauth-1.1.116.tgz",
"integrity": "sha512-oru0+xa/65fVQNJrt236VhYacGO2y5o8dgkqVhR2yf79txNESVIP+5We/HLeaRflEV+kuP5O2zuUg8tyZQ0IWQ==", "integrity": "sha512-bj509pQ4YVvkn1kytMUd8bvMqOAn7Q1VunGn+abX/yDCTjF7z9H3qyDLNBRNy2VhQ7lGSSFQE4LHJ//NXJZxDA==",
"requires": { "requires": {
"axios": "^0.27.2", "axios": "^0.27.2",
"plex-oauth": "^2.0.2", "plex-oauth": "^2.0.2",
@@ -29968,6 +29977,12 @@
"prop-types": "^15.8.1" "prop-types": "^15.8.1"
} }
}, },
"react-icons": {
"version": "4.4.0",
"resolved": "https://registry.npmjs.org/react-icons/-/react-icons-4.4.0.tgz",
"integrity": "sha512-fSbvHeVYo/B5/L4VhB7sBA1i2tS8MkT0Hb9t2H1AVPkwGfVHLJCqyr2Py9dKMxsyM63Eng1GkdZfbWj+Fmv8Rg==",
"requires": {}
},
"react-infinite-scroller": { "react-infinite-scroller": {
"version": "1.2.6", "version": "1.2.6",
"resolved": "https://registry.npmjs.org/react-infinite-scroller/-/react-infinite-scroller-1.2.6.tgz", "resolved": "https://registry.npmjs.org/react-infinite-scroller/-/react-infinite-scroller-1.2.6.tgz",

View File

@@ -47,6 +47,7 @@
"start:preload": "cross-env NODE_ENV=development TS_NODE_TRANSPILE_ONLY=true webpack --config ./.erb/configs/webpack.config.preload.dev.ts", "start:preload": "cross-env NODE_ENV=development TS_NODE_TRANSPILE_ONLY=true webpack --config ./.erb/configs/webpack.config.preload.dev.ts",
"start:renderer": "cross-env NODE_ENV=development TS_NODE_TRANSPILE_ONLY=true webpack serve --config ./.erb/configs/webpack.config.renderer.dev.ts", "start:renderer": "cross-env NODE_ENV=development TS_NODE_TRANSPILE_ONLY=true webpack serve --config ./.erb/configs/webpack.config.renderer.dev.ts",
"test": "jest", "test": "jest",
"predeploy": "npm run build",
"deploy": "gh-pages -d './release/app/dist/renderer'" "deploy": "gh-pages -d './release/app/dist/renderer'"
}, },
"lint-staged": { "lint-staged": {
@@ -137,6 +138,7 @@
"qs": "^6.11.0", "qs": "^6.11.0",
"react": "^18.2.0", "react": "^18.2.0",
"react-dom": "^18.1.0", "react-dom": "^18.1.0",
"react-icons": "^4.4.0",
"react-infinite-scroller": "^1.2.6", "react-infinite-scroller": "^1.2.6",
"react-intl": "^6.0.5", "react-intl": "^6.0.5",
"react-jinke-music-player": "^4.24.2", "react-jinke-music-player": "^4.24.2",

View File

@@ -70,3 +70,11 @@ a:hover {
.site-layout .site-layout-background { .site-layout .site-layout-background {
background: #fff; background: #fff;
} }
.container {
-ms-overflow-style: none; /* Internet Explorer 10+ */
scrollbar-width: none; /* Firefox */
}
.container::-webkit-scrollbar {
display: none; /* Safari and Chrome */
}

View File

@@ -22,6 +22,8 @@ import ListItemText from '@mui/material/ListItemText';
import HomeIcon from '@mui/icons-material/Home'; import HomeIcon from '@mui/icons-material/Home';
import LibraryMusicIcon from '@mui/icons-material/LibraryMusic'; import LibraryMusicIcon from '@mui/icons-material/LibraryMusic';
import FeaturedPlayListIcon from '@mui/icons-material/FeaturedPlayList'; import FeaturedPlayListIcon from '@mui/icons-material/FeaturedPlayList';
import AlbumIcon from '@mui/icons-material/Album';
import MusicNoteIcon from '@mui/icons-material/MusicNote';
import SettingsIcon from '@mui/icons-material/Settings'; import SettingsIcon from '@mui/icons-material/Settings';
import LockOpenIcon from '@mui/icons-material/LockOpen'; import LockOpenIcon from '@mui/icons-material/LockOpen';
import DarkModeIcon from '@mui/icons-material/DarkMode'; import DarkModeIcon from '@mui/icons-material/DarkMode';
@@ -49,6 +51,12 @@ import {
Stack, Stack,
ImageList, ImageList,
ImageListItem, ImageListItem,
Skeleton,
Snackbar,
Alert,
Grow,
Slide,
SnackbarContent,
} from '@mui/material'; } from '@mui/material';
import Table from '@mui/material/Table'; import Table from '@mui/material/Table';
import TableBody from '@mui/material/TableBody'; import TableBody from '@mui/material/TableBody';
@@ -77,6 +85,8 @@ const drawerWidth = 240;
const iconindex = { const iconindex = {
Home: <HomeIcon />, Home: <HomeIcon />,
Library: <LibraryMusicIcon />, Library: <LibraryMusicIcon />,
Album: <AlbumIcon />,
Song: <MusicNoteIcon />,
Playlists: <FeaturedPlayListIcon />, Playlists: <FeaturedPlayListIcon />,
Settings: <SettingsIcon />, Settings: <SettingsIcon />,
}; };
@@ -115,6 +125,7 @@ function App() {
const [query, setQuery] = useState(''); const [query, setQuery] = useState('');
const [pageNumber, setPageNumber] = useState(0); const [pageNumber, setPageNumber] = useState(0);
const [isLoading, setIsLoading] = useState(false); const [isLoading, setIsLoading] = useState(false);
const [isRefreshing, setIsRefreshing] = useState(true);
const [topic, setTopic] = useState(); const [topic, setTopic] = useState();
function handleSearch(event) { function handleSearch(event) {
@@ -154,6 +165,10 @@ function App() {
console.log('Theme'); console.log('Theme');
console.log(activeTheme); console.log(activeTheme);
function SlideTransition(props) {
return <Slide {...props} direction="left" />;
}
async function PlexLoginButton() { async function PlexLoginButton() {
const tempPlexTVAuthToken = await PlexLogin(plexClientInformation); const tempPlexTVAuthToken = await PlexLogin(plexClientInformation);
const tempPlexTVUserData = await GetPlexUserData( const tempPlexTVUserData = await GetPlexUserData(
@@ -195,6 +210,7 @@ function App() {
setPlexServers(tempPlexServers); setPlexServers(tempPlexServers);
setPlexTVUserData(tempPlexTVUserData); setPlexTVUserData(tempPlexTVUserData);
setPlexLibraries(tempPlexLibraries); setPlexLibraries(tempPlexLibraries);
setIsRefreshing(false);
} }
// useEffect(() => { // useEffect(() => {
@@ -211,6 +227,21 @@ function App() {
// setSearchData({ searchItems, searchHasMore, searchLoading, searchError }); // setSearchData({ searchItems, searchHasMore, searchLoading, searchError });
// }, [pageNumber, topic, query, plexSessionData]); // }, [pageNumber, topic, query, plexSessionData]);
function ShowArtist(Obj) {
setActiveArtist(Obj);
setActivePage(7);
}
function ShowAlbum(Obj) {
setActiveAlbum(Obj);
setActivePage(8);
}
function ShowPlaylist(Obj) {
setActivePlaylist(Obj);
setActivePage(9);
}
async function UpdateLibrary() { async function UpdateLibrary() {
setIsLoading(true); setIsLoading(true);
let returnObject = await GetLibraryPages( let returnObject = await GetLibraryPages(
@@ -218,7 +249,7 @@ function App() {
plexLibraries, plexLibraries,
topic, topic,
pageNumber, pageNumber,
50 100
); );
console.log(returnObject); console.log(returnObject);
returnObject.items = [...new Set([...libraryItems, ...returnObject.items])]; returnObject.items = [...new Set([...libraryItems, ...returnObject.items])];
@@ -254,6 +285,7 @@ function App() {
}, [pageNumber, plexServers, plexLibraries, topic]); }, [pageNumber, plexServers, plexLibraries, topic]);
useEffect(() => { useEffect(() => {
setIsRefreshing(true);
Refresh(); Refresh();
}, []); }, []);
@@ -332,6 +364,7 @@ function App() {
<List> <List>
<ListItem key="HomeTab" disablePadding> <ListItem key="HomeTab" disablePadding>
<ListItemButton <ListItemButton
selected={activePage === 0}
onClick={() => { onClick={() => {
setActivePage(0); setActivePage(0);
setPageNumber(0); setPageNumber(0);
@@ -344,6 +377,7 @@ function App() {
<Divider /> <Divider />
<ListItem key="LibrariesTab" disablePadding> <ListItem key="LibrariesTab" disablePadding>
<ListItemButton <ListItemButton
selected={activePage === 1}
onClick={() => { onClick={() => {
setActivePage(1); setActivePage(1);
setPageNumber(0); setPageNumber(0);
@@ -356,6 +390,7 @@ function App() {
<Divider /> <Divider />
<ListItem key="ArtistsTab" disablePadding> <ListItem key="ArtistsTab" disablePadding>
<ListItemButton <ListItemButton
selected={topic === 'artists' && activePage === 2}
onClick={() => { onClick={() => {
setActivePage(2); setActivePage(2);
topic !== 'artists' && setLibraryItems([]); topic !== 'artists' && setLibraryItems([]);
@@ -370,6 +405,7 @@ function App() {
<Divider /> <Divider />
<ListItem key="AlbumsTab" disablePadding> <ListItem key="AlbumsTab" disablePadding>
<ListItemButton <ListItemButton
selected={topic === 'albums' && activePage === 2}
onClick={() => { onClick={() => {
setActivePage(2); setActivePage(2);
topic !== 'albums' && setLibraryItems([]); topic !== 'albums' && setLibraryItems([]);
@@ -377,13 +413,14 @@ function App() {
setTopic('albums'); setTopic('albums');
}} }}
> >
<ListItemIcon>{iconindex.Library}</ListItemIcon> <ListItemIcon>{iconindex.Album}</ListItemIcon>
<ListItemText primary="Albums" /> <ListItemText primary="Albums" />
</ListItemButton> </ListItemButton>
</ListItem> </ListItem>
<Divider /> <Divider />
<ListItem key="SongsTab" disablePadding> <ListItem key="SongsTab" disablePadding>
<ListItemButton <ListItemButton
selected={topic === 'songs' && activePage === 2}
onClick={() => { onClick={() => {
setActivePage(2); setActivePage(2);
topic !== 'songs' && setLibraryItems([]); topic !== 'songs' && setLibraryItems([]);
@@ -391,13 +428,14 @@ function App() {
setTopic('songs'); setTopic('songs');
}} }}
> >
<ListItemIcon>{iconindex.Library}</ListItemIcon> <ListItemIcon>{iconindex.Song}</ListItemIcon>
<ListItemText primary="Songs" /> <ListItemText primary="Songs" />
</ListItemButton> </ListItemButton>
</ListItem> </ListItem>
<Divider /> <Divider />
<ListItem key="PlaylistsTab" disablePadding> <ListItem key="PlaylistsTab" disablePadding>
<ListItemButton <ListItemButton
selected={activePage === 5}
onClick={() => { onClick={() => {
setActivePage(5); setActivePage(5);
setPageNumber(0); setPageNumber(0);
@@ -410,6 +448,7 @@ function App() {
<Divider /> <Divider />
<ListItem key="SettingsTab" disablePadding> <ListItem key="SettingsTab" disablePadding>
<ListItemButton <ListItemButton
selected={activePage === 6}
onClick={() => { onClick={() => {
setActivePage(6); setActivePage(6);
setPageNumber(0); setPageNumber(0);
@@ -425,7 +464,7 @@ function App() {
hidden={isHidden(0)} hidden={isHidden(0)}
component="main" component="main"
sx={{ sx={{
overflow: 'hidden', overflow: 'auto',
flexGrow: 1, flexGrow: 1,
maxWidth: self.innerWidth - drawerWidth, maxWidth: self.innerWidth - drawerWidth,
bgcolor: 'background.default', bgcolor: 'background.default',
@@ -444,9 +483,10 @@ function App() {
<div> <div>
{Obj.title} {Obj.title}
<ImageList <ImageList
gap={15}
direction="row" direction="row"
sx={{ sx={{
overflow: 'scroller', 'overflow-x': 'scroll',
flexGrow: 1, flexGrow: 1,
margin: 4, margin: 4,
gridAutoFlow: 'column', gridAutoFlow: 'column',
@@ -463,6 +503,7 @@ function App() {
component="img" component="img"
height="240" height="240"
width="240" width="240"
loading="lazy"
image={listItem.thumb || NoArt} image={listItem.thumb || NoArt}
onError={({ currentTarget }) => { onError={({ currentTarget }) => {
currentTarget.onerror = null; // prevents looping currentTarget.onerror = null; // prevents looping
@@ -470,7 +511,13 @@ function App() {
}} }}
/> />
<CardContent> <CardContent>
<Typography noWrap>{listItem.title}</Typography> <Typography
variant="h6"
justifyContent="center"
noWrap
>
{listItem.title}
</Typography>
</CardContent> </CardContent>
</Card> </Card>
</ImageListItem> </ImageListItem>
@@ -590,6 +637,19 @@ function App() {
</Grid> </Grid>
); );
})} })}
{isLoading &&
[0, 1, 2, 3].map((Obj, index) => {
return (
<Grid item xs="auto" key={`Skeleton${index}`}>
<Skeleton
animation="wave"
variant="rectangular"
width={240}
height={240}
/>
</Grid>
);
})}
</Grid> </Grid>
</Box> </Box>
</Box> </Box>
@@ -662,7 +722,10 @@ function App() {
action={ action={
<div> <div>
<Button <Button
onClick={() => Refresh()} onClick={() => {
setIsRefreshing(true);
Refresh();
}}
variant="outlined" variant="outlined"
sx={{ margin: 1 }} sx={{ margin: 1 }}
> >
@@ -827,6 +890,14 @@ function App() {
</Grid> </Grid>
</Box> </Box>
</Box> </Box>
<Snackbar
TransitionComponent={SlideTransition}
open={isRefreshing}
autoHideDuration={10000}
anchorOrigin={{ vertical: 'top', horizontal: 'right' }}
>
<Alert severity="info">Refreshing Data</Alert>
</Snackbar>
</CssBaseline> </CssBaseline>
</ThemeProvider> </ThemeProvider>
); );

View File

@@ -7787,9 +7787,9 @@
"version" "1.1.0" "version" "1.1.0"
"plex-api-oauth@^1.0.4": "plex-api-oauth@^1.0.4":
"integrity" "sha512-oru0+xa/65fVQNJrt236VhYacGO2y5o8dgkqVhR2yf79txNESVIP+5We/HLeaRflEV+kuP5O2zuUg8tyZQ0IWQ==" "integrity" "sha512-bj509pQ4YVvkn1kytMUd8bvMqOAn7Q1VunGn+abX/yDCTjF7z9H3qyDLNBRNy2VhQ7lGSSFQE4LHJ//NXJZxDA=="
"resolved" "https://registry.npmjs.org/plex-api-oauth/-/plex-api-oauth-1.1.114.tgz" "resolved" "https://registry.npmjs.org/plex-api-oauth/-/plex-api-oauth-1.1.116.tgz"
"version" "1.1.114" "version" "1.1.116"
dependencies: dependencies:
"axios" "^0.27.2" "axios" "^0.27.2"
"plex-oauth" "^2.0.2" "plex-oauth" "^2.0.2"
@@ -8342,6 +8342,11 @@
"clsx" "^1.1.1" "clsx" "^1.1.1"
"prop-types" "^15.8.1" "prop-types" "^15.8.1"
"react-icons@^4.4.0":
"integrity" "sha512-fSbvHeVYo/B5/L4VhB7sBA1i2tS8MkT0Hb9t2H1AVPkwGfVHLJCqyr2Py9dKMxsyM63Eng1GkdZfbWj+Fmv8Rg=="
"resolved" "https://registry.npmjs.org/react-icons/-/react-icons-4.4.0.tgz"
"version" "4.4.0"
"react-infinite-scroller@^1.2.6": "react-infinite-scroller@^1.2.6":
"integrity" "sha512-mGdMyOD00YArJ1S1F3TVU9y4fGSfVVl6p5gh/Vt4u99CJOptfVu/q5V/Wlle72TMgYlBwIhbxK5wF0C/R33PXQ==" "integrity" "sha512-mGdMyOD00YArJ1S1F3TVU9y4fGSfVVl6p5gh/Vt4u99CJOptfVu/q5V/Wlle72TMgYlBwIhbxK5wF0C/R33PXQ=="
"resolved" "https://registry.npmjs.org/react-infinite-scroller/-/react-infinite-scroller-1.2.6.tgz" "resolved" "https://registry.npmjs.org/react-infinite-scroller/-/react-infinite-scroller-1.2.6.tgz"