feat: show and hide quiz answers
This commit is contained in:
@@ -8,13 +8,17 @@
|
|||||||
"engine": "InnoDB",
|
"engine": "InnoDB",
|
||||||
"field_order": [
|
"field_order": [
|
||||||
"title",
|
"title",
|
||||||
|
"show_answers",
|
||||||
|
"column_break_gaac",
|
||||||
|
"max_attempts",
|
||||||
|
"show_submission_history",
|
||||||
|
"section_break_sbjx",
|
||||||
"questions",
|
"questions",
|
||||||
"section_break_3",
|
"section_break_3",
|
||||||
"max_attempts",
|
|
||||||
"time",
|
|
||||||
"column_break_5",
|
|
||||||
"lesson",
|
"lesson",
|
||||||
"course"
|
"column_break_5",
|
||||||
|
"course",
|
||||||
|
"time"
|
||||||
],
|
],
|
||||||
"fields": [
|
"fields": [
|
||||||
{
|
{
|
||||||
@@ -66,11 +70,31 @@
|
|||||||
{
|
{
|
||||||
"fieldname": "section_break_3",
|
"fieldname": "section_break_3",
|
||||||
"fieldtype": "Section Break"
|
"fieldtype": "Section Break"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"default": "1",
|
||||||
|
"fieldname": "show_answers",
|
||||||
|
"fieldtype": "Check",
|
||||||
|
"label": "Show Answers"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "column_break_gaac",
|
||||||
|
"fieldtype": "Column Break"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "section_break_sbjx",
|
||||||
|
"fieldtype": "Section Break"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"default": "0",
|
||||||
|
"fieldname": "show_submission_history",
|
||||||
|
"fieldtype": "Check",
|
||||||
|
"label": "Show Submission History"
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"index_web_pages_for_search": 1,
|
"index_web_pages_for_search": 1,
|
||||||
"links": [],
|
"links": [],
|
||||||
"modified": "2023-06-23 12:35:25.204131",
|
"modified": "2023-07-04 15:26:24.457745",
|
||||||
"modified_by": "Administrator",
|
"modified_by": "Administrator",
|
||||||
"module": "LMS",
|
"module": "LMS",
|
||||||
"name": "LMS Quiz",
|
"name": "LMS Quiz",
|
||||||
|
|||||||
@@ -143,13 +143,17 @@ def quiz_summary(quiz, results):
|
|||||||
|
|
||||||
|
|
||||||
@frappe.whitelist()
|
@frappe.whitelist()
|
||||||
def save_quiz(quiz_title, max_attempts=1, quiz=None):
|
def save_quiz(
|
||||||
|
quiz_title, max_attempts=1, quiz=None, show_answers=1, show_submission_history=0
|
||||||
|
):
|
||||||
if not can_create_courses():
|
if not can_create_courses():
|
||||||
return
|
return
|
||||||
|
|
||||||
values = {
|
values = {
|
||||||
"title": quiz_title,
|
"title": quiz_title,
|
||||||
"max_attempts": max_attempts,
|
"max_attempts": max_attempts,
|
||||||
|
"show_answers": show_answers,
|
||||||
|
"show_submission_history": show_submission_history,
|
||||||
}
|
}
|
||||||
|
|
||||||
if quiz:
|
if quiz:
|
||||||
@@ -232,15 +236,17 @@ def get_question_details(question):
|
|||||||
|
|
||||||
|
|
||||||
@frappe.whitelist()
|
@frappe.whitelist()
|
||||||
def check_answer(question, type, answer):
|
def check_answer(question, type, answers):
|
||||||
|
answers = json.loads(answers)
|
||||||
if type == "Choices":
|
if type == "Choices":
|
||||||
return check_choice_answers(question, answer)
|
return check_choice_answers(question, answers)
|
||||||
else:
|
else:
|
||||||
return check_input_answers(question, answer)
|
return check_input_answers(question, answers[0])
|
||||||
|
|
||||||
|
|
||||||
def check_choice_answers(question, answer):
|
def check_choice_answers(question, answers):
|
||||||
fields = []
|
fields = []
|
||||||
|
is_correct = []
|
||||||
for num in range(1, 5):
|
for num in range(1, 5):
|
||||||
fields.append(f"option_{cstr(num)}")
|
fields.append(f"option_{cstr(num)}")
|
||||||
fields.append(f"is_correct_{cstr(num)}")
|
fields.append(f"is_correct_{cstr(num)}")
|
||||||
@@ -250,9 +256,13 @@ def check_choice_answers(question, answer):
|
|||||||
)
|
)
|
||||||
|
|
||||||
for num in range(1, 5):
|
for num in range(1, 5):
|
||||||
if question_details[f"option_{num}"] == answer:
|
print(question_details[f"option_{num}"], answers)
|
||||||
return question_details[f"is_correct_{num}"]
|
if question_details[f"option_{num}"] in answers:
|
||||||
return 0
|
is_correct.append(question_details[f"is_correct_{num}"])
|
||||||
|
else:
|
||||||
|
is_correct.append(0)
|
||||||
|
|
||||||
|
return is_correct
|
||||||
|
|
||||||
|
|
||||||
def check_input_answers(question, answer):
|
def check_input_answers(question, answer):
|
||||||
|
|||||||
@@ -165,6 +165,7 @@
|
|||||||
{
|
{
|
||||||
"fieldname": "type",
|
"fieldname": "type",
|
||||||
"fieldtype": "Select",
|
"fieldtype": "Select",
|
||||||
|
"in_list_view": 1,
|
||||||
"label": "Type",
|
"label": "Type",
|
||||||
"options": "Choices\nUser Input"
|
"options": "Choices\nUser Input"
|
||||||
},
|
},
|
||||||
@@ -206,7 +207,7 @@
|
|||||||
"index_web_pages_for_search": 1,
|
"index_web_pages_for_search": 1,
|
||||||
"istable": 1,
|
"istable": 1,
|
||||||
"links": [],
|
"links": [],
|
||||||
"modified": "2023-06-09 17:09:53.740179",
|
"modified": "2023-07-04 16:43:49.837134",
|
||||||
"modified_by": "Administrator",
|
"modified_by": "Administrator",
|
||||||
"module": "LMS",
|
"module": "LMS",
|
||||||
"name": "LMS Quiz Question",
|
"name": "LMS Quiz Question",
|
||||||
|
|||||||
@@ -114,22 +114,23 @@ def quiz_renderer(quiz_name):
|
|||||||
"LMS Quiz Submission", {"owner": frappe.session.user, "quiz": quiz_name}
|
"LMS Quiz Submission", {"owner": frappe.session.user, "quiz": quiz_name}
|
||||||
)
|
)
|
||||||
|
|
||||||
all_submissions = frappe.get_all(
|
if quiz.show_submission_history:
|
||||||
"LMS Quiz Submission",
|
all_submissions = frappe.get_all(
|
||||||
{
|
"LMS Quiz Submission",
|
||||||
"quiz": quiz.name,
|
{
|
||||||
"member": frappe.session.user,
|
"quiz": quiz.name,
|
||||||
},
|
"member": frappe.session.user,
|
||||||
["name", "score", "creation"],
|
},
|
||||||
order_by="creation desc",
|
["name", "score", "creation"],
|
||||||
)
|
order_by="creation desc",
|
||||||
|
)
|
||||||
|
|
||||||
return frappe.render_template(
|
return frappe.render_template(
|
||||||
"templates/quiz/quiz.html",
|
"templates/quiz/quiz.html",
|
||||||
{
|
{
|
||||||
"quiz": quiz,
|
"quiz": quiz,
|
||||||
"no_of_attempts": no_of_attempts,
|
"no_of_attempts": no_of_attempts,
|
||||||
"all_submissions": all_submissions,
|
"all_submissions": all_submissions if quiz.show_submission_history else None,
|
||||||
"hide_quiz": False,
|
"hide_quiz": False,
|
||||||
},
|
},
|
||||||
)
|
)
|
||||||
|
|||||||
@@ -242,7 +242,7 @@ textarea.field-input {
|
|||||||
input[type=checkbox] {
|
input[type=checkbox] {
|
||||||
appearance: auto;
|
appearance: auto;
|
||||||
position: relative;
|
position: relative;
|
||||||
width: var(--checkbox-size)!important;
|
width: var(--checkbox-size) !important;
|
||||||
height: var(--checkbox-size);
|
height: var(--checkbox-size);
|
||||||
margin-right: var(--checkbox-right-margin)!important;
|
margin-right: var(--checkbox-right-margin)!important;
|
||||||
background-repeat: no-repeat;
|
background-repeat: no-repeat;
|
||||||
@@ -252,8 +252,6 @@ input[type=checkbox] {
|
|||||||
box-shadow: 0 1px 2px #0000001a;
|
box-shadow: 0 1px 2px #0000001a;
|
||||||
border-radius: 4px;
|
border-radius: 4px;
|
||||||
-webkit-appearance: none;
|
-webkit-appearance: none;
|
||||||
-moz-appearance: none;
|
|
||||||
appearance: none;
|
|
||||||
-webkit-print-color-adjust: exact;
|
-webkit-print-color-adjust: exact;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1904,10 +1902,6 @@ li {
|
|||||||
padding: 0 1rem !important;
|
padding: 0 1rem !important;
|
||||||
}
|
}
|
||||||
|
|
||||||
.modal-dialog-scrollable .modal-body {
|
|
||||||
overflow-y: unset;
|
|
||||||
}
|
|
||||||
|
|
||||||
.modal-dialog-scrollable .modal-content {
|
.modal-dialog-scrollable .modal-content {
|
||||||
overflow: unset;
|
overflow: unset;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -24,7 +24,8 @@
|
|||||||
<div id="start-banner" class="common-card-style column-card align-items-center">
|
<div id="start-banner" class="common-card-style column-card align-items-center">
|
||||||
|
|
||||||
<div class="text-center my-10">
|
<div class="text-center my-10">
|
||||||
<div class="bold-heading" id="quiz-title" data-name="{{ quiz.name }}" data-max-attempts="{{ quiz.max_attempts }}">
|
<div class="bold-heading" id="quiz-title" data-max-attempts="{{ quiz.max_attempts }}"
|
||||||
|
data-name="{{ quiz.name }}" data-show-answers="{{ quiz.show_answers }}">
|
||||||
{{ quiz.title }}
|
{{ quiz.title }}
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
@@ -105,10 +106,13 @@
|
|||||||
</div>
|
</div>
|
||||||
{% endif %}
|
{% endif %}
|
||||||
|
|
||||||
|
{% if quiz.show_answers %}
|
||||||
<button class="btn btn-secondary btn-sm pull-right" id="check" disabled>
|
<button class="btn btn-secondary btn-sm pull-right" id="check" disabled>
|
||||||
{{ _("Check") }}
|
{{ _("Check") }}
|
||||||
</button>
|
</button>
|
||||||
<button class="btn btn-secondary btn-sm hide" id="next">
|
{% endif %}
|
||||||
|
|
||||||
|
<button class="btn btn-secondary btn-sm {% if quiz.show_answers %} hide {% endif %}" id="next" disabled>
|
||||||
{{ _("Next Question") }}
|
{{ _("Next Question") }}
|
||||||
</button>
|
</button>
|
||||||
<button class="btn btn-secondary btn-sm hide" id="summary">
|
<button class="btn btn-secondary btn-sm hide" id="summary">
|
||||||
@@ -122,7 +126,7 @@
|
|||||||
</div>
|
</div>
|
||||||
{% endif %}
|
{% endif %}
|
||||||
|
|
||||||
{% if all_submissions | length %}
|
{% if quiz.show_submission_history and all_submissions | length %}
|
||||||
<article class="mt-8">
|
<article class="mt-8">
|
||||||
<div class="field-label">
|
<div class="field-label">
|
||||||
{{ _("All Submissions") }}
|
{{ _("All Submissions") }}
|
||||||
@@ -131,9 +135,9 @@
|
|||||||
<div class="grid-heading-row">
|
<div class="grid-heading-row">
|
||||||
<div class="grid-row">
|
<div class="grid-row">
|
||||||
<div class="data-row row">
|
<div class="data-row row">
|
||||||
<div class="col grid-static-col">{{ _("No.") }}</div>
|
<div class="col grid-static-col col-xs-1">{{ _("No.") }}</div>
|
||||||
<div class="col grid-static-col">{{ _("Date") }}</div>
|
|
||||||
<div class="col grid-static-col text-right">{{ _("Score") }}</div>
|
<div class="col grid-static-col text-right">{{ _("Score") }}</div>
|
||||||
|
<div class="col grid-static-col">{{ _("Date") }}</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@@ -141,9 +145,11 @@
|
|||||||
{% for submission in all_submissions %}
|
{% for submission in all_submissions %}
|
||||||
<div class="grid-row">
|
<div class="grid-row">
|
||||||
<div class="data-row row">
|
<div class="data-row row">
|
||||||
<div class="col grid-static-col">{{ loop.index }}</div>
|
<div class="col grid-static-col col-xs-1">{{ loop.index }}</div>
|
||||||
<div class="col grid-static-col">{{ frappe.utils.format_datetime(submission.creation, "medium") }}</div>
|
|
||||||
<div class="col grid-static-col text-right">{{ submission.score }}</div>
|
<div class="col grid-static-col text-right">{{ submission.score }}</div>
|
||||||
|
<div class="col grid-static-col" title="{{ frappe.utils.format_datetime(submission.creation, "medium") }}">
|
||||||
|
{{ frappe.utils.pretty_date(submission.creation) }}
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
{% endfor %}
|
{% endfor %}
|
||||||
|
|||||||
@@ -1,8 +1,9 @@
|
|||||||
frappe.ready(() => {
|
frappe.ready(() => {
|
||||||
|
const self = this;
|
||||||
this.quiz_submitted = false;
|
this.quiz_submitted = false;
|
||||||
this.answer = [];
|
this.answer = [];
|
||||||
this.is_correct = [];
|
this.is_correct = [];
|
||||||
const self = this;
|
this.show_answers = $("#quiz-title").data("show-answers");
|
||||||
localStorage.removeItem($("#quiz-title").data("name"));
|
localStorage.removeItem($("#quiz-title").data("name"));
|
||||||
|
|
||||||
$(".btn-start-quiz").click((e) => {
|
$(".btn-start-quiz").click((e) => {
|
||||||
@@ -21,8 +22,11 @@ frappe.ready(() => {
|
|||||||
|
|
||||||
$("#summary").click((e) => {
|
$("#summary").click((e) => {
|
||||||
e.preventDefault();
|
e.preventDefault();
|
||||||
add_to_local_storage();
|
if (!this.show_answers) check_answer();
|
||||||
quiz_summary(e);
|
|
||||||
|
setTimeout(() => {
|
||||||
|
quiz_summary(e);
|
||||||
|
}, 500);
|
||||||
});
|
});
|
||||||
|
|
||||||
$("#check").click((e) => {
|
$("#check").click((e) => {
|
||||||
@@ -32,7 +36,8 @@ frappe.ready(() => {
|
|||||||
|
|
||||||
$("#next").click((e) => {
|
$("#next").click((e) => {
|
||||||
e.preventDefault();
|
e.preventDefault();
|
||||||
add_to_local_storage();
|
if (!this.show_answers) check_answer();
|
||||||
|
|
||||||
mark_active_question(e);
|
mark_active_question(e);
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -42,21 +47,30 @@ frappe.ready(() => {
|
|||||||
});
|
});
|
||||||
|
|
||||||
const mark_active_question = (e = undefined) => {
|
const mark_active_question = (e = undefined) => {
|
||||||
$(".timer").addClass("hide");
|
let total_questions = $(".question").length;
|
||||||
calculate_and_display_time(100);
|
|
||||||
$(".timer").removeClass("hide");
|
|
||||||
|
|
||||||
let current_index = $(".active-question").attr("data-qt-index") || 0;
|
let current_index = $(".active-question").attr("data-qt-index") || 0;
|
||||||
let next_index = parseInt(current_index) + 1;
|
let next_index = parseInt(current_index) + 1;
|
||||||
|
|
||||||
|
if (this.show_answers) {
|
||||||
|
$("#next").addClass("hide");
|
||||||
|
} else if (!this.show_answers && next_index == total_questions) {
|
||||||
|
$("#next").addClass("hide");
|
||||||
|
$("#summary").removeClass("hide");
|
||||||
|
}
|
||||||
|
|
||||||
$(".question").addClass("hide").removeClass("active-question");
|
$(".question").addClass("hide").removeClass("active-question");
|
||||||
$(`.question[data-qt-index='${next_index}']`)
|
$(`.question[data-qt-index='${next_index}']`)
|
||||||
.removeClass("hide")
|
.removeClass("hide")
|
||||||
.addClass("active-question");
|
.addClass("active-question");
|
||||||
|
|
||||||
$(".current-question").text(`${next_index}`);
|
$(".current-question").text(`${next_index}`);
|
||||||
$("#check").removeClass("hide").attr("disabled", true);
|
$("#check").removeClass("hide").attr("disabled", true);
|
||||||
$("#next").addClass("hide");
|
$("#next").attr("disabled", true);
|
||||||
$(".explanation").addClass("hide");
|
$(".explanation").addClass("hide");
|
||||||
|
|
||||||
|
$(".timer").addClass("hide");
|
||||||
|
calculate_and_display_time(100);
|
||||||
|
$(".timer").removeClass("hide");
|
||||||
initialize_timer();
|
initialize_timer();
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -95,6 +109,7 @@ const initialize_timer = () => {
|
|||||||
const enable_check = (e) => {
|
const enable_check = (e) => {
|
||||||
if ($(".option:checked").length || $(".possibility").val().trim()) {
|
if ($(".option:checked").length || $(".possibility").val().trim()) {
|
||||||
$("#check").removeAttr("disabled");
|
$("#check").removeAttr("disabled");
|
||||||
|
$("#next").removeAttr("disabled");
|
||||||
$(".custom-checkbox").removeClass("active-option");
|
$(".custom-checkbox").removeClass("active-option");
|
||||||
$(".option:checked")
|
$(".option:checked")
|
||||||
.closest(".custom-checkbox")
|
.closest(".custom-checkbox")
|
||||||
@@ -145,8 +160,10 @@ const try_quiz_again = (e) => {
|
|||||||
|
|
||||||
const check_answer = (e = undefined) => {
|
const check_answer = (e = undefined) => {
|
||||||
e && e.preventDefault();
|
e && e.preventDefault();
|
||||||
|
|
||||||
let answer = $(".active-question textarea");
|
let answer = $(".active-question textarea");
|
||||||
|
let total_questions = $(".question").length;
|
||||||
|
let current_index = $(".active-question").attr("data-qt-index");
|
||||||
|
|
||||||
if (answer.length && !answer.val().trim()) {
|
if (answer.length && !answer.val().trim()) {
|
||||||
frappe.throw(__("Please enter your answer"));
|
frappe.throw(__("Please enter your answer"));
|
||||||
}
|
}
|
||||||
@@ -154,73 +171,77 @@ const check_answer = (e = undefined) => {
|
|||||||
clearInterval(self.timer);
|
clearInterval(self.timer);
|
||||||
$(".timer").addClass("hide");
|
$(".timer").addClass("hide");
|
||||||
|
|
||||||
let total_questions = $(".question").length;
|
|
||||||
let current_index = $(".active-question").attr("data-qt-index");
|
|
||||||
|
|
||||||
$(".explanation").removeClass("hide");
|
$(".explanation").removeClass("hide");
|
||||||
$("#check").addClass("hide");
|
$("#check").addClass("hide");
|
||||||
|
|
||||||
if (current_index == total_questions) {
|
if (current_index == total_questions) {
|
||||||
$("#summary").removeClass("hide");
|
$("#summary").removeClass("hide");
|
||||||
} else {
|
} else if (this.show_answers) {
|
||||||
$("#next").removeClass("hide");
|
$("#next").removeClass("hide");
|
||||||
}
|
}
|
||||||
parse_options();
|
parse_options();
|
||||||
};
|
};
|
||||||
|
|
||||||
const parse_options = () => {
|
const parse_options = () => {
|
||||||
|
let user_answers = [];
|
||||||
|
let element;
|
||||||
let type = $(".active-question").data("type");
|
let type = $(".active-question").data("type");
|
||||||
|
|
||||||
if (type == "Choices") {
|
if (type == "Choices") {
|
||||||
$(".active-question input").each((i, element) => {
|
$(".active-question input").each((i, element) => {
|
||||||
is_answer_correct(type, element);
|
if ($(element).prop("checked")) {
|
||||||
|
user_answers.push(decodeURIComponent($(element).val()));
|
||||||
|
}
|
||||||
});
|
});
|
||||||
|
element = $(".active-question input");
|
||||||
} else {
|
} else {
|
||||||
is_answer_correct(type, $(".active-question textarea"));
|
user_answers.push($(".active-question textarea").val());
|
||||||
|
element = $(".active-question textarea");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
is_answer_correct(type, user_answers, element);
|
||||||
};
|
};
|
||||||
|
|
||||||
const is_answer_correct = (type, element) => {
|
const is_answer_correct = (type, user_answers, element) => {
|
||||||
let answer = decodeURIComponent($(element).val());
|
|
||||||
|
|
||||||
frappe.call({
|
frappe.call({
|
||||||
async: false,
|
async: false,
|
||||||
method: "lms.lms.doctype.lms_quiz.lms_quiz.check_answer",
|
method: "lms.lms.doctype.lms_quiz.lms_quiz.check_answer",
|
||||||
args: {
|
args: {
|
||||||
question: $(".active-question").data("name"),
|
question: $(".active-question").data("name"),
|
||||||
type: type,
|
type: type,
|
||||||
answer: answer,
|
answers: user_answers,
|
||||||
},
|
},
|
||||||
callback: (data) => {
|
callback: (data) => {
|
||||||
type == "Choices"
|
type == "Choices"
|
||||||
? parse_choices(element, data.message)
|
? parse_choices(element, data.message)
|
||||||
: parse_possible_answers(element, data.message);
|
: parse_possible_answers(element, data.message);
|
||||||
|
add_to_local_storage();
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
const parse_choices = (element, correct) => {
|
const parse_choices = (element, is_correct) => {
|
||||||
if ($(element).prop("checked")) {
|
element.each((i, elem) => {
|
||||||
self.answer.push(decodeURIComponent($(element).val()));
|
if ($(elem).prop("checked")) {
|
||||||
correct && self.is_correct.push(1);
|
self.answer.push(decodeURIComponent($(elem).val()));
|
||||||
correct ? add_icon(element, "check") : add_icon(element, "wrong");
|
self.is_correct.push(is_correct[i]);
|
||||||
} else {
|
if (this.show_answers)
|
||||||
correct && self.is_correct.push(0);
|
is_correct[i]
|
||||||
correct
|
? add_icon(elem, "check")
|
||||||
? add_icon(element, "minus-circle-green")
|
: add_icon(elem, "wrong");
|
||||||
: add_icon(element, "minus-circle");
|
} else {
|
||||||
}
|
add_icon(elem, "minus-circle");
|
||||||
|
}
|
||||||
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
const parse_possible_answers = (element, correct) => {
|
const parse_possible_answers = (element, correct) => {
|
||||||
self.answer.push(decodeURIComponent($(element).val()));
|
self.answer.push(decodeURIComponent($(element).val()));
|
||||||
if (correct) {
|
self.is_correct.push(correct);
|
||||||
self.is_correct.push(1);
|
if (this.show_answers)
|
||||||
show_indicator("success", element);
|
correct
|
||||||
} else {
|
? show_indicator("success", element)
|
||||||
self.is_correct.push(0);
|
: show_indicator("failure", element);
|
||||||
show_indicator("failure", element);
|
|
||||||
}
|
|
||||||
};
|
};
|
||||||
|
|
||||||
const show_indicator = (class_name, element) => {
|
const show_indicator = (class_name, element) => {
|
||||||
@@ -253,7 +274,7 @@ const add_to_local_storage = () => {
|
|||||||
let quiz_stored = JSON.parse(localStorage.getItem(quiz_name));
|
let quiz_stored = JSON.parse(localStorage.getItem(quiz_name));
|
||||||
|
|
||||||
let quiz_obj = {
|
let quiz_obj = {
|
||||||
question_index: current_index,
|
question_index: current_index - 1,
|
||||||
answer: self.answer.join(),
|
answer: self.answer.join(),
|
||||||
is_correct: self.is_correct,
|
is_correct: self.is_correct,
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -78,7 +78,7 @@
|
|||||||
<div class="field-parent">
|
<div class="field-parent">
|
||||||
<div class="field-group">
|
<div class="field-group">
|
||||||
<div>
|
<div>
|
||||||
<div class="field-label">
|
<div class="field-label reqd">
|
||||||
{{ _("Title") }}
|
{{ _("Title") }}
|
||||||
</div>
|
</div>
|
||||||
<div class="field-description">
|
<div class="field-description">
|
||||||
@@ -102,6 +102,18 @@
|
|||||||
<input type="number" class="field-input" id="max-attempts" value="{{ max_attempts }}">
|
<input type="number" class="field-input" id="max-attempts" value="{{ max_attempts }}">
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<div class="field-group vertically-center">
|
||||||
|
{% set show_answers = quiz.show_answers or not quiz.name %}
|
||||||
|
<label for="show-answers" class="vertically-center mb-0">
|
||||||
|
<input type="checkbox" id="show-answers" {% if show_answers %} checked {% endif %}>
|
||||||
|
{{ _("Show Answers") }}
|
||||||
|
</label>
|
||||||
|
<label for="upcoming" class="vertically-center mb-0 ml-20">
|
||||||
|
<input type="checkbox" id="show-submission-history" {% if quiz.show_submission_history %} checked {% endif %}>
|
||||||
|
{{ _("Show Submission History") }}
|
||||||
|
</label>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
{% endmacro %}
|
{% endmacro %}
|
||||||
|
|
||||||
|
|||||||
@@ -119,12 +119,19 @@ const edit_question = (e) => {
|
|||||||
};
|
};
|
||||||
|
|
||||||
const save_quiz = (values) => {
|
const save_quiz = (values) => {
|
||||||
|
validate_mandatory();
|
||||||
frappe.call({
|
frappe.call({
|
||||||
method: "lms.lms.doctype.lms_quiz.lms_quiz.save_quiz",
|
method: "lms.lms.doctype.lms_quiz.lms_quiz.save_quiz",
|
||||||
args: {
|
args: {
|
||||||
quiz_title: values.quiz_title,
|
quiz_title: values.quiz_title,
|
||||||
max_attempts: values.max_attempts,
|
max_attempts: values.max_attempts,
|
||||||
quiz: $("#quiz-form").data("name") || "",
|
quiz: $("#quiz-form").data("name") || "",
|
||||||
|
show_answers: $("#show-answers").is(":checked") ? 1 : 0,
|
||||||
|
show_submission_history: $("#show-submission-history").is(
|
||||||
|
":checked"
|
||||||
|
)
|
||||||
|
? 1
|
||||||
|
: 0,
|
||||||
},
|
},
|
||||||
callback: (data) => {
|
callback: (data) => {
|
||||||
frappe.show_alert({
|
frappe.show_alert({
|
||||||
@@ -138,6 +145,17 @@ const save_quiz = (values) => {
|
|||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
|
const validate_mandatory = () => {
|
||||||
|
if (!$("#quiz-title").val()) {
|
||||||
|
let error = $("p")
|
||||||
|
.addClass("error-message")
|
||||||
|
.text(__("Please enter a Quiz Title"));
|
||||||
|
$(error).insertAfter("#quiz-title");
|
||||||
|
$("#quiz-title").focus();
|
||||||
|
throw "Title is mandatory";
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
const save_question = (values) => {
|
const save_question = (values) => {
|
||||||
frappe.call({
|
frappe.call({
|
||||||
method: "lms.lms.doctype.lms_quiz.lms_quiz.save_question",
|
method: "lms.lms.doctype.lms_quiz.lms_quiz.save_question",
|
||||||
|
|||||||
@@ -21,7 +21,10 @@ def get_context(context):
|
|||||||
fields_arr = ["name", "question", "type"]
|
fields_arr = ["name", "question", "type"]
|
||||||
|
|
||||||
context.quiz = frappe.db.get_value(
|
context.quiz = frappe.db.get_value(
|
||||||
"LMS Quiz", quizname, ["title", "name", "max_attempts"], as_dict=1
|
"LMS Quiz",
|
||||||
|
quizname,
|
||||||
|
["title", "name", "max_attempts", "show_answers", "show_submission_history"],
|
||||||
|
as_dict=1,
|
||||||
)
|
)
|
||||||
context.quiz.questions = frappe.get_all(
|
context.quiz.questions = frappe.get_all(
|
||||||
"LMS Quiz Question", {"parent": quizname}, fields_arr, order_by="idx"
|
"LMS Quiz Question", {"parent": quizname}, fields_arr, order_by="idx"
|
||||||
|
|||||||
Reference in New Issue
Block a user