MDL-20636 Fix the numerical qtype editing form.

This commit is contained in:
Tim Hunt 2011-03-28 22:03:18 +01:00
parent 397bd29549
commit 1fa3936440
6 changed files with 330 additions and 442 deletions

View File

@ -27,7 +27,7 @@
<FIELD NAME="instructionsformat" TYPE="int" LENGTH="2" NOTNULL="true" UNSIGNED="false" DEFAULT="0" SEQUENCE="false" PREVIOUS="instructions" NEXT="showunits"/>
<FIELD NAME="showunits" TYPE="int" LENGTH="4" NOTNULL="true" UNSIGNED="true" DEFAULT="0" SEQUENCE="false" COMMENT="display units as multichoice" PREVIOUS="instructionsformat" NEXT="unitsleft"/>
<FIELD NAME="unitsleft" TYPE="int" LENGTH="4" NOTNULL="true" UNSIGNED="false" DEFAULT="0" SEQUENCE="false" COMMENT="display the unit at left as in $1.00" PREVIOUS="showunits" NEXT="unitgradingtype"/>
<FIELD NAME="unitgradingtype" TYPE="int" LENGTH="4" NOTNULL="true" UNSIGNED="true" DEFAULT="0" SEQUENCE="false" COMMENT="0 no penalty, 1 total grade, 2 response grade" PREVIOUS="unitsleft" NEXT="unitpenalty"/>
<FIELD NAME="unitgradingtype" TYPE="int" LENGTH="4" NOTNULL="true" UNSIGNED="true" DEFAULT="0" SEQUENCE="false" COMMENT="0 no penalty, 1 response grade, 2 total grade" PREVIOUS="unitsleft" NEXT="unitpenalty"/>
<FIELD NAME="unitpenalty" TYPE="number" LENGTH="12" NOTNULL="true" UNSIGNED="true" DEFAULT="0.1" SEQUENCE="false" DECIMALS="7" PREVIOUS="unitgradingtype"/>
</FIELDS>
<KEYS>

View File

