add question image preload
This commit is contained in:
parent
a796fae504
commit
a63994a33f
@ -1,3 +1,7 @@
|
||||
import { ContactForm } from "@/components/ViewPublicationPage/ContactForm/ContactForm.tsx";
|
||||
import { extractImageLinksFromQuestion } from "@/utils/extractImageLinks";
|
||||
import { useVKMetrics } from "@/utils/hooks/metrics/useVKMetrics";
|
||||
import { useYandexMetrics } from "@/utils/hooks/metrics/useYandexMetrics";
|
||||
import { sendAnswer } from "@api/quizRelase";
|
||||
import { useQuizSettings } from "@contexts/QuizDataContext";
|
||||
import { ThemeProvider, Typography } from "@mui/material";
|
||||
@ -7,15 +11,13 @@ import { notReachable } from "@utils/notReachable";
|
||||
import { quizThemes } from "@utils/themes/Publication/themePublication";
|
||||
import { enqueueSnackbar } from "notistack";
|
||||
import { ReactElement, useEffect } from "react";
|
||||
import { Helmet } from "react-helmet";
|
||||
import { Question } from "./Question";
|
||||
import QuestionSelect from "./QuestionSelect";
|
||||
import { ResultForm } from "./ResultForm";
|
||||
import { StartPageViewPublication } from "./StartPageViewPublication";
|
||||
import NextButton from "./tools/NextButton";
|
||||
import PrevButton from "./tools/PrevButton";
|
||||
import QuestionSelect from "./QuestionSelect";
|
||||
import { useYandexMetrics } from "@/utils/hooks/metrics/useYandexMetrics";
|
||||
import { useVKMetrics } from "@/utils/hooks/metrics/useVKMetrics";
|
||||
import { ContactForm } from "@/components/ViewPublicationPage/ContactForm/ContactForm.tsx";
|
||||
|
||||
export default function ViewPublicationPage() {
|
||||
const { settings, recentlyCompleted, quizId, preview, changeFaviconAndTitle } = useQuizSettings();
|
||||
@ -24,6 +26,7 @@ export default function ViewPublicationPage() {
|
||||
const {
|
||||
currentQuestion,
|
||||
currentQuestionStepNumber,
|
||||
nextQuestion,
|
||||
isNextButtonEnabled,
|
||||
isPreviousButtonEnabled,
|
||||
moveToPrevQuestion,
|
||||
@ -56,7 +59,10 @@ export default function ViewPublicationPage() {
|
||||
if (!currentQuestion)
|
||||
return (
|
||||
<ThemeProvider theme={quizThemes[settings.cfg.theme || "StandardTheme"].theme}>
|
||||
<Typography textAlign={"center"} mt="50px">
|
||||
<Typography
|
||||
textAlign={"center"}
|
||||
mt="50px"
|
||||
>
|
||||
Вопрос не выбран
|
||||
</Typography>
|
||||
</ThemeProvider>
|
||||
@ -80,7 +86,10 @@ export default function ViewPublicationPage() {
|
||||
currentQuestion={currentQuestion}
|
||||
currentQuestionStepNumber={currentQuestionStepNumber}
|
||||
prevButton={
|
||||
<PrevButton isPreviousButtonEnabled={isPreviousButtonEnabled} moveToPrevQuestion={moveToPrevQuestion} />
|
||||
<PrevButton
|
||||
isPreviousButtonEnabled={isPreviousButtonEnabled}
|
||||
moveToPrevQuestion={moveToPrevQuestion}
|
||||
/>
|
||||
}
|
||||
nextButton={
|
||||
<NextButton
|
||||
@ -102,20 +111,47 @@ export default function ViewPublicationPage() {
|
||||
}}
|
||||
/>
|
||||
}
|
||||
questionSelect={<QuestionSelect selectedQuestion={currentQuestion} setQuestion={setQuestion} />}
|
||||
questionSelect={
|
||||
<QuestionSelect
|
||||
selectedQuestion={currentQuestion}
|
||||
setQuestion={setQuestion}
|
||||
/>
|
||||
}
|
||||
/>
|
||||
);
|
||||
break;
|
||||
}
|
||||
case "contactform": {
|
||||
quizStepElement = <ContactForm currentQuestion={currentQuestion} onShowResult={showResultAfterContactForm} />;
|
||||
quizStepElement = (
|
||||
<ContactForm
|
||||
currentQuestion={currentQuestion}
|
||||
onShowResult={showResultAfterContactForm}
|
||||
/>
|
||||
);
|
||||
break;
|
||||
}
|
||||
default:
|
||||
notReachable(currentQuizStep);
|
||||
}
|
||||
|
||||
const preloadLinks = new Set([
|
||||
...extractImageLinksFromQuestion(currentQuestion),
|
||||
...extractImageLinksFromQuestion(nextQuestion),
|
||||
]);
|
||||
|
||||
return (
|
||||
<ThemeProvider theme={quizThemes[settings.cfg.theme || "StandardTheme"].theme}>{quizStepElement}</ThemeProvider>
|
||||
<ThemeProvider theme={quizThemes[settings.cfg.theme || "StandardTheme"].theme}>
|
||||
<Helmet>
|
||||
{Array.from(preloadLinks).map((link) => (
|
||||
<link
|
||||
key={link}
|
||||
rel="preload"
|
||||
as="image"
|
||||
href={link}
|
||||
/>
|
||||
))}
|
||||
</Helmet>
|
||||
{quizStepElement}
|
||||
</ThemeProvider>
|
||||
);
|
||||
}
|
||||
|
29
lib/utils/extractImageLinks.ts
Normal file
29
lib/utils/extractImageLinks.ts
Normal file
@ -0,0 +1,29 @@
|
||||
import { AnyTypedQuizQuestion } from "@/model/questionTypes";
|
||||
|
||||
export function extractImageLinksFromQuestion(question: AnyTypedQuizQuestion | null | undefined): string[] {
|
||||
if (!question) return [];
|
||||
|
||||
const links: string[] = [];
|
||||
|
||||
if (question.type === "images") {
|
||||
question.content.variants.forEach((variant) => {
|
||||
if (variant.extendedText.startsWith("https://")) links.push(variant.extendedText);
|
||||
});
|
||||
}
|
||||
|
||||
if (question.type === "varimg") {
|
||||
question.content.variants.forEach((variant) => {
|
||||
if (variant.extendedText.startsWith("https://")) links.push(variant.extendedText);
|
||||
});
|
||||
}
|
||||
|
||||
if (question.type === "page") {
|
||||
if (question.content.back?.startsWith("https://")) links.push(question.content.back);
|
||||
}
|
||||
|
||||
if (question.type === "result") {
|
||||
if (question.content.back?.startsWith("https://")) links.push(question.content.back);
|
||||
}
|
||||
|
||||
return links;
|
||||
}
|
@ -197,6 +197,7 @@ export function useQuestionFlowControl() {
|
||||
return {
|
||||
currentQuestion,
|
||||
currentQuestionStepNumber: linearQuestionIndex === null ? null : linearQuestionIndex + 1,
|
||||
nextQuestion,
|
||||
isNextButtonEnabled,
|
||||
isPreviousButtonEnabled,
|
||||
moveToPrevQuestion,
|
||||
|
@ -39,6 +39,7 @@
|
||||
"@types/node": "^16.7.13",
|
||||
"@types/react": "^18.2.43",
|
||||
"@types/react-dom": "^18.2.17",
|
||||
"@types/react-helmet": "^6.1.11",
|
||||
"@typescript-eslint/eslint-plugin": "^6.14.0",
|
||||
"@typescript-eslint/parser": "^6.14.0",
|
||||
"@vitejs/plugin-react": "^4.2.1",
|
||||
@ -95,6 +96,7 @@
|
||||
"hex-rgb": "^5.0.0",
|
||||
"mobile-detect": "^1.4.5",
|
||||
"mui-tel-input": "^5.1.2",
|
||||
"react-helmet": "^6.1.0",
|
||||
"react-imask": "^7.6.0",
|
||||
"react-phone-number-input": "^3.4.1"
|
||||
},
|
||||
@ -108,7 +110,8 @@
|
||||
"endOfLine": "auto",
|
||||
"bracketSpacing": true,
|
||||
"arrowParens": "always",
|
||||
"jsxSingleQuote": false
|
||||
"jsxSingleQuote": false,
|
||||
"singleAttributePerLine": true
|
||||
},
|
||||
"lint-staged": {
|
||||
"*": "prettier --write --ignore-unknown"
|
||||
|
29
yarn.lock
29
yarn.lock
@ -985,6 +985,13 @@
|
||||
dependencies:
|
||||
"@types/react" "*"
|
||||
|
||||
"@types/react-helmet@^6.1.11":
|
||||
version "6.1.11"
|
||||
resolved "https://registry.yarnpkg.com/@types/react-helmet/-/react-helmet-6.1.11.tgz#8cafcafff38f75361f451563ba7b406b0c5d3907"
|
||||
integrity sha512-0QcdGLddTERotCXo3VFlUSWO3ztraw8nZ6e3zJSgG7apwV5xt+pJUS8ewPBqT4NYB1optGLprNQzFleIY84u/g==
|
||||
dependencies:
|
||||
"@types/react" "*"
|
||||
|
||||
"@types/react-transition-group@^4.4.10", "@types/react-transition-group@^4.4.8":
|
||||
version "4.4.10"
|
||||
resolved "https://registry.yarnpkg.com/@types/react-transition-group/-/react-transition-group-4.4.10.tgz#6ee71127bdab1f18f11ad8fb3322c6da27c327ac"
|
||||
@ -3213,7 +3220,7 @@ process@^0.11.10:
|
||||
resolved "https://registry.yarnpkg.com/process/-/process-0.11.10.tgz#7332300e840161bda3e69a1d1d91a7d4bc16f182"
|
||||
integrity sha512-cdGef/drWFoydD1JsMzuFf8100nZl+GT+yacc2bEced5f9Rjk4z+WtFUTBu9PhOi9j/jfmBPu0mMEY4wIdAF8A==
|
||||
|
||||
prop-types@^15.6.2, prop-types@^15.8.1:
|
||||
prop-types@^15.6.2, prop-types@^15.7.2, prop-types@^15.8.1:
|
||||
version "15.8.1"
|
||||
resolved "https://registry.yarnpkg.com/prop-types/-/prop-types-15.8.1.tgz#67d87bf1a694f48435cf332c24af10214a3140b5"
|
||||
integrity sha512-oj87CgZICdulUohogVAR7AjlC0327U4el4L6eAvOqCeudMDVU0NThNaV+b9Df4dXgSP1gXMTnPdhfe/2qDH5cg==
|
||||
@ -3282,6 +3289,21 @@ react-error-boundary@^4.0.12:
|
||||
dependencies:
|
||||
"@babel/runtime" "^7.12.5"
|
||||
|
||||
react-fast-compare@^3.1.1:
|
||||
version "3.2.2"
|
||||
resolved "https://registry.yarnpkg.com/react-fast-compare/-/react-fast-compare-3.2.2.tgz#929a97a532304ce9fee4bcae44234f1ce2c21d49"
|
||||
integrity sha512-nsO+KSNgo1SbJqJEYRE9ERzo7YtYbou/OqjSQKxV7jcKox7+usiUVZOAC+XnDOABXggQTno0Y1CpVnuWEc1boQ==
|
||||
|
||||
react-helmet@^6.1.0:
|
||||
version "6.1.0"
|
||||
resolved "https://registry.yarnpkg.com/react-helmet/-/react-helmet-6.1.0.tgz#a750d5165cb13cf213e44747502652e794468726"
|
||||
integrity sha512-4uMzEY9nlDlgxr61NL3XbKRy1hEkXmKNXhjbAIOVw5vcFrsdYbH2FEwcNyWvWinl103nXgzYNlns9ca+8kFiWw==
|
||||
dependencies:
|
||||
object-assign "^4.1.1"
|
||||
prop-types "^15.7.2"
|
||||
react-fast-compare "^3.1.1"
|
||||
react-side-effect "^2.1.0"
|
||||
|
||||
react-imask@^7.6.0:
|
||||
version "7.6.0"
|
||||
resolved "https://registry.yarnpkg.com/react-imask/-/react-imask-7.6.0.tgz#5948fc39e1d7d036292d4fade43df4636d43e7b7"
|
||||
@ -3331,6 +3353,11 @@ react-router@6.23.1:
|
||||
dependencies:
|
||||
"@remix-run/router" "1.16.1"
|
||||
|
||||
react-side-effect@^2.1.0:
|
||||
version "2.1.2"
|
||||
resolved "https://registry.yarnpkg.com/react-side-effect/-/react-side-effect-2.1.2.tgz#dc6345b9e8f9906dc2eeb68700b615e0b4fe752a"
|
||||
integrity sha512-PVjOcvVOyIILrYoyGEpDN3vmYNLdy1CajSFNt4TDsVQC5KpTijDvWVoR+/7Rz2xT978D8/ZtFceXxzsPwZEDvw==
|
||||
|
||||
react-transition-group@^4.4.5:
|
||||
version "4.4.5"
|
||||
resolved "https://registry.yarnpkg.com/react-transition-group/-/react-transition-group-4.4.5.tgz#e53d4e3f3344da8521489fbef8f2581d42becdd1"
|
||||
|
Loading…
Reference in New Issue
Block a user