added ServiceList.tsx for handling individual services

This commit is contained in:
2025-10-10 17:29:17 +05:30
parent 8353ced08c
commit 2c5cb966ad
3 changed files with 59 additions and 86 deletions

View File

@@ -0,0 +1,41 @@
import React from 'react';
import {Grid, Paper, Link, Typography} from '@mui/material';
interface ServiceList {
name: string;
url: string;
desc: string;
external?: boolean;
}
interface ServiceListProps {
serviceList: ServiceList[];
}
const ServiceList: React.FC<ServiceListProps> = ({serviceList}) => {
return (
<Grid container spacing={3} justifyContent="center">
{serviceList.map((s) => (
<Paper
elevation={3}
sx={{p: 2, textAlign: "center", bgcolor: "#2d2d2d", borderRadius: 2}}
>
<Link
href={s.url}
target={s.external ? "_blank" : undefined}
rel="noopener"
underline="none"
sx={{fontSize: 18, fontWeight: "bold", color: "success.main"}}
>
{s.name}
</Link>
<Typography variant="body2" sx={{mt: 1, color: "#ccc"}}>
{s.desc}
</Typography>
</Paper>
))}
</Grid>
);
};
export default ServiceList;

View File

@@ -10,6 +10,7 @@ import { styled } from '@mui/material/styles';
import DevicesRoundedIcon from '@mui/icons-material/DevicesRounded'; import DevicesRoundedIcon from '@mui/icons-material/DevicesRounded';
import EdgesensorHighRoundedIcon from '@mui/icons-material/EdgesensorHighRounded'; import EdgesensorHighRoundedIcon from '@mui/icons-material/EdgesensorHighRounded';
import ViewQuiltRoundedIcon from '@mui/icons-material/ViewQuiltRounded'; import ViewQuiltRoundedIcon from '@mui/icons-material/ViewQuiltRounded';
import ServiceList from "~/components/ServiceList";
const services = { const services = {
media: [ media: [
@@ -32,26 +33,34 @@ const items = [
{ {
icon: <ViewQuiltRoundedIcon />, icon: <ViewQuiltRoundedIcon />,
title: 'Dashboard', title: 'Dashboard',
serviceList: [
{ name: "Jellyseerr", url: "http://jellyseerr.aetoskia.com", desc: "Summon films and series from the digital void.", external: true },
{ name: "Sonarr", url: "http://sonarr.aetoskia.com", desc: "Keep the endless chronicles of TV under iron control.", external: true },
{ name: "Radarr", url: "http://radarr.aetoskia.com", desc: "Command the legions of cinema, enforce cinematic order.", external: true },
{ name: "qBit", url: "http://qbit.aetoskia.com", desc: "Torrent war engine, fetching data across the nether realms.", external: true },
],
description: description:
'This item could provide a snapshot of the most important metrics or data points related to the product.', 'This item could provide a snapshot of the most important metrics or data points related to the product.',
imageLight: "url('/extended_sigil.png')",
imageDark: "url('/extended_sigil.png')",
}, },
{ {
icon: <EdgesensorHighRoundedIcon />, icon: <EdgesensorHighRoundedIcon />,
title: 'Mobile integration', title: 'Mobile integration',
serviceList: [
{ name: "Gitea", url: "http://gitea.aetoskia.com", desc: "Forge and safeguard code like a sacred relic.", external: true },
{ name: "Registry", url: "http://registry.aetoskia.com", desc: "Monitor core constructs of the digital empire.", external: true },
{ name: "Drone", url: "http://drone.aetoskia.com", desc: "Automaton architect, building pipelines of perfection.", external: true },
],
description: description:
'This item could provide information about the mobile app version of the product.', 'This item could provide information about the mobile app version of the product.',
imageLight: "url('/extended_sigil.png')",
imageDark: "url('/extended_sigil.png')",
}, },
{ {
icon: <DevicesRoundedIcon />, icon: <DevicesRoundedIcon />,
title: 'Available on all platforms', title: 'Available on all platforms',
serviceList:[
{ name: "Portainer", url: "http://portainer.aetoskia.com", desc: "Oversee the fleet of containers with unyielding vigilance.", external: true },
],
description: description:
'This item could let users know the product is available on all platforms, such as web, mobile, and desktop.', 'This item could let users know the product is available on all platforms, such as web, mobile, and desktop.',
imageLight: "url('/extended_sigil.png')",
imageDark: "url('/extended_sigil.png')",
}, },
]; ];
@@ -114,26 +123,7 @@ export function MobileLayout({
))} ))}
</Box> </Box>
<Card variant="outlined"> <Card variant="outlined">
<Box <ServiceList serviceList={selectedFeature.serviceList} />
sx={(theme) => ({
mb: 2,
backgroundSize: 'cover',
backgroundPosition: 'center',
minHeight: 280,
backgroundImage: 'var(--items-imageLight)',
...theme.applyStyles('dark', {
backgroundImage: 'var(--items-imageDark)',
}),
})}
style={
items[selectedItemIndex]
? ({
'--items-imageLight': items[selectedItemIndex].imageLight,
'--items-imageDark': items[selectedItemIndex].imageDark,
} as any)
: {}
}
/>
<Box sx={{ px: 2, pb: 2 }}> <Box sx={{ px: 2, pb: 2 }}>
<Typography <Typography
gutterBottom gutterBottom
@@ -237,32 +227,11 @@ export default function Services() {
<Card <Card
variant="outlined" variant="outlined"
sx={{ sx={{
height: '100%',
width: '100%',
display: { xs: 'none', sm: 'flex' }, display: { xs: 'none', sm: 'flex' },
pointerEvents: 'none', pointerEvents: 'none',
}} }}
> >
<Box <ServiceList serviceList={selectedFeature.serviceList} />
sx={(theme) => ({
m: 'auto',
width: 420,
height: 500,
backgroundSize: 'contain',
backgroundImage: 'var(--items-imageLight)',
...theme.applyStyles('dark', {
backgroundImage: 'var(--items-imageDark)',
}),
})}
style={
items[selectedItemIndex]
? ({
'--items-imageLight': items[selectedItemIndex].imageLight,
'--items-imageDark': items[selectedItemIndex].imageDark,
} as any)
: {}
}
/>
</Card> </Card>
</Box> </Box>
</Box> </Box>

View File

@@ -6,6 +6,7 @@ import Link from "@mui/material/Link";
import Grid from "@mui/material/Grid"; import Grid from "@mui/material/Grid";
import Paper from "@mui/material/Paper"; import Paper from "@mui/material/Paper";
import Services from "~/components/Services"; import Services from "~/components/Services";
import ServiceList from "~/components/ServiceList";
export function meta() { export function meta() {
return [ return [
@@ -52,44 +53,6 @@ export default function Home() {
<Box sx={{ height: "60vh", overflowY: "auto", p: 2 }}> <Box sx={{ height: "60vh", overflowY: "auto", p: 2 }}>
<Services /> <Services />
<Container
maxWidth="lg"
sx={{ bgcolor: "#1a1a1a", borderRadius: 3, p: 3, boxShadow: 6 }}
>
{Object.entries(services).map(([sectionName, serviceList]) => (
<React.Fragment key={sectionName}>
<Typography
variant="h5"
align="center"
sx={{ color: "warning.main", mt: 4, mb: 2 }}
>
{sectionName.charAt(0).toUpperCase() + sectionName.slice(1)} Services
</Typography>
<Grid container spacing={3} justifyContent="center">
{serviceList.map((s) => (
<Paper
key={s.name}
elevation={3}
sx={{ p: 2, textAlign: "center", bgcolor: "#2d2d2d", borderRadius: 2 }}
>
<Link
href={s.url}
target={s.external ? "_blank" : undefined}
rel="noopener"
underline="none"
sx={{ fontSize: 18, fontWeight: "bold", color: "success.main" }}
>
{s.name}
</Link>
<Typography variant="body2" sx={{ mt: 1, color: "#ccc" }}>
{s.desc}
</Typography>
</Paper>
))}
</Grid>
</React.Fragment>
))}
</Container>
</Box> </Box>
</Box> </Box>
</Container> </Container>