simplify question variant types

This commit is contained in:
nflnkr 2023-11-28 22:16:00 +03:00
parent 9c438de1f9
commit f39ffb9c23
9 changed files with 56 additions and 73 deletions

@ -18,7 +18,8 @@ export const QUIZ_QUESTION_EMOJI: Omit<QuizQuestionEmoji, "id" | "backendId"> =
id: nanoid(),
answer: "",
extendedText: "",
hints: ""
hints: "",
originalImageUrl: "",
},
],
},

@ -13,6 +13,6 @@ export const QUIZ_QUESTION_SELECT: Omit<QuizQuestionSelect, "id" | "backendId">
innerNameCheck: false,
innerName: "",
default: "",
variants: [{ id: nanoid(), answer: "", extendedText: "", hints: "" }],
variants: [{ id: nanoid(), answer: "", extendedText: "", hints: "", originalImageUrl: "" }],
},
};

@ -14,6 +14,6 @@ export const QUIZ_QUESTION_VARIANT: Omit<QuizQuestionVariant, "id" | "backendId"
innerNameCheck: false,
required: false,
innerName: "",
variants: [{ id: nanoid(), answer: "", extendedText: "", hints: "" }],
variants: [{ id: nanoid(), answer: "", extendedText: "", hints: "", originalImageUrl: "" }],
},
};

