Merge branch 'main' into webpack-5
# Conflicts: # src/components/ProfileCalendar/ProfileCalendar.js # src/hooks/useRequest.js
This commit is contained in:
commit
80316d3ba8
@ -18,6 +18,7 @@ import {InstructionPage} from './pages/quiz/InstructionPage'
|
|||||||
import {ResultPage} from './pages/quiz/ResultPage'
|
import {ResultPage} from './pages/quiz/ResultPage'
|
||||||
import {Profile} from './pages/Profile/Profile.js'
|
import {Profile} from './pages/Profile/Profile.js'
|
||||||
import {Summary} from './pages/Summary/Summary'
|
import {Summary} from './pages/Summary/Summary'
|
||||||
|
import {ViewReport} from './pages/ViewReport/ViewReport'
|
||||||
|
|
||||||
import './fonts/stylesheet.css'
|
import './fonts/stylesheet.css'
|
||||||
import 'bootstrap/dist/css/bootstrap.min.css'
|
import 'bootstrap/dist/css/bootstrap.min.css'
|
||||||
@ -56,6 +57,7 @@ const App = () => {
|
|||||||
<Route index element={<Profile/>}/>
|
<Route index element={<Profile/>}/>
|
||||||
<Route exact path='calendar' element={<ProfileCalendar/>}/>
|
<Route exact path='calendar' element={<ProfileCalendar/>}/>
|
||||||
<Route exact path='summary' element={<Summary/>}/>
|
<Route exact path='summary' element={<Summary/>}/>
|
||||||
|
<Route exact path='view' element={<ViewReport/>}/>
|
||||||
</Route>
|
</Route>
|
||||||
|
|
||||||
<Route path="*" element={<Navigate to="/" replace/>}/>
|
<Route path="*" element={<Navigate to="/" replace/>}/>
|
||||||
|
@ -1,13 +1,14 @@
|
|||||||
import React, { useEffect, useState } from 'react'
|
import React, { useEffect, useState } from 'react'
|
||||||
import {useDispatch, useSelector} from 'react-redux'
|
import {useDispatch, useSelector} from 'react-redux'
|
||||||
|
|
||||||
|
import {currentMonth, getReports} from '../Calendar/calendarHelper'
|
||||||
import { Link } from 'react-router-dom'
|
import { Link } from 'react-router-dom'
|
||||||
import moment from "moment";
|
import moment from "moment";
|
||||||
|
|
||||||
import {currentMonth, getReports} from '../Calendar/calendarHelper'
|
|
||||||
import {ProfileCalendarComponent} from "./ProfileCalendarComponent";
|
import {ProfileCalendarComponent} from "./ProfileCalendarComponent";
|
||||||
import { Footer } from '../Footer/Footer'
|
import {Loader} from "../Loader/Loader";
|
||||||
import {ProfileHeader} from "../ProfileHeader/ProfileHeader";
|
import {ProfileHeader} from "../ProfileHeader/ProfileHeader";
|
||||||
|
import { Footer } from '../Footer/Footer'
|
||||||
|
|
||||||
import {urlForLocal} from "../../helper";
|
import {urlForLocal} from "../../helper";
|
||||||
|
|
||||||
@ -25,6 +26,7 @@ export const ProfileCalendar = () => {
|
|||||||
const [reports, setReports] = useState([]);
|
const [reports, setReports] = useState([]);
|
||||||
const [totalHours, setTotalHours] = useState(0);
|
const [totalHours, setTotalHours] = useState(0);
|
||||||
const [requestDates, setRequestDates] = useState('');
|
const [requestDates, setRequestDates] = useState('');
|
||||||
|
const [loader, setLoader] = useState(false)
|
||||||
|
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
@ -32,19 +34,23 @@ export const ProfileCalendar = () => {
|
|||||||
},[]);
|
},[]);
|
||||||
|
|
||||||
useEffect( () => {
|
useEffect( () => {
|
||||||
|
setLoader(true)
|
||||||
if (!requestDates) {
|
if (!requestDates) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
apiRequest(`/reports/reports-by-date?${requestDates}&user_id=${localStorage.getItem('id')}`)
|
apiRequest(`/reports/reports-by-date?${requestDates}&user_card_id=${localStorage.getItem('cardId')}`)
|
||||||
.then((reports) => {
|
.then((reports) => {
|
||||||
let spendTime = 0;
|
let spendTime = 0;
|
||||||
reports.map((report) => {
|
for (const report of reports) {
|
||||||
if (report.spendTime) {
|
report.task.map((task) => {
|
||||||
spendTime += Number(report.spendTime)
|
if(task.hours_spent) {
|
||||||
|
spendTime += Number(task.hours_spent)
|
||||||
|
}
|
||||||
|
})
|
||||||
}
|
}
|
||||||
});
|
|
||||||
setTotalHours(spendTime);
|
setTotalHours(spendTime);
|
||||||
setReports(reports)
|
setReports(reports)
|
||||||
|
setLoader(false)
|
||||||
})
|
})
|
||||||
}, [requestDates]);
|
}, [requestDates]);
|
||||||
|
|
||||||
@ -68,6 +74,9 @@ export const ProfileCalendar = () => {
|
|||||||
}}>Заполнить отчет за день</button>
|
}}>Заполнить отчет за день</button>
|
||||||
</Link>
|
</Link>
|
||||||
</div>
|
</div>
|
||||||
|
{loader ?
|
||||||
|
<Loader height={80} width={80} />
|
||||||
|
:
|
||||||
<div className='row'>
|
<div className='row'>
|
||||||
<div className='col-12 col-xl-12'>
|
<div className='col-12 col-xl-12'>
|
||||||
<ProfileCalendarComponent reportsDates={reports} />
|
<ProfileCalendarComponent reportsDates={reports} />
|
||||||
@ -76,6 +85,7 @@ export const ProfileCalendar = () => {
|
|||||||
</p>
|
</p>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
}
|
||||||
</div>
|
</div>
|
||||||
<Footer />
|
<Footer />
|
||||||
</div>
|
</div>
|
||||||
|
@ -37,7 +37,7 @@ export const ProfileCalendarComponent = ({reportsDates}) => {
|
|||||||
function dayStyles(day) {
|
function dayStyles(day) {
|
||||||
if (value < day) return `block`
|
if (value < day) return `block`
|
||||||
for (const date of reportsDates) {
|
for (const date of reportsDates) {
|
||||||
if (`${new Date(day).getFullYear()}-${correctDay(new Date(day).getMonth() + 1)}-${correctDay(new Date(day).getDate())}` === date.date) {
|
if (`${new Date(day).getFullYear()}-${correctDay(new Date(day).getMonth() + 1)}-${correctDay(new Date(day).getDate())}` === date.created_at) {
|
||||||
return `before`
|
return `before`
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -48,8 +48,8 @@ export const ProfileCalendarComponent = ({reportsDates}) => {
|
|||||||
|
|
||||||
function correctRoute(day) {
|
function correctRoute(day) {
|
||||||
for (const date of reportsDates) {
|
for (const date of reportsDates) {
|
||||||
if (`${new Date(day).getFullYear()}-${correctDay(new Date(day).getMonth() + 1)}-${correctDay(new Date(day).getDate())}` === date.date) {
|
if (`${new Date(day).getFullYear()}-${correctDay(new Date(day).getMonth() + 1)}-${correctDay(new Date(day).getDate())}` === date.created_at) {
|
||||||
return `../../view/report`
|
return `../view`
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return '../../report'
|
return '../../report'
|
||||||
|
@ -16,6 +16,15 @@
|
|||||||
.summary__info {
|
.summary__info {
|
||||||
padding-right: 25px;
|
padding-right: 25px;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.loader {
|
||||||
|
margin: 20px 0 50px;
|
||||||
|
&:hover {
|
||||||
|
path {
|
||||||
|
fill: #ffffff;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
.profile__calendar {
|
.profile__calendar {
|
||||||
margin-top: 20px;
|
margin-top: 20px;
|
||||||
}
|
}
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
import React, {useState} from 'react'
|
import React, {useState} from 'react'
|
||||||
import {useSelector} from 'react-redux'
|
import {useSelector} from 'react-redux'
|
||||||
import {Link} from 'react-router-dom'
|
import {Link, useNavigate} from 'react-router-dom'
|
||||||
|
|
||||||
import {Loader} from '../Loader/Loader'
|
import {Loader} from '../Loader/Loader'
|
||||||
import {currentMonthAndDay} from '../Calendar/calendarHelper'
|
import {currentMonthAndDay} from '../Calendar/calendarHelper'
|
||||||
@ -33,10 +33,11 @@ const getCreatedDate = (day) => {
|
|||||||
};
|
};
|
||||||
|
|
||||||
const ReportForm = () => {
|
const ReportForm = () => {
|
||||||
|
const navigate= useNavigate();
|
||||||
const reportDate = useSelector(getReportDate);
|
const reportDate = useSelector(getReportDate);
|
||||||
|
|
||||||
const [isFetching, setIsFetching] = useState(false);
|
const [isFetching, setIsFetching] = useState(false);
|
||||||
const [reportSuccess, setReportSuccess] = useState(false);
|
const [reportSuccess, setReportSuccess] = useState('');
|
||||||
|
|
||||||
const [inputs, setInputs] = useState([{task: '', hours_spent: '', minutes_spent: 0}]);
|
const [inputs, setInputs] = useState([{task: '', hours_spent: '', minutes_spent: 0}]);
|
||||||
const [troublesInputValue, setTroublesInputValue] = useState('');
|
const [troublesInputValue, setTroublesInputValue] = useState('');
|
||||||
@ -55,6 +56,11 @@ const ReportForm = () => {
|
|||||||
};
|
};
|
||||||
|
|
||||||
const handler = () => {
|
const handler = () => {
|
||||||
|
if(!inputs[0].task) {
|
||||||
|
setReportSuccess('Заполните задачи');
|
||||||
|
setTimeout(() => setReportSuccess(''), 1000)
|
||||||
|
return
|
||||||
|
}
|
||||||
apiRequest('/reports/create', {
|
apiRequest('/reports/create', {
|
||||||
method: 'POST',
|
method: 'POST',
|
||||||
data: {
|
data: {
|
||||||
@ -65,10 +71,11 @@ const ReportForm = () => {
|
|||||||
status: 1,
|
status: 1,
|
||||||
},
|
},
|
||||||
}).then((res) => {
|
}).then((res) => {
|
||||||
if (res.status === 200) {
|
setReportSuccess('Отчет отправлен');
|
||||||
setReportSuccess(true);
|
setTimeout(() => {
|
||||||
setTimeout(() => setReportSuccess(false), 2000)
|
setReportSuccess('')
|
||||||
}
|
navigate('/profile/calendar');
|
||||||
|
}, 1000)
|
||||||
setInputs(() => []);
|
setInputs(() => []);
|
||||||
setTroublesInputValue('');
|
setTroublesInputValue('');
|
||||||
setScheduledInputValue('');
|
setScheduledInputValue('');
|
||||||
@ -188,7 +195,7 @@ const ReportForm = () => {
|
|||||||
Всего за день : <span>{totalHours} часов</span>
|
Всего за день : <span>{totalHours} часов</span>
|
||||||
</p>
|
</p>
|
||||||
{reportSuccess &&
|
{reportSuccess &&
|
||||||
<p className='report-form__footer-done'>Отчет отправлен</p>
|
<p className={`report-form__footer-done ${reportSuccess === 'Заполните задачи' ? 'errorText' : ''}`}>{reportSuccess}</p>
|
||||||
}
|
}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
@ -314,6 +314,11 @@
|
|||||||
font-weight: 500;
|
font-weight: 500;
|
||||||
margin-left: 20px;
|
margin-left: 20px;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.errorText {
|
||||||
|
color: #bf3c3c;
|
||||||
|
font-weight: 600;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
&__form {
|
&__form {
|
||||||
|
0
src/hooks/useRequest.js
Normal file
0
src/hooks/useRequest.js
Normal file
BIN
src/images/arrowViewReport.png
Normal file
BIN
src/images/arrowViewReport.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 183 B |
3
src/images/arrowViewReport.svg
Normal file
3
src/images/arrowViewReport.svg
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
<svg width="9" height="16" viewBox="0 0 9 16" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||||
|
<path d="M1.00008 1L8.00008 8L1.00008 15" stroke="white" stroke-width="1.8" stroke-linecap="round" stroke-linejoin="round"/>
|
||||||
|
</svg>
|
After Width: | Height: | Size: 226 B |
@ -67,7 +67,7 @@ export const Summary = () => {
|
|||||||
<button>Редактировать раздел</button>
|
<button>Редактировать раздел</button>
|
||||||
</div>
|
</div>
|
||||||
<div className='summary__sectionGitItems'>
|
<div className='summary__sectionGitItems'>
|
||||||
{gitInfo.length && gitInfo.map((itemGit) => {
|
{Boolean(gitInfo.length) && gitInfo.map((itemGit) => {
|
||||||
return <div key={itemGit.id} className='summary__sectionGitItem gitItem'>
|
return <div key={itemGit.id} className='summary__sectionGitItem gitItem'>
|
||||||
<div className='gitItem__info'>
|
<div className='gitItem__info'>
|
||||||
<div className='gitItem__info__about'>
|
<div className='gitItem__info__about'>
|
||||||
|
175
src/pages/ViewReport/ViewReport.js
Normal file
175
src/pages/ViewReport/ViewReport.js
Normal file
@ -0,0 +1,175 @@
|
|||||||
|
import React, {useEffect, useState} from 'react'
|
||||||
|
import {Link} from "react-router-dom";
|
||||||
|
import {useRequest} from "../../hooks/useRequest";
|
||||||
|
import {useSelector} from "react-redux";
|
||||||
|
import {getReportDate} from "../../redux/reportSlice";
|
||||||
|
import SVG from 'react-inlinesvg'
|
||||||
|
|
||||||
|
import {Loader} from "../../components/Loader/Loader"
|
||||||
|
import {ProfileHeader} from "../../components/ProfileHeader/ProfileHeader";
|
||||||
|
import {Footer} from "../../components/Footer/Footer";
|
||||||
|
|
||||||
|
import arrow from "../../images/right-arrow.png";
|
||||||
|
import arrowSwitchDate from "../../images/arrowViewReport.png";
|
||||||
|
|
||||||
|
import './viewReport.scss'
|
||||||
|
|
||||||
|
export const ViewReport = () => {
|
||||||
|
const getCreatedDate = (day) => {
|
||||||
|
if (day) {
|
||||||
|
return `${new Date(day).getFullYear()}-${new Date(day).getMonth() + 1}-${new Date(day).getDate()}`
|
||||||
|
} else {
|
||||||
|
const date = new Date();
|
||||||
|
const dd = String(date.getDate()).padStart(2, '0');
|
||||||
|
const mm = String(date.getMonth() + 1).padStart(2, '0');
|
||||||
|
const yyyy = date.getFullYear();
|
||||||
|
return `${yyyy}-${mm}-${dd}`
|
||||||
|
}
|
||||||
|
};
|
||||||
|
const {apiRequest} = useRequest();
|
||||||
|
const reportDate = useSelector(getReportDate);
|
||||||
|
|
||||||
|
const [taskText, setTaskText] = useState([]);
|
||||||
|
const [difficulties, setDifficulties] = useState([])
|
||||||
|
const [tomorrowTask, setTomorrowTask] = useState([])
|
||||||
|
const [totalHours, setTotalHours] = useState(0);
|
||||||
|
const [reportDay] = useState(new Date (getCreatedDate(reportDate)))
|
||||||
|
const [currentDay] = useState(new Date ())
|
||||||
|
const [loader, setLoader] = useState(false)
|
||||||
|
|
||||||
|
function getReportFromDate(day) {
|
||||||
|
setLoader(true)
|
||||||
|
setTaskText([])
|
||||||
|
setDifficulties([])
|
||||||
|
setTomorrowTask([])
|
||||||
|
apiRequest(`reports/find-by-date?user_card_id=${localStorage.getItem('cardId')}&date=${day}`)
|
||||||
|
.then(res => {
|
||||||
|
let spendTime = 0
|
||||||
|
for (const item of res) {
|
||||||
|
if(item.difficulties) {
|
||||||
|
setDifficulties(prevArray => [...prevArray, item.difficulties])
|
||||||
|
}
|
||||||
|
if(item.tomorrow) {
|
||||||
|
setTomorrowTask(prevArray => [...prevArray, item.tomorrow])
|
||||||
|
}
|
||||||
|
item.task.map((task) => {
|
||||||
|
const taskInfo = {
|
||||||
|
hours: task.hours_spent,
|
||||||
|
task: task.task,
|
||||||
|
id: task.id
|
||||||
|
}
|
||||||
|
if(task.hours_spent) {
|
||||||
|
spendTime += Number(task.hours_spent)
|
||||||
|
}
|
||||||
|
setTaskText(prevArray => [...prevArray, taskInfo])
|
||||||
|
})
|
||||||
|
}
|
||||||
|
setTotalHours(spendTime)
|
||||||
|
setLoader(false)
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
function nextDay() {
|
||||||
|
reportDay.setDate(reportDay.getDate() + 1);
|
||||||
|
getReportFromDate(getCreatedDate(reportDay))
|
||||||
|
}
|
||||||
|
|
||||||
|
function previousDay() {
|
||||||
|
reportDay.setDate(reportDay.getDate() - 1);
|
||||||
|
getReportFromDate(getCreatedDate(reportDay))
|
||||||
|
}
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
getReportFromDate(getCreatedDate(reportDate))
|
||||||
|
}, []);
|
||||||
|
return (
|
||||||
|
<div className='viewReport'>
|
||||||
|
<ProfileHeader/>
|
||||||
|
<div className='container'>
|
||||||
|
<div className='viewReport__info'>
|
||||||
|
<h2 className='viewReport__title'>Ваши отчеты - <span>просмотр отчета за день</span></h2>
|
||||||
|
<Link className='viewReport__back' to={`/profile/calendar`}>
|
||||||
|
<img src={arrow} alt='arrow'/><p>Вернуться</p>
|
||||||
|
</Link>
|
||||||
|
<div className='viewReport__bar'>
|
||||||
|
<h3 className='viewReport__bar__date'>{getCreatedDate(reportDay)}</h3>
|
||||||
|
<p className='viewReport__bar__hours'>Вами потрачено на работу : <span>{totalHours} часов</span></p>
|
||||||
|
{/*<div className='viewReport__bar__progressBar'>*/}
|
||||||
|
{/* <span></span>*/}
|
||||||
|
{/*</div>*/}
|
||||||
|
{/*<p className='viewReport__bar__total'>122 часа из 160</p>*/}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div className='viewReport__switchDate'>
|
||||||
|
<div className='viewReport__switchDate__prev switchDate' onClick={() => previousDay()}>
|
||||||
|
<img src={arrowSwitchDate} alt='arrow'/>
|
||||||
|
</div>
|
||||||
|
<p>{getCreatedDate(reportDay)}</p>
|
||||||
|
<div className={`viewReport__switchDate__next switchDate ${getCreatedDate(currentDay) === getCreatedDate(reportDay) ? 'disable' : ''}`} onClick={() => nextDay()}>
|
||||||
|
<img src={arrowSwitchDate} alt='arrow'/>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
{loader &&
|
||||||
|
<Loader width={75} height={75}/>
|
||||||
|
}
|
||||||
|
{Boolean(taskText.length) &&
|
||||||
|
<div className='viewReport__content'>
|
||||||
|
<div className='table__container'>
|
||||||
|
<table className='viewReport__done'>
|
||||||
|
<thead>
|
||||||
|
<tr>
|
||||||
|
<th><p>Какие задачи были выполнены?</p></th>
|
||||||
|
<th><p>Время</p></th>
|
||||||
|
</tr>
|
||||||
|
</thead>
|
||||||
|
<tbody>
|
||||||
|
{taskText.length && taskText.map((task) => {
|
||||||
|
return <tr key={task.id}>
|
||||||
|
<td>
|
||||||
|
<p>{task.task}</p>
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
<div className='viewReport__done__hours__item'>
|
||||||
|
<span>{task.hours}</span>
|
||||||
|
<p>часа на задачу</p>
|
||||||
|
</div>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
})}
|
||||||
|
<tr>
|
||||||
|
<td></td>
|
||||||
|
<td><span>Всего: {totalHours} часов</span></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
{Boolean(difficulties.length) &&
|
||||||
|
<div className='viewReport__item'>
|
||||||
|
<h3>Какие сложности возникли?</h3>
|
||||||
|
{difficulties.map((item, index) => {
|
||||||
|
return <p key={index}>{item}</p>
|
||||||
|
}
|
||||||
|
)}
|
||||||
|
</div>
|
||||||
|
}
|
||||||
|
{Boolean(tomorrowTask.length) &&
|
||||||
|
<div className='viewReport__item'>
|
||||||
|
<h3>Что планируется сделать завтра?</h3>
|
||||||
|
{tomorrowTask.map((item, index) => {
|
||||||
|
return <p key={index}>{item}</p>
|
||||||
|
}
|
||||||
|
)}
|
||||||
|
</div>
|
||||||
|
}
|
||||||
|
</div>
|
||||||
|
}
|
||||||
|
{!Boolean(taskText.length) && !loader &&
|
||||||
|
<div className='viewReport__noTask'>
|
||||||
|
<p>В этот день вы <span>не заполняли</span> отчет</p>
|
||||||
|
</div>
|
||||||
|
}
|
||||||
|
<Footer />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
)
|
||||||
|
};
|
308
src/pages/ViewReport/viewReport.scss
Normal file
308
src/pages/ViewReport/viewReport.scss
Normal file
@ -0,0 +1,308 @@
|
|||||||
|
.viewReport {
|
||||||
|
background: #F1F1F1;
|
||||||
|
height: 100%;
|
||||||
|
min-height: 100vh;
|
||||||
|
font-family: 'LabGrotesque', sans-serif;
|
||||||
|
|
||||||
|
.container {
|
||||||
|
max-width: 1160px;
|
||||||
|
margin-top: 23px;
|
||||||
|
|
||||||
|
@media (max-width: 570px) {
|
||||||
|
margin-top: 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
&__info {
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
margin-top: 23px;
|
||||||
|
}
|
||||||
|
|
||||||
|
&__title {
|
||||||
|
font-weight: 700;
|
||||||
|
font-size: 22px;
|
||||||
|
line-height: 32px;
|
||||||
|
color: #000000;
|
||||||
|
span {
|
||||||
|
color: #52B709;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
&__back {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
column-gap: 30px;
|
||||||
|
margin-top: 20px;
|
||||||
|
cursor: pointer;
|
||||||
|
|
||||||
|
&:hover {
|
||||||
|
text-decoration: none;
|
||||||
|
}
|
||||||
|
p {
|
||||||
|
margin-bottom: 0;
|
||||||
|
font-weight: 400;
|
||||||
|
font-size: 14px;
|
||||||
|
line-height: 32px;
|
||||||
|
color: #000000;
|
||||||
|
text-decoration: none;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
&__bar {
|
||||||
|
display: flex;
|
||||||
|
margin-top: 20px;
|
||||||
|
background: #FFFFFF;
|
||||||
|
border-radius: 12px;
|
||||||
|
padding: 20px 33px;
|
||||||
|
align-items: center;
|
||||||
|
column-gap: 60px;
|
||||||
|
height: 72px;
|
||||||
|
justify-content: space-between;
|
||||||
|
|
||||||
|
&__date {
|
||||||
|
font-weight: 500;
|
||||||
|
font-size: 22px;
|
||||||
|
line-height: 32px;
|
||||||
|
color: #000000;
|
||||||
|
}
|
||||||
|
|
||||||
|
&__hours {
|
||||||
|
font-weight: 400;
|
||||||
|
font-size: 12px;
|
||||||
|
line-height: 32px;
|
||||||
|
color: #000000;
|
||||||
|
|
||||||
|
span {
|
||||||
|
color: #52B709;
|
||||||
|
font-weight: 700;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
&__progressBar {
|
||||||
|
max-width: 390px;
|
||||||
|
width: 100%;
|
||||||
|
background: #F1F1F1;
|
||||||
|
border-radius: 12px;
|
||||||
|
height: 8px;
|
||||||
|
position: relative;
|
||||||
|
|
||||||
|
span {
|
||||||
|
position: absolute;
|
||||||
|
height: 100%;
|
||||||
|
left: 0;
|
||||||
|
width: 60%;
|
||||||
|
background: #52B709;
|
||||||
|
border-radius: 12px;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
&__total {
|
||||||
|
font-weight: 400;
|
||||||
|
font-size: 12px;
|
||||||
|
line-height: 32px;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
h3 {
|
||||||
|
margin-bottom: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
p {
|
||||||
|
margin-bottom: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
&__switchDate {
|
||||||
|
display: flex;
|
||||||
|
margin: 30px 0;
|
||||||
|
justify-content: center;
|
||||||
|
column-gap: 140px;
|
||||||
|
align-items: center;
|
||||||
|
|
||||||
|
p {
|
||||||
|
font-weight: 400;
|
||||||
|
font-size: 18px;
|
||||||
|
line-height: 32px;
|
||||||
|
color: #000000;
|
||||||
|
}
|
||||||
|
|
||||||
|
.switchDate {
|
||||||
|
width: 48px;
|
||||||
|
height: 48px;
|
||||||
|
background: #8DC63F;
|
||||||
|
border-radius: 50px;
|
||||||
|
display: flex;
|
||||||
|
justify-content: center;
|
||||||
|
align-items: center;
|
||||||
|
cursor: pointer;
|
||||||
|
|
||||||
|
img {
|
||||||
|
margin-left: 3px;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
&__prev {
|
||||||
|
transform: rotate(180deg);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.disable {
|
||||||
|
pointer-events: none;
|
||||||
|
opacity: 0.3;
|
||||||
|
}
|
||||||
|
|
||||||
|
.loader {
|
||||||
|
&:hover {
|
||||||
|
path {
|
||||||
|
fill: #ffffff;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.table__container {
|
||||||
|
margin: 0 -28px;
|
||||||
|
overflow: hidden;
|
||||||
|
position: relative;
|
||||||
|
}
|
||||||
|
|
||||||
|
&__done {
|
||||||
|
width: 100%;
|
||||||
|
border-collapse: separate;
|
||||||
|
border-spacing: 28px 0;
|
||||||
|
|
||||||
|
th {
|
||||||
|
padding: 32px 40px;
|
||||||
|
background: white;
|
||||||
|
border-radius: 12px 12px 0 0;
|
||||||
|
font-weight: 500;
|
||||||
|
font-size: 22px;
|
||||||
|
line-height: 32px;
|
||||||
|
color: #000000;
|
||||||
|
}
|
||||||
|
|
||||||
|
td {
|
||||||
|
padding: 15px 40px;
|
||||||
|
background: white;
|
||||||
|
|
||||||
|
p {
|
||||||
|
font-weight: 400;
|
||||||
|
font-size: 12px;
|
||||||
|
line-height: 24px;
|
||||||
|
color: #000000;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
tr:last-child {
|
||||||
|
td {
|
||||||
|
border-radius: 0 0 12px 12px;
|
||||||
|
}
|
||||||
|
|
||||||
|
td:last-child {
|
||||||
|
font-weight: 500;
|
||||||
|
font-size: 17px;
|
||||||
|
line-height: 32px;
|
||||||
|
color: #000000;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
&__hours {
|
||||||
|
width: 25%;
|
||||||
|
background: #FFFFFF;
|
||||||
|
border-radius: 12px;
|
||||||
|
padding: 32px 40px 18px;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
row-gap: 30px;
|
||||||
|
|
||||||
|
h3 {
|
||||||
|
font-weight: 500;
|
||||||
|
font-size: 22px;
|
||||||
|
line-height: 32px;
|
||||||
|
color: #000000;
|
||||||
|
}
|
||||||
|
|
||||||
|
&__item {
|
||||||
|
display: flex;
|
||||||
|
column-gap: 25px;
|
||||||
|
align-items: center;
|
||||||
|
min-width: 155px;
|
||||||
|
|
||||||
|
span {
|
||||||
|
width: 48px;
|
||||||
|
height: 48px;
|
||||||
|
background: #8DC63F;
|
||||||
|
border-radius: 50px;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
font-weight: 700;
|
||||||
|
font-size: 22px;
|
||||||
|
line-height: 32px;
|
||||||
|
color: #000000;
|
||||||
|
}
|
||||||
|
|
||||||
|
p {
|
||||||
|
font-weight: 400;
|
||||||
|
font-size: 12px;
|
||||||
|
line-height: 32px;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
&__total {
|
||||||
|
font-weight: 500;
|
||||||
|
font-size: 17px;
|
||||||
|
line-height: 32px;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
&__item {
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
row-gap: 22px;
|
||||||
|
background: #FFFFFF;
|
||||||
|
border-radius: 12px;
|
||||||
|
margin: 25px 0;
|
||||||
|
padding: 25px 35px;
|
||||||
|
|
||||||
|
h3 {
|
||||||
|
font-weight: 500;
|
||||||
|
font-size: 22px;
|
||||||
|
line-height: 32px;
|
||||||
|
}
|
||||||
|
|
||||||
|
p {
|
||||||
|
font-weight: 400;
|
||||||
|
font-size: 12px;
|
||||||
|
line-height: 24px;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
&__item:last-child {
|
||||||
|
margin-bottom: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
&__noTask {
|
||||||
|
padding: 25px 10px;
|
||||||
|
background: #FFFFFF;
|
||||||
|
border-radius: 12px;
|
||||||
|
text-align: center;
|
||||||
|
|
||||||
|
p {
|
||||||
|
font-weight: 400;
|
||||||
|
font-size: 22px;
|
||||||
|
line-height: 32px;
|
||||||
|
color: #000000;
|
||||||
|
|
||||||
|
span {
|
||||||
|
color: #8BCC60;
|
||||||
|
font-weight: 500;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
footer {
|
||||||
|
margin-top: 70px;
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user