Press n or j to go to the next uncovered block, b, p or k for the previous block.
| 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 | 1x 1x 1x 1x 1x 12x 12x 12x 12x 1x 11x 11x 11x 17x 1x 20x 20x 20x 20x 20x 20x 2x 20x 1x 20x 11x 20x 20x | import { useRouter } from 'next/router';
import { useMemo, useReducer } from 'react';
import { buildSurveyQuestions, sanitizeSurveyName, DEFAULT_SURVEY_NAME, type Question } from '@/constants/survey';
interface Answer {
question: string;
answer: string;
isCorrect: boolean;
questionNum: number;
}
interface SurveyState {
currentQuestion: number;
questionsDone: number;
success: boolean;
answers: Answer[];
}
type SurveyAction = { type: 'NEXT_QUESTION' } | { type: 'PREVIOUS_QUESTION' } | { type: 'ADD_ANSWER'; payload: Answer };
const initialState: SurveyState = {
currentQuestion: 0,
questionsDone: 0,
success: false,
answers: [],
};
const reducer = (state: SurveyState, action: SurveyAction): SurveyState => {
const { questionNum } = 'payload' in action ? action.payload : ({} as Partial<Answer>);
const { answers, questionsDone, currentQuestion } = state;
const newAnswers: Answer[] = [...answers];
switch (action.type) {
case 'NEXT_QUESTION':
return {
...state,
currentQuestion: currentQuestion + 1,
};
case 'PREVIOUS_QUESTION':
return {
...state,
currentQuestion: currentQuestion - 1,
};
case 'ADD_ANSWER':
if (questionNum !== undefined) {
newAnswers[questionNum] = {
...action.payload,
};
return {
...state,
answers: newAnswers,
currentQuestion: currentQuestion + 1,
questionsDone: questionNum > questionsDone ? questionNum : questionsDone,
success: newAnswers.every((answer) => answer.isCorrect) && currentQuestion === 10,
};
}
return state;
default:
return state;
}
};
const useSurvey = () => {
const { query } = useRouter();
const rawName = Array.isArray(query.name) ? query.name[0] : query.name ?? DEFAULT_SURVEY_NAME;
const name = sanitizeSurveyName(rawName);
const [state, dispatch] = useReducer(reducer, initialState);
const questions = useMemo(() => buildSurveyQuestions(name, state.success), [name, state.success]);
const handlePreviousQuestion = () => {
if (state.currentQuestion > 1) dispatch({ type: 'PREVIOUS_QUESTION' });
};
const handleNextQuestion = () => {
Iif (state.currentQuestion !== 0 && state.questionsDone >= state.currentQuestion)
dispatch({ type: 'NEXT_QUESTION' });
};
const handleAnswerOptionClick = (payload: {
question: string;
answer: string;
isCorrect: boolean;
questionNum: number;
}) => dispatch({ type: 'ADD_ANSWER', payload });
return {
questions,
answers: state.answers,
surveySuccess: state.success,
currentQuestionNum: state.currentQuestion,
questionsDoneNum: state.questionsDone,
totalQuestions: questions.length,
handleAnswerOptionClick,
handleNextQuestion,
handlePreviousQuestion,
};
};
export default useSurvey;
export type { Question };
|