-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
#2 add PreviewTest.jsx and TakeTest.jsx
- Loading branch information
Showing
13 changed files
with
509 additions
and
11 deletions.
There are no files selected for viewing
Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,43 @@ | ||
import React from 'react'; | ||
import { Link } from 'react-router-dom'; | ||
import { Box, Heading, Text, Button, VStack } from '@chakra-ui/react'; | ||
|
||
const NotFound = () => { | ||
return ( | ||
<Box | ||
display="flex" | ||
justifyContent="center" | ||
alignItems="center" | ||
minH="100vh" | ||
bg="white" | ||
> | ||
<VStack spacing={6} textAlign="center"> | ||
<Heading | ||
as="h1" | ||
size="4xl" | ||
color="cyan.600" | ||
>404</Heading> | ||
<Text fontSize="lg" fontWeight="bold" color="cyan.500"> | ||
Page Not Found | ||
</Text> | ||
<Text color="cyan.500" fontSize="lg"> | ||
The page you are looking for does not exist or has been moved. | ||
</Text> | ||
<Link to="/"> | ||
<Button | ||
colorScheme="cyan" | ||
bg="cyan.400" | ||
_hover={{ bg: "cyan.500" }} | ||
color="white" | ||
variant="solid" | ||
size="lg" | ||
> | ||
Go Back to Home | ||
</Button> | ||
</Link> | ||
</VStack> | ||
</Box> | ||
); | ||
}; | ||
|
||
export default NotFound; |
This file was deleted.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,171 @@ | ||
import React from 'react'; | ||
import { | ||
Box, | ||
Radio, | ||
RadioGroup, | ||
Checkbox, | ||
CheckboxGroup, | ||
VStack, | ||
Text, | ||
Image, | ||
Input, | ||
} from '@chakra-ui/react'; | ||
import { QUESTION_TYPES } from '~/utils/constants'; | ||
|
||
class TestQuestion { | ||
constructor(id, text, options, type, items = [], images = [], sentence = "") { | ||
this.id = id; | ||
this.text = text; | ||
this.options = options; | ||
this.type = type; | ||
this.items = items; | ||
this.images = images; | ||
this.sentence = sentence; | ||
} | ||
} | ||
|
||
// Helper functions for each question type | ||
const renderSingleChoice = (question, selectedAnswer, onAnswerChange) => ( | ||
<RadioGroup | ||
value={selectedAnswer || ''} | ||
onChange={(value) => onAnswerChange(question.id, value)} | ||
> | ||
<VStack align="start"> | ||
{question.options.map((option, index) => ( | ||
<Radio key={index} value={option}> | ||
{option} | ||
</Radio> | ||
))} | ||
</VStack> | ||
</RadioGroup> | ||
); | ||
|
||
const renderMultiChoice = (question, selectedAnswer, onAnswerChange) => ( | ||
<CheckboxGroup | ||
value={selectedAnswer || []} | ||
onChange={(value) => onAnswerChange(question.id, value)} | ||
> | ||
<VStack align="start"> | ||
{question.options.map((option, index) => ( | ||
<Checkbox key={index} value={option}> | ||
{option} | ||
</Checkbox> | ||
))} | ||
</VStack> | ||
</CheckboxGroup> | ||
); | ||
|
||
const renderTrueFalse = (question, selectedAnswer, onAnswerChange) => ( | ||
<RadioGroup | ||
value={selectedAnswer || ''} | ||
onChange={(value) => onAnswerChange(question.id, value)} | ||
> | ||
<VStack align="start"> | ||
<Radio value="True">True</Radio> | ||
<Radio value="False">False</Radio> | ||
</VStack> | ||
</RadioGroup> | ||
); | ||
|
||
const renderItemMatch = (question, selectedAnswer, onAnswerChange) => ( | ||
<VStack align="start"> | ||
{question.items.map((item, index) => ( | ||
<Box key={index}> | ||
<Text>{item}</Text> | ||
<Input | ||
placeholder="Enter corresponding match" | ||
value={selectedAnswer ? selectedAnswer[index] : ''} | ||
onChange={(e) => { | ||
const newAnswer = [...(selectedAnswer || [])]; | ||
newAnswer[index] = e.target.value; | ||
onAnswerChange(question.id, newAnswer); | ||
}} | ||
/> | ||
</Box> | ||
))} | ||
</VStack> | ||
); | ||
|
||
const renderImageMatch = (question, selectedAnswer, onAnswerChange) => ( | ||
<VStack align="start"> | ||
{question.images.map((image, index) => ( | ||
<Box key={index}> | ||
<Image src={image.src} alt={`Option ${index}`} /> | ||
<RadioGroup | ||
value={selectedAnswer} | ||
onChange={(value) => onAnswerChange(question.id, value)} | ||
> | ||
{image.options.map((option, idx) => ( | ||
<Radio key={idx} value={option}> | ||
{option} | ||
</Radio> | ||
))} | ||
</RadioGroup> | ||
</Box> | ||
))} | ||
</VStack> | ||
); | ||
|
||
const renderKeywords = (question, selectedAnswer, onAnswerChange) => ( | ||
<VStack align="start"> | ||
<Input | ||
placeholder="Enter keywords" | ||
value={selectedAnswer || ''} | ||
onChange={(e) => onAnswerChange(question.id, e.target.value)} | ||
/> | ||
</VStack> | ||
); | ||
|
||
const renderFillTheGap = (question, selectedAnswer, onAnswerChange) => ( | ||
<VStack align="start"> | ||
{question.sentence.split('__').map((part, index) => ( | ||
<span key={index}> | ||
{part} | ||
{index < question.sentence.split('__').length - 1 && ( | ||
<Input | ||
placeholder="Fill the gap" | ||
value={selectedAnswer ? selectedAnswer[index] : ''} | ||
onChange={(e) => { | ||
const newAnswer = [...(selectedAnswer || [])]; | ||
newAnswer[index] = e.target.value; | ||
onAnswerChange(question.id, newAnswer); | ||
}} | ||
/> | ||
)} | ||
</span> | ||
))} | ||
</VStack> | ||
); | ||
|
||
// Main component | ||
const QuestionItem = ({ question, onAnswerChange, selectedAnswer }) => { | ||
const renderQuestion = () => { | ||
switch (question.type) { | ||
case QUESTION_TYPES.SINGLE_CHOICE: | ||
return renderSingleChoice(question, selectedAnswer, onAnswerChange); | ||
case QUESTION_TYPES.MULTI_CHOICE: | ||
return renderMultiChoice(question, selectedAnswer, onAnswerChange); | ||
case QUESTION_TYPES.TRUE_FALSE: | ||
return renderTrueFalse(question, selectedAnswer, onAnswerChange); | ||
case QUESTION_TYPES.ITEM_MATCH: | ||
return renderItemMatch(question, selectedAnswer, onAnswerChange); | ||
case QUESTION_TYPES.IMAGE_MATCH: | ||
return renderImageMatch(question, selectedAnswer, onAnswerChange); | ||
case QUESTION_TYPES.KEYWORDS: | ||
return renderKeywords(question, selectedAnswer, onAnswerChange); | ||
case QUESTION_TYPES.FILL_THE_GAP: | ||
return renderFillTheGap(question, selectedAnswer, onAnswerChange); | ||
default: | ||
return <Text>Unknown question type</Text>; | ||
} | ||
}; | ||
|
||
return ( | ||
<Box borderWidth="1px" borderRadius="lg" p={4} w="100%"> | ||
<Text fontWeight="bold">{question.text}</Text> | ||
{renderQuestion()} | ||
</Box> | ||
); | ||
}; | ||
|
||
export default QuestionItem; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,42 @@ | ||
import React from 'react'; | ||
import { Box, VStack, Text } from '@chakra-ui/react'; | ||
import QuestionItem from '~/components/Test/Question/QuestionItem'; | ||
|
||
class TestSection { | ||
constructor(id, title, questions) { | ||
this.id = id; | ||
this.title = title; | ||
this.questions = questions; | ||
} | ||
} | ||
|
||
const TestSectionComponent = ({ section, onAnswerChange, answers }) => { | ||
return ( | ||
<Box> | ||
<Text fontSize="2xl" fontWeight="bold"> | ||
{section.title} | ||
</Text> | ||
|
||
<VStack spacing={6} w="100%"> | ||
{section.questions.map((question) => ( | ||
<Box | ||
key={question.id} | ||
w="100%" | ||
borderWidth="1px" | ||
borderRadius="lg" | ||
p={4} | ||
mb={4} | ||
> | ||
<QuestionItem | ||
question={question} | ||
selectedAnswer={answers[question.id]} | ||
onAnswerChange={onAnswerChange} | ||
/> | ||
</Box> | ||
))} | ||
</VStack> | ||
</Box> | ||
); | ||
}; | ||
|
||
export default TestSectionComponent; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,64 @@ | ||
import React from 'react'; | ||
import { Box, VStack, Text, Button, Tabs, TabList, TabPanels, Tab, TabPanel } from '@chakra-ui/react'; | ||
import NavbarForStudent from '~/components/Navbars/NavbarForStudent'; | ||
import Footer from '~/components/Footer'; | ||
|
||
const PreviewTest = ({ test, onStart }) => { | ||
return ( | ||
<Box> | ||
<NavbarForStudent /> | ||
|
||
<Box p={4}> | ||
{/* Test Title and Description */} | ||
<VStack spacing={4} align="stretch"> | ||
<Text fontSize="2xl" fontWeight="bold"> | ||
{test.title} | ||
</Text> | ||
<Text>{test.description}</Text> | ||
<Text fontSize="lg" color="gray.600"> | ||
Course: {test.course.name} | ||
</Text> | ||
<Text fontSize="lg" color="gray.600"> | ||
Duration: {test.durationInMilis / 60000} minutes | ||
</Text> | ||
</VStack> | ||
|
||
{/* Tabs showing each section of the test */} | ||
<Tabs variant="soft-rounded" mt="50px"> | ||
<TabList> | ||
{test.sections.map((section) => ( | ||
<Tab key={section.id}>{section.title}</Tab> | ||
))} | ||
</TabList> | ||
|
||
<TabPanels> | ||
{test.sections.map((section) => ( | ||
<TabPanel key={section.id}> | ||
<VStack spacing={4} align="stretch"> | ||
<Text fontSize="xl" fontWeight="bold"> | ||
{section.title} | ||
</Text> | ||
<Text color="gray.600">Questions in this section:</Text> | ||
{section.questions.map((question) => ( | ||
<Text key={question.id}> | ||
{question.text} (Type: {question.type}) | ||
</Text> | ||
))} | ||
</VStack> | ||
</TabPanel> | ||
))} | ||
</TabPanels> | ||
</Tabs> | ||
|
||
{/* Start Test Button */} | ||
<Button colorScheme="blue" size="lg" mt={6} onClick={onStart}> | ||
Start Test | ||
</Button> | ||
</Box> | ||
|
||
<Footer /> | ||
</Box> | ||
); | ||
}; | ||
|
||
export default PreviewTest; |
Oops, something went wrong.