feat: default store objects

This commit is contained in:
IlyaDoronin 2023-10-02 22:43:07 +03:00
parent 0f90722769
commit 6f21c992a6
15 changed files with 424 additions and 28 deletions

28
src/constants/date.ts Normal file

@ -0,0 +1,28 @@
import type { QuizQuestionDate } from "../model/questionTypes/date";
export const QuizQuestionDateEmpty: Omit<QuizQuestionDate, "id"> = {
title: "",
type: "date",
content: {
required: false,
innerNameCheck: false,
innerName: "",
type: "calendar",
dateRange: false,
time: false,
hint: {
text: "",
video: "",
},
rule: {
or: true,
show: true,
reqs: [
{
id: "",
vars: [],
},
],
},
},
};

34
src/constants/emoji.ts Normal file

@ -0,0 +1,34 @@
import type { QuizQuestionEmoji } from "../model/questionTypes/emoji";
export const QuizQuestionEmojiEmpty: Omit<QuizQuestionEmoji, "id"> = {
title: "",
type: "emoji",
content: {
multi: false,
own: false,
innerNameCheck: false,
innerName: "",
required: false,
variants: [
{
answer: "",
hints: "",
emoji: "",
},
],
hint: {
text: "",
video: "",
},
rule: {
or: true,
show: true,
reqs: [
{
id: "",
vars: [],
},
],
},
},
};

27
src/constants/file.ts Normal file

@ -0,0 +1,27 @@
import type { QuizQuestionFile } from "../model/questionTypes/file";
export const QuizQuestionFileEmpty: Omit<QuizQuestionFile, "id"> = {
title: "",
type: "file",
content: {
required: false,
innerNameCheck: false,
innerName: "",
autofill: false,
type: "all",
hint: {
text: "",
video: "",
},
rule: {
or: true,
show: true,
reqs: [
{
id: "",
vars: [],
},
],
},
},
};

36
src/constants/images.ts Normal file

@ -0,0 +1,36 @@
import type { QuizQuestionImages } from "../model/questionTypes/images";
export const QuizQuestionImagesEmpty: Omit<QuizQuestionImages, "id"> = {
title: "",
type: "images",
content: {
own: false,
multi: false,
xy: "1:1",
innerNameCheck: false,
innerName: "",
large: false,
format: "carousel",
required: false,
variants: [
{
answer: "",
hints: "",
},
],
hint: {
text: "",
video: "",
},
rule: {
or: true,
show: true,
reqs: [
{
id: "",
vars: [],
},
],
},
},
};

29
src/constants/number.ts Normal file

@ -0,0 +1,29 @@
import type { QuizQuestionNumber } from "../model/questionTypes/number";
export const QuizQuestionNumberEmpty: Omit<QuizQuestionNumber, "id"> = {
title: "",
type: "number",
content: {
required: false,
innerNameCheck: false,
innerName: "",
range: [0, 1],
defaultValue: 0,
step: 1,
chooseRange: false,
hint: {
text: "",
video: "",
},
rule: {
or: true,
show: true,
reqs: [
{
id: "",
vars: [],
},
],
},
},
};

26
src/constants/page.ts Normal file

@ -0,0 +1,26 @@
import type { QuizQuestionPage } from "../model/questionTypes/page";
export const QuizQuestionPageEmpty: Omit<QuizQuestionPage, "id"> = {
title: "",
type: "page",
content: {
innerNameCheck: false,
innerName: "",
text: "",
video: "",
hint: {
text: "",
video: "",
},
rule: {
or: true,
show: true,
reqs: [
{
id: "",
vars: [],
},
],
},
},
};

29
src/constants/rating.ts Normal file

@ -0,0 +1,29 @@
import type { QuizQuestionRating } from "../model/questionTypes/rating";
export const QuizQuestionRatingEmpty: Omit<QuizQuestionRating, "id"> = {
title: "",
type: "rating",
content: {
required: false,
innerNameCheck: false,
innerName: "",
steps: 5,
ratingExpanded: false,
ratingDescription: "",
form: "",
hint: {
text: "",
video: "",
},
rule: {
or: true,
show: true,
reqs: [
{
id: "",
vars: [],
},
],
},
},
};

