fixed hover

This commit is contained in:
wrzesinski-hubert 2021-01-12 22:59:12 +01:00
parent d4f7ad341a
commit 1c7888a478
13 changed files with 210 additions and 58 deletions

View File

@ -0,0 +1,120 @@
import React, { useEffect, useState } from 'react';
import styled from 'styled-components/macro';
import { axiosInstance } from '../utils/axiosInstance';
const AdministratorWrapper = styled.div`
display: flex;
flex-direction: column;
margin:0 auto;
height:100vh;
`;
const Wrap = styled.div`
display: flex;
flex: 1;
flex-direction: column;
justify-content: center;
align-items: center;
`;
const LogoWrapper = styled.div`
display: flex;
flex: 1;
flex-direction: column;
justify-content: center;
align-items: center;
`;
const Text = styled.div`
font-family: 'Roboto', sans-serif;
font-size: 5rem;
user-select: none;
`;
const Logo = styled.img`
width: 400px;
height: 400px;
`;
const Form = styled.form`
flex: 1;
display: flex;
justify-content: center;
align-items: center;
flex-direction: column;
input {
padding: 5px;
margin-top: 10px;
margin-bottom: 10px;
width: 210px;
}
`;
export const Administrator = () => {
const today = new Date();
const dd = String(today.getDate()).padStart(2, '0');
const mm = String(today.getMonth() + 1).padStart(2, '0');
const yyyy = today.getFullYear();
const date = yyyy + '-' + mm + '-' + dd;
const [selectedFile, setSelectedFile] = useState<File|null>(null);
const destination = `${process.env.REACT_APP_API_URL}/api/v1/configurator/config`;
useEffect(() => {
}, [selectedFile]);
const uploadFile = async (event:React.FormEvent<HTMLFormElement>) => {
event.preventDefault();
const formData = new FormData();
formData.append("file",selectedFile as Blob);
const response = await axiosInstance.post(`${process.env.REACT_APP_API_URL}/api/v1/configurator/config`, formData)
console.log(response);
}
return (
<AdministratorWrapper>
<Wrap>
<LogoWrapper>
<Logo alt="logo" src="https://plannaplan.pl/img/logo.svg" />
<Text> plan na plan </Text>
</LogoWrapper>
<Form
onSubmit={uploadFile}
>
<div>
<div>Start:</div>{' '}
<div>
<input type="date" min={date} />
</div>
</div>
<div>
<div>Koniec:</div>{' '}
<div>
<input type="date" min={date} />
</div>
</div>
<div>
<input
type="file"
onChange={(e) => {
if (e.target.files && e.target.files[0]) {
const file = e.target.files[0];
setSelectedFile(file);
}
}}
/>
</div>
<div>
<input type="submit"/>
</div>
</Form>
</Wrap>
</AdministratorWrapper>
);
};

View File