@ -1,7 +1,7 @@
import type {
ImageQuestionVariant,
QuestionBranchingRule,
QuestionHint,
QuestionVariant,
QuizQuestionBase
} from "./shared";
@ -25,7 +25,7 @@ export interface QuizQuestionImages extends QuizQuestionBase {
/** Чекбокс "Необязательный вопрос" */
required: boolean;
/** Варианты (картинки) */
variants: ImageQuestionVariant[];
variants: QuestionVariant[];
hint: QuestionHint;
rule: QuestionBranchingRule;
back: string;

@ -40,12 +40,9 @@ export type QuestionVariant = {
hints: string;
/** Дополнительное поле для текста, emoji, ссылки на картинку */
extendedText: string;
};
export interface ImageQuestionVariant extends QuestionVariant {
/** Оригинал изображения (до кропа) */
originalImageUrl: string;
}
};
export interface QuizQuestionBase {
backendId: number;
@ -89,7 +86,7 @@ export type AnyQuizQuestion =
// | QuizQuestionInitial;
type FilterQuestionsWithVariants<T> = T extends {
content: { variants: QuestionVariant[] | ImageQuestionVariant[]; };
content: { variants: QuestionVariant[]; };
} ? T : never;
export type QuizQuestionsWithVariants = FilterQuestionsWithVariants<AnyQuizQuestion>;
@ -100,9 +97,5 @@ export const createQuestionVariant: () => QuestionVariant = () => ({
answer: "",
extendedText: "",
hints: "",
});
export const createQuestionImageVariant: () => ImageQuestionVariant = () => ({
...createQuestionVariant(),
originalImageUrl: "",
});

@ -1,7 +1,7 @@
import type {
ImageQuestionVariant,
QuestionBranchingRule,
QuestionHint,
QuestionVariant,
QuizQuestionBase
} from "./shared";
@ -16,7 +16,7 @@ export interface QuizQuestionVarImg extends QuizQuestionBase {
innerName: string;
/** Чекбокс "Необязательный вопрос" */
required: boolean;
variants: ImageQuestionVariant[];
variants: QuestionVariant[];
hint: QuestionHint;
rule: QuestionBranchingRule;
back: string;

@ -16,14 +16,13 @@ import { addQuestionVariant, deleteQuestionVariant, setQuestionVariantField } fr
import type { KeyboardEvent, ReactNode } from "react";
import { useState } from "react";
import { Draggable } from "react-beautiful-dnd";
import { useDebouncedCallback } from "use-debounce";
import type { ImageQuestionVariant, QuestionVariant } from "../../../model/questionTypes/shared";
import type { QuestionVariant } from "../../../model/questionTypes/shared";
type AnswerItemProps = {
index: number;
questionId: string;
variant: QuestionVariant | ImageQuestionVariant;
variant: QuestionVariant;
largeCheck: boolean;
additionalContent?: ReactNode;
additionalMobile?: ReactNode;
@ -73,7 +72,7 @@ export const AnswerItem = ({
placeholder={"Добавьте ответ"}
multiline={largeCheck}
onChange={({ target }) => {
setQuestionVariantField(questionId, variant.id, "answer", target.value)
setQuestionVariantField(questionId, variant.id, "answer", target.value);
}}
onKeyDown={(event: KeyboardEvent<HTMLInputElement>) => {
if (event.code === "Enter" && !largeCheck) {

@ -3,14 +3,14 @@ import { reorderQuestionVariants } from "@root/questions/actions";
import { type ReactNode } from "react";
import type { DropResult } from "react-beautiful-dnd";
import { DragDropContext, Droppable } from "react-beautiful-dnd";
import type { ImageQuestionVariant, QuestionVariant, QuizQuestionsWithVariants } from "../../../model/questionTypes/shared";
import type { QuestionVariant, QuizQuestionsWithVariants } from "../../../model/questionTypes/shared";
import { AnswerItem } from "./AnswerItem";
type AnswerDraggableListProps = {
question: QuizQuestionsWithVariants;
additionalContent?: (variant: QuestionVariant | ImageQuestionVariant, index: number) => ReactNode;
additionalMobile?: (variant: QuestionVariant | ImageQuestionVariant, index: number) => ReactNode;
additionalContent?: (variant: QuestionVariant, index: number) => ReactNode;
additionalMobile?: (variant: QuestionVariant, index: number) => ReactNode;
};
export const AnswerDraggableList = ({

@ -2,14 +2,13 @@ import { questionApi } from "@api/question";
import { devlog } from "@frontend/kitui";
import { questionToEditQuestionRequest } from "@model/question/edit";
import { QuestionType, RawQuestion, rawQuestionToQuestion } from "@model/question/question";
import { AnyQuizQuestion, ImageQuestionVariant, QuestionVariant, createQuestionImageVariant, createQuestionVariant } from "@model/questionTypes/shared";
import { AnyQuizQuestion, QuestionVariant, createQuestionVariant } from "@model/questionTypes/shared";
import { produce } from "immer";
import { nanoid } from "nanoid";
import { enqueueSnackbar } from "notistack";
import { isAxiosCanceledError } from "../../utils/isAxiosCanceledError";
import { notReachable } from "../../utils/notReachable";
import { RequestQueue } from "../../utils/requestQueue";
import { QuestionsStore, useQuestionsStore } from "./store";
import { nanoid } from "nanoid";
export const setQuestions = (questions: RawQuestion[] | null) => setProducedState(state => {
@ -76,20 +75,11 @@ export const addQuestionVariant = (questionId: string) => {
case "variant":
case "emoji":
case "select":
question.content.variants.push(createQuestionVariant());
break;
case "images":
case "varimg":
question.content.variants.push(createQuestionImageVariant());
question.content.variants.push(createQuestionVariant());
break;
case "text":
case "date":
case "number":
case "file":
case "page":
case "rating":
throw new Error(`Cannot add variant to question of type "${question.type}"`);
default: notReachable(question);
default: throw new Error(`Cannot add variant to question of type "${question.type}"`);
}
});
};
@ -173,7 +163,7 @@ export const setVariantImageUrl = (
if (!("variants" in question.content)) return;
const variant = question.content.variants.find(variant => variant.id === variantId);
if (!variant || !("originalImageUrl" in variant)) return;
if (!variant) return;
if (variant.extendedText === url) return;
@ -192,8 +182,8 @@ export const setVariantOriginalImageUrl = (
const variant = question.content.variants.find(
variant => variant.id === variantId
) as ImageQuestionVariant | undefined;
if (!variant || !("originalImageUrl" in variant)) return;
) as QuestionVariant | undefined;
if (!variant) return;
if (variant.originalImageUrl === url) return;