Skip to content

Commit

Permalink
Merge pull request #23 from zakie2003/zak-branch
Browse files Browse the repository at this point in the history
edit-question added
  • Loading branch information
nishant0708 authored Sep 8, 2024
2 parents c58cce0 + 648f35c commit 6077b60
Show file tree
Hide file tree
Showing 4 changed files with 280 additions and 13 deletions.
3 changes: 2 additions & 1 deletion src/App.js
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ import Editpaper from './Edit_paper/Editpaper';
import ReadyPaperDashboard from './ReadyPaperDashboard/ReadyPaperDashboard';

import Error404 from './error/error404';
import EditQuestion from './Edit_question/edit_question';


const App = () => {
Expand Down Expand Up @@ -68,7 +69,7 @@ const App = () => {
<Route path="/create-paper" element={<Createpaper />} />
<Route path="/edit-paper" element={<Editpaper/>} />
<Route path="/add-question/:paperId" element={<Question />} />
<Route path="/edit-question/:paperId/:questionId" element={<Question/>} />
<Route path="/edit-question/:paperId/:questionId" element={<EditQuestion/>} />
<Route path="/questionPaperDashboard/:paperId" element={<QuestionPaperDashboard />}/>
<Route path="/ready_papers" element={<ReadyPaperDashboard />}/>
</>
Expand Down
206 changes: 206 additions & 0 deletions src/Edit_question/edit_question.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,206 @@
import React, { useState } from 'react';
import '../question/question.css';
import { FaTimes } from 'react-icons/fa';
import { useDropzone } from 'react-dropzone';
import { IoCloudUploadOutline } from "react-icons/io5";
import Navbar from '../Navbar/Navbar';
import axios from 'axios';
import { useParams, useLocation } from 'react-router-dom';
import AlertModal from '../AlertModal/AlertModal'; // Import the AlertModal component

const EditQuestion = () => {
const { paperId } = useParams();
const location = useLocation();

const { remainingMarks } = location.state || {}; // Get remaining marks from props
const [questionheading, setQuestionHeading] = useState(location.state.questionheading);
const [questionDescription, setQuestionDescription] = useState(location.state.questionDescription);
const [compilerReq, setCompilerReq] = useState(location.state.compilerReq);
const [marks, setMarks] = useState(location.state.marks);
const [image, setImage] = useState(null);
const [loading, setLoading] = useState(false);
const [modalIsOpen, setModalIsOpen] = useState(false);
const [modalMessage, setModalMessage] = useState('');
const [isError, setIsError] = useState(false);
// const navigate=useNavigate();

const handleEditQuestion = async () => {
if (!questionheading || !questionDescription || !compilerReq || !marks) {
setModalMessage('Please fill in all the required fields.');
setIsError(true);
setModalIsOpen(true);
return;
}

if (parseInt(marks) > remainingMarks) {
setModalMessage(`You can assign a maximum of ${remainingMarks} marks to this question.`);
setIsError(true);
setModalIsOpen(true);
return;
}

setLoading(true);
try {
let imageUrl = '';

if (image) {
const formData = new FormData();
formData.append('file', image);
formData.append('upload_preset', 'question');

const uploadResponse = await axios.post('http://localhost:5000/paper/upload', formData, {
headers: { 'Content-Type': 'multipart/form-data' },
});

imageUrl = uploadResponse.data.url; // Assuming the backend responds with the image URL
}

await editQuestion(imageUrl);
} catch (error) {
console.error('Failed to add question:', error.message);
setModalMessage('Failed to add question. Please try again.');
setIsError(true);
setModalIsOpen(true);
setLoading(false);
}
};



const editQuestion = async (imageUrl) => {
const response = await axios.post('http://localhost:5000/paper/edit-question', {
_id: location.state._id,
paperId,
questionheading,
questionDescription,
compilerReq,
marks,
image: imageUrl, // Include imageUrl even if it's an empty string
});

if (response.status === 200) {
setModalMessage('Question Edited successfully!');
setIsError(false);
setModalIsOpen(true);
}
else
{
setModalMessage('Question Edit Failed!');
setIsError(true);
setModalIsOpen(true);
}
setLoading(false);
};

const onDrop = (acceptedFiles) => {
setImage(acceptedFiles[0]);
};

const handleRemoveImage = () => {
setImage(null);
};

const { getRootProps, getInputProps } = useDropzone({
onDrop,
maxSize: 10485760, // 10MB limit,

});

return (
<>
<Navbar />
<div className='add_question_container_main'>
<div className="add_question_container">
<h2 className="add_question_heading">Edit Question</h2>

<div>
<label className="add_question_label">Question Heading:</label>
<input
type="text"
value={questionheading}
onChange={(e) => setQuestionHeading(e.target.value)}
placeholder="Enter your question heading"
required
className="add_question_input"
/>
</div>

<div>
<label className="add_question_label">Question Description:</label>
<textarea
value={questionDescription}
onChange={(e) => setQuestionDescription(e.target.value)}
placeholder="Enter question description"
required
rows="3"
className="add_question_textarea"
/>
</div>

<div className="add_question_row">
<div className="add_question_column">
<label className="add_question_label">Compiler Requirement:</label>
<select
value={compilerReq}
onChange={(e) => setCompilerReq(e.target.value)}
required
className="add_question_select"
>
<option value="" disabled>Select Compiler</option>
<option value="cpp">C++</option>
<option value="java">Java</option>
<option value="python">Python</option>
<option value="sql">SQL</option>
</select>
</div>
<div className="add_question_column">
<label className="add_question_label">Marks:</label>
<input
type="number"
value={marks}
onChange={(e) => setMarks(e.target.value)}
placeholder="Enter marks"
required
className="add_question_input"
/>
</div>
</div>

<div>
<label className="add_question_label">Upload Image (optional):</label>
<div {...getRootProps({ className: 'add_question_dropbox' })}>
<input {...getInputProps()} />
{image ? (
<div className="add_question_image_preview">
<img src={URL.createObjectURL(image)} alt="Question" className="add_question_preview_image" />
<FaTimes className="add_question_remove_image_icon" onClick={handleRemoveImage} />
</div>
) : (
<p>
<div className='add_question_cloudicon'>
<IoCloudUploadOutline />
</div>
Drag and drop an image here, or click to select one
</p>
)}
</div>
</div>

<button onClick={handleEditQuestion} className="add_question_button" disabled={loading}>
{loading ? 'Adding...' : 'Edit Question'}
</button>
</div>
</div>

{/* Alert Modal */}
<AlertModal
isOpen={modalIsOpen}
onClose={() => setModalIsOpen(false)}
message={modalMessage}
iserror={isError}
/>
</>
);
};

export default EditQuestion;
4 changes: 3 additions & 1 deletion src/QuestionPaperDashboard/QuestionPaperDashboard.css
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,7 @@
{
width: 100%;
height: auto;
margin-top: 40px;
margin-bottom: 20px;
}
.question-table-data
Expand All @@ -41,7 +42,7 @@
z-index: 0;
display: flex;
justify-content: center;
padding: 20px;
padding: 35px;
color: white;
text-align: left;
border-bottom: 1px solid #ddd;
Expand All @@ -55,6 +56,7 @@
{
position: relative;
margin: 20px;
margin-bottom: 60px;
font-size: large;
}
.compiler
Expand Down
80 changes: 69 additions & 11 deletions src/QuestionPaperDashboard/QuestionPaperDashboard.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,10 +4,13 @@ import Navbar from "../Navbar/Navbar";
import { FaPlus } from "react-icons/fa";
import { useNavigate, useParams } from "react-router-dom";
import axios from "axios";
import defaultImage from "../Assets/no-image-420x370-1.jpg";
import Nothing from "../Assets/nothing.svg";
import AlertModal from "../AlertModal/AlertModal";

import { CiEdit } from "react-icons/ci";
import { HiDocumentDuplicate } from "react-icons/hi2";
import { MdDelete } from "react-icons/md";


const QuestionPaperDashboard = () => {

Expand All @@ -24,6 +27,8 @@ const QuestionPaperDashboard = () => {
const [modalMessage, setModalMessage] = useState("");
const [isError, setIsError] = useState(false);

const [hoveredItem, setHoveredItem] = useState(null);

useEffect(() => {
const fetchQuestions = async () => {
try {
Expand Down Expand Up @@ -71,16 +76,26 @@ const QuestionPaperDashboard = () => {

const deleteQuestion=async (question)=>
{
console.log(question);
try
{
await axios.post('http://localhost:5000/paper/delete-question', { _id: question._id })
const response = await axios.post('http://localhost:5000/paper/delete-question', { _id: question._id })
setQuestions((prevQuestions) => prevQuestions.filter(q => q._id !== question._id));

if (questions.length === 1) {
setQuestions([]);
}

if(response.status===200){
setModalMessage('Question deleted successfully!');
setIsError(false);
setModalIsOpen(true);
}
else{
setModalMessage('Question deleted failed!');
setIsError(true);
setModalIsOpen(true);
}

setReload(prev => !prev);
}
catch(error)
Expand All @@ -92,9 +107,23 @@ const QuestionPaperDashboard = () => {
const duplicateQuestion= async (question)=>
{
console.log(question);
await axios.post(`http://localhost:5000/paper/duplicate-question`, { question})
const response =await axios.post(`http://localhost:5000/paper/duplicate-question`, { question})
if(response.status===201){
setModalMessage('Question duplicated successfully!');
setIsError(false);
setModalIsOpen(true);
}
else{
setModalMessage('Question duplication failed!');
setIsError(true);
setModalIsOpen(true);
}
setReload(prev => !prev);
}

const editQuestion =(question)=>
{
navigate(`/edit-question/${question.paperId}/${question._id}`,{state:question});
}
const handleSubmit = async () => {
try {
Expand Down Expand Up @@ -152,8 +181,35 @@ const QuestionPaperDashboard = () => {
</div>
)}
<div className="question-table">
{questions.map((question, index) => (
<div className="questions-table" key={index}>
{questions.map((question) => (

<div className="questions-table" key={question._id}
onMouseEnter={() => setHoveredItem(question._id)}
onMouseLeave={() => setHoveredItem(null)}

>
{hoveredItem === question._id && (
<div className="hovered-buttons">
<button onClick={()=>editQuestion(question)}>
<div className="flex-class">
<CiEdit />
<div>Edit</div>
</div>
</button>
<button id="duplicate" onClick={()=>duplicateQuestion(question)}>
<div className="flex-class">
<HiDocumentDuplicate />
<div>Duplicate</div>
</div>
</button>
<button id="delete" onClick={()=>deleteQuestion(question)}>
<div className="flex-class">
<MdDelete />
<div>Delete</div>
</div>
</button>
</div>
)}
<div className="question-table-data">
<div className="compiler">
Compiler: {question.compilerReq}
Expand All @@ -167,16 +223,18 @@ const QuestionPaperDashboard = () => {
{question.questionDescription}
</div>
</div>
<button onClick={()=>duplicateQuestion(question)} style={{width:"200px"}}>Duplicate</button>
<button onClick={()=>deleteQuestion(question)} style={{width:"200px"}}>Delete</button>
{/* <button onClick={()=>editQuestion(question)} >Edit</button>
<button onClick={()=>duplicateQuestion(question)}>Duplicate</button>
<button onClick={()=>deleteQuestion(question)}>Delete</button> */}
{question.image ? (
<div className="question-image">
<img src={question.image} alt="question" />
</div>
) : (
<div className="question-image">
<img src={defaultImage} alt="question" />
</div>
// <div className="question-image">
// <img src={defaultImage} alt="question" />
// </div>
<></>
)}
</div>
</div>
Expand Down

0 comments on commit 6077b60

Please sign in to comment.