diff --git a/src/components/App.tsx b/src/components/App.tsx index 14810b2..5390571 100644 --- a/src/components/App.tsx +++ b/src/components/App.tsx @@ -7,19 +7,19 @@ import styled from 'styled-components'; const Wrapper = styled.div` display: flex; + height: calc(100vh - 80px); `; export const App = () => { const [isOpenTransfer, setOpenTransfer] = useState(false); - const handleTransfer = () => { setOpenTransfer(!isOpenTransfer); }; return ( <> - + diff --git a/src/components/CourseCard.tsx b/src/components/CourseCard.tsx index eb42f7b..803f9e3 100644 --- a/src/components/CourseCard.tsx +++ b/src/components/CourseCard.tsx @@ -1,10 +1,11 @@ -import React, { useContext, MouseEvent } from 'react'; +import React, { useState, useContext, MouseEvent } from 'react'; import Collapse from '@material-ui/core/Collapse'; import ExpandIcon from '../assets/expand.png'; -import { Course, Group } from '../types/index'; +import { Course, Group, GroupType } from '../types/index'; import { coursesContext } from '../contexts/CoursesProvider'; import styled from 'styled-components'; import { makeStyles } from '@material-ui/core/styles'; +import { ReactComponent as CloseIcon } from '../assets/close.svg'; interface ClassExandIconProps { isSelected: boolean; @@ -23,6 +24,7 @@ const CourseStyled = styled.div` border-radius: 10px; cursor: pointer; align-items: stretch; + position: relative; `; const CourseNameStyled = styled.div` @@ -30,14 +32,18 @@ const CourseNameStyled = styled.div` padding-bottom: 10px; `; -const ClassGroupStyled = styled.div` +interface ClassGroupProps{ + groupType:GroupType; +} + +const ClassGroupStyled = styled.div` padding-top: 1px; padding-bottom: 1px; :hover { cursor: pointer; - transition: 1s; - background-color: #8bc8fb; } + outline-offset: -5px; + outline:${({groupType})=>groupType === "CLASS" ? "2px solid #5642AA" : "2px solid #866DF7"}; `; const ClassExandIconStyled = styled.img` @@ -67,33 +73,43 @@ const useStyles = makeStyles({ }, }); +const DeleteFromBasketIcon = styled(CloseIcon)` + width: 20px; + cursor: pointer; + position: absolute; + left: 235px; + top: -10px; + &:hover { + fill: #d3d3d3; + } +`; + interface CourseCardProps { - onCardClick: (event: MouseEvent) => void; course: Course; - id: string; - isSelected: boolean; } -export const CourseCard = ({ onCardClick, course, id, isSelected }: CourseCardProps) => { +export const CourseCard = ({ course }: CourseCardProps) => { + const [isSelected, setSelected] = useState(false); const classes = useStyles(); - const { addGroup } = useContext(coursesContext)!; + const { addGroup, deleteFromBasket } = useContext(coursesContext)!; const onGroupClick = (group: Group, id: number) => addGroup(group, id); return ( - - {course.name} + + deleteFromBasket(course.id)}> + setSelected(!isSelected)}>{course.name} - {course.groups.map((group, index) => ( - onGroupClick(group, course.id)}> + {course.groups.sort((a,b)=> b.type.localeCompare(a.type)).map((group, index) => ( + onGroupClick(group, course.id)}>

{group.time} {group.room}

{group.lecturer}

))}
-
+
setSelected(!isSelected)}>
diff --git a/src/components/Dropdown.tsx b/src/components/Dropdown.tsx index 4defa11..26186b5 100644 --- a/src/components/Dropdown.tsx +++ b/src/components/Dropdown.tsx @@ -1,4 +1,4 @@ -import React, { useState, useContext, useEffect, MouseEvent } from 'react'; +import React, { useState, useContext, useEffect, MouseEvent, ChangeEvent } from 'react'; import axios from 'axios'; import { Input } from '@material-ui/core'; import ClickAwayListener from '@material-ui/core/ClickAwayListener'; @@ -64,13 +64,10 @@ export const Dropdown = ({ clearInput, handleClearInput }: DropdownProps) => { }, [input, open, basket]); useEffect(() => { - if (clearInput) { - setInput(''); - handleClearInput(); - } + clearInput && (setInput(''), handleClearInput()); }, [clearInput]); - const handleChange = (event: React.ChangeEvent) => setInput(event.target.value); + const handleChange = (event: ChangeEvent) => setInput(event.target.value); const handleClick = () => setOpen(true); @@ -83,7 +80,7 @@ export const Dropdown = ({ clearInput, handleClearInput }: DropdownProps) => { const name = target.textContent; //porozmawiać z Filipem, żeby odrobinę przerobił endpoint - const course: Basket = { name: name.trim(), id: parseInt(id), lecture: null, classes: null }; + const course: Basket = { name: name.trim(), id: parseInt(id) }; addToBasket(course); setOpen(false); diff --git a/src/components/Rightbar.tsx b/src/components/Rightbar.tsx index 874ec0a..d300e33 100644 --- a/src/components/Rightbar.tsx +++ b/src/components/Rightbar.tsx @@ -9,8 +9,8 @@ const RightbarStyled = styled.div` padding-right: 15px; text-align: center; font-family: Lato; + height: 100%; width: 300px; - height: 85vh; overflow-y: scroll; ::-webkit-scrollbar-track { border-radius: 10px; @@ -27,12 +27,24 @@ const RightbarStyled = styled.div` } `; const RightbarTextStyled = styled.div` + display: flex; + flex-direction: column; border-bottom: 1px solid; `; -export const Rightbar = () => { - const [selectedCardId, setSelectedCardId] = useState(null); +const SaveButton = styled.div` + display: flex; + justify-content: center; + align-items: center; + background-color: rgb(100, 181, 246) !important; + border-radius: 10px; + cursor: pointer; + height: 40px; + background-color: red; + margin-bottom: 10px; +`; +export const Rightbar = () => { const { courses, basket } = useContext(coursesContext)!; const getBasketGroups = () => { @@ -42,27 +54,18 @@ export const Rightbar = () => { const filteredCourses = getBasketGroups(); - //działa clunky - const onCardClick = (event: MouseEvent) => { - const target = event.currentTarget; - selectedCardId === target.id ? setSelectedCardId(null) : setSelectedCardId(target.id); - }; - //need to insert student name from db and course maybe based on current time or from db too return ( - Hubert Wrzesiński

- Semestr zimowy 2020/2021 +

+ Hubert Wrzesiński

+ Semestr zimowy 2020/2021 +

+ SAVE
{filteredCourses.map((course, index) => ( - + ))}
); diff --git a/src/components/Scheduler.tsx b/src/components/Scheduler.tsx index a4f851a..b2d7598 100644 --- a/src/components/Scheduler.tsx +++ b/src/components/Scheduler.tsx @@ -1,32 +1,22 @@ -import React, { useEffect, useRef } from 'react'; +import React, { useEffect, MouseEvent, useRef } from 'react'; import { useState } from 'react'; import { SchedulerEvents } from './SchedulerEvents'; import { days, hours } from '../constants/index'; -import styled from 'styled-components'; +import styled from 'styled-components/macro'; const SchedulerWrapper = styled.div` - flex-grow: 3; - margin-top: 20px; border-collapse: collapse; + flex-grow: 1; `; const TableBody = styled.div` width: 100%; - height: 100%; display: flex; flex-direction: column; `; const TableRow = styled.div` display: flex; - flex-direction: row; -`; - -const TableCell = styled.div` - border: 1px solid #ddd; - padding: 10px; - text-align: center; - flex: 1; `; const TableHead = styled.div` @@ -34,57 +24,53 @@ const TableHead = styled.div` width: 100%; `; -const TableHeadCell = styled.div` +interface TableCellProps { + height: number; +} + +const TableCell = styled.div` + height: ${({ height }) => height}px; border: 1px solid #ddd; - padding: 10px; - text-align: center; + display: flex; + align-items: center; + justify-content: center; flex: 1; + font-size: 24px; +`; + +const T = styled.table` + width: 100%; + height: 100%; `; export const Scheduler = () => { - const [currentEventsIds, setCurrentEventsIds] = useState>([]); const cellRef = useRef(null); const [cellWidth, setCellWidth] = useState(0); const [cellTop, setCellTop] = useState(0); + const wrapperRef = useRef(null); + const [wrapperHeight, setWrapperHeight] = useState(0); + useEffect(() => { const handleResize = () => { - if (cellRef.current) { + if (cellRef.current && wrapperRef.current) { setCellWidth(cellRef.current.getBoundingClientRect().width); setCellTop(cellRef.current.getBoundingClientRect().top); + setWrapperHeight(wrapperRef.current.getBoundingClientRect().height); } }; handleResize(); window.addEventListener('resize', handleResize); }, []); - useEffect(() => { - const displayEvents = () => { - currentEventsIds.map((eventId: string) => { - const event = document.getElementById(eventId); - if (event) { - event.style.display = 'block'; - } - }); - }; - displayEvents(); - }, [currentEventsIds]); - - // const handleClick = (e: React.MouseEvent) => { - // const cellId = e.currentTarget.id; - // const column = cellId.slice(0, 1); - // const row = cellId.slice(1); - // const eventId = `eventCol${column}eventRow${Math.floor(parseInt(row) / 2)}`; - - // setCurrentEventsIds((currentEventsIds) => [...currentEventsIds, eventId]); - // }; - return ( <> - + {days.map((day, index) => ( - {day} + + {day} + ))} @@ -92,15 +78,17 @@ export const Scheduler = () => { {[hour, '', '', '', '', ''].map((value, indexCell) => indexRow === 0 && indexCell === 1 ? ( - + ) : ( - {value} + + {value} + ), )} ))} - + ); diff --git a/src/components/SchedulerEvents.tsx b/src/components/SchedulerEvents.tsx index 304d658..c0b447b 100644 --- a/src/components/SchedulerEvents.tsx +++ b/src/components/SchedulerEvents.tsx @@ -1,15 +1,15 @@ -import React, { useContext, useEffect, useState } from 'react'; +import React, { useContext, useEffect, useState, MouseEvent } from 'react'; import { SchedulerRow } from './SchedulerRow'; import { coursesContext } from '../contexts/CoursesProvider'; import { Group, Basket } from '../types'; -import classes from '*.module.css'; interface SchedulerEventsProps { cellTop: number; cellWidth: number; + cellHeight: number; } -export const SchedulerEvents = ({ cellTop, cellWidth }: SchedulerEventsProps) => { +export const SchedulerEvents = ({ cellTop, cellWidth, cellHeight }: SchedulerEventsProps) => { const { basket } = useContext(coursesContext)!; const [choosenGroupsMappedToEvents, setChoosenGroupsMappedToEvents] = useState([]); @@ -28,20 +28,21 @@ export const SchedulerEvents = ({ cellTop, cellWidth }: SchedulerEventsProps) => useEffect(() => { function mapGroupTimeToEventRow(basket: Array) { - const classes = basket.map(({ classes }) => classes).filter((cl) => cl !== null) as Array; - const lectures = basket.map(({ lecture }) => lecture).filter((lec) => lec !== null) as Array; + const classes = basket.map(({ classes, name }) => ({ ...classes, name })) as Array; + const lectures = basket.map(({ lecture, name }) => ({ ...lecture, name })) as Array; const merged = [...classes, ...lectures]; - if (merged.length >= 1) { - const groupsMapped = merged.map(({ id, day, lecturer, room, time }) => ({ - id, - day, - lecturer, - room, - eventRow: groupTimeToEventRowMapping[time], - })); - setChoosenGroupsMappedToEvents(groupsMapped); - } + //deleted if statement, maybe it is needed + const groupsMapped = merged.map(({ id, day, lecturer, room, time, name,type }) => ({ + id, + day: day === 5 ? 4 : day, + lecturer, + room, + eventRow: groupTimeToEventRowMapping[time], + name, + type, + })); + setChoosenGroupsMappedToEvents(groupsMapped); } mapGroupTimeToEventRow(basket); }, [basket]); @@ -51,18 +52,25 @@ export const SchedulerEvents = ({ cellTop, cellWidth }: SchedulerEventsProps) => {[...Array(6)].map((_, index) => ( { - return group.eventRow === index; - })} + groups={choosenGroupsMappedToEvents.filter((group: any) => group.eventRow === index)} indexRow={index} cellTop={ - index == 3 - ? cellTop + (25 + 80 * index) - : index < 3 - ? cellTop + (12 + 80 * index) - : cellTop + (25 + 80 * index) + index === 0 + ? cellTop + (cellHeight + cellHeight * 2 * index + cellHeight / 4) + : index === 1 + ? cellTop + (cellHeight + cellHeight * 2 * index) + : index === 2 + ? cellTop + (cellHeight + cellHeight * 2 * index - cellHeight / 4) + : index === 3 + ? cellTop + (cellHeight + cellHeight * 2 * index - cellHeight / 4) + : index === 4 + ? cellTop + (cellHeight + cellHeight * 2 * index - cellHeight / 2) + : index === 5 + ? cellTop + (cellHeight + cellHeight * 2 * index - (cellHeight * 3) / 4) + : 0 } cellWidth={cellWidth} + cellHeight={cellHeight} /> ))}
diff --git a/src/components/SchedulerRow.tsx b/src/components/SchedulerRow.tsx index 42fd6d6..9d62060 100644 --- a/src/components/SchedulerRow.tsx +++ b/src/components/SchedulerRow.tsx @@ -1,32 +1,87 @@ -import React from 'react'; -import { Group } from '../types'; -import styled from 'styled-components'; +import React, { MouseEvent, useEffect, useState } from 'react'; +import { Group, GroupType } from '../types'; +import styled from 'styled-components/macro'; +import Popover from '@material-ui/core/Popover'; +import Typography from '@material-ui/core/Typography'; +import { makeStyles, createStyles, Theme } from '@material-ui/core/styles'; + +const useStyles = makeStyles((theme: Theme) => + createStyles({ + popover: { + pointerEvents: 'none', + }, + paper: { + padding: theme.spacing(1), + marginLeft: 5, + textAlign: 'center', + }, + }), +); interface SchedulerEventProps { eventIndex: number; cellTop: number; cellWidth: number; + cellHeight: number; } const SchedulerEvent = styled.div` position: absolute; - top: ${(props) => props.cellTop}px; - left: ${(props) => props.cellWidth + 5 + props.cellWidth * props.eventIndex}px; - width: ${(props) => (props.cellWidth * 2) / 3}px; - height: 69px; - background-color: lightblue; + display: flex; + top: ${({ cellTop }) => cellTop}px; + left: ${({ cellWidth, eventIndex }) => cellWidth + 5 + cellWidth * eventIndex}px; + width: ${({ cellWidth }) => (cellWidth * 2.5) / 3}px; + height: ${({ cellHeight }) => (cellHeight * 2 * 3) / 4}px; z-index: 2; `; +interface ClassesProps{ + cellWidth: number; + cellHeight: number; + groupType: GroupType; +} + +const Classes = styled.div` + display: flex; + justify-content: center; + align-items: center; + z-index: 2; + border-radius: 10px; + /* background-color: rgb(100, 181, 246); */ + width: ${({ cellWidth }) => (cellWidth * 2.5) / 3}px; + height: ${({ cellHeight }) => (cellHeight * 2 * 3) / 4}px; + margin-right: 5px; + text-align: center; + background-color:${({groupType})=>groupType === "CLASS" ? "#5642AA" : "#866DF7"} +`; + interface SchedulerRowProps { - groups: Array; + groups: Array; indexRow: number; cellTop: number; cellWidth: number; + cellHeight: number; } -export const SchedulerRow = ({ groups, indexRow, cellTop, cellWidth }: SchedulerRowProps) => { +export const SchedulerRow = ({ groups, indexRow, cellTop, cellWidth, cellHeight }: SchedulerRowProps) => { + const classes = useStyles(); + const [anchorEl, setAnchorEl] = React.useState(null); + const [popoverId, setPopoverId] = useState(null); + console.log("123s"+JSON.stringify(groups)); + + //looks weird + const handlePopoverOpen = (event: MouseEvent) => { + setAnchorEl(event.currentTarget); + setPopoverId(event.currentTarget.id); + }; + + const handlePopoverClose = () => { + setAnchorEl(null); + setPopoverId(null); + }; + + const open = Boolean(anchorEl); return ( <> @@ -35,11 +90,58 @@ export const SchedulerRow = ({ groups, indexRow, cellTop, cellWidth }: Scheduler eventIndex={eventIndex} cellTop={cellTop} cellWidth={cellWidth} + cellHeight={cellHeight} key={eventIndex} id={`eventRow${indexRow}eventCol${eventIndex}`} > - {groups.map((group, index) => - group.day === eventIndex &&
{groups[index]?.lecturer}
, + {groups.map( + (group, index) => + group.day === eventIndex && ( + <> + handlePopoverOpen(e)} + onMouseLeave={handlePopoverClose} + > +

+ {groups[index].name} +

+ {groups[index].room} +

+
+ + +

{groups[index].name}

+

{groups[index].lecturer}

+

{groups[index].room}

+
+
+ + ), )} ))} diff --git a/src/components/Topbar.tsx b/src/components/Topbar.tsx index c7cfcb7..1b2f0f5 100644 --- a/src/components/Topbar.tsx +++ b/src/components/Topbar.tsx @@ -102,9 +102,9 @@ export default function ({ handleTransfer }: TopbarProps) { - + - + @@ -114,4 +114,4 @@ export default function ({ handleTransfer }: TopbarProps) {
); -}; +} diff --git a/src/constants/index.ts b/src/constants/index.ts index ad14654..cd6753a 100644 --- a/src/constants/index.ts +++ b/src/constants/index.ts @@ -1,10 +1,10 @@ export const days = [ "", - "poniedziałek", - "wtorek", - "środa", - "czwartek", - "piątek", + "Poniedziałek", + "Wtorek", + "Środa", + "Czwartek", + "Piątek", ]; export const hours = [ "8:00", diff --git a/src/contexts/CoursesProvider.tsx b/src/contexts/CoursesProvider.tsx index 722b80b..70c7167 100644 --- a/src/contexts/CoursesProvider.tsx +++ b/src/contexts/CoursesProvider.tsx @@ -1,4 +1,4 @@ -import React, { useState, createContext, useEffect } from 'react'; +import React, { useState, createContext, useEffect, ReactNode } from 'react'; import { Course, Group, Basket, GroupType } from '../types'; import axios from 'axios'; @@ -7,11 +7,12 @@ interface CourseContext { basket: Array; addToBasket: (courses: Basket) => void; addGroup: (group: Group, id: number) => void; + deleteFromBasket: (id: number) => void; } export const coursesContext = createContext(null); interface CoursesProviderProps { - children: React.ReactNode; + children: ReactNode; } export const CoursesProvider = ({ children }: CoursesProviderProps) => { @@ -21,6 +22,9 @@ export const CoursesProvider = ({ children }: CoursesProviderProps) => { const addToBasket = (course: Basket) => setBasket([...basket, course]); + const deleteFromBasket = (id: number) => setBasket(basket.filter(course => course.id !== id)); + + useEffect(() => { console.log('BASKET'); console.log(basket); @@ -52,6 +56,6 @@ export const CoursesProvider = ({ children }: CoursesProviderProps) => { }, []); return ( - {children} + {children} ); }; diff --git a/src/types/index.ts b/src/types/index.ts index cdec17f..09c6f40 100644 --- a/src/types/index.ts +++ b/src/types/index.ts @@ -6,8 +6,8 @@ export enum GroupType { export interface Basket { id: number; name: string; - lecture: Group | null; - classes: Group | null; + lecture?: Group; + classes?: Group; } export interface Group {