From b6cd3a6c7f7798548360d6e3b541469685acf71d Mon Sep 17 00:00:00 2001 From: IlyaDoronin Date: Wed, 13 Dec 2023 14:00:59 +0300 Subject: [PATCH] feat: CustomVariant (WIP) --- .../ViewPublicationPage/questions/Rating.tsx | 12 +- .../ViewPublicationPage/questions/Variant.tsx | 157 ++++++++++++------ src/stores/quizView.ts | 50 ++++++ 3 files changed, 157 insertions(+), 62 deletions(-) diff --git a/src/pages/ViewPublicationPage/questions/Rating.tsx b/src/pages/ViewPublicationPage/questions/Rating.tsx index 3ad5c674..e7813d9e 100644 --- a/src/pages/ViewPublicationPage/questions/Rating.tsx +++ b/src/pages/ViewPublicationPage/questions/Rating.tsx @@ -41,18 +41,10 @@ export const Rating = ({ currentQuestion }: RatingProps) => { sx={{ height: "50px", gap: "15px" }} max={currentQuestion.content.steps} icon={ - + } emptyIcon={ - + } /> { - const { answers } = useQuizViewStore(); - const theme = useTheme(); + const { answers, ownVariants } = useQuizViewStore(); const { answer } = answers.find( ({ questionId }) => questionId === currentQuestion.content.id ) ?? {}; + const ownVariant = ownVariants.find( + (variant) => variant.contentId === currentQuestion.content.id + ); const Group = currentQuestion.content.multi ? FormGroup : RadioGroup; + useEffect(() => { + if (!ownVariant) { + updateOwnVariant(currentQuestion.content.id, ""); + } + }, []); + return ( {currentQuestion.title} @@ -60,58 +85,23 @@ export const Variant = ({ currentQuestion }: VariantProps) => { }} > {currentQuestion.content.variants.map((variant, index) => ( - } - icon={} - /> - ) : ( - } icon={} /> - ) - } - label={variant.answer} - onClick={(event) => { - event.preventDefault(); - const variantId = currentQuestion.content.variants[index].id; - - if (currentQuestion.content.multi) { - const currentAnswer = - typeof answer !== "string" ? answer || [] : []; - - updateAnswer( - currentQuestion.content.id, - currentAnswer?.includes(variantId) - ? currentAnswer?.filter((item) => item !== variantId) - : [...currentAnswer, variantId] - ); - - return; - } - - updateAnswer(currentQuestion.content.id, variantId); - - if (answer === variantId) { - deleteAnswer(currentQuestion.content.id); - } - }} + currentQuestion={currentQuestion} + variant={variant} + answer={answer} + index={index} /> ))} + {currentQuestion.content.own && ownVariant && ( + + )} {currentQuestion.content.back && ( @@ -127,3 +117,66 @@ export const Variant = ({ currentQuestion }: VariantProps) => { ); }; + +const VariantItem = ({ + currentQuestion, + variant, + answer, + index, + own = false, +}: VariantItemProps) => { + const theme = useTheme(); + + return ( + } + icon={} + /> + ) : ( + } icon={} /> + ) + } + label={own ? : variant.answer} + onClick={(event) => { + event.preventDefault(); + const variantId = currentQuestion.content.variants[index].id; + + if (currentQuestion.content.multi) { + const currentAnswer = typeof answer !== "string" ? answer || [] : []; + + updateAnswer( + currentQuestion.content.id, + currentAnswer.includes(variantId) + ? currentAnswer?.filter((item) => item !== variantId) + : [...currentAnswer, variantId] + ); + + return; + } + + updateAnswer(currentQuestion.content.id, variantId); + + if (answer === variantId) { + deleteAnswer(currentQuestion.content.id); + } + }} + /> + ); +}; diff --git a/src/stores/quizView.ts b/src/stores/quizView.ts index ae68a8fe..d39a8e6e 100644 --- a/src/stores/quizView.ts +++ b/src/stores/quizView.ts @@ -1,6 +1,8 @@ import { create } from "zustand"; import { devtools } from "zustand/middleware"; +import type { QuestionVariant } from "../model/questionTypes/shared"; + type Answer = { questionId: string; answer: string | string[]; @@ -8,14 +10,21 @@ type Answer = { changed: boolean; }; +type OwnVariant = { + contentId: string; + variant: QuestionVariant; +}; + interface QuizViewStore { answers: Answer[]; + ownVariants: OwnVariant[]; } export const useQuizViewStore = create()( devtools( (set, get) => ({ answers: [], + ownVariants: [], }), { name: "quizView", @@ -50,3 +59,44 @@ export const deleteAnswer = (questionId: string) => { useQuizViewStore.setState({ answers: filteredItems }); }; + +export const updateOwnVariant = (contentId: string, answer: string) => { + const ownVariants = [...useQuizViewStore.getState().ownVariants]; + const ownVariantIndex = ownVariants.findIndex( + (variant) => variant.contentId === contentId + ); + + if (ownVariantIndex < 0) { + ownVariants.push({ + contentId, + variant: { + id: getRandom(), + answer, + extendedText: "", + hints: "", + originalImageUrl: "", + }, + }); + } else { + ownVariants[ownVariantIndex].variant.answer = answer; + } + + useQuizViewStore.setState({ ownVariants }); +}; + +export const deleteOwnVariant = (contentId: string) => { + const ownVariants = [...useQuizViewStore.getState().ownVariants]; + + const filteredOwnVariants = ownVariants.filter( + (variant) => variant.contentId !== contentId + ); + + useQuizViewStore.setState({ ownVariants: filteredOwnVariants }); +}; + +function getRandom() { + const min = Math.ceil(1000000); + const max = Math.floor(10000000); + + return String(Math.floor(Math.random() * (max - min)) + min); +}