Skip to content

Commit

Permalink
Bug 5968 - Improvements to the numerical question type. You can now d…
Browse files Browse the repository at this point in the history
…isplay feedback for wrong answers. You can also award partial credit for different levels of accuracy.
  • Loading branch information
tjhunt committed Jul 12, 2006
1 parent 78b9c96 commit 1fe641f
Show file tree
Hide file tree
Showing 4 changed files with 227 additions and 153 deletions.
35 changes: 29 additions & 6 deletions question/format/gift/format.php
Expand Up @@ -393,6 +393,14 @@ function readquestion($lines) {
// Note similarities to ShortAnswer
$answertext = substr($answertext, 1); // remove leading "#"

// If there is feedback for a wrong answer, store it for now.
if (($pos = strpos($answertext, '~')) !== false) {
$wrongfeedback = substr($answertext, $pos);
$answertext = substr($answertext, 0, $pos);
} else {
$wrongfeedback = '';
}

$answers = explode("=", $answertext);
if (isset($answers[0])) {
$answers[0] = trim($answers[0]);
Expand Down Expand Up @@ -454,6 +462,14 @@ function readquestion($lines) {
$question->tolerance[$key] = $tol;
} // end foreach

if ($wrongfeedback) {
$key += 1;
$question->fraction[$key] = 0;
$question->feedback[$key] = $this->commentparser($wrongfeedback);
$question->answer[$key] = '';
$question->tolerance[$key] = '';
}

//$question->defaultgrade = 1;
//$question->image = ""; // No images with this format
//$question->multiplier = array(); // no numeric multipliers with GIFT
Expand Down Expand Up @@ -571,12 +587,19 @@ function writequestion( $question ) {
$expout .= "}\n";
break;
case NUMERICAL:
$answer = array_pop( $question->options->answers );
$tolerance = $answer->tolerance;
$min = $answer->answer - $tolerance;
$max = $answer->answer + $tolerance;
$expout .= "::".$question->name."::".$tfname.$this->repchar( $question->questiontext, $textformat )."{\n";
$expout .= "\t#".$min."..".$max."#".$this->repchar( $answer->feedback )."\n";
$expout .= "::".$question->name."::".$tfname.$this->repchar( $question->questiontext, $textformat )."{#\n";
foreach ($question->options->answers as $answer) {
// DONOTCOMMIT
echo '<pre>';
var_export($answer);
echo '</pre>';

if ($answer->answer != '') {
$expout .= "\t=".$answer->answer.":".(float)$answer->tolerance."#".$this->repchar( $answer->feedback )."\n";
} else {
$expout .= "\t~#".$this->repchar( $answer->feedback )."\n";
}
}
$expout .= "}\n";
break;
case MATCH:
Expand Down
84 changes: 54 additions & 30 deletions question/type/numerical/editquestion.html
Expand Up @@ -2,20 +2,20 @@
<center>
<table cellpadding="5">
<tr valign="top">
<td align="right"><b><?php print_string("category", "quiz") ?>:</b></td>
<td align="right"><b><?php print_string("category", "quiz") ?>:</b></td>
<td align="left">
<?php question_category_select_menu($course->id, true, true, $question->category); ?>
<?php question_category_select_menu($course->id, true, true, $question->category); ?>
</td>
</tr>
<tr valign="top">
<td align="right"><b><?php print_string("questionname", "quiz") ?>:</b></td>
<td align="right"><b><?php print_string("questionname", "quiz") ?>:</b></td>
<td align="left">
<input type="text" name="name" size="50" value="<?php p($question->name) ?>" alt="<?php print_string("questionname", "quiz") ?>" />
<?php if (isset($err["name"])) formerr($err["name"]); ?>
<input type="text" name="name" size="50" value="<?php p($question->name) ?>" alt="<?php print_string("questionname", "quiz") ?>" />
<?php if (isset($err["name"])) formerr($err["name"]); ?>
</td>
</tr>
<tr valign="top">
<td align="right"><b><?php print_string("question", "quiz") ?>:</b>
<td align="right"><b><?php print_string("question", "quiz") ?>:</b>
<br />
<br />
<br />
Expand All @@ -30,7 +30,7 @@
</font>
</td>
<td align="left">
<?php if (isset($err["questiontext"])) {
<?php if (isset($err["questiontext"])) {
formerr($err["questiontext"]);
echo "<br />";
}
Expand All @@ -54,9 +54,10 @@
</td>
</tr>
<tr valign="top">
<td align="right"><b><?php print_string("imagedisplay", "quiz") ?>:</b></td>
<td align="right"><b><?php print_string("imagedisplay", "quiz") ?>:</b></td>
<td align="left">
<?php if (empty($images)) {
<?php
if (empty($images)) {
print_string("noimagesyet");
} else {
choose_from_menu($images, "image", "$question->image", get_string("none"),"","");
Expand All @@ -65,42 +66,65 @@
</td>
</tr>
<tr valign="top">
<td align="right"><b><?php print_string("defaultgrade", "quiz") ?>:</b></td>
<td align="right"><b><?php print_string("defaultgrade", "quiz") ?>:</b></td>
<td align="left">
<input type="text" name="defaultgrade" size="3" value="<?php p($question->defaultgrade) ?>" alt="<?php print_string("defaultgrade", "quiz") ?>" />
<input type="text" name="defaultgrade" size="3" value="<?php p($question->defaultgrade) ?>" alt="<?php print_string("defaultgrade", "quiz") ?>" />

<?php if (isset($err["defaultgrade"])) formerr($err["defaultgrade"]); ?>
<?php if (isset($err["defaultgrade"])) formerr($err["defaultgrade"]); ?>
</td>
</tr>
<tr valign="top">
<td align="right"><b><?php print_string("penaltyfactor", "quiz") ?>:</b></td>
<td align="right"><b><?php print_string("penaltyfactor", "quiz") ?>:</b></td>
<td align="left">
<input type="text" name="penalty" size="3" value="<?php p($question->penalty) ?>" alt="<?php print_string("penaltyfactor", "quiz") ?>" />
<input type="text" name="penalty" size="3" value="<?php p($question->penalty) ?>" alt="<?php print_string("penaltyfactor", "quiz") ?>" />
<?php helpbutton('penalty', get_string('penalty', 'quiz'), 'quiz'); ?>
<?php if (isset($err["penalty"])) formerr($err["penalty"]); ?>
<?php if (isset($err["penalty"])) formerr($err["penalty"]); ?>
</td>
</tr>
<!-- Answers. -->
<?php
for ($i=1; $i<=count($answers); $i++) {
$answer = $answers[$i-1];
?>
<tr valign="top">
<td align="right"><b><?php print_string("correctanswer", "quiz") ?>:</b></td>
<td align="right"><b><?php echo get_string("answer", "quiz")." $i"; ?>:</b></td>
<td align="left">
<input align="left" type="text" id="correct0" name="answer[]" size="10" value="<?php p($answer->answer) ?>" alt="<?php print_string("correctanswer", "quiz") ?>" />
<?php
if ($answer->answer === '' && !isset($answer->tolerance) && !isset($answer->fraction)) {
$answervalue = '';
$answertolerance = '';
$fractionval = 0;
$feedbacktext = '';
} else {
$answervalue = $answer->answer;
$answertolerance = $answer->tolerance;
$fractionval = $answer->fraction;
$feedbacktext = $answer->feedback;
}
?>
<input type="text" name="answer[]" size="25" value="<?php p($answervalue); ?>" />&nbsp;&nbsp;
<?php echo get_string("acceptederror", "quiz"); ?>&nbsp;<input type="text" name="tolerance[]" size="15" value="<?php p($answertolerance) ?>" />&plusmn;&nbsp;&nbsp;
<?php print_string("grade");
echo ":&nbsp;";
choose_from_menu($gradeoptions, "fraction[]", $fractionval,""); ?>
<br />
</td>
</tr>
<tr valign="top">
<td align="right"><b><?php print_string("acceptederror", "quiz"); ?>:</b></td>
<td align="right"><b><?php print_string("feedback", "quiz") ?>:</b></td>
<td align="left">
<input align="left" type="text" id="acceptederror0" name="tolerance[]" size="10" value="<?php p($tolerance); ?>" alt="<?php print_string("acceptederror", "quiz"); ?>" />&plusmn;
<input type="hidden" name="fraction[]" value="1" />
<textarea name="feedback[]" rows="2" cols="50"><?php p($feedbacktext) ?></textarea>
</td>
</tr>
<tr valign="top">
<td align="right"><b><?php print_string("feedback", "quiz") ?>:</b></td>
<td align="left">
<textarea name="feedback[]" rows="2" cols="50"><?php p($answer->feedback); ?></textarea>
</td>
<td colspan="2">&nbsp;</td>
</tr>
<?php
}
?>
<!-- Units. -->
<tr valign="top">
<td align="right"><b><?php print_string("unit", "quiz") ?>:</b></td>
<td align="right"><b><?php print_string("unit", "quiz") ?>:</b></td>
<td align="left"><?php
if (isset($units[0]) && 1.0 === (float)$units[0]->multiplier) {
$unit = $units[0]->unit;
Expand All @@ -111,12 +135,12 @@
?>
<input type="hidden" name="multiplier[]" value="<?php p($multiplier) ?>" />
<input align="left" type="text" id="defaultunit" name="unit[]" size="10" value="<?php p($unit) ?>" alt="<?php print_string("unit", "quiz") ?>" />
<b>(<?php print_string("optional", "quiz") ?>)</b>
<b>(<?php print_string("optional", "quiz") ?>)</b>
</td>
</tr>
<tr valign="top">
<td></td>
<td align="left"><b><?php print_string("alternativeunits", "quiz") ?>:</b></td>
<td align="left"><b><?php print_string("alternativeunits", "quiz") ?>:</b></td>
<td></td>
</tr>
<?php
Expand All @@ -132,11 +156,11 @@
<tr valign="top">
<td></td>
<td align="left">
<b><?php print_string("multiplier", "quiz") ?>:</b>
<input type="text" size="10" name="multiplier[]" value="<?php p($multiplier) ?>"
<b><?php print_string("multiplier", "quiz") ?>:</b>
<input type="text" size="10" name="multiplier[]" value="<?php p($multiplier) ?>"
alt="<?php print_string("multiplier", "quiz") ?>" />
<b>&nbsp;&nbsp;&nbsp;<?php print_string("unit", "quiz") ?>:</b>
<input type="text" name="unit[]" size="5" value="<?php p($unit) ?>" />
<input type="text" name="unit[]" size="5" value="<?php p($unit) ?>" />
</td>
</tr>
<?php
Expand Down
31 changes: 17 additions & 14 deletions question/type/numerical/editquestion.php
Expand Up @@ -2,26 +2,29 @@

// Get all the extra information if we're editing
if (!empty($question->id) && isset($question->qtype) &&
$QTYPES[$question->qtype]->get_question_options($question)) {
$answer = array_values($question->options->answers);
usort($answer, create_function('$a, $b',
'if ($a->fraction == $a->fraction) { return 0; }' .
'else { return $a->fraction < $b->fraction ? -1 : 1; }'));
$answer = $answer[0]; // Get the answer with the highest fraction (i.e. 1)
$QTYPES[$question->qtype]->get_question_options($question)) {

$answers = array_values($question->options->answers);
$units = array_values($question->options->units);
usort($units, create_function('$a, $b', // make sure the default unit is at index 0
'if (1.0 === (float)$a->multiplier) { return -1; } else '.
'if (1.0 === (float)$b->multiplier) { return 1; } else { return 0; }'));
$tolerance = $answer->tolerance;
'if (1.0 === (float)$a->multiplier) { return -1; } else '.
'if (1.0 === (float)$b->multiplier) { return 1; } else { return 0; }'));
} else {
$answer = new stdClass;
$answer->answer = '';
$answer->feedback = '';
$answers = array();
$units = array();
$tolerance = '';
}

// Add blank answers to make the number up to QUESTION_NUMANS
// or one more than current, if there are already lots.
$emptyanswer = new stdClass;
$emptyanswer->answer = '';
$i = count($answers);
$limit = QUESTION_NUMANS;
$limit = $limit <= $i ? $i+1 : $limit;
for (; $i < $limit; $i++) {
$answers[] = $emptyanswer;
}

print_heading_with_help(get_string("editingnumerical", "quiz"), "numerical", "quiz");
require("$CFG->dirroot/question/type/numerical/editquestion.html");

?>

0 comments on commit 1fe641f

Please sign in to comment.