add colors to different modes and stationaryMode to supervisors

This commit is contained in:
patrol16d 2022-12-16 03:19:26 +01:00
parent 817095cc3f
commit 6ae0854fb9
8 changed files with 189 additions and 8 deletions

View File

@ -7,7 +7,8 @@ import AddGroup from './views/coordinator/AddGroup'
import AddStudent from './views/coordinator/AddStudent' import AddStudent from './views/coordinator/AddStudent'
import AddLeader from './views/coordinator/AddLeader' import AddLeader from './views/coordinator/AddLeader'
import Coordinator from './views/coordinator/Coordinator' import Coordinator from './views/coordinator/Coordinator'
import Groups from './views/coordinator/Groups' import CoordinatorGroups from './views/coordinator/CoordinatorGroups'
import SupervisorGroups from './views/supervisor/SupervisorGroups'
import Leaders from './views/coordinator/Leaders' import Leaders from './views/coordinator/Leaders'
import Students from './views/coordinator/Students' import Students from './views/coordinator/Students'
import Login from './views/Login' import Login from './views/Login'
@ -42,7 +43,7 @@ function App() {
<Route index element={<Login />} /> <Route index element={<Login />} />
<Route path="coordinator" element={<Coordinator />}> <Route path="coordinator" element={<Coordinator />}>
<Route index element={<Home />} /> <Route index element={<Home />} />
<Route path="groups" element={<Groups />} /> <Route path="groups" element={<CoordinatorGroups />} />
<Route path="groups/:id" element={<Group />} /> <Route path="groups/:id" element={<Group />} />
<Route path="students" element={<Students />} /> <Route path="students" element={<Students />} />
<Route path="leaders" element={<Leaders />} /> <Route path="leaders" element={<Leaders />} />
@ -69,7 +70,7 @@ function App() {
</Route> </Route>
<Route path="supervisor" element={<Supervisor />}> <Route path="supervisor" element={<Supervisor />}>
<Route index element={<Navigate to="groups" />} /> <Route index element={<Navigate to="groups" />} />
<Route path="groups" element={<Groups />} /> <Route path="groups" element={<SupervisorGroups />} />
<Route path="schedule" element={<SupervisorSchedules />} /> <Route path="schedule" element={<SupervisorSchedules />} />
<Route path="schedule/:id" element={<SupervisorSchedule />} /> <Route path="schedule/:id" element={<SupervisorSchedule />} />
</Route> </Route>

View File

@ -1,10 +1,10 @@
import { NavLink } from 'react-router-dom' import { NavLink } from 'react-router-dom'
const TopBar = ({ routes }: { routes: { name: string; path: string }[] }) => { const TopBar = ({ routes, color }: { routes: { name: string; path: string }[]; color: string}, ) => {
const linkClass = ({ isActive }: { isActive: boolean }) => const linkClass = ({ isActive }: { isActive: boolean }) =>
isActive ? 'underline font-bold' : '' isActive ? 'underline font-bold' : ''
return ( return (
<div className="flex items-center bg-gray-300 py-6 px-10 shadow"> <div className={"flex items-center py-6 px-10 shadow " + color}>
<h1 className="text-xl font-bold">System PRI</h1> <h1 className="text-xl font-bold">System PRI</h1>
<div className="flex ml-10 gap-3"> <div className="flex ml-10 gap-3">
{routes.map(({ path, name }) => ( {routes.map(({ path, name }) => (

View File

@ -83,7 +83,23 @@ const AddLeader = () => {
<InputError>Email jest wymagany</InputError> <InputError>Email jest wymagany</InputError>
)} )}
</div> </div>
{/* <div className="form-control"> <div className="form-control">
<label className="label" htmlFor="stationary_mode">
Tryb stacjonarny
</label>
<input
className="input input-bordered"
id="stationary_mode"
type="checkbox"
{...register('stationary_mode', {
required: true,
})}
/>
{errors.email?.type === 'required' && (
<InputError>Email jest wymagany</InputError>
)}
</div>
<div className="form-control">
<label className="label" htmlFor="limit_group"> <label className="label" htmlFor="limit_group">
Limit grup Limit grup
</label> </label>
@ -99,7 +115,7 @@ const AddLeader = () => {
{errors.limit_group?.type === 'pattern' && ( {errors.limit_group?.type === 'pattern' && (
<InputError>Limit grup musi być liczbą dodatnią</InputError> <InputError>Limit grup musi być liczbą dodatnią</InputError>
)} )}
</div> */} </div>
<button className="btn btn-success mt-4">Dodaj opiekuna</button> <button className="btn btn-success mt-4">Dodaj opiekuna</button>
</form> </form>
) )

View File

@ -4,7 +4,7 @@ import TopBar from '../../components/TopBar'
const Coordinator = () => { const Coordinator = () => {
return ( return (
<> <>
<TopBar <TopBar
routes={[ routes={[
{ name: 'Home', path: '/coordinator/' }, { name: 'Home', path: '/coordinator/' },
{ name: 'Grupy', path: '/coordinator/groups' }, { name: 'Grupy', path: '/coordinator/groups' },
@ -13,6 +13,7 @@ const Coordinator = () => {
{ name: 'Harmonogram', path: '/coordinator/schedule' }, { name: 'Harmonogram', path: '/coordinator/schedule' },
{ name: 'Dostępność', path: '/coordinator/supervisors_availability' }, { name: 'Dostępność', path: '/coordinator/supervisors_availability' },
]} ]}
color="bg-violet-400"
/> />
<div className="m-10"> <div className="m-10">
<Outlet /> <Outlet />

View File

@ -9,6 +9,7 @@ const Student = () => {
{ name: 'Zapisy', path: '/student/enrollment' }, { name: 'Zapisy', path: '/student/enrollment' },
{ name: 'Harmonogram', path: '/student/schedule' }, { name: 'Harmonogram', path: '/student/schedule' },
]} ]}
color="bg-gray-300"
/> />
<div className="m-10"> <div className="m-10">
<Outlet /> <Outlet />

View File

@ -9,6 +9,7 @@ const Supervisor = () => {
{ name: 'Grupy', path: '/supervisor/groups' }, { name: 'Grupy', path: '/supervisor/groups' },
{ name: 'Harmonogram', path: '/supervisor/schedule' }, { name: 'Harmonogram', path: '/supervisor/schedule' },
]} ]}
color="bg-amber-300"
/> />
<div className="m-10"> <div className="m-10">
<Outlet /> <Outlet />

View File

@ -0,0 +1,161 @@
import classNames from 'classnames'
import { useEffect, useState } from 'react'
import { useMutation, useQuery } from 'react-query'
import { useNavigate } from 'react-router-dom'
import useLocalStorageState from 'use-local-storage-state'
import { deleteGroup, getGroups } from '../../api/groups'
import { ReactComponent as IconRemove } from '../../assets/svg/icon-remove.svg'
import { Link } from 'react-router-dom'
const SupervisorGroups = () => {
let navigate = useNavigate()
const [page, setPage] = useState(1)
const [perPage, setPerPage] = useState(10)
const [yearGroupId] = useLocalStorageState('yearGroupId')
const perPageOptions = [
{
value: 10,
label: '10 rekordów',
},
{
value: 20,
label: '20 rekordów',
},
{
value: 50,
label: '50 rekordów',
},
{
value: 1000,
label: 'Pokaż wszystkie',
},
]
const {
isLoading: areGroupsLoading,
data: groups,
refetch: refetchGroups,
} = useQuery(['groups', page, perPage], () =>
getGroups({ year_group_id: Number(yearGroupId), page, per_page: perPage }),
)
const { mutate: mutateDelete } = useMutation(
'deleteGroup',
(index: number) => deleteGroup(index),
{
onSuccess: () => refetchGroups(),
},
)
useEffect(() => {
setPage(1)
}, [perPage])
if (areGroupsLoading) {
return <div>Ładowanie</div>
}
return (
<div>
<div className="flex items-center justify-between flex-col gap-3 md:flex-row md:gap-0">
<button
className="btn btn-success"
onClick={() => navigate('/coordinator/add-group')}
>
Dodaj nową grupę
</button>
<div className="flex">
<select className="select select-xs md:select-md select-bordered mr-3">
{perPageOptions.map(({ value, label }) => (
<option key={value} onClick={() => setPerPage(value)}>
{label}
</option>
))}
</select>
</div>
</div>
<div className="flex mx-auto mt-5 overflow-hidden overflow-x-auto border border-gray-100 rounded">
<table className="min-w-full table table-compact">
<thead>
<tr className="bg-gray-50">
<th>Nazwa</th>
<th>Opiekun</th>
<th>Semestr 1</th>
<th>Semestr 2</th>
<th></th>
</tr>
</thead>
<tbody className="divide-y divide-gray-100">
{groups?.data?.groups?.map(
({
id,
name,
project_supervisor,
points_for_first_term,
points_for_second_term,
}) => (
<tr key={id}>
<td>
<Link
to={`/coordinator/groups/${id}`}
className="underline font-bold"
>
{name}
</Link>
</td>
<td>
{`${project_supervisor.first_name} ${project_supervisor.last_name}`}
</td>
<td>{points_for_first_term}</td>
<td>{points_for_second_term}</td>
<td>
<button onClick={() => mutateDelete(id)}>
<IconRemove />
</button>
</td>
</tr>
),
)}
</tbody>
</table>
</div>
<div className="w-full flex items-center justify-center mt-2">
<div className="btn-group">
<button
className="btn btn-outline"
onClick={() => setPage(page - 1)}
disabled={page === 1}
>
«
</button>
{[
...Array(
groups?.data?.max_pages && groups?.data?.max_pages + 1,
).keys(),
]
.slice(1)
.map((p) => (
<button
key={p}
className={classNames('btn btn-outline', {
'bg-success': p === page,
})}
onClick={() => setPage(p)}
>
{p}
</button>
))}
<button
className="btn btn-outline"
onClick={() => setPage(page + 1)}
disabled={page === groups?.data?.max_pages}
>
»
</button>
</div>
</div>
</div>
)
}
export default SupervisorGroups