source: pages/index/+Page.tsx@ f727252

main
Last change on this file since f727252 was f727252, checked in by Mihail <mihail2.naumov@…>, 5 months ago

Optimizations & Layout/Text changes

  • Property mode set to 100644
File size: 9.0 KB
Line 
1import React, {useEffect, useState} from 'react';
2import {
3 Container, Box, Typography, Button, IconButton, Dialog, DialogTitle, DialogContent
4} from '@mui/material';
5import CloseIcon from '@mui/icons-material/Close';
6import AutoFixHighIcon from '@mui/icons-material/AutoFixHigh';
7import ListIcon from '@mui/icons-material/List';
8
9import BuildDetailsDialog from '../../components/BuildDetailsDialog';
10import BuildCard from '../../components/BuildCard';
11
12import {onGetApprovedBuilds, onGetAuthState} from '../+Layout.telefunc';
13
14export default function HomePage() {
15 const [data, setData] = useState<any>(null);
16 const [allRanked, setAllRanked] = useState<any[]>([]);
17
18 const [selectedBuildId, setSelectedBuildId] = useState<number | null>(null);
19 const [openRankedPopup, setOpenRankedPopup] = useState(false);
20
21 useEffect(() => {
22 async function loadSite() {
23 try {
24 const [
25 authData,
26 highestRankedBuilds,
27 communityBuilds,
28 fullRankedList
29 ] = await Promise.all([
30 onGetAuthState(),
31 onGetApprovedBuilds({limit: 5, sort: 'rating_desc'}),
32 onGetApprovedBuilds({limit: 12}),
33 onGetApprovedBuilds({limit: 20, sort: 'rating_desc'})
34 ]);
35
36 setData({
37 isLoggedIn: authData.isLoggedIn,
38 userId: authData.userId,
39 prebuilts: highestRankedBuilds,
40 communityBuilds: communityBuilds
41 });
42 setAllRanked(fullRankedList);
43 } catch (error) {
44 console.error("Error loading homepage data:", error);
45 }
46 }
47
48 void loadSite();
49 }, []);
50
51 if (!data) return <Box sx={{p: 10, textAlign: 'center'}}>Loading Forge...</Box>;
52
53 return (
54 <Box>
55 <Box sx={{
56 position: 'relative', height: '500px',
57 display: 'flex', alignItems: 'center', justifyContent: 'center', color: 'white',
58 '&::before': {
59 content: '""', position: 'absolute', top: 0, left: 0, width: '100%', height: '100%',
60 backgroundColor: 'rgba(0,0,0,0.6)'
61 }
62 }}>
63 <Box sx={{position: 'relative', textAlign: 'center', zIndex: 1, p: 2}}>
64 <Typography variant="h2" fontWeight="bold" gutterBottom>Forge Your Ultimate Machine</Typography>
65 <Typography variant="h5" sx={{maxWidth: '800px', mx: 'auto', mb: 1}}>
66 Build, share, discuss, and discover custom PC configurations.
67 </Typography>
68 <Button variant="contained" size="large" href="/forge" startIcon={<AutoFixHighIcon/>}
69 sx={{fontSize: '1.2rem', px: 4, py: 1.5, mt: 2}}>
70 Start Forging
71 </Button>
72 </Box>
73 </Box>
74
75 <Container maxWidth="xl" sx={{mt: 6, mb: 10}}>
76 <Box sx={{
77 mb: 2, borderLeft: '5px solid #ff8201', pl: 1,
78 display: 'flex', justifyContent: 'space-between', alignItems: 'end'
79 }}>
80 <Box>
81 <Typography variant="h4" fontWeight="bold">Hall of Fame</Typography>
82 <Typography variant="subtitle1" color="text.secondary">
83 The highest rated configurations from across the community.
84 </Typography>
85 </Box>
86 <Button variant="outlined" startIcon={<ListIcon/>} onClick={() => setOpenRankedPopup(true)}>
87 Show All Top Ranked
88 </Button>
89 </Box>
90 <Box
91 sx={{
92 display: 'grid',
93 gridTemplateColumns: {
94 xs: '1fr',
95 sm: 'repeat(2, 1fr)',
96 md: 'repeat(3, 1fr)',
97 lg: 'repeat(4, 1fr)',
98 xl: 'repeat(5, 1fr)',
99 },
100 gap: 3,
101 width: '100%',
102 mb: 8
103 }}
104 >
105 {data.prebuilts.map((build: any) => (
106 <BuildCard
107 key={build.id}
108 build={build}
109 onClick={() => setSelectedBuildId(build.id)}
110 />
111 ))}
112 </Box>
113
114 <Box sx={{
115 mb: 2, mt: 2, borderLeft: '5px solid #ff8201', pl: 1,
116 }}>
117 <Typography variant="h4" fontWeight="bold" color="text.primary">Community Forge</Typography>
118 <Typography variant="subtitle1" color="text.secondary" sx={{mb: 2}}>Fresh builds from users around the world.</Typography>
119 </Box>
120 <Box
121 sx={{
122 display: 'grid',
123 gridTemplateColumns: {
124 xs: '1fr',
125 sm: 'repeat(2, 1fr)',
126 md: 'repeat(3, 1fr)',
127 lg: 'repeat(4, 1fr)',
128 xl: 'repeat(5, 1fr)',
129 },
130 gap: 3,
131 width: '100%',
132 }}
133 >
134 {data.communityBuilds.map((build: any) => (
135 <BuildCard
136 key={build.id}
137 build={build}
138 onClick={() => setSelectedBuildId(build.id)}
139 />
140 ))}
141 </Box>
142
143 <Box sx={{display: 'flex', justifyContent: 'center', mt: 6}}>
144 <Button variant="outlined" size="large" href="/completed-builds">View All Community Builds</Button>
145 </Box>
146 </Container>
147
148 <BuildDetailsDialog
149 open={!!selectedBuildId}
150 buildId={selectedBuildId}
151 currentUser={data.userId}
152 onClose={() => setSelectedBuildId(null)}
153 />
154
155 <Dialog open={openRankedPopup} onClose={() => setOpenRankedPopup(false)} maxWidth="xl" fullWidth scroll="paper">
156 <DialogTitle sx={{display: 'flex', justifyContent: 'space-between', alignItems: 'center'}}>
157 Hall of Fame (Top Rated)
158 <IconButton onClick={() => setOpenRankedPopup(false)}><CloseIcon/></IconButton>
159 </DialogTitle>
160 <DialogContent dividers sx={{p: 3}}>
161 <Box
162 sx={{
163 display: 'grid',
164 gridTemplateColumns: {
165 xs: '1fr',
166 sm: 'repeat(2, 1fr)',
167 md: 'repeat(3, 1fr)',
168 lg: 'repeat(4, 1fr)',
169 xl: 'repeat(5, 1fr)',
170 },
171 gap: 3,
172 width: '100%'
173 }}
174 >
175 {allRanked.map((build: any, index: number) => (
176 <Box key={`ranked-${build.id}`} sx={{position: 'relative', width: '100%'}}>
177 <Box sx={{
178 position: 'absolute',
179 top: -10,
180 left: -10,
181 zIndex: 1,
182 width: 35,
183 height: 35,
184 borderRadius: '50%',
185 bgcolor: index < 3 ? '#ff8201' : 'grey.800',
186 color: 'white',
187 display: 'flex',
188 alignItems: 'center',
189 justifyContent: 'center',
190 fontWeight: 'bold',
191 border: '2px solid white',
192 boxShadow: 2,
193 }}>
194 #{index + 1}
195 </Box>
196 <BuildCard
197 build={build}
198 onClick={() => {
199 setOpenRankedPopup(false);
200 setSelectedBuildId(build.id);
201 }}
202 />
203 </Box>
204 ))}
205 </Box>
206 </DialogContent>
207 </Dialog>
208 </Box>
209 );
210}
Note: See TracBrowser for help on using the repository browser.