Skip to content

Commit 1530c07

Browse files
committed
Merge branch 'feature/Change-Request-Redesign' of https://github.com/Northeastern-Electric-Racing/FinishLine into #1644-proposed-solution-redesign
2 parents b26eb13 + ecfeeb6 commit 1530c07

3 files changed

Lines changed: 130 additions & 73 deletions

File tree

src/frontend/src/components/Tabs.tsx

Lines changed: 2 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -36,14 +36,10 @@ const NERTabs = ({ setTab, tabsLabels, baseUrl, defaultTab, id }: TabProps) => {
3636
};
3737

3838
return (
39-
<Tabs
40-
sx={{ borderBottom: 1, borderColor: 'divider' }}
41-
value={tabValue}
42-
onChange={handleTabChange}
43-
aria-label={`${id}-tabs`}
44-
>
39+
<Tabs value={tabValue} onChange={handleTabChange} aria-label={`${id}-tabs`}>
4540
{tabsLabels.map((tab, idx) => (
4641
<Tab
42+
sx={{ borderBottom: 1, borderColor: 'divider' }}
4743
label={tab.tabName}
4844
aria-label={tab.tabUrlValue}
4945
value={idx}

src/frontend/src/layouts/PageTitle/PageTitle.tsx

Lines changed: 11 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -28,28 +28,24 @@ const PageTitle: React.FC<PageTitleProps> = ({ title, previousPages, headerRight
2828

2929
return (
3030
<>
31-
<Box mb={sticky ? -1 : 0}>
32-
<PageBreadcrumbs currentPageTitle={title} previousPages={previousPages} />
33-
</Box>
34-
<Box
35-
mb={2}
36-
position={sticky ? 'sticky' : 'initial'}
37-
top={65}
38-
pt={sticky ? 1 : 0}
39-
zIndex={1}
40-
bgcolor={theme.palette.background.default}
41-
>
42-
<Grid container>
43-
<Grid item xs={6} md={8}>
31+
<PageBreadcrumbs currentPageTitle={title} previousPages={previousPages} />
32+
<Box sx={{ mb: 2 }}>
33+
<Grid container rowSpacing={1}>
34+
<Grid item xs={6} md={4}>
4435
<Typography variant="h4" fontSize={30}>
4536
{title}
4637
</Typography>
4738
</Grid>
48-
<Grid item xs={6} md={4} textAlign={'right'}>
39+
<Grid item xs={0} md={4} sx={{ display: { xs: 'none', md: 'block' } }}>
40+
{tabs}
41+
</Grid>
42+
<Grid item xs={6} md={4} textAlign={['left', 'right']}>
4943
{headerRight}
5044
</Grid>
45+
<Grid item xs={12} md={0} justifyContent={'center'} sx={{ display: { xs: 'flex', md: 'none' } }}>
46+
{tabs}
47+
</Grid>
5148
</Grid>
52-
{tabs && <Box sx={{ borderBottom: 1, borderColor: 'divider' }}>{tabs}</Box>}
5349
</Box>
5450
</>
5551
);

src/frontend/src/pages/ChangeRequestsPage/ChangeRequestsTable.tsx

Lines changed: 117 additions & 52 deletions
Original file line numberDiff line numberDiff line change
@@ -3,20 +3,37 @@
33
* See the LICENSE file in the repository root folder for details.
44
*/
55

6-
import { DataGrid, GridColDef, GridFilterModel, GridRow, GridRowProps, GridToolbar } from '@mui/x-data-grid';
6+
import {
7+
DataGrid,
8+
GridColDef,
9+
GridFilterModel,
10+
GridRow,
11+
GridRowProps,
12+
GridToolbarContainer,
13+
GridToolbarFilterButton,
14+
GridToolbarQuickFilter
15+
} from '@mui/x-data-grid';
716
import { routes } from '../../utils/routes';
817
import { datePipe, fullNamePipe, wbsPipe } from '../../utils/pipes';
918
import { useAllChangeRequests } from '../../hooks/change-requests.hooks';
1019
import LoadingIndicator from '../../components/LoadingIndicator';
1120
import ErrorPage from '../ErrorPage';
12-
import { useTheme } from '@mui/system';
13-
import { useState } from 'react';
21+
import { Box, useTheme } from '@mui/system';
22+
import { useEffect, useState } from 'react';
1423
import { ChangeRequest, ChangeRequestType, validateWBS, WbsNumber } from 'shared';
1524
import { GridColDefStyle } from '../../utils/tables';
1625
import { Link } from '@mui/material';
1726
import { Link as RouterLink } from 'react-router-dom';
1827

28+
const CustomToolbar = () => (
29+
<GridToolbarContainer>
30+
<GridToolbarQuickFilter />
31+
<GridToolbarFilterButton />
32+
</GridToolbarContainer>
33+
);
34+
1935
const ChangeRequestsTable: React.FC = () => {
36+
const [windowSize, setWindowSize] = useState(window.innerWidth);
2037
const { isLoading, isError, data, error } = useAllChangeRequests();
2138
if (localStorage.getItem('cr-table-row-count') === null) {
2239
localStorage.setItem('cr-table-row-count', '50');
@@ -32,18 +49,76 @@ const ChangeRequestsTable: React.FC = () => {
3249

3350
const theme = useTheme();
3451

52+
useEffect(() => {
53+
const handleResize = () => {
54+
setWindowSize(window.innerWidth);
55+
};
56+
57+
// Attach the event listener to the window object
58+
window.addEventListener('resize', handleResize);
59+
60+
// Remove the event listener when the component unmounts
61+
return () => {
62+
window.removeEventListener('resize', handleResize);
63+
};
64+
}, []);
65+
3566
if (isLoading || !data) return <LoadingIndicator />;
3667

3768
if (isError) return <ErrorPage message={error?.message} />;
3869

70+
const idColumn: GridColDef = {
71+
...baseColDef,
72+
field: 'crId',
73+
type: 'number',
74+
headerName: 'ID',
75+
maxWidth: 75
76+
};
77+
78+
const dateReviewedColumn: GridColDef = {
79+
...baseColDef,
80+
field: 'dateReviewed',
81+
headerName: 'Date Reviewed',
82+
type: 'date',
83+
valueFormatter: (params) => (params.value ? datePipe(params.value) : ''),
84+
maxWidth: 200
85+
};
86+
87+
const wbsColumn: GridColDef = {
88+
...baseColDef,
89+
field: 'wbs',
90+
headerName: 'WBS',
91+
filterable: true,
92+
sortable: true,
93+
maxWidth: 300,
94+
valueGetter: (params) => `${wbsPipe(params.value.wbsNum)} - ${params.value.name}`,
95+
sortComparator: (_v1, _v2, param1, param2) => {
96+
const wbs1: WbsNumber = validateWBS((param1.value as string).split(' ')[0]);
97+
const wbs2: WbsNumber = validateWBS((param2.value as string).split(' ')[0]);
98+
99+
if (wbs1.carNumber !== wbs2.carNumber) {
100+
return wbs1.carNumber - wbs2.carNumber;
101+
} else if (wbs1.projectNumber !== wbs2.projectNumber) {
102+
return wbs1.projectNumber - wbs2.projectNumber;
103+
} else if (wbs1.workPackageNumber !== wbs2.workPackageNumber) {
104+
return wbs1.workPackageNumber - wbs2.workPackageNumber;
105+
} else {
106+
return 0;
107+
}
108+
}
109+
};
110+
111+
const submitterColumn: GridColDef = {
112+
...baseColDef,
113+
field: 'submitter',
114+
headerName: 'Submitter',
115+
maxWidth: 200
116+
};
117+
118+
const smallColumns: GridColDef[] = [idColumn, dateReviewedColumn, wbsColumn, submitterColumn];
119+
39120
const columns: GridColDef[] = [
40-
{
41-
...baseColDef,
42-
field: 'crId',
43-
type: 'number',
44-
headerName: 'ID',
45-
maxWidth: 75
46-
},
121+
idColumn,
47122
{
48123
...baseColDef,
49124
field: 'type',
@@ -53,29 +128,7 @@ const ChangeRequestsTable: React.FC = () => {
53128
maxWidth: 150
54129
},
55130
{ ...baseColDef, field: 'carNumber', headerName: 'Car #', type: 'number', maxWidth: 50 },
56-
{
57-
...baseColDef,
58-
field: 'wbs',
59-
headerName: 'WBS',
60-
filterable: true,
61-
sortable: true,
62-
maxWidth: 300,
63-
valueGetter: (params) => `${wbsPipe(params.value.wbsNum)} - ${params.value.name}`,
64-
sortComparator: (_v1, _v2, param1, param2) => {
65-
const wbs1: WbsNumber = validateWBS((param1.value as string).split(' ')[0]);
66-
const wbs2: WbsNumber = validateWBS((param2.value as string).split(' ')[0]);
67-
68-
if (wbs1.carNumber !== wbs2.carNumber) {
69-
return wbs1.carNumber - wbs2.carNumber;
70-
} else if (wbs1.projectNumber !== wbs2.projectNumber) {
71-
return wbs1.projectNumber - wbs2.projectNumber;
72-
} else if (wbs1.workPackageNumber !== wbs2.workPackageNumber) {
73-
return wbs1.workPackageNumber - wbs2.workPackageNumber;
74-
} else {
75-
return 0;
76-
}
77-
}
78-
},
131+
wbsColumn,
79132
{
80133
...baseColDef,
81134
field: 'dateSubmitted',
@@ -84,20 +137,8 @@ const ChangeRequestsTable: React.FC = () => {
84137
valueFormatter: (params) => datePipe(params.value),
85138
maxWidth: 200
86139
},
87-
{
88-
...baseColDef,
89-
field: 'submitter',
90-
headerName: 'Submitter',
91-
maxWidth: 200
92-
},
93-
{
94-
...baseColDef,
95-
field: 'dateReviewed',
96-
headerName: 'Date Reviewed',
97-
type: 'date',
98-
valueFormatter: (params) => (params.value ? datePipe(params.value) : ''),
99-
maxWidth: 200
100-
},
140+
submitterColumn,
141+
dateReviewedColumn,
101142
{
102143
...baseColDef,
103144
field: 'reviewer',
@@ -141,7 +182,15 @@ const ChangeRequestsTable: React.FC = () => {
141182
);
142183

143184
return (
144-
<div>
185+
<Box
186+
sx={{
187+
'& .Mui-even': {
188+
backgroundColor: theme.palette.background.paper,
189+
border: `1px solid ${theme.palette.mode === 'light' ? '#f0f0f0' : '#303030'}`
190+
},
191+
'& .Mui-odd': { border: `1px solid ${theme.palette.mode === 'light' ? '#f0f0f0' : '#303030'}` }
192+
}}
193+
>
145194
<DataGrid
146195
autoHeight
147196
disableSelectionOnClick
@@ -164,11 +213,27 @@ const ChangeRequestsTable: React.FC = () => {
164213
reviewer: fullNamePipe(v.reviewer)
165214
})) || []
166215
}
167-
columns={columns}
216+
columns={windowSize < 900 ? smallColumns : columns}
168217
getRowId={(row) => row.crId}
169-
sx={{ background: theme.palette.background.paper }}
218+
sx={{
219+
border: 0,
220+
'& .MuiDataGrid-row:hover': {
221+
backgroundColor: '#ef4345'
222+
},
223+
'& .MuiDataGrid-columnHeader': {
224+
borderRight: `1px solid ${theme.palette.mode === 'light' ? '#f0f0f0' : '#303030'}`,
225+
borderLeft: `1px solid ${theme.palette.mode === 'light' ? '#f0f0f0' : '#303030'}`
226+
},
227+
'& .MuiDataGrid-columnHeaders': {
228+
border: `1px solid ${theme.palette.mode === 'light' ? '#f0f0f0' : '#303030'}`
229+
},
230+
'.MuiDataGrid-columnSeparator': {
231+
display: 'none'
232+
}
233+
}}
234+
getRowClassName={(params) => (params.indexRelativeToCurrentPage % 2 === 0 ? 'Mui-even' : 'Mui-odd')}
170235
components={{
171-
Toolbar: GridToolbar,
236+
Toolbar: CustomToolbar,
172237
Row: (props: GridRowProps & { row: ChangeRequest }) => {
173238
return (
174239
<Link
@@ -213,7 +278,7 @@ const ChangeRequestsTable: React.FC = () => {
213278
}
214279
}}
215280
/>
216-
</div>
281+
</Box>
217282
);
218283
};
219284

0 commit comments

Comments
 (0)