feat: adjust proxy page
This commit is contained in:
parent
4979a472de
commit
5fcd25506e
@ -1,15 +1,12 @@
|
|||||||
import { useState } from "react";
|
import { useState } from "react";
|
||||||
import { Virtuoso } from "react-virtuoso";
|
import { Virtuoso } from "react-virtuoso";
|
||||||
import {
|
import {
|
||||||
alpha,
|
|
||||||
Box,
|
Box,
|
||||||
Collapse,
|
Collapse,
|
||||||
Divider,
|
Divider,
|
||||||
IconButton,
|
IconButton,
|
||||||
List,
|
List,
|
||||||
ListItem,
|
ListItem,
|
||||||
ListItemButton,
|
|
||||||
ListItemIcon,
|
|
||||||
ListItemText,
|
ListItemText,
|
||||||
} from "@mui/material";
|
} from "@mui/material";
|
||||||
import {
|
import {
|
||||||
@ -18,53 +15,11 @@ import {
|
|||||||
ExpandMoreRounded,
|
ExpandMoreRounded,
|
||||||
MyLocationRounded,
|
MyLocationRounded,
|
||||||
NetworkCheckRounded,
|
NetworkCheckRounded,
|
||||||
CheckCircleOutlineRounded,
|
|
||||||
} from "@mui/icons-material";
|
} from "@mui/icons-material";
|
||||||
import { updateProxy } from "../services/api";
|
import { updateProxy } from "../services/api";
|
||||||
import { ApiType } from "../services/types";
|
import { ApiType } from "../services/types";
|
||||||
import { getProfiles, patchProfile } from "../services/cmds";
|
import { getProfiles, patchProfile } from "../services/cmds";
|
||||||
|
import ProxyItem from "./proxy-item";
|
||||||
interface ItemProps {
|
|
||||||
proxy: ApiType.ProxyItem;
|
|
||||||
selected: boolean;
|
|
||||||
onClick?: (name: string) => void;
|
|
||||||
}
|
|
||||||
|
|
||||||
const Item = ({ proxy, selected, onClick }: ItemProps) => {
|
|
||||||
return (
|
|
||||||
<ListItem sx={{ py: 0, pl: 4 }}>
|
|
||||||
<ListItemButton
|
|
||||||
dense
|
|
||||||
selected={selected}
|
|
||||||
onClick={() => onClick?.(proxy.name)}
|
|
||||||
sx={[
|
|
||||||
{
|
|
||||||
borderRadius: 1,
|
|
||||||
},
|
|
||||||
({ palette: { mode, primary } }) => {
|
|
||||||
const bgcolor =
|
|
||||||
mode === "light"
|
|
||||||
? alpha(primary.main, 0.15)
|
|
||||||
: alpha(primary.main, 0.35);
|
|
||||||
const color = mode === "light" ? primary.main : primary.light;
|
|
||||||
|
|
||||||
return {
|
|
||||||
"&.Mui-selected": { bgcolor },
|
|
||||||
"&.Mui-selected .MuiListItemText-secondary": { color },
|
|
||||||
};
|
|
||||||
},
|
|
||||||
]}
|
|
||||||
>
|
|
||||||
<ListItemText title={proxy.name} secondary={proxy.name} />
|
|
||||||
<ListItemIcon
|
|
||||||
sx={{ justifyContent: "flex-end", color: "primary.main" }}
|
|
||||||
>
|
|
||||||
{selected && <CheckCircleOutlineRounded sx={{ fontSize: 16 }} />}
|
|
||||||
</ListItemIcon>
|
|
||||||
</ListItemButton>
|
|
||||||
</ListItem>
|
|
||||||
);
|
|
||||||
};
|
|
||||||
|
|
||||||
interface Props {
|
interface Props {
|
||||||
group: ApiType.ProxyGroupItem;
|
group: ApiType.ProxyGroupItem;
|
||||||
@ -146,9 +101,10 @@ const ProxyGroup = ({ group }: Props) => {
|
|||||||
style={{ height: "400px", marginBottom: "4px" }}
|
style={{ height: "400px", marginBottom: "4px" }}
|
||||||
totalCount={proxies.length}
|
totalCount={proxies.length}
|
||||||
itemContent={(index) => (
|
itemContent={(index) => (
|
||||||
<Item
|
<ProxyItem
|
||||||
proxy={proxies[index]}
|
proxy={proxies[index]}
|
||||||
selected={proxies[index].name === now}
|
selected={proxies[index].name === now}
|
||||||
|
sx={{ py: 0, pl: 4 }}
|
||||||
onClick={onUpdate}
|
onClick={onUpdate}
|
||||||
/>
|
/>
|
||||||
)}
|
)}
|
||||||
@ -160,10 +116,11 @@ const ProxyGroup = ({ group }: Props) => {
|
|||||||
sx={{ maxHeight: "400px", overflow: "auto", mb: "4px" }}
|
sx={{ maxHeight: "400px", overflow: "auto", mb: "4px" }}
|
||||||
>
|
>
|
||||||
{proxies.map((proxy) => (
|
{proxies.map((proxy) => (
|
||||||
<Item
|
<ProxyItem
|
||||||
key={proxy.name}
|
key={proxy.name}
|
||||||
proxy={proxy}
|
proxy={proxy}
|
||||||
selected={proxy.name === now}
|
selected={proxy.name === now}
|
||||||
|
sx={{ py: 0, pl: 4 }}
|
||||||
onClick={onUpdate}
|
onClick={onUpdate}
|
||||||
/>
|
/>
|
||||||
))}
|
))}
|
||||||
|
58
src/components/proxy-item.tsx
Normal file
58
src/components/proxy-item.tsx
Normal file
@ -0,0 +1,58 @@
|
|||||||
|
import { CheckCircleOutlineRounded } from "@mui/icons-material";
|
||||||
|
import {
|
||||||
|
alpha,
|
||||||
|
ListItem,
|
||||||
|
ListItemButton,
|
||||||
|
ListItemIcon,
|
||||||
|
ListItemText,
|
||||||
|
SxProps,
|
||||||
|
Theme,
|
||||||
|
} from "@mui/material";
|
||||||
|
import { ApiType } from "../services/types";
|
||||||
|
|
||||||
|
interface Props {
|
||||||
|
proxy: ApiType.ProxyItem;
|
||||||
|
selected: boolean;
|
||||||
|
sx?: SxProps<Theme>;
|
||||||
|
onClick?: (name: string) => void;
|
||||||
|
}
|
||||||
|
|
||||||
|
const ProxyItem = (props: Props) => {
|
||||||
|
const { proxy, selected, sx, onClick } = props;
|
||||||
|
|
||||||
|
return (
|
||||||
|
<ListItem sx={sx}>
|
||||||
|
<ListItemButton
|
||||||
|
dense
|
||||||
|
selected={selected}
|
||||||
|
onClick={() => onClick?.(proxy.name)}
|
||||||
|
sx={[
|
||||||
|
{
|
||||||
|
borderRadius: 1,
|
||||||
|
},
|
||||||
|
({ palette: { mode, primary } }) => {
|
||||||
|
const bgcolor =
|
||||||
|
mode === "light"
|
||||||
|
? alpha(primary.main, 0.15)
|
||||||
|
: alpha(primary.main, 0.35);
|
||||||
|
const color = mode === "light" ? primary.main : primary.light;
|
||||||
|
|
||||||
|
return {
|
||||||
|
"&.Mui-selected": { bgcolor },
|
||||||
|
"&.Mui-selected .MuiListItemText-secondary": { color },
|
||||||
|
};
|
||||||
|
},
|
||||||
|
]}
|
||||||
|
>
|
||||||
|
<ListItemText title={proxy.name} secondary={proxy.name} />
|
||||||
|
<ListItemIcon
|
||||||
|
sx={{ justifyContent: "flex-end", color: "primary.main" }}
|
||||||
|
>
|
||||||
|
{selected && <CheckCircleOutlineRounded sx={{ fontSize: 16 }} />}
|
||||||
|
</ListItemIcon>
|
||||||
|
</ListItemButton>
|
||||||
|
</ListItem>
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
|
export default ProxyItem;
|
@ -3,11 +3,12 @@ import { useEffect } from "react";
|
|||||||
import { Box, List, Paper, Typography } from "@mui/material";
|
import { Box, List, Paper, Typography } from "@mui/material";
|
||||||
import { getProxies } from "../services/api";
|
import { getProxies } from "../services/api";
|
||||||
import ProxyGroup from "../components/proxy-group";
|
import ProxyGroup from "../components/proxy-group";
|
||||||
|
import ProxyItem from "../components/proxy-item";
|
||||||
|
|
||||||
const ProxyPage = () => {
|
const ProxyPage = () => {
|
||||||
const { mutate } = useSWRConfig();
|
const { mutate } = useSWRConfig();
|
||||||
const { data: proxiesData } = useSWR("getProxies", getProxies);
|
const { data: proxiesData } = useSWR("getProxies", getProxies);
|
||||||
const { groups = [] } = proxiesData ?? {};
|
const { groups = [], proxies = [] } = proxiesData ?? {};
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
// fix the empty proxies on the first sight
|
// fix the empty proxies on the first sight
|
||||||
@ -20,18 +21,31 @@ const ProxyPage = () => {
|
|||||||
return (
|
return (
|
||||||
<Box sx={{ width: 0.9, maxWidth: "850px", mx: "auto", mb: 2 }}>
|
<Box sx={{ width: 0.9, maxWidth: "850px", mx: "auto", mb: 2 }}>
|
||||||
<Typography variant="h4" component="h1" sx={{ py: 2 }}>
|
<Typography variant="h4" component="h1" sx={{ py: 2 }}>
|
||||||
Proxy Groups
|
{groups.length ? "Proxy Groups" : "Proxies"}
|
||||||
</Typography>
|
</Typography>
|
||||||
|
|
||||||
{groups.length > 0 && (
|
<Paper sx={{ borderRadius: 1, boxShadow: 2 }}>
|
||||||
<Paper sx={{ borderRadius: 1, boxShadow: 2 }}>
|
{groups.length > 0 && (
|
||||||
<List>
|
<List>
|
||||||
{groups.map((group) => (
|
{groups.map((group) => (
|
||||||
<ProxyGroup key={group.name} group={group} />
|
<ProxyGroup key={group.name} group={group} />
|
||||||
))}
|
))}
|
||||||
</List>
|
</List>
|
||||||
</Paper>
|
)}
|
||||||
)}
|
|
||||||
|
{!groups.length && (
|
||||||
|
<List>
|
||||||
|
{Object.values(proxies).map((proxy) => (
|
||||||
|
<ProxyItem
|
||||||
|
key={proxy.name}
|
||||||
|
proxy={proxy}
|
||||||
|
selected={false}
|
||||||
|
sx={{ py: 0, px: 2 }}
|
||||||
|
/>
|
||||||
|
))}
|
||||||
|
</List>
|
||||||
|
)}
|
||||||
|
</Paper>
|
||||||
</Box>
|
</Box>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
Loading…
Reference in New Issue
Block a user