@ -1,13 +1,15 @@
import React, { useContext, useState } from 'react';
import Topbar from './Topbar';
import { Transfer } from './Transfer';
import { Admin } from './Admin';
import { Deanery } from './DeaneryPanel';
import { Scheduler } from './Scheduler';
import { Rightbar } from './Rightbar';
import { Administrator } from './Administrator';
import styled from 'styled-components';
import LoadingOverlay from 'react-loading-overlay';
import { SyncLoader } from 'react-spinners';
import { CASContext } from '../contexts/CASProvider';
import { coursesContext } from '../contexts/CoursesProvider';
const Wrapper = styled.div`
display: flex;
height: calc(100vh - 80px);
@ -21,6 +23,9 @@ export const App = () => {
const { role } = useContext(CASContext)!;
const [isOpenTransfer, setOpenTransfer] = useState(false);
const { selectSchedulerEvents } = useContext(coursesContext)!;
const schedulerEvents = selectSchedulerEvents();
const handleTransfer = () => {
setOpenTransfer(!isOpenTransfer);
};
@ -29,17 +34,24 @@ export const App = () => {
return (
<>
<LoadingOverlay active={role === undefined} spinner={<SyncLoader />}>
<Topbar handleTransfer={handleTransfer} />
<Transfer isOpen={isOpenTransfer} handleClose={handleTransfer} />
<Wrapper>
{userPrivilige === 'STUDENT' && (
{userPrivilige !== 'ADMIN' && (
<>
<Scheduler />
<Rightbar />
<Topbar handleTransfer={handleTransfer} />
<Transfer isOpen={isOpenTransfer} handleClose={handleTransfer} />
<Wrapper>
{userPrivilige === 'STUDENT' && (
<>
<Scheduler schedulerEvents={schedulerEvents} />
<Rightbar />
</>
)}
{userPrivilige === 'DEANERY' && <Deanery schedulerEvents={schedulerEvents} />}
</Wrapper>
</>
)}
{userPrivilige === 'DEANERY' && <Admin />}
</Wrapper>
{userPrivilige === 'ADMIN' && (
<Administrator></Administrator>
)}
</LoadingOverlay>
</>
);

View File

@ -162,7 +162,7 @@ export const CourseCard = ({ course }: CourseCardProps) => {
const [previous, setPrevious] = useState(basketCourseGroups);
const onGroupClick = (group: Group, courseId: number) => {
setPrevious((prev) => (group.type === GroupType.CLASS ? { ...prev, classes: group } : { ...prev, lecture: group }));
setPrevious((prev) => (group.type === GroupType.CLASS ? { ...prev, classes: group, prev:"classes" } : { ...prev, lecture: group,prev:"lecture" }));
changeGroupInBasket(group, courseId);
};
@ -187,22 +187,17 @@ export const CourseCard = ({ course }: CourseCardProps) => {
onClick={() => onGroupClick(group, course.id)}
onMouseEnter={() => {
if (group.type === GroupType.CLASS) {
changeGroupInBasket(group, course.id);
changeGroupInBasket({classes: group,lecture:previous.lecture}, course.id);
}
if (group.type === GroupType.LECTURE) {
changeGroupInBasket(group, course.id);
changeGroupInBasket({lecture: group,classes:previous.classes}, course.id);
}
}}
onMouseLeave={() => {
if (hoveredGroup) {
if (hoveredGroup.type === GroupType.CLASS && previous.classes !== undefined) {
changeGroupInBasket(previous.classes, course.id);
}
if (hoveredGroup.type === GroupType.LECTURE && previous.lecture !== undefined) {
changeGroupInBasket(previous.lecture, course.id);
}
changeHoveredGroup(null);
changeGroupInBasket(previous, course.id);
}
changeHoveredGroup(null);
}}
>
<StyledGroupType groupType={group.type}>{group.type === 'CLASS' ? 'ĆW' : 'WYK'}</StyledGroupType>

View File

@ -7,6 +7,7 @@ import { Scheduler } from './Scheduler';
import { Rightbar } from './Rightbar';
import { SchedulerHistory } from './SchedulerHistory';
import { coursesContext } from '../contexts/CoursesProvider';
import { SchedulerEvent } from '../types';
const LeftSide = styled.div`
height: 100%;
@ -96,9 +97,15 @@ const Icon = styled.img`
margin: 5px;
`;
export const Admin = () => {
interface Deanery {
schedulerEvents: Array<SchedulerEvent>;
}
export const Deanery = ({ schedulerEvents }: Deanery) => {
const [currentTab, setCurrentTab] = useState<null | number>(1);
const { getNewestStudentTimetable,userID } = useContext(coursesContext)!;
const { selectHistorySchedulerEvents } = useContext(coursesContext)!;
const schedulerHistoryEvents = selectHistorySchedulerEvents();
const handleClick = (e: MouseEvent<HTMLDivElement>) => {
setCurrentTab(Number(e.currentTarget.id));
@ -124,11 +131,11 @@ export const Admin = () => {
<Wrapper>
{currentTab === 1 ? (
<>
<Scheduler />
<Scheduler schedulerEvents={schedulerEvents}/>
<Rightbar />
</>
) : currentTab === 2 ? (
<SchedulerHistory />
<SchedulerHistory schedulerHistoryEvents={schedulerHistoryEvents}/>
) : currentTab === 3 ? (
<StatsDiv />
) : (

View File

@ -67,7 +67,6 @@ export const Dropdown = ({ open, input, handleCloseDropdown, selectedOption }: D
const onUserClick = (event: MouseEvent) => {
const target = event.currentTarget;
console.log('target: ', target);
//to be moved to students provider
changeStudent(target.id);
changeSelectedStudent(Number(target.id));

View File

@ -3,6 +3,7 @@ import { useState } from 'react';
import { SchedulerEvents } from './SchedulerEvents';
import { days, hours } from '../constants/index';
import styled from 'styled-components/macro';
import { SchedulerEvent } from '../types';
const SchedulerWrapper = styled.div`
border-collapse: collapse;
@ -61,7 +62,11 @@ const TableCell = styled.div<TableCellProps>`
font-weight: bold;
`;
export const Scheduler = () => {
interface SchedulerProps {
schedulerEvents: Array<SchedulerEvent>;
}
export const Scheduler = ({ schedulerEvents }: SchedulerProps) => {
const cellRef = useRef<HTMLDivElement>(null);
const [cellWidth, setCellWidth] = useState(0);
const [cellHeight, setCellHeight] = useState(0);
@ -123,7 +128,7 @@ export const Scheduler = () => {
)}
</TableRow>
))}
<SchedulerEvents cellWidth={cellWidth} cellHeight={cellHeight} />
<SchedulerEvents cellWidth={cellWidth} cellHeight={cellHeight} schedulerEvents={schedulerEvents} />
</TableBody>
</SchedulerWrapper>
);

View File

@ -3,15 +3,15 @@ import { SchedulerRow } from './SchedulerRow';
import { coursesContext } from '../contexts/CoursesProvider';
import { selectGroupsToShow } from '../utils/index';
import { ROWS_COUNT } from '../constants';
import { SchedulerEvent } from '../types';
interface SchedulerEventsProps {
cellWidth: number;
cellHeight: number;
schedulerEvents: Array<SchedulerEvent>;
}
export const SchedulerEvents = ({ cellWidth, cellHeight }: SchedulerEventsProps) => {
const { selectSchedulerEvents } = useContext(coursesContext)!;
const schedulerEvents = selectSchedulerEvents();
export const SchedulerEvents = ({ cellWidth, cellHeight,schedulerEvents }: SchedulerEventsProps) => {
return (
<div>

View File

@ -1,6 +1,7 @@
import React, { useContext, useEffect, useState } from 'react';
import styled from 'styled-components';
import { coursesContext } from '../contexts/CoursesProvider';
import { SchedulerEvent } from '../types';
import { Scheduler } from './Scheduler';
import { SchedulerHistoryNavigation } from './SchedulerHistoryNavigation';
@ -10,8 +11,12 @@ const Wrapper = styled.div`
width: 100%;
`;
export const SchedulerHistory = () => {
const { timetableHistory, setBasketFromHistoryGroups } = useContext(coursesContext)!;
interface SchedulerHistoryProps {
schedulerHistoryEvents: Array<SchedulerEvent>;
}
export const SchedulerHistory = ({schedulerHistoryEvents}:SchedulerHistoryProps) => {
const { timetableHistory, setHistoryBasketFromHistoryGroups } = useContext(coursesContext)!;
const [currentTimetable, setCurrentTimetable] = useState(timetableHistory.length===0 ? 0 : timetableHistory.length - 1);
let commisionDate = timetableHistory[currentTimetable]?.commisionDate;
@ -28,12 +33,13 @@ export const SchedulerHistory = () => {
};
useEffect(() => {
console.log('current timetable is: ', currentTimetable);
console.log('23113knkalsdnkasdlk', timetableHistory);
const timetable = timetableHistory[currentTimetable];
if (timetable) {
const { groups } = timetable;
setBasketFromHistoryGroups(groups);
setHistoryBasketFromHistoryGroups(groups);
}
else{
setHistoryBasketFromHistoryGroups([]);
}
}, [currentTimetable,timetableHistory]);
@ -42,7 +48,7 @@ export const SchedulerHistory = () => {
{timetableHistory.length > 0 && (
<SchedulerHistoryNavigation commisionDate={commisionDate} SubstractCurrentTimetable={SubstractCurrentTimetable} AddCurrentTimetable={AddCurrentTimetable} />
)}
<Scheduler />
<Scheduler schedulerEvents={schedulerHistoryEvents}/>
</Wrapper>
);
};

View File

@ -65,8 +65,6 @@ export const SchedulerHistoryNavigation = ({
AddCurrentTimetable,
}: SchedulerHistoryNavigationProps) => {
console.log("231213231231",commisionDate)
return (
<Wrapper>
<StyledButton

View File

@ -36,7 +36,6 @@ export const CASProvider = ({ children }: CASProviderProps) => {
const { data: user } = await axiosInstance.get<LoggedUser & { token: string; refreshToken: string }>(
`${process.env.REACT_APP_API_URL}/token?ticket=${ticket}`,
);
console.log('token response: ', user);
setUser({ authorityRole: user.authorityRole, email: user.email, id: user.id });
localStorage.setItem('userToken', user.token);
localStorage.setItem('userPrivilige', user.authorityRole);

View File

@ -20,21 +20,23 @@ interface CourseContext {
hoveredGroup: Group | undefined | null;
userID: string;
isDataLoading: boolean;
historyBasket: Array<Basket>;
addCourseToBasket: (courses: Course) => void;
changeHoveredGroup: (group: Group | null) => void;
changeGroupInBasket: (group: Group, courseId: number) => void;
changeGroupInBasket: (group: any, courseId: number) => void;
restoreGroupInBasket: (restoreGroup: Group, courseId: number) => void;
deleteFromBasket: (id: number) => void;
saveBasket: (userID: string) => Promise<void>;
changeStudent: (studentId: string) => void;
selectSchedulerEvents: () => Array<SchedulerEvent>;
selectHistorySchedulerEvents: () => Array<SchedulerEvent>;
selectBasketNames: () => Array<string>;
selectBasketCourses: () => Array<Course>;
selectBasketCourseGroups: (courseId: number) => { lecture: Group | undefined; classes: Group | undefined };
getNewestStudentTimetable: (studentId: string) => void;
getStudentTimetablesHistory: (studentId: string) => void;
changeDataLoading: (isLoading: boolean) => void;
setBasketFromHistoryGroups: (groupsIds: Array<number>) => void;
setHistoryBasketFromHistoryGroups: (groupsIds: Array<number>) => void;
}
export const coursesContext = createContext<CourseContext | undefined>(undefined);
@ -49,6 +51,7 @@ export const CoursesProvider = ({ children }: CoursesProviderProps) => {
//fetch courses with groups
const [courses, setCourses] = useState<Array<Course>>([]);
const [basket, setBasket] = useState<Array<Basket>>([]);
const [historyBasket, setHistoryBasket] = useState<Array<Basket>>([]);
const [timetableHistory, setTimetableHistory] = useState<Array<TimetableHistory>>([]);
const [userID, setUserID] = useState('');
const [hoveredGroup, setHoveredGroup] = useState<Group | undefined | null>(null);
@ -83,6 +86,20 @@ export const CoursesProvider = ({ children }: CoursesProviderProps) => {
}, [] as Array<SchedulerEvent>);
};
const selectHistorySchedulerEvents = () => {
return historyBasket.reduce((res, el) => {
const { name } = el;
if (el.classes) {
res.push({ ...el.classes, name });
}
if (el.lecture) {
res.push({ ...el.lecture, name });
}
return res;
}, [] as Array<SchedulerEvent>);
};
const selectBasketCourseGroups = (courseId: number) => {
const course = basket.find(({ id }) => id === courseId);
if (course !== undefined) {
@ -147,19 +164,16 @@ export const CoursesProvider = ({ children }: CoursesProviderProps) => {
getStudentTimetablesHistory(userID);
};
const changeGroupInBasket = (choosenGroup: Group, courseId: number) => {
const changeGroupInBasket = (choosenGroup: any, courseId: number) => {
const basketCourse = basket.filter((course) => course.id === courseId)[0];
const { type } = choosenGroup;
if (type === GroupType.CLASS) {
if (choosenGroup.lecture && choosenGroup.classes)
{
const prev = choosenGroup.prev==="lecture"?choosenGroup.lecture : choosenGroup.classes
setBasket(
basket.map((basket) => (basket.id === basketCourse.id ? { ...basket, classes: choosenGroup } : basket)),
);
} else if (type === GroupType.LECTURE) {
setBasket(
basket.map((basket) => (basket.id === basketCourse.id ? { ...basket, lecture: choosenGroup } : basket)),
basket.map((basket) => (basket.id === basketCourse.id ? { ...basket, lecture: choosenGroup.lecture, classes:choosenGroup.classes } : basket)),
);
changeHoveredGroup(prev);
}
changeHoveredGroup(choosenGroup);
};
const restoreGroupInBasket = (restoreGroup: Group, courseId: number) => {
@ -225,7 +239,7 @@ export const CoursesProvider = ({ children }: CoursesProviderProps) => {
}
};
const setBasketFromHistoryGroups = (groupsIds: Array<number>) => {
const setHistoryBasketFromHistoryGroups = (groupsIds: Array<number>) => {
const basket: Array<Basket> = [];
for (const groupId of groupsIds) {
for (const course of courses) {
@ -251,7 +265,7 @@ export const CoursesProvider = ({ children }: CoursesProviderProps) => {
}
}
console.log('baskeeeeeet: ', basket);
setBasket(basket);
setHistoryBasket(basket);
};
useEffect(() => {
@ -272,6 +286,7 @@ export const CoursesProvider = ({ children }: CoursesProviderProps) => {
hoveredGroup,
timetableHistory,
isDataLoading,
historyBasket,
addCourseToBasket,
changeHoveredGroup,
changeGroupInBasket,
@ -279,13 +294,14 @@ export const CoursesProvider = ({ children }: CoursesProviderProps) => {
restoreGroupInBasket,
saveBasket,
selectSchedulerEvents,
selectHistorySchedulerEvents,
selectBasketNames,
selectBasketCourses,
selectBasketCourseGroups,
getNewestStudentTimetable,
changeStudent,
getStudentTimetablesHistory,
setBasketFromHistoryGroups,
setHistoryBasketFromHistoryGroups,
changeDataLoading,
}}
>

View File

@ -18,10 +18,6 @@ export const StudentsProvider = ({ children }: StudentsProviderProps) => {
const [students, setStudents] = useState<Array<Student>>([]);
const [selectedStudent, setSelectedStudent] = useState<Student | null>(null);
useEffect(() => {
console.log('selected student: ', selectedStudent);
}, [selectedStudent]);
const getStudents = async () => {
try {
const { data } = await axiosInstance.get<Array<Student>>(

View File

@ -37,7 +37,6 @@ axiosInstance.interceptors.response.use(
},
async (error) => {
const originalRequest = error.config;
console.log("original request is: ", originalRequest)
if (error.response.status === 403 && !originalRequest._retry) {
originalRequest._retry = true;
const access_token = await getNewTokens();