27
src/constants/select.ts Normal file

@ -0,0 +1,27 @@
import type { QuizQuestionSelect } from "../model/questionTypes/select";
export const QuizQuestionSelectEmpty: Omit<QuizQuestionSelect, "id"> = {
title: "",
type: "select",
content: {
multi: false,
required: false,
innerNameCheck: false,
innerName: "",
default: "",
hint: {
text: "",
video: "",
},
rule: {
or: true,
show: true,
reqs: [
{
id: "",
vars: [],
},
],
},
},
};

28
src/constants/text.ts Normal file

@ -0,0 +1,28 @@
import type { QuizQuestionText } from "../model/questionTypes/text";
export const QuizQuestionTextEmpty: Omit<QuizQuestionText, "id"> = {
title: "",
type: "text",
content: {
placeholder: "",
innerNameCheck: false,
innerName: "",
required: false,
autofill: false,
answerType: "single",
hint: {
text: "",
video: "",
},
rule: {
or: true,
show: true,
reqs: [
{
id: "",
vars: [],
},
],
},
},
};

34
src/constants/variant.ts Normal file

@ -0,0 +1,34 @@
import type { QuizQuestionVariant } from "../model/questionTypes/variant";
export const QuizQuestionVariantEmpty: Omit<QuizQuestionVariant, "id"> = {
title: "",
type: "variant",
content: {
largeCheck: false,
multi: false,
own: false,
innerNameCheck: false,
required: false,
innerName: "",
variants: [
{
answer: "",
hints: "",
},
],
hint: {
text: "",
video: "",
},
rule: {
or: true,
show: true,
reqs: [
{
id: "",
vars: [],
},
],
},
},
};

32
src/constants/varimg.ts Normal file

@ -0,0 +1,32 @@
import type { QuizQuestionVarImg } from "../model/questionTypes/varimg";
export const QuizQuestionVarImgEmpty: Omit<QuizQuestionVarImg, "id"> = {
title: "",
type: "varimg",
content: {
own: false,
innerNameCheck: false,
innerName: "",
required: false,
variants: [
{
answer: "",
hints: "",
},
],
hint: {
text: "",
video: "",
},
rule: {
or: true,
show: true,
reqs: [
{
id: "",
vars: [],
},
],
},
},
};

@ -21,7 +21,10 @@ export interface QuizQuestionImages extends QuizQuestionBase {
/** Чекбокс "Необязательный вопрос" */ /** Чекбокс "Необязательный вопрос" */
required: boolean; required: boolean;
/** Варианты (картинки) */ /** Варианты (картинки) */
variants: unknown; variants: {
answer: string;
hints: string;
}[];
hint: QuizQuestionHint; hint: QuizQuestionHint;
rule: QuizQuestionBranchingRules; rule: QuizQuestionBranchingRules;
}; };

