Commit f4f3d78b by Sola Committed by Piotr Mitros

fixed git issues

parent 9a3b4626
...@@ -224,7 +224,7 @@ class CrowdXBlock(XBlock): ...@@ -224,7 +224,7 @@ class CrowdXBlock(XBlock):
else: else:
feedback_data[str(hints)] = str(answer_keys) feedback_data[str(hints)] = str(answer_keys)
else: else:
feedback_data[str("There are no hints for" + " " + str(answer_keys))] = str(answer_keys) feedback_data[None] = str(answer_keys)
elif len(self.WrongAnswers) == 0: elif len(self.WrongAnswers) == 0:
return return
else: else:
...@@ -254,7 +254,7 @@ class CrowdXBlock(XBlock): ...@@ -254,7 +254,7 @@ class CrowdXBlock(XBlock):
self.Used.append(str(random_hint_key)) self.Used.append(str(random_hint_key))
else: else:
self.no_hints(index) self.no_hints(index)
feedback_data[str("There are no hints for" + " " + str(self.WrongAnswers[index]))] = str(self.WrongAnswers[index]) feedback_data[None] = str(self.WrongAnswers[index])
self.WrongAnswers=[] self.WrongAnswers=[]
self.Used=[] self.Used=[]
return feedback_data return feedback_data
...@@ -273,7 +273,7 @@ class CrowdXBlock(XBlock): ...@@ -273,7 +273,7 @@ class CrowdXBlock(XBlock):
This function is used to return the ratings of hints during hint feedback. This function is used to return the ratings of hints during hint feedback.
data['student_answer'] is the answer for the hint being displayed data['student_answer'] is the answer for the hint being displayed
data['hint_used'] is the hint being shown to the student data['hint'] is the hint being shown to the student
returns: returns:
hint_rating: the rating of the hint as well as data on what the hint in question is hint_rating: the rating of the hint as well as data on what the hint in question is
...@@ -282,13 +282,13 @@ class CrowdXBlock(XBlock): ...@@ -282,13 +282,13 @@ class CrowdXBlock(XBlock):
if data['student_answer'] == 'Flagged': if data['student_answer'] == 'Flagged':
hint_rating['rating'] = 0 hint_rating['rating'] = 0
hint_rating['student_ansxwer'] = 'Flagged' hint_rating['student_ansxwer'] = 'Flagged'
hint_rating['hint_used'] = data['hint_used'] hint_rating['hint'] = data['hint']
return hint_rating return hint_rating
temporary_dictionary = str(self.hint_database[data['student_answer']]) temporary_dictionary = str(self.hint_database[data['student_answer']])
temporary_dictionary = (ast.literal_eval(temporary_dictionary)) temporary_dictionary = (ast.literal_eval(temporary_dictionary))
hint_rating['rating'] = temporary_dictionary[data['hint_used']] hint_rating['rating'] = temporary_dictionary[data['hint']]
hint_rating['student_answer'] = data['student_answer'] hint_rating['student_answer'] = data['student_answer']
hint_rating['hint_used'] = data['hint_used'] hint_rating['hint'] = data['hint']
return hint_rating return hint_rating
@XBlock.json_handler @XBlock.json_handler
...@@ -302,7 +302,7 @@ class CrowdXBlock(XBlock): ...@@ -302,7 +302,7 @@ class CrowdXBlock(XBlock):
Args: Args:
data['student_answer']: The incorrect answer that corresponds to the hint that is being voted on data['student_answer']: The incorrect answer that corresponds to the hint that is being voted on
data['used_hint']: The hint that is being voted on data['hint']: The hint that is being voted on
data['student_rating']: The rating chosen by the student. The value is -1, 1, or 0. data['student_rating']: The rating chosen by the student. The value is -1, 1, or 0.
Returns: Returns:
...@@ -314,7 +314,7 @@ class CrowdXBlock(XBlock): ...@@ -314,7 +314,7 @@ class CrowdXBlock(XBlock):
# answer_data is manipulated to remove symbols to prevent errors that # answer_data is manipulated to remove symbols to prevent errors that
# might arise due to certain symbols. I don't think I have this fully working but am not sure. # might arise due to certain symbols. I don't think I have this fully working but am not sure.
data_rating = data['student_rating'] data_rating = data['student_rating']
data_hint = data['used_hint'] data_hint = data['hint']
if data['student_rating'] == 'unflag': if data['student_rating'] == 'unflag':
for flagged_hints in self.Flagged: for flagged_hints in self.Flagged:
if self.Flagged[str(flagged_hints)] == data_hint: if self.Flagged[str(flagged_hints)] == data_hint:
...@@ -332,23 +332,23 @@ class CrowdXBlock(XBlock): ...@@ -332,23 +332,23 @@ class CrowdXBlock(XBlock):
if data['student_rating'] == 'flag': if data['student_rating'] == 'flag':
# add hint to # add hint to
self.Flagged[str(answer_data)] = data_hint self.Flagged[str(answer_data)] = data_hint
return {"rating": 'flagged', 'used_hint': data_hint} return {"rating": 'flagged', 'hint': data_hint}
if str(data_hint) not in self.Voted: if str(data_hint) not in self.Voted:
self.Voted.append(str(data_hint)) # add data to Voted to prevent multiple votes self.Voted.append(str(data_hint)) # add data to Voted to prevent multiple votes
rating = self.change_rating(data_hint, data_rating, answer_data) # change hint rating rating = self.change_rating(data_hint, data_rating, answer_data) # change hint rating
if str(rating) == str(0): if str(rating) == str(0):
return {"rating": str(0), 'used_hint': data_hint} return {"rating": str(0), 'hint': data_hint}
else: else:
return {"rating": str(rating), 'used_hint': data_hint} return {"rating": str(rating), 'hint': data_hint}
else: else:
return {"rating": str('voted'), 'used_hint': data_hint} return {"rating": str('voted'), 'hint': data_hint}
# def hint_flagged(self, data_hint, answer_data): # def hint_flagged(self, data_hint, answer_data):
# """ # """
# This is used to add a hint to the self.flagged dictionary. When a hint is returned with the rating # This is used to add a hint to the self.flagged dictionary. When a hint is returned with the rating
# of 0, it is considered to be flagged. # of 0, it is considered to be flagged.
# Args: # Args:
# data_hint: This is equal to the data['used_hint'] in self.rate_hint # data_hint: This is equal to the data['hint'] in self.rate_hint
# answer_data: This is equal to the data['student_answer'] in self.rate_hint # answer_data: This is equal to the data['student_answer'] in self.rate_hint
# """ # """
# for answer_keys in self.hint_database: # for answer_keys in self.hint_database:
...@@ -364,7 +364,7 @@ class CrowdXBlock(XBlock): ...@@ -364,7 +364,7 @@ class CrowdXBlock(XBlock):
in self.rate_hint in self.rate_hint
Args: Args:
data_hint: This is equal to the data['used_hint'] in self.rate_hint data_hint: This is equal to the data['hint'] in self.rate_hint
data_rating: This is equal to the data['student_rating'] in self.rate_hint data_rating: This is equal to the data['student_rating'] in self.rate_hint
answer_data: This is equal to the data['student_answer'] in self.rate_hint answer_data: This is equal to the data['student_answer'] in self.rate_hint
......
...@@ -35,17 +35,17 @@ ...@@ -35,17 +35,17 @@
margin-right:auto; margin-right:auto;
} }
d2[data-rate="flag"] { div[data-rate="flag"] {
align-self: flex-end; align-self: flex-end;
} }
d1[data-rate="upvote"] { div[data-rate="upvote"] {
color: green; color: green;
font-weight: bold; font-weight: bold;
margin-right:15px; margin-right:15px;
} }
d5[data-rate="downvote"] { div[data-rate="downvote"] {
color: red; color: red;
font-weight: bold; font-weight: bold;
} }
......
<script type="x-tmpl-mustache" id="show_hint_feedback">
<div class="hint_value" value={{hint}}>
<div role="button" class="rate_hint" data-rate="upvote" data-icon="arrow-u" aria-label="upvote">
<b></b>
</div>
<div role="button" class="rate_hint" data-rate="flag" data-icon="flag" aria-label="flag">
<b>!</b>
</div>
<div class ="rating"> {{rating}} </div>
<div class="hint"> {{hint}} </div>
<div role="button" class="rate_hint" data-rate="downvote" aria-label="downvote">
<b></b>
</div>
</div>
</script>
<div class="crowdxblock_block"> <!--most stuff just for testing purposes--> <div class="crowdxblock_block"> <!--most stuff just for testing purposes-->
<p> <span class='HintsToUse'></span> <p> <span class='HintsToUse'></span>
......
...@@ -2,39 +2,33 @@ function CrowdXBlock(runtime, element){ ...@@ -2,39 +2,33 @@ function CrowdXBlock(runtime, element){
//use executionFunctions to prevent old initializations of hinter from working after switching units //use executionFunctions to prevent old initializations of hinter from working after switching units
var executeFunctions = true; var executeFunctions = true;
if(executeFunctions){ if(executeFunctions){
var isShowingHintFeedback = false;
var isStaff = false; var isStaff = false;
$(".HintsToUse", element).text(""); $(".HintsToUse", element).text("");
function stopScript(){ function stopScript(){
//This function is used to prevent a particular instance of the hinter from acting after
//switching between edX course's units.
executionFunctions = false; executionFunctions = false;
} }
Logger.listen('seq_next', null, stopScript); Logger.listen('seq_next', null, stopScript);
Logger.listen('seq_prev', null, stopScript); Logger.listen('seq_prev', null, stopScript);
Logger.listen('seq_goto', null, stopScript); Logger.listen('seq_goto', null, stopScript);
function logError(details) {
$.ajax({
type: 'POST',
url: '/home/sola/crowdxblock',
data: JSON.stringify({context: navigator.userAgent, details: details}),
contentType: 'application/json; charset=utf-8'
});
}
//read the data from the problem_graded event here //read the data from the problem_graded event here
function get_event_data(event_type, data, element){ function get_event_data(event_type, data, element){
check_correct(event_type, data, element); onStudentSubmission(data);
} }
Logger.listen('problem_graded', null, get_event_data); Logger.listen('problem_graded', null, get_event_data);
function check_correct(var_event_type, var_data, var_element){ function onStudentSubmission(problem_graded_event_data){
//check that problem wasn't correctly answered //This function will determine whether or not the student correctly answered the question.
if (var_data[1].search(/class="correct/) === -1){ //If it was correctly answered it will begin the process for giving feedback on hints.
if (problem_graded_event_data[1].search(/class="correct/) === -1){
$.ajax({ $.ajax({
type: "POST", type: "POST",
url: runtime.handlerUrl(element, 'get_hint'), url: runtime.handlerUrl(element, 'get_hint'),
data: JSON.stringify({"submittedanswer": unescape(var_data[0])}), data: JSON.stringify({"submittedanswer": unescape(problem_graded_event_data[0])}),
success: seehint success: seehint
}); });
}else{ }else{
...@@ -69,105 +63,117 @@ function CrowdXBlock(runtime, element){ ...@@ -69,105 +63,117 @@ function CrowdXBlock(runtime, element){
} }
function seehint(result){ function seehint(result){
//show hint to student //Show a hint to the student after an incorrect answer is submitted.
$('.HintsToUse', element).text(result.HintsToUse); $('.HintsToUse', element).text(result.HintsToUse);
} }
function appendHint(result){ function showHintFeedback(result){
//Append answer-specific hints for each student answer during the feedback stage.
//This appended div includes upvote/downvote/flagging buttons, the hint, and the hint's rating
$(".student_answer", element).each(function(){ $(".student_answer", element).each(function(){
if ($(this).find("span").text() == result.student_answer){ if ($(this).find("span").text() == result.student_answer){
$(this).append(unescape("<div class=\"hint_value\" value = \"" + result.hint_used + "\">" + var template = $('#show_hint_feedback').html();
"<div> <d1 role=\"button\"class=\"rate_hint\" data-rate=\"upvote\" data-icon=\"arrow-u\" aria-label=\"upvote\"><b>↑</b></d1>" + var data = {
"<d2 role=\"button\" class=\"rate_hint\" data-rate=\"flag\" data-icon=\"flag\" aria-label=\"flag\"><b>!</b></d2></div>"+ "hint": result.hint,
"<div><d3 class = \"rating\">" + result.rating + "</d3>"+ "rating": result.rating
"<d4 class=\"hint_used\">" + ""+result.hint_used+"</d4></div>" + };
"<div> <d5 role=\"button\" class=\"rate_hint\" data-rate=\"downvote\" aria-label=\"downvote\"><b>↓</b></div> </d5></div>")); $(this).append(Mustache.to_html(template, data));
/**$(this).append(unescape("<div class=\"hint_value\" value = \"" + result.hint + "\">" +
"<div role=\"button\"class=\"rate_hint\"data-rate=\"upvote\" data-icon=\"arrow-u\" aria-label=\"upvote\"><b>↑</b></div>" +
"<div role=\"button\" class=\"rate_hint\" data-rate=\"flag\" data-icon=\"flag\" aria-label=\"flag\"><b>!</b></div>"+
"<div class = \"rating\">" + result.rating + "</div>"+
"<div class=\"hint\">" + ""+result.hint+"</div>" +
"<div role=\"button\" class=\"rate_hint\" data-rate=\"downvote\" aria-label=\"downvote\"><b>↓</b></div> </div>"));**/
} }
}); });
} }
//appendFlagged is only for staff - shows all hints that are flagged function showFlaggedFeedback(result){
function appendFlagged(result){ //For staff use, shows hints that have been flagged by students and allows for the hints' unflagging/removal.
$(".flagged_hints", element).append("<div class=\"hint_value\" value = \"" + result.hint_used + "\">" + $(".flagged_hints", element).append("<div class=\"hint_value\" value = \"" + result.hint + "\">" +
"<div role=\"button\" class=\"staff_rate\" data-rate=\"unflag\" aria-label=\"unflag\"><b>O</b></div>" + "<div role=\"button\" class=\"staff_rate\" data-rate=\"unflag\" aria-label=\"unflag\"><b>O</b></div>" +
"<div class=\"hint_used\">" + ""+result.hint_used+"</div>" + "<hint class=\"hint\">" + ""+result.hint+"</hint>" +
"<div role=\"button\" class=\"staff_rate\" data-rate=\"remove\" aria-label=\"remove\"><b>X</b></div> </div>"); "<div role=\"button\" class=\"staff_rate\" data-rate=\"remove\" aria-label=\"remove\"><b>X</b></div> </div>");
} }
function getFeedback(result){ function setStudentAnswers(student_answers){
if(isStaff){ //Append divs for each answer the student submitted before correctly answering the question.
$('.feedback', element).append("<div class=\"flagged_hints\"><span>Flagged</span></div>"); //showHintFeedback appends new hints into these divs.
for(var i = 0; i < student_answers.length; i++){
$('.feedback', element).append("<div class=\"student_answer\"><span><b>"+student_answers[i]+"</b></span>"+
"<div><input type =\"button\" class=\"student_hint_creation\"value=\"Submit a new hint for this answer.\" </input></div></div>");
} }
$.each(result, function(index, value) { }
//data of student answer and hints are stored in the paragraphs/buttons
//so that when a button is clicked, the answer and hint can be sent to the python script function getFeedback(result){
student_answer = value; //Set up the student feedback stage. Each student answer and all answer-specific hints for that answer are shown
hint_used = index; //to the student, as well as an option to create a new hint for an answer.
//check if <div> for a student answer already exists, if not create the first one if(!isShowingHintFeedback){
if(student_answer != "Flagged"){ if(isStaff){
if($('.student_answer', element).length == 0){ $('.feedback', element).append("<div class=\"flagged_hints\"><span>Flagged</span></div>");
$('.feedback', element).append("<div class=\"student_answer\"><span><b>"+student_answer+"</b></span>"+
"<div><input type =\"button\" class=\"student_hint_creation\" value=\"Submit a new hint for this answer.\" </input></div></div>");
}
else {
//cycle through each .student_answer to check if this answer has been accounted for
answerShown = false;
$(".student_answer", element).each(function(){
if($(this).find("span").text() == student_answer){
answerShown = true;
}
});
if (answerShown == false){
$('.feedback', element).append("<div class=\"student_answer\"><span><b>"+student_answer+"</b></span>"+
"<div><input type =\"button\" class=\"student_hint_creation\"value=\"Submit a new hint for this answer.\" </input></div></div>");
}
} }
} var student_answers = [];
//if an answer doesn't have any hints to display, "There are no hints for"+student_answer is received $.each(result, function(index, value) {
//as the hint. use substring to determine if that is the case. answer = value;
if(hint_used.substring(0, 22) == "There are no hints for"){ if($.inArray(answer, student_answers) === -1 && answer != "Flagged"){
$(".student_answer", element).each(function(){ student_answers.push(answer);
if ($(this).find("span").text() == student_answer){
$(this).append("<div class=\"hint_value\" value=\"There are no answer-specific hints for this answer.\"></div>");
} }
}); });
} setStudentAnswers(student_answers);
//flagged hints have their corresponding answer set to "Flagged" $.each(result, function(index, value) {
else if(student_answer != "Flagged"){ student_answer = value;
$.ajax({ hint = index;
type: "POST", //hints return undefined if no answer-specific hints exist
url: runtime.handlerUrl(element, 'get_ratings'), if(hint == undefined){
data: JSON.stringify({"student_answer": student_answer, "hint_used": hint_used}), $(".student_answer", element).each(function(){
success: appendHint if ($(this).find("span").text() == student_answer){
}); $(this).append("<div class=\"hint_value\" value=\"There are no answer-specific hints for this answer.\"></div>");
} }
else{ });
$.ajax({ }
type: "POST", //flagged hints have their corresponding answer set to "Flagged"
url: runtime.handlerUrl(element, 'get_ratings'), else if(student_answer != "Flagged"){
data: JSON.stringify({"student_answer": student_answer, "hint_used": hint_used}), $.ajax({
success: appendFlagged type: "POST",
url: runtime.handlerUrl(element, 'get_ratings'),
data: JSON.stringify({"student_answer": student_answer, "hint": hint}),
success: showHintFeedback
});
}
else{
$.ajax({
type: "POST",
url: runtime.handlerUrl(element, 'get_ratings'),
data: JSON.stringify({"student_answer": student_answer, "hint": hint}),
success: showFlaggedFeedback
});
}
}); });
isShowingHintFeedback = true;
} }
});
} }
$(document).on('click', '.student_hint_creation', function(){ $(document).on('click', '.student_hint_creation', function(){
//remove all other hint inputs and replace //Click event for the creation of a new hint. This button will bring up the text input.
$('.math').remove(); $('.student_hint_creation').each(function(){
$(this).show();
});
$('.student_text_input').remove();
$('.submit_new').remove(); $('.submit_new').remove();
$(this).hide();
student_answer = $(this).parent().parent().find("span").text(); student_answer = $(this).parent().parent().find("span").text();
$(".student_answer", element).each(function(){ $(".student_answer", element).each(function(){
if ($(this).find("span").text() == student_answer){ if ($(this).find("span").text() == student_answer){
$(this).append("<p><input type=\"text\" name=\"studentinput\" class=\"math\" size=\"40\"><input id=\""+student_answer+"\" type=\"button\" class=\"submit_new\" value=\"Submit Hint\"> </p>"); $(this).append("<p><input type=\"text\" name=\"studentinput\" class=\"student_text_input\" size=\"40\"><input answer=\""+student_answer+"\" type=\"button\" class=\"submit_new\" value=\"Submit Hint\"> </p>");
} }
}); });
}) })
$(document).on('click', '.submit_new', function(){ $(document).on('click', '.submit_new', function(){
if($(this).parent().find('.math').val() != null){ //Click event to submit a new hint for an answer.
var answerdata = unescape($(this).attr('id')); if($(this).parent().find('.student_text_input').val() != null){
var newhint = unescape($('.math').val()); var answerdata = unescape($(this).attr('answer'));
var newhint = unescape($('.student_text_input').val());
Logger.log('submit_new.click.event', {"student_answer": answerdata, "new_hint_submission": newhint}); Logger.log('submit_new.click.event', {"student_answer": answerdata, "new_hint_submission": newhint});
$('.submitbutton').show(); $('.submitbutton').show();
$.ajax({ $.ajax({
...@@ -178,32 +184,34 @@ function CrowdXBlock(runtime, element){ ...@@ -178,32 +184,34 @@ function CrowdXBlock(runtime, element){
$.ajax({ $.ajax({
type: "POST", type: "POST",
url: runtime.handlerUrl(element, 'get_ratings'), url: runtime.handlerUrl(element, 'get_ratings'),
data: JSON.stringify({"student_answer": answerdata, "hint_used": newhint}), data: JSON.stringify({"student_answer": answerdata, "hint": newhint}),
success: appendHint success: showHintFeedback
}); });
} }
}); });
$(this).parent('p').remove(); $(this).parent().find('.student_text_input').remove();
$(this).remove();
} }
}) })
$(document).on('click', '.rate_hint', function(){ $(document).on('click', '.rate_hint', function(){
used_hint = $(this).parent().find(".hint_used").text(); //Click event to change the rating/flag a hint. The attribute 'data-rate' within each .rate_hint button is used
//to determine whether the student is upvoting, downvoting, or flagging the hint.
hint = $(this).parent().find(".hint").text();
student_answer = $(this).parent().parent().find("span").text(); student_answer = $(this).parent().parent().find("span").text();
Logger.log('rate_hint.click.event', {"used_hint": used_hint, "student_answer": student_answer, "rating": $(this).attr('data-rate')}); Logger.log('crowd_hinter.rate_hint.click.event', {"hint": hint, "student_answer": student_answer, "rating": $(this).attr('data-rate')});
$.ajax({ $.ajax({
type: "POST", type: "POST",
url: runtime.handlerUrl(element, 'rate_hint'), url: runtime.handlerUrl(element, 'rate_hint'),
data: JSON.stringify({"student_rating": $(this).attr('data-rate'), "used_hint": used_hint, "student_answer": student_answer}), data: JSON.stringify({"student_rating": $(this).attr('data-rate'), "hint": hint, "student_answer": student_answer}),
success: function (result){ success: function (result){
if(result.rating == "flagged"){ if(result.rating == "flagged"){
console.log("flagged");
$(this).parent().hide(); $(this).parent().hide();
$(this).parent().remove(); $(this).parent().remove();
} }
else if(result.rating != "voted"){ else if(result.rating != "voted"){
$(".hint_used", element).each(function(){ $(".hint", element).each(function(){
if ($(this).parent().find(".hint_used").text() == used_hint && $(this).parent().parent().find("span").text() == student_answer){ if ($(this).parent().find(".hint").text() == hint && $(this).parent().parent().find("span").text() == student_answer){
$(this).parent().find('.rating').text(result.rating); $(this).parent().find('.rating').text(result.rating);
} }
}) })
...@@ -212,17 +220,18 @@ function CrowdXBlock(runtime, element){ ...@@ -212,17 +220,18 @@ function CrowdXBlock(runtime, element){
}); });
}) })
//staff ratings are the removal or unflagging of flagged hints from the database
$(document).on('click', '.staff_rate', function(){ $(document).on('click', '.staff_rate', function(){
used_hint = $(this).parent().find(".hint_used").text(); //Staff ratings are the removal or unflagging of flagged hints from the database. The attribute 'data-rate' is used
//to determine whether to unflag or delete the hint.
hint = $(this).parent().find(".hint").text();
student_answer = $(this).parent().parent().find("span").text(); student_answer = $(this).parent().parent().find("span").text();
$.ajax({ $.ajax({
type: "POST", type: "POST",
url: runtime.handlerUrl(element, 'rate_hint'), url: runtime.handlerUrl(element, 'rate_hint'),
data: JSON.stringify({"student_rating": $(this).attr('data-rate'), "used_hint": used_hint, "student_answer": student_answer}), data: JSON.stringify({"student_rating": $(this).attr('data-rate'), "hint": hint, "student_answer": student_answer}),
success: function (result){ success: function (result){
$('.hint_value', element).each(function(){ $('.hint_value', element).each(function(){
if($(this).attr('value') == used_hint){ if($(this).attr('value') == hint){
$(this).remove(); $(this).remove();
} }
}); });
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment