Skip to content
This repository has been archived by the owner on May 24, 2022. It is now read-only.

Commit

Permalink
feat: add clicking in students page & change reload parameters
Browse files Browse the repository at this point in the history
  • Loading branch information
Mikxox committed Apr 28, 2022
1 parent 8057c31 commit 01f92b2
Show file tree
Hide file tree
Showing 6 changed files with 73 additions and 19 deletions.
15 changes: 12 additions & 3 deletions frontend/components/StudentSidebar.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,8 @@ type StudentsSidebarProps = {
setError: (error: string) => void;
refresh: [boolean, boolean];
setRefresh: (refresh: [boolean, boolean]) => void;
setStudentBase: (studentBase: StudentBase) => void;
studentBase: StudentBase;
};

/**
Expand Down Expand Up @@ -67,7 +69,7 @@ async function searchStudent(
// Fallback for no status selected
if (!getStatusFilterList(studentSearchParameters)) {
const newState = { ...state };
newState.page = state.page + 1;
newState.page = 0;
newState.hasMoreItems = false;
newState.loading = false;
setState(newState);
Expand Down Expand Up @@ -143,6 +145,8 @@ const StudentSidebar: React.FC<StudentsSidebarProps> = ({
setError,
refresh,
setRefresh,
setStudentBase,
studentBase,
}: StudentsSidebarProps) => {
const router = useRouter();
const [showFilter, setShowFilter] = useState(true);
Expand Down Expand Up @@ -238,7 +242,7 @@ const StudentSidebar: React.FC<StudentsSidebarProps> = ({
state.pageSize = prevPageSize;
setRefresh([false, refresh[1]]);
}
}, [refresh[0]]);
}, [refresh]);

/**
* Call to refresh students list from page 0 with current filters applied
Expand Down Expand Up @@ -601,7 +605,12 @@ const StudentSidebar: React.FC<StudentsSidebarProps> = ({
<FlatList
list={students}
renderItem={(student: StudentBase) => (
<StudentTile key={student.id} student={student} />
<StudentTile
key={student.id}
student={student}
setStudentBase={setStudentBase}
studentBase={studentBase}
/>
)}
renderWhenEmpty={showBlank} // let user know if initial data is loading or there is no data to show
hasMoreItems={state.hasMoreItems}
Expand Down
12 changes: 9 additions & 3 deletions frontend/components/student/StudentHolder.tsx
Original file line number Diff line number Diff line change
@@ -1,16 +1,18 @@
import { useState } from 'react';
import { ItemTypes, Student, StudentBase } from '../../lib/types';
import { useDrop } from 'react-dnd';
import StudentView from './StudentView';

type StudentHolderProp = {
setRefresh: (refresh: [boolean, boolean]) => void;
studentBase: StudentBase;
setStudentBase: (studentBase: StudentBase) => void;
};

const StudentHolder: React.FC<StudentHolderProp> = ({
setRefresh,
studentBase,
setStudentBase,
}: StudentHolderProp) => {
const [studentBase, setStudentBase] = useState({} as StudentBase);
/**
* This catches the dropped studentTile
* The studentTile passes its student as the DragObject to this function on drop
Expand Down Expand Up @@ -41,7 +43,11 @@ const StudentHolder: React.FC<StudentHolderProp> = ({
{/* hold the student information, only load this if an actual studentBase object exists */}
{/* studentBase.id is used to check if this is an actual object or just an empty dummy */}
{studentBase.id && (
<StudentView studentInput={studentBase} setRefresh={setRefresh} />
<StudentView
studentInput={studentBase}
setRefresh={setRefresh}
setOriginalStudentBase={setStudentBase}
/>
)}
</section>
);
Expand Down
4 changes: 3 additions & 1 deletion frontend/components/student/StudentView.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ const x_mark = <FontAwesomeIcon icon={faXmark} />;
type StudentViewProp = {
studentInput: StudentBase;
setRefresh: (refresh: [boolean, boolean]) => void;
setOriginalStudentBase: (originalStudentBase: StudentBase) => void;
};