@ -1,14 +1,14 @@
import { QuizQuestionDate } from "./date"; import type { QuizQuestionDate } from "./date";
import { QuizQuestionEmoji } from "./emoji"; import type { QuizQuestionEmoji } from "./emoji";
import { QuizQuestionFile } from "./file"; import type { QuizQuestionFile } from "./file";
import { QuizQuestionImages } from "./images"; import type { QuizQuestionImages } from "./images";
import { QuizQuestionNumber } from "./number"; import type { QuizQuestionNumber } from "./number";
import { QuizQuestionPage } from "./page"; import type { QuizQuestionPage } from "./page";
import { QuizQuestionRating } from "./rating"; import type { QuizQuestionRating } from "./rating";
import { QuizQuestionSelect } from "./select"; import type { QuizQuestionSelect } from "./select";
import { QuizQuestionText } from "./text"; import type { QuizQuestionText } from "./text";
import { QuizQuestionVariant } from "./variant"; import type { QuizQuestionVariant } from "./variant";
import { QuizQuestionVarImg } from "./varimg"; import type { QuizQuestionVarImg } from "./varimg";
export interface QuizQuestionBranchingRules { export interface QuizQuestionBranchingRules {

@ -7,15 +7,19 @@ import SwitchEmoji from "./switchEmoji";
import { AnswerDraggableList } from "../AnswerDraggableList"; import { AnswerDraggableList } from "../AnswerDraggableList";
import { questionStore, updateQuestionsList } from "@root/questions"; import { questionStore, updateQuestionsList } from "@root/questions";
import type { QuizQuestionEmoji } from "../../../model/questionTypes/emoji";
interface Props { interface Props {
totalIndex: number; totalIndex: number;
} }
export default function Emoji({ totalIndex }: Props) { export default function Emoji({ totalIndex }: Props) {
const [switchState, setSwitchState] = useState<string>("setting"); const [switchState, setSwitchState] = useState<string>("setting");
const { listQuestions } = questionStore(); const { listQuestions } = questionStore();
const quizId = Number(useParams().quizId); const quizId = Number(useParams().quizId);
const theme = useTheme(); const theme = useTheme();
const isMobile = useMediaQuery(theme.breakpoints.down(790)); const isMobile = useMediaQuery(theme.breakpoints.down(790));
const question = listQuestions[quizId][totalIndex] as QuizQuestionEmoji;
const SSHC = (data: string) => { const SSHC = (data: string) => {
setSwitchState(data); setSwitchState(data);
@ -25,7 +29,7 @@ export default function Emoji({ totalIndex }: Props) {
<> <>
<Box sx={{ padding: "20px" }}> <Box sx={{ padding: "20px" }}>
<AnswerDraggableList <AnswerDraggableList
variants={listQuestions[quizId][totalIndex].content.variants} variants={question.content.variants}
totalIndex={totalIndex} totalIndex={totalIndex}
emoji emoji
/> />
@ -35,8 +39,7 @@ export default function Emoji({ totalIndex }: Props) {
variant="body2" variant="body2"
sx={{ color: theme.palette.brightPurple.main }} sx={{ color: theme.palette.brightPurple.main }}
onClick={() => { onClick={() => {
const answerNew = const answerNew = question.content.variants.slice();
listQuestions[quizId][totalIndex].content.variants.slice();
answerNew.push({ answer: "", hints: "", emoji: "" }); answerNew.push({ answer: "", hints: "", emoji: "" });
updateQuestionsList(quizId, totalIndex, { updateQuestionsList(quizId, totalIndex, {

@ -1,6 +1,27 @@
import { create } from "zustand"; import { create } from "zustand";
import { persist } from "zustand/middleware"; import { persist } from "zustand/middleware";
import { QuizQuestionEmoji } from "../model/questionTypes/emoji";
import { QuizQuestionImages } from "../model/questionTypes/images";
import { QuizQuestionVariant } from "../model/questionTypes/variant";
import { QuizQuestionVarImg } from "../model/questionTypes/varimg";
import type {
AnyQuizQuestion,
QuizQuestionType,
} from "../model/questionTypes/shared";
import { QuizQuestionDateEmpty } from "../constants/date";
import { QuizQuestionEmojiEmpty } from "../constants/emoji";
import { QuizQuestionFileEmpty } from "../constants/file";
import { QuizQuestionImagesEmpty } from "../constants/images";
import { QuizQuestionNumberEmpty } from "../constants/number";
import { QuizQuestionPageEmpty } from "../constants/page";
import { QuizQuestionRatingEmpty } from "../constants/rating";
import { QuizQuestionSelectEmpty } from "../constants/select";
import { QuizQuestionTextEmpty } from "../constants/text";
import { QuizQuestionVariantEmpty } from "../constants/variant";
import { QuizQuestionVarImgEmpty } from "../constants/varimg";
export type Variants = { export type Variants = {
answer: string; answer: string;
hints: string; hints: string;
@ -75,7 +96,7 @@ export interface Question {
} }
interface QuestionStore { interface QuestionStore {
listQuestions: Record<string, Question[]>; listQuestions: Record<string, AnyQuizQuestion[]>;
openedModalSettings: string; openedModalSettings: string;
} }
@ -159,10 +180,10 @@ export const questionStore = create<QuestionStore>()(
} }
) )
); );
export const updateQuestionsList = ( export const updateQuestionsList = <T = AnyQuizQuestion>(
quizId: number, quizId: number,
index: number, index: number,
data: Partial<Question> data: Partial<T>
) => { ) => {
const questionListClone = { ...questionStore.getState()["listQuestions"] }; const questionListClone = { ...questionStore.getState()["listQuestions"] };
questionListClone[quizId][index] = { questionListClone[quizId][index] = {
@ -188,12 +209,35 @@ export const updateVariants = (
variants: Variants[] variants: Variants[]
) => { ) => {
const listQuestions = { ...questionStore.getState()["listQuestions"] }; const listQuestions = { ...questionStore.getState()["listQuestions"] };
listQuestions[quizId][index].content.variants = variants;
questionStore.setState({ listQuestions }); switch (listQuestions[quizId][index].type) {
case "emoji":
const emojiState = listQuestions[quizId][index] as QuizQuestionEmoji;
emojiState.content.variants = variants;
return questionStore.setState({ listQuestions });
case "images":
const imagesState = listQuestions[quizId][index] as QuizQuestionImages;
imagesState.content.variants = variants;
return questionStore.setState({ listQuestions });
case "variant":
const variantState = listQuestions[quizId][index] as QuizQuestionVariant;
variantState.content.variants = variants;
return questionStore.setState({ listQuestions });
case "varimg":
const varImgState = listQuestions[quizId][index] as QuizQuestionVarImg;
varImgState.content.variants = variants;
return questionStore.setState({ listQuestions });
}
}; };
export const createQuestion = (quizId: number, placeIndex = -1) => { export const createQuestion = (
quizId: number,
questionType: QuizQuestionType,
placeIndex = -1
) => {
const id = getRandom(1000000, 10000000); const id = getRandom(1000000, 10000000);
const newData = { ...questionStore.getState()["listQuestions"] }; const newData = { ...questionStore.getState()["listQuestions"] };
@ -201,13 +245,29 @@ export const createQuestion = (quizId: number, placeIndex = -1) => {
newData[quizId] = []; newData[quizId] = [];
} }
const defaultObject = [
QuizQuestionDateEmpty,
QuizQuestionEmojiEmpty,
QuizQuestionFileEmpty,
QuizQuestionImagesEmpty,
QuizQuestionNumberEmpty,
QuizQuestionPageEmpty,
QuizQuestionRatingEmpty,
QuizQuestionSelectEmpty,
QuizQuestionTextEmpty,
QuizQuestionVariantEmpty,
QuizQuestionVarImgEmpty,
].find((defaultObjectItem) => defaultObjectItem.type === questionType);
if (defaultObject) {
newData[quizId].splice( newData[quizId].splice(
placeIndex < 0 ? newData[quizId].length : placeIndex, placeIndex < 0 ? newData[quizId].length : placeIndex,
0, 0,
{ ...DEFAULT_QUESTION, id } { ...defaultObject, id }
); );
questionStore.setState({ listQuestions: newData }); questionStore.setState({ listQuestions: newData });
}
}; };
export const copyQuestion = (quizId: number, copiedQuestionIndex: number) => { export const copyQuestion = (quizId: number, copiedQuestionIndex: number) => {
@ -238,7 +298,7 @@ export const findQuestionById = (quizId: number) => {
let found = null; let found = null;
questionStore questionStore
.getState() .getState()
["listQuestions"][quizId].some((quiz: Question, index: number) => { ["listQuestions"][quizId].some((quiz: AnyQuizQuestion, index: number) => {
if (quiz.id === quizId) { if (quiz.id === quizId) {
found = { quiz, index }; found = { quiz, index };
return true; return true;