@ -34,12 +34,22 @@ defined('MOODLE_INTERNAL') || die();
* @copyright 2007 Jamie Pratt me@jamiep.org
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
class question_edit_numerical_form extends question_edit_form {
class qtype_numerical_edit_form extends question_edit_form {
protected function definition_inner($mform) {
$creategrades = get_grade_options();
$this->add_per_answer_fields($mform, get_string('answerno', 'qtype_numerical', '{no}'),
$creategrades->gradeoptions);
$this->add_units_options($mform);
$this->add_units_elements($mform);
$this->add_interactive_settings();
}
protected function get_per_answer_fields($mform, $label, $gradeoptions, &$repeatedoptions, &$answersoption) {
$repeated = parent::get_per_answer_fields($mform, $label, $gradeoptions, $repeatedoptions, $answersoption);
$tolerance =& $mform->createElement('text', 'tolerance', get_string('acceptederror', 'qtype_numerical'));
$tolerance = $mform->createElement('text', 'tolerance', get_string('acceptederror', 'qtype_numerical'));
$repeatedoptions['tolerance']['type'] = PARAM_NUMBER;
array_splice($repeated, 3, 0, array($tolerance));
$repeated[1]->setSize(10);
@ -48,51 +58,176 @@ class question_edit_numerical_form extends question_edit_form {
}
/**
* Add question-type specific form fields.
*
* @param MoodleQuickForm $mform the form being built.
* Add the unit handling options to the form.
* @param object $mform the form being built.
*/
protected function definition_inner($mform) {
protected function add_units_options($mform) {
//------------------------------------------------------------------------------------------
$creategrades = get_grade_options();
$this->add_per_answer_fields($mform, get_string('answerno', 'qtype_numerical', '{no}'),
$creategrades->gradeoptions);
//------------------------------------------------------------------------------------------
question_bank::get_qtype('numerical')->add_units_options($mform, $this);
question_bank::get_qtype('numerical')->add_units_elements($mform, $this);
$mform->addElement('header', 'unithandling', get_string('unithandling', 'qtype_numerical'));
$unitoptions = array(
qtype_numerical::UNITNONE => get_string('onlynumerical', 'qtype_numerical'),
qtype_numerical::UNITDISPLAY => get_string('oneunitshown', 'qtype_numerical'),
qtype_numerical::UNITOPTIONAL => get_string('manynumerical', 'qtype_numerical'),
qtype_numerical::UNITGRADED => get_string('unitgraded', 'qtype_numerical'),
);
$mform->addElement('select', 'unitrole', get_string('unithandling', 'qtype_numerical'), $unitoptions);
$penaltygrp = array();
$penaltygrp[] = $mform->createElement('text', 'unitpenalty', get_string('unitpenalty', 'qtype_numerical') ,
array('size' => 6));
$mform->setType('unitpenalty', PARAM_NUMBER);
$mform->setDefault('unitpenalty', 0.1000000);
$unitgradingtypes = array(
qtype_numerical::UNITGRADEDOUTOFMARK => get_string('decfractionofresponsegrade', 'qtype_numerical'),
qtype_numerical::UNITGRADEDOUTOFMAX => get_string('decfractionofquestiongrade', 'qtype_numerical'),
);
$penaltygrp[] = $mform->createElement('select', 'unitgradingtypes', '' , $unitgradingtypes );
$mform->setDefault('unitgradingtypes', 1);
$mform->addGroup($penaltygrp, 'penaltygrp', get_string('unitpenalty', 'qtype_numerical'),' ' , false);
$mform->addHelpButton('penaltygrp', 'unitpenalty', 'qtype_numerical');
$unitinputoptions = array(
qtype_numerical::UNITINPUT => get_string('editableunittext', 'qtype_numerical'),
qtype_numerical::UNITSELECT => get_string('unitchoice', 'qtype_numerical'),
);
$mform->addElement('select', 'multichoicedisplay', get_string('studentunitanswer', 'qtype_numerical'), $unitinputoptions);
$unitslefts = array(
0 => get_string('rightexample', 'qtype_numerical'),
1 => get_string('leftexample', 'qtype_numerical')
);
$mform->addElement('select', 'unitsleft', get_string('unitposition', 'qtype_numerical') , $unitslefts );
$mform->setDefault('unitsleft', 0);
$mform->addElement('editor', 'instructions', get_string('instructions', 'qtype_numerical'), null, $this->editoroptions);
$mform->setType('instructions', PARAM_RAW);
$mform->addHelpButton('instructions', 'numericalinstructions', 'qtype_numerical');
$mform->disabledIf('penaltygrp', 'unitrole', 'eq', qtype_numerical::UNITNONE);
$mform->disabledIf('penaltygrp', 'unitrole', 'eq', qtype_numerical::UNITDISPLAY);
$mform->disabledIf('penaltygrp', 'unitrole', 'eq', qtype_numerical::UNITOPTIONAL);
$mform->disabledIf('unitsleft', 'unitrole', 'eq', qtype_numerical::UNITNONE);
$mform->disabledIf('multichoicedisplay', 'unitrole', 'eq', qtype_numerical::UNITNONE);
$mform->disabledIf('multichoicedisplay', 'unitrole', 'eq', qtype_numerical::UNITDISPLAY);
$mform->disabledIf('multichoicedisplay', 'unitrole', 'eq', qtype_numerical::UNITOPTIONAL);
}
/**
* Add the input areas for each unit.
* @param object $mform the form being built.
*/
protected function add_units_elements($mform) {
$repeated = array(
$mform->createElement('header', 'unithdr', get_string('unithdr', 'qtype_numerical', '{no}')),
$mform->createElement('text', 'unit', get_string('unit', 'quiz')),
$mform->createElement('text', 'multiplier', get_string('multiplier', 'quiz')),
);
$repeatedoptions['unit']['type'] = PARAM_NOTAGS;
$repeatedoptions['multiplier']['type'] = PARAM_NUMBER;
$repeatedoptions['unit']['disabledif'] = array('unitrole', 'eq', qtype_numerical::UNITNONE);
$repeatedoptions['multiplier']['disabledif'] = array('unitrole', 'eq', qtype_numerical::UNITNONE);
if (isset($this->question->options->units)) {
$countunits = count($this->question->options->units);
} else {
$countunits = 0;
}
if ($this->question->formoptions->repeatelements) {
$repeatsatstart = $countunits + 1;
} else {
$repeatsatstart = $countunits;
}
$this->repeat_elements($repeated, $repeatsatstart, $repeatedoptions,
'nounits', 'addunits', 2, get_string('addmoreunitblanks', 'qtype_calculated', '{no}'));
if ($mform->elementExists('multiplier[0]')) {
$firstunit = $mform->getElement('multiplier[0]');
$firstunit->freeze();
$firstunit->setValue('1.0');
$firstunit->setPersistantFreeze(true);
$mform->addHelpButton('multiplier[0]', 'numericalmultiplier', 'qtype_numerical');
}
}
protected function data_preprocessing($question) {
if (isset($question->options)){
$answers = $question->options->answers;
if (count($answers)) {
$key = 0;
foreach ($answers as $answer){
$draftid = file_get_submitted_draft_itemid('feedback['.$key.']');
$default_values['answer['.$key.']'] = $answer->answer;
$default_values['fraction['.$key.']'] = $answer->fraction;
$default_values['tolerance['.$key.']'] = $answer->tolerance;
$default_values['feedback['.$key.']'] = array();
$default_values['feedback['.$key.']']['format'] = $answer->feedbackformat;
$default_values['feedback['.$key.']']['text'] = file_prepare_draft_area(
$draftid, // draftid
$this->context->id, // context
'question', // component
'answerfeedback', // filarea
!empty($answer->id)?(int)$answer->id:null, // itemid
$this->fileoptions, // options
$answer->feedback // text
);
$default_values['feedback['.$key.']']['itemid'] = $draftid;
$key++;
}
}
question_bank::get_qtype('numerical')->set_numerical_unit_data($this, $question, $default_values);
$question = parent::data_preprocessing($question);
$question = $this->data_preprocessing_answers($question);
$question = $this->data_preprocessing_hints($question);
$question = $this->data_preprocessing_units($question);
$question = $this->data_preprocessing_numerical_options($question);
return $question;
}
$question = (object)((array)$question + $default_values);
protected function data_preprocessing_answers($question) {
$question = parent::data_preprocessing_answers($question);
if (empty($question->options->answers)) {
return $question;
}
$key = 0;
foreach ($question->options->answers as $answer) {
$question->tolerance[$key] = $answer->tolerance;
$key++;
}
return $question;
}
/**
* TODO
*/
function data_preprocessing_units($question) {
if (empty($question->options->units)) {
return $question;
}
foreach ($question->options->units as $key => $unit) {
$question->unit[$key] = $unit->unit;
$question->multiplier[$key] = $unit->multiplier;
}
return $question;
}
/**
* TODO
*/
function data_preprocessing_numerical_options($question) {
if (empty($question->options)) {
return $question;
}
$question->unitpenalty = $question->options->unitpenalty;
$question->unitsleft = $question->options->unitsleft;
if ($question->options->unitgradingtype) {
$question->unitgradingtypes = $question->options->unitgradingtype;
$question->multichoicedisplay = $question->options->showunits;
$question->unitrole = qtype_numerical::UNITGRADED;
} else {
$question->unitrole = $question->options->showunits;
}
// Instructions field.
$draftitemid = file_get_submitted_draft_itemid('instruction');
$question->instructions['text'] = file_prepare_draft_area(
$draftitemid, // draftid
$this->context->id, // context
'qtype_' . $this->qtype(), // component
'instruction', // filarea
!empty($question->id) ? (int) $question->id : null, // itemid
$this->fileoptions, // options
$question->options->instructions // text
);
$question->instructions['itemid'] = $draftitemid ;
$question->instructions['format'] = $question->options->instructionsformat;
return $question;
}
@ -124,7 +259,62 @@ class question_edit_numerical_form extends question_edit_form {
if ($maxgrade == false) {
$errors['fraction[0]'] = get_string('fractionsnomax', 'question');
}
question_bank::get_qtype('numerical')->validate_numerical_options($data, $errors);
$errors = $this->validate_numerical_options($data, $errors);
return $errors;
}
/**
* Validate the unit options.
*/
function validate_numerical_options($data, $errors) {
print_object($data); // DONOTCOMMIT
if ($data['unitrole'] != qtype_numerical::UNITNONE && trim($data['unit'][0]) == '') {
$errors['unit[0]'] = get_string('unitonerequired', 'qtype_numerical');
}
if (empty($data['unit'])) {
return $errors;
}
// Basic unit validation.
foreach ($data['unit'] as $key => $unit) {
if (is_numeric($unit)) {
$errors['unit[' . $key . ']'] =
get_string('mustnotbenumeric', 'qtype_calculated');
}
$trimmedunit = trim($unit);
if (empty($trimmedunit)) {
continue;
}
$trimmedmultiplier = trim($data['multiplier'][$key]);
if (empty($trimmedmultiplier)) {
$errors['multiplier[' . $key . ']'] =
get_string('youmustenteramultiplierhere', 'qtype_calculated');
} else if (!is_numeric($trimmedmultiplier)) {
$errors['multiplier[' . $key . ']'] =
get_string('mustbenumeric', 'qtype_calculated');
}
}
// Check for repeated units.
$alreadyseenunits = array();
foreach ($data['unit'] as $key => $unit) {
$trimmedunit = trim($unit);
if ($trimmedunit == '') {
continue;
}
if (in_array($trimmedunit, $alreadyseenunits)) {
$errors['unit[' . $key . ']'] =
get_string('errorrepeatedunit', 'qtype_numerical');
} else {
$alreadyseenunits[] = $trimmedunit;
}
}
return $errors;
}

View File

@ -30,10 +30,10 @@ $string['addmoreanswerblanks'] = 'Blanks for {no} More Answers';
$string['addmoreunitblanks'] = 'Blanks for {no} More Units';
$string['answermustbenumberorstar'] = 'The answer must be a number, or \'*\'.';
$string['answerno'] = 'Answer {$a}';
$string['decfractionofquestiongrade'] = 'as decimal fraction (0-1) of question grade';
$string['decfractionofresponsegrade'] = 'as decimal fraction (0-1) of response grade';
$string['decfractionofquestiongrade'] = 'as a fraction (0-1) of the question grade';
$string['decfractionofresponsegrade'] = 'as a fraction (0-1) of the response grade';
$string['decimalformat'] = 'decimals';
$string['editableunittext'] = 'Text input element';
$string['editableunittext'] = 'a text input element';
$string['editingnumerical'] = 'Editing a Numerical question';
$string['errornomultiplier'] = 'You must specify a multiplier for this unit.';
$string['errorrepeatedunit'] = 'You cannot have two units with the same name.';
@ -41,7 +41,7 @@ $string['geometric'] = 'Geometric';
$string['instructions'] = 'Instructions ';
$string['invalidnumericanswer'] = 'One of the answers you entered was not a valid number.';
$string['invalidnumerictolerance'] = 'One of the tolerances you entered was not a valid number.';
$string['leftexample'] = 'LEFT as $1.00';
$string['leftexample'] = 'on the left, for example $1.00 or £1.00';
$string['multiplier'] = 'Multiplier';
$string['noneditableunittext'] = 'NON editable text of Unit No1';
$string['nonvalidcharactersinnumber'] = 'NON valid characters in number';
@ -52,10 +52,7 @@ $string['numerical_help'] = 'From the student perspective, a numerical question
$string['numerical_link'] = 'question/type/numerical';
$string['numericalsummary'] = 'Allows a numerical response, possibly with units, that is graded by comparing against various model answers, possibly with tolerances.';
$string['numericalinstructions'] = 'Instructions';
$string['numericalinstructions_help'] = 'Specific instructions related to the question as
* Examples of number formats
* Complex units';
$string['numericalinstructions_help'] = 'Enter any instructions you would like to give the student about how to complete their response.';
$string['numericalmultiplier'] = 'Multiplier';
$string['numericalmultiplier_help'] = 'The multiplier is the factor by which the correct numerical response will be multiplied.
@ -64,24 +61,21 @@ The first unit (Unit 1) has a default multiplier of 1. Thus if the correct numer
If you add the unit kW with a multiplier of 0.001, this will add a correct response of 5.5 kW. This means that the answers 5500W or 5.5kW would be marked correct.
Note that the accepted error is also multiplied, so an allowed error of 100W would become an error of 0.1kW.';
$string['manynumerical'] = 'Only the NUMERICAL ANSWER will be graded using optional units ';
$string['manynumerical'] = 'Units are optional. If a unit is entered, it is used to convert the reponse to Unit 1 before grading.';
$string['nominal'] = 'Nominal';
$string['onlynumerical'] = 'Only the NUMERICAL ANSWER will be graded, no units allowed';
$string['oneunitshown'] = 'Only the NUMERICAL ANSWER will be graded, Unit1 will be shown';
$string['onlynumerical'] = 'Units are not used at all. Only the numerical value is graded.';
$string['oneunitshown'] = 'Unit 1 is automatically displayed beside the answer box.';
$string['pleaseenterananswer'] = 'Please enter an answer.';
$string['relative'] = 'Relative';
$string['rightexample'] = 'RIGHT as 1.00cm';
$string['rightexample'] = 'on the right, for example 1.00cm or 1.00km';
$string['selectunits'] = 'Select units';
$string['selectunit'] = 'Select one unit';
$string['studentunitanswer'] = 'UNIT ANSWER displayed as a ';
$string['studentunitanswer'] = 'Units are input using';
$string['tolerancetype'] = 'Tolerance type';
$string['unit'] = 'Unit';
$string['unitchoice'] = 'Multichoice (radio elements)';
$string['unitdisplay'] = '<STRONG>Unit 1 displayed </STRONG>';
$string['unitchoice'] = 'a multiple choice selection';
$string['unitedit'] = 'Edit unit';
$string['unitgraded'] = ' NUMERICAL ANSWER and UNIT ANSWER will be graded ';
$string['unitgraded1'] = '<STRONG>UNIT GRADED</STRONG>';
$string['unitsused'] = '<STRONG>UNIT USED</STRONG>';
$string['unitgraded'] = 'The unit must be given, and will be graded.';
$string['unithdr'] = 'Unit {$a}';
$string['unitmandatory'] = 'Mandatory';
$string['unitmandatory_help'] = '
@ -91,32 +85,24 @@ $string['unitmandatory_help'] = '
* The unit penalty will be applied if the unit field is empty
';
$string['unitnotgraded'] = '<STRONG>UNIT NOT GRADED</STRONG>';
$string['unitnotused'] = '<STRONG>UNIT NOT USED</STRONG>';
$string['unitonerequired'] = 'You must enter at least one unit';
$string['unitoptional'] = 'Optional unit';
$string['unitoptional_help'] = '
* If the unit field is not empty, the response will be graded using this unit.
* If the unit is badly written or unknown, the response will be considered as non valid.
';
$string['unitused'] = '<STRONG>UNIT USED</STRONG>';
$string['unituses'] = 'Unit uses';
$string['unituses_help'] = 'The unit(s) are uses as in pre 2,0 Moodle version
* The student can answer using units predefined by the teacher
* in which case the constant will be applied to the student value.
* If the student does not add any unit, his numerical answer is used as is.';
$string['unitnotvalid'] = ' Unit not valid with this numerical value';
$string['unitunknown'] = ' Undefined unit ';
$string['unitpenalty'] = 'Unit penalty';
$string['unitpenalty_help'] = 'The penalty is applied if
* An undefined unit name is put in the Unit answer element or
* An unit name is put in the Number answer element ';
* the wrong unit name is entered into the unit input, or
* a unit is entered into the value input box';
$string['unitappliedpenalty'] = 'These marks include a penalty of {$a} for bad unit.';
$string['unitposition'] = 'Unit position';
$string['unitposition'] = 'Units are displayed';
$string['unitnotselected'] = 'No unit selected';
$string['unitshandling'] = 'Units handling';
$string['unithandling'] = 'Unit handling';
$string['validnumberformats'] = 'Valid number formats';
$string['validnumberformats_help'] = '
* regular numbers 13500.67 : 13 500.67 : 13500,67: 13 500,67

View File

@ -31,20 +31,6 @@ defined('MOODLE_INTERNAL') || die();
require_once($CFG->dirroot . '/question/type/numerical/question.php');
if ( ! defined ("NUMERICALQUESTIONUNITTEXTINPUTDISPLAY")) {
define("NUMERICALQUESTIONUNITTEXTINPUTDISPLAY", 0);
}
if ( ! defined ("NUMERICALQUESTIONUNITMULTICHOICEDISPLAY")) {
define("NUMERICALQUESTIONUNITMULTICHOICEDISPLAY", 1);
}
if ( ! defined ("NUMERICALQUESTIONUNITTEXTDISPLAY")) {
define("NUMERICALQUESTIONUNITTEXTDISPLAY", 2);
}
if ( ! defined ("NUMERICALQUESTIONUNITNODISPLAY")) {
define("NUMERICALQUESTIONUNITNODISPLAY", 3);
}
/**
* The numerical question type class.
*
@ -55,6 +41,17 @@ if ( ! defined ("NUMERICALQUESTIONUNITNODISPLAY")) {
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
class qtype_numerical extends question_type {
const UNITINPUT = 0;
const UNITSELECT = 1;
const UNITNONE = 3;
const UNITDISPLAY = 2;
const UNITGRADED = 1;
const UNITOPTIONAL = 0;
const UNITGRADEDOUTOFMARK = 1;
const UNITGRADEDOUTOFMAX = 2;
public function has_wildcards_in_responses() {
return true;
}
@ -149,7 +146,7 @@ class qtype_numerical extends question_type {
$question->options->showunits = $options->showunits;
$question->options->unitsleft = $options->unitsleft;
$question->options->instructions = $options->instructions;
$question->options->instructionsformat = $options->instructionsformat;
$question->options->instructionsformat = $options->instructionsformat;
}
return true;
@ -244,6 +241,8 @@ class qtype_numerical extends question_type {
return $result;
}
$this->save_hints($question);
return true;
}
@ -269,49 +268,35 @@ class qtype_numerical extends question_type {
$options->id = $DB->insert_record('question_numerical_options', $options);
}
if (isset($question->options->unitgradingtype)) {
$options->unitgradingtype = $question->options->unitgradingtype;
} else {
$options->unitgradingtype = 0 ;
}
if (isset($question->unitpenalty)){
if (isset($question->unitpenalty)) {
$options->unitpenalty = $question->unitpenalty;
} else { //so this is either an old question or a close question type
} else {
// Either an old question or a close question type.
$options->unitpenalty = 1 ;
}
// if we came from the form then 'unitrole' exists
if (isset($question->unitrole)){
switch ($question->unitrole){
case '0' : $options->showunits = NUMERICALQUESTIONUNITNODISPLAY ;
break ;
case '1' : $options->showunits = NUMERICALQUESTIONUNITTEXTDISPLAY ;
break ;
case '2' : $options->showunits = NUMERICALQUESTIONUNITTEXTINPUTDISPLAY ;
$options->unitgradingtype = 0 ;
break ;
case '3' : $options->showunits = $question->multichoicedisplay ;
$options->unitgradingtype = $question->unitgradingtypes ;
break ;
$options->unitgradingtype = 0;
if (isset($question->unitrole)) {
// Saving the editing form.
$options->showunits = $question->unitrole;
if ($question->unitrole == self::UNITGRADED) {
$options->unitgradingtype = $question->unitgradingtypes;
}
} else if (isset($question->showunits)) {
// Updated import, e.g. Moodle XML.
$options->showunits = $question->showunits;
} else {
if (isset($question->showunits)){
$options->showunits = $question->showunits;
// Legacy import.
if ($defaultunit = $this->get_default_numerical_unit($question)) {
$options->showunits = self::UNITINPUT;
} else {
if ($defaultunit = $this->get_default_numerical_unit($question)) {
// so units can be used
$options->showunits = NUMERICALQUESTIONUNITTEXTINPUTDISPLAY ;
} else {
// only numerical will be graded
$options->showunits = NUMERICALQUESTIONUNITNODISPLAY ;
}
$options->showunits = self::UNITNONE;
}
}
if (isset($question->unitsleft)) {
$options->unitsleft = $question->unitsleft;
} else {
$options->unitsleft = 0 ;
}
$options->unitsleft = !empty($question->unitsleft);
$options->instructions = $this->import_or_save_files($question->instructions,
$question->context, 'qtype_'.$question->qtype , 'instruction', $question->id);
@ -319,8 +304,6 @@ class qtype_numerical extends question_type {
$DB->update_record('question_numerical_options', $options);
$this->save_hints($question);
// Report any problems.
if (!empty($result->notice)) {
return $result;
@ -362,10 +345,10 @@ class qtype_numerical extends question_type {
return $result;
}
function find_unit_index(&$question,$value){
function find_unit_index($question, $value) {
$length = 0;
$goodkey = 0 ;
foreach ($question->options->units as $key => $unit){
foreach ($question->options->units as $key => $unit) {
if($unit->unit ==$value ) {
return $key ;
}
@ -424,8 +407,8 @@ class qtype_numerical extends question_type {
$formatoptions->noclean = true;
$formatoptions->para = false;
$nameprefix = $question->name_prefix;
$component = 'qtype_' . $question->qtype;
// rewrite instructions text
$component = 'qtype_' . $question->qtype;
// rewrite instructions text
$question->options->instructions = quiz_rewrite_question_urls($question->options->instructions, 'pluginfile.php', $context->id, $component, 'instruction', array($state->attempt, $state->question), $question->id);
/// Print question text and media
@ -445,7 +428,7 @@ class qtype_numerical extends question_type {
$nameanswer = "name=\"".$question->name_prefix."answer\"";
$nameunit = "name=\"".$question->name_prefix."unit\"";
// put old answer data in $state->responses['answer'] and $state->responses['unit']
if (isset($state->responses['']) && $state->responses[''] != '' && !isset($state->responses['answer'])){
if (isset($state->responses['']) && $state->responses[''] != '' && !isset($state->responses['answer'])) {
$this->split_old_answer($state->responses[''], $question->options->units, $state->responses['answer'] ,$state->responses['unit'] );
}
// prepare the values of the input elements to be dispalyed answer i.e. number and unit
@ -458,7 +441,7 @@ class qtype_numerical extends question_type {
$valueunit = ' value="'.s($state->responses['unit']).'" ';
} else {
$valueunit = ' value="" ';
if ($question->options->showunits == NUMERICALQUESTIONUNITTEXTDISPLAY ){
if ($question->options->showunits == NUMERICALQUESTIONUNITTEXTDISPLAY ) {
$valueunit = ' value="'.s($question->options->units[0]->unit).'" ';
}
}
@ -491,13 +474,13 @@ class qtype_numerical extends question_type {
foreach($question->options->answers as $answer) {
if ($this->test_response($question, $state, $answer)) {
// Answer was correct or partially correct.
if ( $answer->answer === '*'){
if ( $answer->answer === '*') {
$answerasterisk = true ;
}
// in all cases
$class = question_get_feedback_class($answer->fraction);
$feedbackimg = question_get_feedback_image($answer->fraction);
if ($question->options->unitgradingtype == 0 || ($question->options->unitgradingtype == 0 && $answer->answer === '*')){
if ($question->options->unitgradingtype == 0 || ($question->options->unitgradingtype == 0 && $answer->answer === '*')) {
// if * then unit has the $answer->fraction value
// if $question->options->unitgradingtype == 0 everything has been checked
// if $question->options->showunits == NUMERICALQUESTIONUNITTEXTINPUTDISPLAY
@ -533,12 +516,12 @@ class qtype_numerical extends question_type {
$feedbackimgunit = question_get_feedback_image($answer->fraction);
$valid_numerical_unit = true ;//everything is true with *
} else {
// if( isset($state->responses['unit']) && $state->responses['unit'] != '' ){// unit should be written in the unit input or checked in multichoice
// if( isset($state->responses['unit']) && $state->responses['unit'] != '' ) {// unit should be written in the unit input or checked in multichoice
// we need to see if something was written in the answer field that was not in the number
// although we cannot actually detect units put before the number which will cause bad numerical.
// use extract response
$response = $this->extract_numerical_response($state->responses['answer']);
if(isset($response->unit ) && $response->unit != ''){
if(isset($response->unit ) && $response->unit != '') {
$unit_in_numerical_answer = true ;
}else {
$unit_in_numerical_answer = false ;
@ -547,7 +530,7 @@ class qtype_numerical extends question_type {
// the we let the testing to the two cases either
// NUMERICALQUESTIONUNITTEXTINPUTDISPLAY or
// NUMERICALQUESTIONUNITMULTICHOICEDISPLAY
if( !isset($state->responses['unit']) || $state->responses['unit'] == '' ){
if( !isset($state->responses['unit']) || $state->responses['unit'] == '' ) {
// unit should be written in the unit input or checked in multichoice
$valid_numerical_unit = false ;
$classunit = question_get_feedback_class(0);
@ -560,7 +543,7 @@ class qtype_numerical extends question_type {
$valid_numerical_unit = false ;
foreach ($question->options->units as $key => $unit) {
if ($unit->unit == $state->responses['unit']){
if ($unit->unit == $state->responses['unit']) {
// $response = $this->apply_unit($state->responses['answer'].$unit->unit, array($question->options->units[$key])) ;
// echo "<p> avant false valid_numerical_unit_index $valid_numerical_unit_index ".$state->responses['answer']."</p>";
$invalid_unit_found = 0 ;
@ -568,7 +551,7 @@ class qtype_numerical extends question_type {
//echo "<p> avanr get valid_numerical_unit_index $valid_numerical_unit_index </p>";
// $this->get_tolerance_interval($answer);
$testresponse = $response->number /$unit->multiplier ;
if($answer->min <= $testresponse && $testresponse <= $answer->max){
if($answer->min <= $testresponse && $testresponse <= $answer->max) {
//echo "<p> apres min max valid_numerical_unit_index $valid_numerical_unit_index </p>";
$classunit = question_get_feedback_class($answer->fraction) ; //question_get_feedback_class(1);
$feedbackimgunit = question_get_feedback_image($rawgrade);
@ -598,8 +581,8 @@ class qtype_numerical extends question_type {
$classunitvalue = 1 ;
}
if(! $answerasterisk && $question->options->unitgradingtype != 0 && (! $valid_numerical_unit || $unit_in_numerical_answer)){
if($question->options->unitgradingtype == 1){
if(! $answerasterisk && $question->options->unitgradingtype != 0 && (! $valid_numerical_unit || $unit_in_numerical_answer)) {
if($question->options->unitgradingtype == 1) {
$raw_unitpenalty = $question->options->unitpenalty * $rawgrade ;
}else {
$raw_unitpenalty = $question->options->unitpenalty ;
@ -612,25 +595,25 @@ class qtype_numerical extends question_type {
}
function compare_responses(&$question, $state, $teststate) {
function compare_responses($question, $state, $teststate) {
if ($question->options->showunits == NUMERICALQUESTIONUNITMULTICHOICEDISPLAY && isset($question->options->units) && isset($state->responses['unit']) && isset($question->options->units[$state->responses['unit']] )){
if ($question->options->showunits == NUMERICALQUESTIONUNITMULTICHOICEDISPLAY && isset($question->options->units) && isset($state->responses['unit']) && isset($question->options->units[$state->responses['unit']] )) {
$state->responses['unit']=$question->options->units[$state->responses['unit']]->unit;
};
$responses = '';
$testresponses = '';
if (isset($state->responses['answer'])){
if (isset($state->responses['answer'])) {
$responses = $state->responses['answer'];
}
if (isset($state->responses['unit'])){
if (isset($state->responses['unit'])) {
$responses .= $state->responses['unit'];
}
if (isset($teststate->responses['answer'])){
if (isset($teststate->responses['answer'])) {
$testresponses = $teststate->responses['answer'];
}
if (isset($teststate->responses['unit'])){
if (isset($teststate->responses['unit'])) {
$testresponses .= $teststate->responses['unit'];
}
@ -655,19 +638,19 @@ class qtype_numerical extends question_type {
}
// using old grading process if $question->unitgradingtype == 0
// and adding unit1 for the new option NUMERICALQUESTIONUNITTEXTDISPLAY
if ($question->options->unitgradingtype == 0 ){
if ($question->options->unitgradingtype == 0 ) {
// values coming form old question stored in attempts
if (!isset($state->responses['answer']) && isset($state->responses[''])){
if (!isset($state->responses['answer']) && isset($state->responses[''])) {
$state->responses['answer'] = $state->responses[''];
}
$answertotest = $state->responses['answer'];
// values coming from NUMERICALQUESTIONUNITTEXTINPUTDISPLAY
// or NUMERICALQUESTIONUNITTEXTDISPLAY as unit hidden HTML element
if($question->options->showunits == NUMERICALQUESTIONUNITTEXTINPUTDISPLAY ){
if($question->options->showunits == NUMERICALQUESTIONUNITTEXTINPUTDISPLAY ) {
$testresponse = $this->extract_numerical_response($state->responses['answer']);
if($testresponse->unit != '' || $testresponse->number === false){
if($testresponse->unit != '' || $testresponse->number === false) {
return false;
}
$answertotest = $testresponse->number ;
@ -675,7 +658,7 @@ class qtype_numerical extends question_type {
if(isset($state->responses['unit'])) {
$answertotest .= $state->responses['unit'] ;
}
// if ($question->options->showunits == NUMERICALQUESTIONUNITTEXTDISPLAY && isset($question->options->units[0])){
// if ($question->options->showunits == NUMERICALQUESTIONUNITTEXTDISPLAY && isset($question->options->units[0])) {
// $answertotest .= $question->options->units[0]->unit ;
// }
// test OK if only numerical or numerical with known unit names with the unit mltiplier applied
@ -717,12 +700,12 @@ class qtype_numerical extends question_type {
// The student did type a number, so check it with tolerances.
$this->get_tolerance_interval($answer);
if ($answer->min <= $response->number && $response->number <= $answer->max){
if ($answer->min <= $response->number && $response->number <= $answer->max) {
return true;
}
// testing for other units
if ( isset($question->options->units) && count($question->options->units) > 0) {
foreach($question->options->units as $key =>$unit){
foreach($question->options->units as $key =>$unit) {
$testresponse = $response->number /$unit->multiplier ;
if($answer->min <= $testresponse && $testresponse<= $answer->max) {
return true;
@ -758,7 +741,7 @@ class qtype_numerical extends question_type {
* @param object $cmoptions
*/
function grade_responses(&$question, &$state, $cmoptions) {
if ( isset($state->responses['']) && $state->responses[''] != '' && !isset($state->responses['answer'])){
if ( isset($state->responses['']) && $state->responses[''] != '' && !isset($state->responses['answer'])) {
$this->split_old_answer($state->responses[''], $question->options->units, $state->responses['answer'] ,$state->responses['unit'] );
}
@ -774,7 +757,7 @@ class qtype_numerical extends question_type {
if ($this->test_response($question, $state, $answer)) {
// Answer was correct or partially correct.
$state->raw_grade = $answer->fraction ;
if ($question->options->unitgradingtype == 0 || $answer->answer === '*'){
if ($question->options->unitgradingtype == 0 || $answer->answer === '*') {
// if * then unit has the $answer->fraction value
// if $question->options->unitgradingtype == 0 everything has been checked
// if $question->options->showunits == NUMERICALQUESTIONUNITTEXTINPUTDISPLAY
@ -787,14 +770,14 @@ class qtype_numerical extends question_type {
$valid_numerical_unit = false ;
$class = question_get_feedback_class($answer->fraction);
$feedbackimg = question_get_feedback_image($answer->fraction);
if(isset($state->responses['unit']) && $state->responses['unit'] != '' ){
if(isset($state->responses['unit']) && $state->responses['unit'] != '' ) {
foreach ($question->options->units as $key => $unit) {
if ($unit->unit == $state->responses['unit']){
if ($unit->unit == $state->responses['unit']) {
$response = $this->apply_unit($state->responses['answer'].$state->responses['unit'], array($question->options->units[$key])) ;
if ($response !== false) {
$this->get_tolerance_interval($answer);
if($answer->min <= $response && $response <= $answer->max){
if($answer->min <= $response && $response <= $answer->max) {
$valid_numerical_unit = true ;
}
}
@ -808,8 +791,8 @@ class qtype_numerical extends question_type {
}
// apply unit penalty
$raw_unitpenalty = 0 ;
if($question->options->unitgradingtype != 0 && !empty($question->options->unitpenalty)&& $valid_numerical_unit != true ){
if($question->options->unitgradingtype == 1){
if($question->options->unitgradingtype != 0 && !empty($question->options->unitpenalty)&& $valid_numerical_unit != true ) {
if($question->options->unitgradingtype == 1) {
$raw_unitpenalty = $question->options->unitpenalty * $state->raw_grade ;
}else {
$raw_unitpenalty = $question->options->unitpenalty ;
@ -903,9 +886,9 @@ class qtype_numerical extends question_type {
case '2': case 'nominal':
$tolerance = abs($tolerance); // important - otherwise min and max are swapped
// $answer->tolerance 0 or something else
if ((float)$answer->tolerance == 0.0 && abs((float)$answer->answer) <= $tolerance ){
if ((float)$answer->tolerance == 0.0 && abs((float)$answer->answer) <= $tolerance ) {
$tolerance = (float) ("1.0e-".ini_get('precision')) * abs((float)$answer->answer) ; //tiny fraction
} else if ((float)$answer->tolerance != 0.0 && abs((float)$answer->tolerance) < abs((float)$answer->answer) && abs((float)$answer->answer) <= $tolerance){
} else if ((float)$answer->tolerance != 0.0 && abs((float)$answer->tolerance) < abs((float)$answer->answer) && abs((float)$answer->answer) <= $tolerance) {
$tolerance = (1+("1.0e-".ini_get('precision')) )* abs((float) $answer->tolerance) ;//tiny fraction
}
@ -1015,279 +998,6 @@ class qtype_numerical extends question_type {
return false;
}
/**
* function used in function definition_inner()
* of edit_..._form.php for
* numerical, calculated, calculatedsimple
*/
protected function add_units_options(&$mform, &$that){
// Units are graded
$mform->addElement('header', 'unithandling', get_string('unitshandling', 'qtype_numerical'));
$mform->addElement('radio', 'unitrole', get_string('unitnotused', 'qtype_numerical'), get_string('onlynumerical', 'qtype_numerical'),0);
$mform->addElement('radio', 'unitrole', get_string('unitdisplay', 'qtype_numerical'), get_string('oneunitshown', 'qtype_numerical'),1);
$mform->addElement('radio', 'unitrole', get_string('unitsused', 'qtype_numerical'), get_string('manynumerical', 'qtype_numerical'),2);
$mform->addElement('static', 'separator2', '', '<HR/>');
$mform->addElement('radio', 'unitrole', get_string('unitgraded1', 'qtype_numerical'), get_string('unitgraded', 'qtype_numerical'),3);
$penaltygrp = array();
$penaltygrp[] =& $mform->createElement('text', 'unitpenalty', get_string('unitpenalty', 'qtype_numerical') ,
array('size' => 6));
$unitgradingtypes = array('1' => get_string('decfractionofresponsegrade', 'qtype_numerical'), '2' => get_string('decfractionofquestiongrade', 'qtype_numerical'));
$penaltygrp[] =& $mform->createElement('select', 'unitgradingtypes', '' , $unitgradingtypes );
$mform->addGroup($penaltygrp, 'penaltygrp', get_string('unitpenalty', 'qtype_numerical'),' ' , false);
$multichoicedisplaygrp = array();
$multichoicedisplaygrp[] =& $mform->createElement('radio', 'multichoicedisplay', get_string('unitedit', 'qtype_numerical'), get_string('editableunittext', 'qtype_numerical'),0);
$multichoicedisplaygrp[] =& $mform->createElement('radio', 'multichoicedisplay', get_string('selectunits', 'qtype_numerical') , get_string('unitchoice', 'qtype_numerical'),1);
$mform->addGroup($multichoicedisplaygrp, 'multichoicedisplaygrp', get_string('studentunitanswer', 'qtype_numerical'),' OR ' , false);
$unitslefts = array('0' => get_string('rightexample', 'qtype_numerical'),'1' => get_string('leftexample', 'qtype_numerical'));
$mform->addElement('select', 'unitsleft', get_string('unitposition', 'qtype_numerical') , $unitslefts );
$mform->addElement('static', 'separator2', '<HR/>', '<HR/>');
$mform->addElement('editor', 'instructions', get_string('instructions', 'qtype_numerical'), null, $that->editoroptions);
$showunits1grp = array();
$mform->addElement('static', 'separator2', '<HR/>', '<HR/>');
$mform->setType('unitpenalty', PARAM_NUMBER);
$mform->setDefault('unitpenalty', 0.1);
$mform->setDefault('unitgradingtypes', 1);
$mform->addHelpButton('penaltygrp', 'unitpenalty', 'qtype_numerical');
$mform->setDefault('unitsleft', 0);
$mform->setType('instructions', PARAM_RAW);
$mform->addHelpButton('instructions', 'numericalinstructions', 'qtype_numerical');
$mform->disabledIf('penaltygrp', 'unitrole','eq','0');
$mform->disabledIf('penaltygrp', 'unitrole','eq','1');
$mform->disabledIf('penaltygrp', 'unitrole','eq','2');
$mform->disabledIf('unitsleft', 'unitrole','eq','0');
$mform->disabledIf('multichoicedisplay','unitrole','eq','0');
$mform->disabledIf('multichoicedisplay','unitrole','eq','1');
$mform->disabledIf('multichoicedisplay','unitrole','eq','2');
}
/**
* function used in in function definition_inner()
* of edit_..._form.php for
* numerical, calculated, calculatedsimple
*/
protected function add_units_elements(& $mform,& $that) {
$repeated = array();
$repeated[] =& $mform->createElement('header', 'unithdr', get_string('unithdr', 'qtype_numerical', '{no}'));
$repeated[] =& $mform->createElement('text', 'unit', get_string('unit', 'quiz'));
$mform->setType('unit', PARAM_NOTAGS);
$repeated[] =& $mform->createElement('text', 'multiplier', get_string('multiplier', 'quiz'));
$mform->setType('multiplier', PARAM_NUMBER);
if (isset($that->question->options->units)){
$countunits = count($that->question->options->units);
} else {
$countunits = 0;
}
if ($that->question->formoptions->repeatelements){
$repeatsatstart = $countunits + 1;
} else {
$repeatsatstart = $countunits;
}
$that->repeat_elements($repeated, $repeatsatstart, array(), 'nounits', 'addunits', 2, get_string('addmoreunitblanks', 'qtype_calculated', '{no}'));
if ($mform->elementExists('multiplier[0]')){
$firstunit =& $mform->getElement('multiplier[0]');
$firstunit->freeze();
$firstunit->setValue('1.0');
$firstunit->setPersistantFreeze(true);
$mform->addHelpButton('multiplier[0]', 'numericalmultiplier', 'qtype_numerical');
}
}
/**
* function used in in function data_preprocessing() of edit_numerical_form.php for
* numerical, calculated, calculatedsimple
*/
function set_numerical_unit_data($mform, &$question, &$default_values){
list($categoryid) = explode(',', $question->category);
$context = $this->get_context_by_category_id($categoryid);
if (isset($question->options)){
if (isset($question->options->unitpenalty)){
$default_values['unitpenalty'] = $question->options->unitpenalty ;
}
$default_values['unitgradingtypes'] = 1 ;
if (isset($question->options->unitgradingtype )&& isset($question->options->showunits ) ){
if ( $question->options->unitgradingtype == 2 ) {
$default_values['unitgradingtypes'] = 1 ;
}
if ( $question->options->unitgradingtype == 0 ) {
$default_values['unitgradingtypes'] = 0 ;
}
switch ($question->options->showunits){
case 0 :// NUMERICALQUESTIONUNITTEXTINPUTDISPLAY
if($question->options->unitgradingtype == 0 ){
$default_values['unitrole'] = 2 ;
$default_values['multichoicedisplay'] = 0 ;
}else { // 1 or 2
$default_values['unitrole'] = 3 ;
$default_values['multichoicedisplay'] = 0 ;
$default_values['unitgradingtypes'] = $question->options->unitgradingtype ;
}
break;
case 1 : // NUMERICALQUESTIONUNITMULTICHOICEDISPLAY
$default_values['unitrole'] = 3 ;
$default_values['multichoicedisplay'] = $question->options->unitgradingtype ;
$default_values['unitgradingtypes'] = $question->options->unitgradingtype ;
break;
case 2 : // NUMERICALQUESTIONUNITTEXTDISPLAY
$default_values['unitrole'] = 1 ;
break;
case 3 : // NUMERICALQUESTIONUNITNODISPLAY
$default_values['unitrole'] = 0 ;
// $default_values['showunits1'] = $question->options->showunits ;
break;
}
}
if (isset($question->options->unitsleft)){
$default_values['unitsleft'] = $question->options->unitsleft ;
}
// processing files
$component = 'qtype_' . $question->qtype;
$draftid = file_get_submitted_draft_itemid('instruction');
$default_values['instructions'] = array();
if (isset($question->options->instructionsformat) && isset($question->options->instructions)){
$default_values['instructions']['format'] = $question->options->instructionsformat;
$default_values['instructions']['text'] = file_prepare_draft_area(
$draftid, // draftid
$context->id, // context
$component, // component
'instruction', // filarea
!empty($question->id)?(int)$question->id:null, // itemid
$mform->fileoptions, // options
$question->options->instructions // text
);
}
$default_values['instructions']['itemid'] = $draftid ;
if (isset($question->options->units)) {
$units = array_values($question->options->units);
if (!empty($units)) {
foreach ($units as $key => $unit){
$default_values['unit['.$key.']'] = $unit->unit;
$default_values['multiplier['.$key.']'] = $unit->multiplier;
}
}
}
}
}
/**
* function use in in function validation()
* of edit_..._form.php for
* numerical, calculated, calculatedsimple
*/
function validate_numerical_options(& $data, & $errors){
$units = $data['unit'];
switch ($data['unitrole']){
case '0' : $showunits = NUMERICALQUESTIONUNITNODISPLAY ;
break ;
case '1' : $showunits = NUMERICALQUESTIONUNITTEXTDISPLAY ;
break ;
case '2' : $showunits = NUMERICALQUESTIONUNITTEXTINPUTDISPLAY ;
break ;
case '3' : $showunits = $data['multichoicedisplay'] ;
break ;
}
if (($showunits == NUMERICALQUESTIONUNITTEXTINPUTDISPLAY) ||
($showunits == NUMERICALQUESTIONUNITMULTICHOICEDISPLAY ) ||
($showunits == NUMERICALQUESTIONUNITTEXTDISPLAY )){
if (trim($units[0]) == ''){
$errors['unit[0]'] = 'You must set a valid unit name' ;
}
}
if ($showunits == NUMERICALQUESTIONUNITNODISPLAY ){
if (count($units)) {
foreach ($units as $key => $unit){
if ($units[$key] != ''){
$errors["unit[$key]"] = 'You must erase this unit name' ;
}
}
}
}
// Check double units.
$alreadyseenunits = array();
if (isset($data['unit'])) {
foreach ($data['unit'] as $key => $unit) {
$trimmedunit = trim($unit);
if ($trimmedunit!='' && in_array($trimmedunit, $alreadyseenunits)) {
$errors["unit[$key]"] = get_string('errorrepeatedunit', 'qtype_numerical');
if (trim($data['multiplier'][$key]) == '') {
$errors["multiplier[$key]"] = get_string('errornomultiplier', 'qtype_numerical');
}
} elseif($trimmedunit!='') {
$alreadyseenunits[] = $trimmedunit;
}
}
}
$units = $data['unit'];
if (count($units)) {
foreach ($units as $key => $unit){
if (is_numeric($unit)){
$errors['unit['.$key.']'] = get_string('mustnotbenumeric', 'qtype_calculated');
}
$trimmedunit = trim($unit);
$trimmedmultiplier = trim($data['multiplier'][$key]);
if (!empty($trimmedunit)){
if (empty($trimmedmultiplier)){
$errors['multiplier['.$key.']'] = get_string('youmustenteramultiplierhere', 'qtype_calculated');
}
if (!is_numeric($trimmedmultiplier)){
$errors['multiplier['.$key.']'] = get_string('mustbenumeric', 'qtype_calculated');
}
}
}
}
}
function valid_unit($rawresponse, $units) {
// Make units more useful
$tmpunits = array();
foreach ($units as $unit) {
$tmpunits[$unit->unit] = $unit->multiplier;
}
// remove spaces and normalise decimal places.
$search = array(' ', ',');
$replace = array('', '.');
$rawresponse = str_replace($search, $replace, trim($rawresponse));
// Apply any unit that is present.
if (preg_match('~^([+-]?([0-9]+(\\.[0-9]*)?|\\.[0-9]+)([eE][-+]?[0-9]+)?)([^0-9].*)?$~',
$rawresponse, $responseparts)) {
if (!empty($responseparts[5])) {
if (isset($tmpunits[$responseparts[5]])) {
// Valid number with unit.
return true ; //(float)$responseparts[1] / $tmpunits[$responseparts[5]];
} else {
// Valid number with invalid unit. Must be wrong.
return false;
}
} else {
// Valid number without unit.
return false ; //(float)$responseparts[1];
}
}
// Invalid number. Must be wrong.
return false;
}
/**
* Runs all the code required to set up and save an essay question for testing purposes.
* Alternate DB table prefix may be used to facilitate data deletion.
@ -1338,7 +1048,7 @@ class qtype_numerical extends question_type {
function check_file_access($question, $state, $options, $contextid, $component,
$filearea, $args) {
$itemid = reset($args);
if ($component == 'question' && $filearea == 'answerfeedback') {
$result = $options->feedback && array_key_exists($itemid, $question->options->answers);
if (!$result) {
@ -1363,7 +1073,6 @@ class qtype_numerical extends question_type {
}
}
/**
* This class processes numbers with units.
*

View File

@ -46,7 +46,7 @@ class qtype_numerical_test extends UnitTestCase {
}
public function tearDown() {
$this->qtype = null;
$this->qtype = null;
}
protected function get_test_question_data() {

View File

@ -214,16 +214,19 @@ class question_type {
public function create_editing_form($submiturl, $question, $category,
$contexts, $formeditable) {
global $CFG;
require_once("{$CFG->dirroot}/question/type/edit_question_form.php");
$definition_file = $CFG->dirroot . '/question/type/' . $this->name() .
require_once($CFG->dirroot . '/question/type/edit_question_form.php');
$definitionfile = $CFG->dirroot . '/question/type/' . $this->name() .
'/edit_' . $this->name() . '_form.php';
if (!(is_readable($definition_file) && is_file($definition_file))) {
return null;
if (!is_readable($definitionfile) || !is_file($definitionfile)) {
throw new coding_exception($this->plugin_name() .
' is missing the definition of its editing formin file ' . $definitionfile . '.');
}
require_once($definition_file);
require_once($definitionfile);
$classname = $this->plugin_name() . '_edit_form';
if (!class_exists($classname)) {
return null;
throw new coding_exception($this->plugin_name() .
' does not define the class ' . $this->plugin_name() .
'_edit_form.');
}
return new $classname($submiturl, $question, $category, $contexts, $formeditable);
}