203 lines
5.1 KiB
Vue
203 lines
5.1 KiB
Vue
<script lang="ts" setup>
|
|
import { useExamStore } from "~/store/examStore";
|
|
|
|
import { intervalToDuration, addMinutes, addSeconds, isEqual } from "date-fns";
|
|
|
|
definePageMeta({ middleware: ["exam"] });
|
|
|
|
const nowTime = ref(new Date());
|
|
const timeEnd = addMinutes(new Date(), 25);
|
|
|
|
const timeRemainingTotal = computed(() =>
|
|
intervalToDuration({
|
|
start: nowTime.value,
|
|
end: timeEnd,
|
|
})
|
|
);
|
|
// const timeRemainingQuestion - to implement
|
|
|
|
onMounted(() => {
|
|
const endInterval = setInterval(() => {
|
|
nowTime.value = addSeconds(nowTime.value, 1);
|
|
if (isEqual(nowTime.value, timeEnd)) {
|
|
clearInterval(endInterval);
|
|
endExam();
|
|
}
|
|
}, 1000);
|
|
});
|
|
|
|
const examStore = useExamStore();
|
|
|
|
useHead({
|
|
title: "Pytanie 1/20",
|
|
});
|
|
|
|
const {
|
|
data: dataBasic,
|
|
error: errorBasic,
|
|
status: statusBasic,
|
|
} = await useLazyFetch<BasicQuestion[]>(`/api/basic`, {
|
|
query: {
|
|
category: examStore.category,
|
|
},
|
|
});
|
|
|
|
const {
|
|
data: dataAdvanced,
|
|
error: errorAdvanced,
|
|
status: statusAdvanced,
|
|
} = await useLazyFetch<AdvancedQuestion[]>(`/api/advanced`, {
|
|
query: {
|
|
category: examStore.category,
|
|
},
|
|
});
|
|
|
|
const countBasic = ref(0);
|
|
const countAdvanced = ref(-1);
|
|
|
|
const now = ref("basic");
|
|
|
|
const tak_nie_model = ref();
|
|
const abc_model = ref();
|
|
|
|
const ending = ref(false);
|
|
|
|
async function next() {
|
|
if (countBasic.value + 1 < dataBasic.value?.length!) {
|
|
result.value.basic.push({
|
|
question: questionBasic.value,
|
|
chosen_answer: tak_nie_model.value ?? "",
|
|
chosen_is_correct:
|
|
tak_nie_model.value == questionBasic.value?.poprawna_odp?.toLowerCase(),
|
|
liczba_pkt: questionBasic.value?.liczba_pkt,
|
|
});
|
|
tak_nie_model.value = "";
|
|
countBasic.value++;
|
|
useHead({
|
|
title: `Pytanie ${countBasic.value + 1}/${dataBasic.value?.length}`,
|
|
});
|
|
} else if (countAdvanced.value + 1 <= dataAdvanced.value?.length!) {
|
|
if (countAdvanced.value != -1) {
|
|
result.value.advanced.push({
|
|
question: questionAdvanced.value,
|
|
chosen_answer: abc_model.value ?? "",
|
|
chosen_is_correct:
|
|
abc_model.value ==
|
|
questionAdvanced.value?.poprawna_odp?.toLowerCase(),
|
|
liczba_pkt: questionAdvanced.value?.liczba_pkt,
|
|
});
|
|
} else {
|
|
now.value = "advanced";
|
|
|
|
result.value.basic.push({
|
|
question: questionBasic.value,
|
|
chosen_answer: tak_nie_model.value ?? "",
|
|
chosen_is_correct:
|
|
tak_nie_model.value ==
|
|
questionBasic.value?.poprawna_odp?.toLowerCase(),
|
|
liczba_pkt: questionBasic.value?.liczba_pkt,
|
|
});
|
|
tak_nie_model.value = "";
|
|
}
|
|
if (countAdvanced.value + 1 < dataAdvanced.value?.length!) {
|
|
countAdvanced.value++;
|
|
useHead({
|
|
title: `Pytanie ${countAdvanced.value + 1}/${
|
|
dataAdvanced.value?.length
|
|
}`,
|
|
});
|
|
}
|
|
if (countAdvanced.value == dataAdvanced.value?.length! - 1) {
|
|
ending.value = true;
|
|
}
|
|
abc_model.value = "";
|
|
}
|
|
}
|
|
|
|
function endExam() {
|
|
loading.value = true;
|
|
while (!ending.value) {
|
|
next();
|
|
}
|
|
next();
|
|
examStore.setResult(result.value);
|
|
examStore.setEnd(true);
|
|
return navigateTo("/result", { replace: true });
|
|
}
|
|
|
|
const questionBasic = computed<BasicQuestion | undefined>(() =>
|
|
dataBasic.value?.at(countBasic.value)
|
|
);
|
|
const questionAdvanced = computed<AdvancedQuestion | undefined>(() =>
|
|
dataAdvanced.value?.at(countAdvanced.value)
|
|
);
|
|
|
|
const question = computed(() => {
|
|
if (now.value == "basic") {
|
|
return questionBasic.value;
|
|
} else if (now.value == "advanced") {
|
|
return questionAdvanced.value;
|
|
} else {
|
|
return;
|
|
}
|
|
});
|
|
|
|
const media = computed(() => {
|
|
const mediaSplit = question.value?.media?.split(".");
|
|
return {
|
|
fileType: mediaSplit?.pop()?.toLowerCase(),
|
|
fileName: mediaSplit?.join("."),
|
|
ogName: question.value?.media,
|
|
};
|
|
});
|
|
|
|
const result: Ref<ResultEndType> = ref({
|
|
basic: [],
|
|
advanced: [],
|
|
});
|
|
const loading = ref(false);
|
|
</script>
|
|
|
|
<template>
|
|
<div>
|
|
<Loading v-if="loading" />
|
|
<div v-if="statusBasic === 'success' && statusAdvanced === 'success'">
|
|
<div class="grid grid-cols-4 min-h-dvh">
|
|
<div class="col-span-3 flex flex-col gap-4">
|
|
<TopBar
|
|
:points="question?.liczba_pkt"
|
|
:category="examStore.category"
|
|
:time-remaining="timeRemainingTotal"
|
|
/>
|
|
<Media :media="media" />
|
|
<BasicQuestionBlock
|
|
v-if="countAdvanced < 0"
|
|
:question="questionBasic"
|
|
v-model="tak_nie_model"
|
|
/>
|
|
<AdvancedQuestionBlock
|
|
v-else
|
|
:question="questionAdvanced"
|
|
v-model="abc_model"
|
|
/>
|
|
</div>
|
|
|
|
<RightBarExam
|
|
:result="result"
|
|
:data-basic="dataBasic"
|
|
:data-advanced="dataAdvanced"
|
|
:count-basic="countBasic"
|
|
:count-advanced="countAdvanced"
|
|
@next-question="next()"
|
|
@end-exam="endExam()"
|
|
:now="now"
|
|
:ending="ending"
|
|
/>
|
|
</div>
|
|
</div>
|
|
<div v-else-if="statusBasic === 'error' || statusAdvanced === 'error'">
|
|
An API error occurred: {{ errorBasic }} {{ errorAdvanced }}
|
|
</div>
|
|
<Loading v-else />
|
|
</div>
|
|
</template>
|