134 lines
5.1 KiB
TypeScript
134 lines
5.1 KiB
TypeScript
import { Box, Button, LinearProgress, Paper, Typography } from "@mui/material";
|
||
import { questionStore } from "@root/questions";
|
||
import { decrementCurrentQuestionIndex, incrementCurrentQuestionIndex, useQuizPreviewStore } from "@root/quizPreview";
|
||
import { AnyQuizQuestion, QuizQuestionType } from "model/questionTypes/shared";
|
||
import { FC, useEffect } from "react";
|
||
import { useParams } from "react-router-dom";
|
||
import ArrowLeft from "../../assets/icons/questionsPage/arrowLeft";
|
||
import Date from "./QuizPreviewQuestionTypes/Date";
|
||
import Emoji from "./QuizPreviewQuestionTypes/Emoji";
|
||
import File from "./QuizPreviewQuestionTypes/File";
|
||
import Images from "./QuizPreviewQuestionTypes/Images";
|
||
import Number from "./QuizPreviewQuestionTypes/Number";
|
||
import Page from "./QuizPreviewQuestionTypes/Page";
|
||
import Rating from "./QuizPreviewQuestionTypes/Rating";
|
||
import Select from "./QuizPreviewQuestionTypes/Select";
|
||
import Text from "./QuizPreviewQuestionTypes/Text";
|
||
import Variant from "./QuizPreviewQuestionTypes/Variant";
|
||
import Varimg from "./QuizPreviewQuestionTypes/Varimg";
|
||
|
||
|
||
const QuestionPreviewComponentByType: Record<QuizQuestionType, FC<any>> = {
|
||
variant: Variant,
|
||
images: Images,
|
||
varimg: Varimg,
|
||
emoji: Emoji,
|
||
text: Text,
|
||
select: Select,
|
||
date: Date,
|
||
number: Number,
|
||
file: File,
|
||
page: Page,
|
||
rating: Rating,
|
||
};
|
||
|
||
export default function QuizPreviewLayout() {
|
||
const quizId = useParams().quizId ?? 0;
|
||
const listQuestions = questionStore(state => state.listQuestions);
|
||
const currentQuizStep = useQuizPreviewStore(state => state.currentQuestionIndex);
|
||
|
||
const quizQuestions: AnyQuizQuestion[] | undefined = listQuestions[quizId];
|
||
const nonDeletedQuizQuestions = quizQuestions?.filter(question => !question.deleted);
|
||
const maxCurrentQuizStep = nonDeletedQuizQuestions?.length > 0 ? nonDeletedQuizQuestions.length - 1 : 0;
|
||
const currentProgress = Math.floor((currentQuizStep / maxCurrentQuizStep) * 100);
|
||
|
||
const currentQuestion = nonDeletedQuizQuestions[currentQuizStep];
|
||
const QuestionComponent = currentQuestion
|
||
? QuestionPreviewComponentByType[currentQuestion.type as QuizQuestionType]
|
||
: null;
|
||
|
||
const questionElement = QuestionComponent
|
||
? <QuestionComponent key={currentQuestion.id} question={currentQuestion} />
|
||
: null;
|
||
|
||
useEffect(function resetCurrentQuizStep() {
|
||
if (currentQuizStep > maxCurrentQuizStep) {
|
||
decrementCurrentQuestionIndex();
|
||
}
|
||
}, [currentQuizStep, maxCurrentQuizStep]);
|
||
|
||
return (
|
||
<Paper sx={{
|
||
height: "100%",
|
||
display: "flex",
|
||
flexDirection: "column",
|
||
flexGrow: 1,
|
||
borderRadius: "12px",
|
||
pointerEvents: "auto",
|
||
}}>
|
||
<Box sx={{
|
||
p: "16px",
|
||
whiteSpace: "break-spaces",
|
||
overflowY: "auto",
|
||
flexGrow: 1,
|
||
}}>
|
||
{questionElement}
|
||
</Box>
|
||
<Box sx={{
|
||
mt: "auto",
|
||
p: "16px",
|
||
display: "flex",
|
||
borderTop: "1px solid #E3E3E3",
|
||
alignItems: "center",
|
||
}}>
|
||
<Box sx={{
|
||
flexGrow: 1,
|
||
display: "flex",
|
||
flexDirection: "column",
|
||
gap: 1,
|
||
}}>
|
||
<Typography>
|
||
{nonDeletedQuizQuestions.length > 0
|
||
? `Вопрос ${currentQuizStep + 1} из ${nonDeletedQuizQuestions.length}`
|
||
: "Нет вопросов"
|
||
}
|
||
</Typography>
|
||
{nonDeletedQuizQuestions.length > 0 &&
|
||
<LinearProgress
|
||
variant="determinate"
|
||
value={currentProgress}
|
||
sx={{
|
||
"&.MuiLinearProgress-colorPrimary": {
|
||
backgroundColor: "fadePurple.main",
|
||
},
|
||
"& .MuiLinearProgress-barColorPrimary": {
|
||
backgroundColor: "brightPurple.main",
|
||
},
|
||
}}
|
||
/>
|
||
}
|
||
</Box>
|
||
<Box sx={{
|
||
ml: 2,
|
||
display: "flex",
|
||
gap: 1,
|
||
}}>
|
||
<Button
|
||
variant="outlined"
|
||
onClick={decrementCurrentQuestionIndex}
|
||
disabled={currentQuizStep === 0}
|
||
sx={{ px: 1, minWidth: 0 }}
|
||
>
|
||
<ArrowLeft />
|
||
</Button>
|
||
<Button
|
||
variant="contained"
|
||
onClick={() => incrementCurrentQuestionIndex(maxCurrentQuizStep)}
|
||
disabled={currentQuizStep >= maxCurrentQuizStep}
|
||
>Далее</Button>
|
||
</Box>
|
||
</Box>
|
||
</Paper>
|
||
);
|
||
}
|