type StatusSuggestionProp = {
Expand Down Expand Up @@ -87,7 +88,6 @@ async function setStudentSuggestion(
)
.then(() => {
reloadStudent(studentId, setStudentBase, signal, setError, router);
setRefresh([true, true]);
})
.catch((err) => {
parseError(err, setError, signal, router);
Expand Down Expand Up @@ -163,6 +163,7 @@ async function getEntireStudent(
const StudentView: React.FC<StudentViewProp> = ({
studentInput,
setRefresh,
setOriginalStudentBase,
}: StudentViewProp) => {
const [user] = useUser();
// Needed to reload student when a suggestion is done or status is changed
Expand Down Expand Up @@ -194,6 +195,7 @@ const StudentView: React.FC<StudentViewProp> = ({
const signal = controller.signal;
// This is a safety check, not really needed right now but it avoids accidents
if (studentBase.id !== undefined) {
setOriginalStudentBase(studentBase);
setStatus({ value: '', label: studentBase.status } as {
value: string;
label: string;
Expand Down
41 changes: 32 additions & 9 deletions frontend/components/students/StudentTile.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,8 @@ const tilde_mark = <Icon icon="mdi:tilde" />;
*/
type StudentProp = {
student: StudentBase;
setStudentBase: (studentBase: StudentBase) => void;
studentBase: StudentBase;
};

/**
Expand Down Expand Up @@ -82,21 +84,35 @@ async function getEntireStudent(
/**
* This creates the tiles show in the StudentSidebar
* @param student - The student whose information should be shown
* @param setStudentBase - callback to set studentBase object from dragndrop
* @param studentBase - object
*/
const StudentTile: React.FC<StudentProp> = ({ student }: StudentProp) => {
const StudentTile: React.FC<StudentProp> = ({
student,
setStudentBase,
studentBase,
}: StudentProp) => {
// Need to set a project with all keys present to avoid the render code throwing undefined errors
const [myStudent, setMyStudent]: [Student, (myStudent: Student) => void] =
useState(convertStudentBase(student) as Student); // using different names to avoid confusion

const [myStudentBase]: [StudentBase, (myStudentBase: StudentBase) => void] =
useState(student as StudentBase);
const [myStudentBase, setMyStudentBase]: [
StudentBase,
(myStudentBase: StudentBase) => void
] = useState(student as StudentBase);

// TODO find a place to actually show this error
const [, setError]: [string, (error: string) => void] = useState('');
const router = useRouter();
useAxiosAuth();
let controller = new AbortController();

useEffect(() => {
if (studentBase.id == student.id) {
setMyStudentBase(studentBase);
}
}, [studentBase, student]);

useEffect(() => {
controller.abort();
controller = new AbortController();
Expand All @@ -111,16 +127,23 @@ const StudentTile: React.FC<StudentProp> = ({ student }: StudentProp) => {
};
}, [myStudentBase]);

useEffect(() => {
const newSuggestionCount = {} as statusSuggestionStatusToNumberDict;
myStudent.statusSuggestions.forEach((suggestion) => {
newSuggestionCount[suggestion.status] =
newSuggestionCount[suggestion.status] + 1 || 1;
});
setSuggestionCounts(newSuggestionCount);
}, [myStudent]);

/**
* This counts the different status suggestions to create the pie chart
* The dict is empty without default values so when using suggestionCounts
* you should add '|| 0' to avoid getting an undefined error
*/
const suggestionCounts = {} as statusSuggestionStatusToNumberDict;
myStudent.statusSuggestions.forEach((suggestion) => {
suggestionCounts[suggestion.status] =
suggestionCounts[suggestion.status] + 1 || 1;
});
const [suggestionCounts, setSuggestionCounts] = useState(
{} as statusSuggestionStatusToNumberDict
);

/**
* This hook allows dragging the StudentTile
Expand All @@ -139,7 +162,7 @@ const StudentTile: React.FC<StudentProp> = ({ student }: StudentProp) => {

return (
// TODO add a chevron dropdown to show possible roles, student coach, ...
<div ref={drag} key={student.id}>
<div ref={drag} key={student.id} onClick={() => setStudentBase(student)}>
<div
className={`my-4 mx-1 flex flex-row justify-between p-2 opacity-100 shadow-sm shadow-gray-500`}
>
Expand Down
9 changes: 8 additions & 1 deletion frontend/pages/[editionName]/projects.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,12 @@ import { Icon } from '@iconify/react';
import { FontAwesomeIcon } from '@fortawesome/react-fontawesome';
import { faMagnifyingGlass } from '@fortawesome/free-solid-svg-icons';
import { useEffect, useState } from 'react';
import { ProjectBase, ProjectData, UserRole } from '../../lib/types';
import {
ProjectBase,
ProjectData,
StudentBase,
UserRole,
} from '../../lib/types';
import { axiosAuthenticated } from '../../lib/axios';
import Endpoints from '../../lib/endpoints';
import useAxiosAuth from '../../hooks/useAxiosAuth';
Expand Down Expand Up @@ -250,6 +255,8 @@ const Projects: NextPage = () => {
setError={setError}
refresh={refreshStudents}
setRefresh={setRefreshStudents}
setStudentBase={() => null}
studentBase={{} as StudentBase}
/>
</section>

Expand Down
11 changes: 9 additions & 2 deletions frontend/pages/[editionName]/students.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ import Header from '../../components/Header';
import StudentSidebar from '../../components/StudentSidebar';
import { Icon } from '@iconify/react';
import { useState } from 'react';
import { UserRole } from '../../lib/types';
import { StudentBase, UserRole } from '../../lib/types';
import { HTML5Backend } from 'react-dnd-html5-backend';
import { DndProvider } from 'react-dnd';
import useAxiosAuth from '../../hooks/useAxiosAuth';
Expand All @@ -20,6 +20,7 @@ const arrow_in = <Icon icon="bi:arrow-left-circle" />;
const Students: NextPage = () => {
// Used to hide / show the students sidebar on screen width below 768px
const [showSidebar, setShowSidebar] = useState(false);
const [studentBase, setStudentBase] = useState({} as StudentBase);
const [refreshStudents, setRefreshStudents] = useState([false, true] as [
boolean,
boolean
Expand Down Expand Up @@ -52,6 +53,8 @@ const Students: NextPage = () => {
setError={setError}
refresh={refreshStudents}
setRefresh={setRefreshStudents}
setStudentBase={setStudentBase}
studentBase={studentBase}
/>
</section>

Expand All @@ -78,7 +81,11 @@ const Students: NextPage = () => {

{/* This contains the actual student info */}
<div>
<StudentHolder setRefresh={setRefreshStudents} />
<StudentHolder
setRefresh={setRefreshStudents}
studentBase={studentBase}
setStudentBase={setStudentBase}
/>
</div>
</section>
</main>
Expand Down

0 comments on commit 01f92b2

Please sign in to comment.