summaryrefslogtreecommitdiff
path: root/testapp
diff options
context:
space:
mode:
Diffstat (limited to 'testapp')
-rw-r--r--testapp/exam/forms.py1
-rw-r--r--testapp/exam/models.py1
-rw-r--r--testapp/exam/views.py93
-rw-r--r--testapp/static/exam/js/add_question.js6
-rw-r--r--testapp/static/exam/js/edit_question.js6
-rw-r--r--testapp/templates/exam/question.html11
6 files changed, 71 insertions, 47 deletions
diff --git a/testapp/exam/forms.py b/testapp/exam/forms.py
index c96ac7e..d0b0b74 100644
--- a/testapp/exam/forms.py
+++ b/testapp/exam/forms.py
@@ -25,6 +25,7 @@ languages = (
question_types = (
("select", "Select"),
("mcq", "Multiple Choice"),
+ ("mcc", "Multiple Correct Choices"),
("code", "Code"),
)
diff --git a/testapp/exam/models.py b/testapp/exam/models.py
index 62c707b..0d31b16 100644
--- a/testapp/exam/models.py
+++ b/testapp/exam/models.py
@@ -28,6 +28,7 @@ languages = (
question_types = (
("mcq", "Multiple Choice"),
+ ("mcc", "Multiple Correct Choices"),
("code", "Code"),
)
diff --git a/testapp/exam/views.py b/testapp/exam/views.py
index 422e16f..c4c03df 100644
--- a/testapp/exam/views.py
+++ b/testapp/exam/views.py
@@ -167,7 +167,7 @@ def results_user(request):
papers = AnswerPaper.objects.filter(user=user)
quiz_marks = []
for paper in papers:
- marks_obtained = paper.get_marks_obtained()
+ marks_obtained = paper.update_marks_obtained()
max_marks = paper.question_paper.total_marks
percentage = round((marks_obtained/max_marks)*100, 2)
temp = paper.question_paper.quiz.description, marks_obtained,\
@@ -424,7 +424,7 @@ def automatic_questionpaper(request, questionpaper_id=None):
quest_paper.save()
for quest in questions:
q = Question.objects.get(id=quest)
- quest_paper.questions.add(q)
+ quest_paper.fixed_questions.add(q)
return my_redirect('/exam/manage/showquiz')
else:
no_questions = int(request.POST.get('num_questions'))
@@ -695,7 +695,6 @@ def check(request, q_id, questionpaper_id=None):
q_paper = QuestionPaper.objects.get(id=questionpaper_id)
paper = AnswerPaper.objects.get(user=request.user, question_paper=q_paper)
snippet_code = request.POST.get('snippet')
- user_answer = request.POST.get('answer')
skip = request.POST.get('skip', None)
success_msg = False
success = True
@@ -703,48 +702,32 @@ def check(request, q_id, questionpaper_id=None):
next_q = paper.skip()
return show_question(request, next_q, questionpaper_id)
+ # Add the answer submitted, regardless of it being correct or not.
if question.type == 'mcq':
- # Add the answer submitted, regardless of it being correct or not.
- if user_answer is not None:
- new_answer = Answer(question=question, answer=user_answer,
- correct=False)
- new_answer.save()
- paper.answers.add(new_answer)
-
+ user_answer = request.POST.get('answer')
+ elif question.type == 'mcc':
+ user_answer = request.POST.getlist('answer')
else:
- """Add the answer submitted with the Snippet code,
- regardless of it being correct or not."""
- answer_check = snippet_code + "\n" + user_answer
- new_answer = Answer(question=question, answer=answer_check,
- correct=False)
- new_answer.save()
- paper.answers.add(new_answer)
+ user_code = request.POST.get('answer')
+ user_answer = snippet_code + "\n" + user_code
+
+ new_answer = Answer(question=question, answer=user_answer,
+ correct=False)
+ new_answer.save()
+ paper.answers.add(new_answer)
# If we were not skipped, we were asked to check. For any non-mcq
# questions, we obtain the results via XML-RPC with the code executed
# safely in a separate process (the code_server.py) running as nobody.
- if question.type == 'mcq':
- if user_answer is not None:
- success = True # Only one attempt allowed for MCQ's.
- if user_answer.strip() == question.test.strip():
- new_answer.correct = True
- new_answer.marks = question.points
- new_answer.error = 'Correct answer'
- success_msg = True
- else:
- new_answer.error = 'Incorrect answer'
- new_answer.save()
+ correct, success, err_msg = validate_answer(user, user_answer, question)
+ if correct:
+ new_answer.correct = correct
+ new_answer.marks = question.points
+ new_answer.error = err_msg
+ success_msg = True
else:
- user_dir = get_user_dir(user)
- success, err_msg = code_server.run_code(answer_check, question.test,
- user_dir, question.type)
new_answer.error = err_msg
- if success:
- # Note the success and save it along with the marks.
- new_answer.correct = success
- new_answer.marks = question.points
- success_msg = True
- new_answer.save()
+ new_answer.save()
time_left = paper.time_left()
if not success: # Should only happen for non-mcq questions.
@@ -755,7 +738,7 @@ def check(request, q_id, questionpaper_id=None):
reason = 'The quiz has been deactivated!'
return complete(request, reason, questionpaper_id)
context = {'question': question, 'error_message': err_msg,
- 'paper': paper, 'last_attempt': user_answer,
+ 'paper': paper, 'last_attempt': user_code,
'quiz_name': paper.question_paper.quiz.description,
'time_left': time_left}
ci = RequestContext(request)
@@ -772,6 +755,38 @@ def check(request, q_id, questionpaper_id=None):
questionpaper_id, success_msg)
+def validate_answer(user, user_answer, question):
+ """
+ Checks whether the answer submitted by the user is right or wrong.
+ If right then returns correct = True, success and
+ message = Correct answer.
+ success is True for MCQ's and multiple correct choices because
+ only one attempt are allowed for them.
+ For code questions success is True only if the answer is correct.
+ """
+ success = True
+ correct = False
+ message = 'Incorrect answer'
+
+ if user_answer is not None:
+ if question.type == 'mcq':
+ if user_answer.strip() == question.test.strip():
+ correct = True
+ message = 'Correct answer'
+ elif question.type == 'mcc':
+ answers = set(question.test.splitlines())
+ if set(user_answer) == answers:
+ correct = True
+ message = 'Correct answer'
+ elif question.type == 'code':
+ user_dir = get_user_dir(user)
+ success, message = code_server.run_code(user_answer, question.test,
+ user_dir, question.language)
+ if success:
+ correct = True
+ return correct, success, message
+
+
def quit(request, questionpaper_id=None):
"""Show the quit page when the user logs out."""
context = {'id': questionpaper_id}
@@ -791,7 +806,7 @@ def complete(request, reason=None, questionpaper_id=None):
else:
q_paper = QuestionPaper.objects.get(id=questionpaper_id)
paper = AnswerPaper.objects.get(user=user, question_paper=q_paper)
- obt_marks = paper.get_marks_obtained()
+ obt_marks = paper.update_marks_obtained()
tot_marks = paper.question_paper.total_marks
if obt_marks == paper.question_paper.total_marks:
context = {'message': "Hurray ! You did an excellent job.\
diff --git a/testapp/static/exam/js/add_question.js b/testapp/static/exam/js/add_question.js
index 56fdd1f..267cdb2 100644
--- a/testapp/static/exam/js/add_question.js
+++ b/testapp/static/exam/js/add_question.js
@@ -150,7 +150,7 @@ function textareaformat()
$('#id_type').bind('change',function(event){
var value = document.getElementById('id_type').value;
- if(value == 'mcq')
+ if(value == 'mcq' || value == 'mcc')
{
document.getElementById('id_options').style.visibility='visible';
document.getElementById('label_option').innerHTML="Options :"
@@ -164,7 +164,7 @@ function textareaformat()
});
document.getElementById('my').innerHTML = document.getElementById('id_description').value ;
var value = document.getElementById('id_type').value;
- if(value == 'mcq')
+ if(value == 'mcq' || value == 'mcc')
{
document.getElementById('id_options').style.visibility='visible';
document.getElementById('label_option').innerHTML="Options :"
@@ -192,7 +192,7 @@ function autosubmit()
return false;
}
- if (type.value == 'mcq')
+ if (type.value == 'mcq' || type.value == 'mcc')
{
var value = document.getElementById('id_options').value;
if(value.split('\n').length < 4)
diff --git a/testapp/static/exam/js/edit_question.js b/testapp/static/exam/js/edit_question.js
index c5df631..7a0f56d 100644
--- a/testapp/static/exam/js/edit_question.js
+++ b/testapp/static/exam/js/edit_question.js
@@ -171,7 +171,7 @@ function textareaformat()
var option_id = document.getElementById('id_options' + i);
option_id.onfocus = gainfocus;
option_id.onblur = lostfocus;
- if(value != 'mcq')
+ if(value == 'code' )
{
document.getElementById('id_options'+i).style.visibility='hidden';
document.getElementById('label_option'+(i+1)).innerHTML = "";
@@ -206,7 +206,7 @@ function showOptions(e)
{
var value = this.value;
var no = parseInt(this.id.substring(this.id.length-1));
- if( value == 'mcq')
+ if( value == 'mcq' || value == 'mcc')
{
document.getElementById('id_options'+no).style.visibility = 'visible';
document.getElementById('label_option'+ (no+1)).innerHTML = "Options : "
@@ -256,7 +256,7 @@ function autosubmit()
return false;
}
- if (document.getElementById('id_type' + i).value != 'mcq')
+ if (document.getElementById('id_type' + i).value == 'code')
{
continue;
}
diff --git a/testapp/templates/exam/question.html b/testapp/templates/exam/question.html
index c8454ff..a3e8629 100644
--- a/testapp/templates/exam/question.html
+++ b/testapp/templates/exam/question.html
@@ -106,7 +106,14 @@ function setSnippetHeight()
{% for option in question.options.strip.splitlines %}
<input name="answer" type="radio" value="{{option}}" />{{option}} <br/>
{% endfor %}
- {% else %}
+ {% endif %}
+ {% if question.type == "mcc" %}
+ {% for option in question.options.strip.splitlines %}
+ <input name="answer" type="checkbox" value="{{ option }}"> {{ option }}
+ <br>
+ {% endfor %}
+ {% endif %}
+ {% if question.type == "code" %}
<textarea rows="1" style="padding:0;height:auto;width:750px;overflow:hidden;background-color:white;border: 0 none white;" readonly="yes" name="snippet" id="snippet" wrap="off">{% if last_attempt %}{{ question.snippet }}{% else %}{% if question.type == "bash" %} #!/bin/bash&#13;&#10;{{ question.snippet }}{% else %}{{ question.snippet }}{% endif %}{% endif %}</textarea>
@@ -119,7 +126,7 @@ function setSnippetHeight()
<script>addLineNumbers('snippet');</script>
{% endif %}
- {% if question.type == "mcq" %}
+ {% if question.type == "mcq" or question.type == "mcc "%}
<br><button class="btn" type="submit" name="check" id="check">Submit Answer</button>&nbsp;&nbsp;
{% else %}
<button class="btn" type="submit" name="check" id="check" onClick="submitCode();">Check Answer</button>&nbsp;&nbsp;