on-demand release 2.1beta
[moodle.git] / question / type / calculatedsimple / edit_calculatedsimple_form.php
CommitLineData
aeb15530 1<?php
fe6ce234
DC
2// This file is part of Moodle - http://moodle.org/
3//
4// Moodle is free software: you can redistribute it and/or modify
5// it under the terms of the GNU General Public License as published by
6// the Free Software Foundation, either version 3 of the License, or
7// (at your option) any later version.
8//
9// Moodle is distributed in the hope that it will be useful,
10// but WITHOUT ANY WARRANTY; without even the implied warranty of
11// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12// GNU General Public License for more details.
13//
14// You should have received a copy of the GNU General Public License
15// along with Moodle. If not, see <http://www.gnu.org/licenses/>.
16
83a15d02 17/**
18 * Defines the editing form for the calculated simplequestion type.
19 *
b04a4319
TH
20 * @package qtype
21 * @subpackage calculatedsimple
22 * @copyright 2007 Jamie Pratt me@jamiep.org
23 * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
24 */
25
26
a17b297d
TH
27defined('MOODLE_INTERNAL') || die();
28
efe3e87b
TH
29require_once($CFG->dirroot . '/question/type/calculated/edit_calculated_form.php');
30
a17b297d 31
b04a4319
TH
32/**
33 * Editing form for the calculated simplequestion type.
34 *
35 * @copyright 2007 Jamie Pratt me@jamiep.org
36 * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
83a15d02 37 */
efe3e87b 38class qtype_calculatedsimple_edit_form extends qtype_calculated_edit_form {
83a15d02 39 /**
40 * Handle to the question type for this question.
41 *
42 * @var question_calculatedsimple_qtype
43 */
fe6ce234 44 public $qtypeobj;
0735b509 45
8200ccd6 46 public $wildcarddisplay;
0735b509 47
8200ccd6 48 public $questiondisplay;
83a15d02 49
50 public $datasetdefs;
51
8200ccd6 52 public $reload = false;
aeb15530 53
83a15d02 54 public $maxnumber = -1;
55
56 public $regenerate = true;
57
58 public $noofitems;
aeb15530 59
8200ccd6 60 public $outsidelimit = false;
aeb15530
PS
61
62 public $commentanswer = array();
63
83a15d02 64 public $answer = array();
65
66 public $nonemptyanswer = array();
aeb15530 67
a31697ba 68 public $numbererrors = array();
69
aeb15530
PS
70 public $formdata = array();
71
8200ccd6 72 public function __construct($submiturl, $question, $category, $contexts, $formeditable = true) {
83a15d02 73 $this->regenerate = true;
74 $this->question = $question;
b003b818 75
efe3e87b 76 $this->qtypeobj = question_bank::get_qtype($this->question->qtype);
8200ccd6
TH
77 // get the dataset definitions for this question
78 // coming here everytime even when using a NoSubmitButton
79 // so this will only set the values to the actual question database content
80 // which is not what we want so this should be removed from here
83a15d02 81 // get priority to paramdatasets
aeb15530 82
8200ccd6 83 if ("1" == optional_param('reload', '', PARAM_INT)) {
fe6ce234 84 $this->reload = true;
8200ccd6 85 } else {
fe6ce234 86 $this->reload = false;
83a15d02 87 }
fe6ce234 88 if (!$this->reload) { // use database data as this is first pass
0735b509 89 // question->id == 0 so no stored datasets
fe6ce234
DC
90 if (!empty($question->id)) {
91
8200ccd6
TH
92 $this->datasetdefs = $this->qtypeobj->get_dataset_definitions(
93 $question->id, array());
aeb15530 94
8200ccd6 95 if (!empty($this->datasetdefs)) {
1d1f5784 96 foreach ($this->datasetdefs as $defid => $datasetdef) {
aeb15530 97 // first get the items in case their number does not correspond to itemcount
1d1f5784 98 if (isset($datasetdef->id)) {
8200ccd6
TH
99 $this->datasetdefs[$defid]->items =
100 $this->qtypeobj->get_database_dataset_items($datasetdef->id);
101 if ($this->datasetdefs[$defid]->items != '') {
0735b509 102 $datasetdef->itemcount = count($this->datasetdefs[$defid]->items);
103 } else {
8200ccd6 104 $datasetdef->itemcount = 0;
0735b509 105 }
1d1f5784 106 }
83a15d02 107 // Get maxnumber
108 if ($this->maxnumber == -1 || $datasetdef->itemcount < $this->maxnumber) {
109 $this->maxnumber = $datasetdef->itemcount;
110 }
111 }
83a15d02 112 }
1d1f5784 113
8200ccd6
TH
114 $i = 0;
115 foreach ($this->question->options->answers as $answer) {
116 $this->answer[$i] = $answer;
83a15d02 117 $i++;
aeb15530 118 }
8200ccd6 119 $this->nonemptyanswer = $this->answer;
aeb15530 120 }
83a15d02 121 $datasettoremove = false;
8200ccd6
TH
122 $newdatasetvalues = false;
123 $newdataset = false;
124 } else {
83a15d02 125 // handle reload to get values from the form-elements
8200ccd6
TH
126 // answers, datasetdefs and data_items. In any case the validation
127 // step will warn the user of any error in settings the values.
aeb15530 128 // Verification for the specific dataset values as the other parameters
83a15d02 129 // unints, feeedback etc are handled elsewhere
130 // handle request buttons :
aeb15530 131 // 'analyzequestion' (Identify the wild cards {x..} present in answers)
83a15d02 132 // 'addbutton' (create new set of datatitems)
133 // 'updatedatasets' is handled automatically on each reload
aeb15530 134 // The analyzequestion is done every time on reload
83a15d02 135 // to detect any new wild cards so that the current display reflects
136 // the mandatory (i.e. in answers) datasets
137 // to implement : don't do any changes if the question is used in a quiz.
aeb15530
PS
138 // If new datadef, new properties should erase items.
139 // Most of the data
06f80c6c 140 $datasettoremove = false;
8200ccd6
TH
141 $newdatasetvalues = false;
142 $newdataset = false;
0735b509 143 $dummyform = new stdClass();
144 $mandatorydatasets = array();
aeb15530 145 // should not test on adding a new answer
8200ccd6
TH
146 // should test if there are already olddatasets or if the 'analyzequestion'
147 // submit button has been clicked
148 if ('' != optional_param('datasetdef', '', PARAM_RAW) ||
149 '' != optional_param('analyzequestion', '', PARAM_RAW)) {
aeb15530 150
8200ccd6
TH
151 if ($dummyform->answer = optional_param('answer', '', PARAM_NOTAGS)) {
152 // there is always at least one answer...
2a2c5eff 153 $fraction = optional_param('fraction', '', PARAM_NUMBER);
aeb15530
PS
154 $tolerance = optional_param('tolerance', '', PARAM_NUMBER);
155 $tolerancetype = optional_param('tolerancetype', '', PARAM_NUMBER);
156 $correctanswerlength = optional_param('correctanswerlength', '', PARAM_INT);
157 $correctanswerformat = optional_param('correctanswerformat', '', PARAM_INT);
158
8200ccd6
TH
159 foreach ($dummyform->answer as $key => $answer) {
160 if (trim($answer) != '') { // just look for non-empty
161 $this->answer[$key] = new stdClass();
06f80c6c 162 $this->answer[$key]->answer = $answer;
2a2c5eff 163 $this->answer[$key]->fraction = $fraction[$key];
06f80c6c 164 $this->answer[$key]->tolerance = $tolerance[$key];
165 $this->answer[$key]->tolerancetype = $tolerancetype[$key];
166 $this->answer[$key]->correctanswerlength = $correctanswerlength[$key];
167 $this->answer[$key]->correctanswerformat = $correctanswerformat[$key];
168 $this->nonemptyanswer[]= $this->answer[$key];
8200ccd6 169 $mandatorydatasets += $this->qtypeobj->find_dataset_names($answer);
06f80c6c 170 }
0735b509 171 }
83a15d02 172 }
06f80c6c 173 $this->datasetdefs = array();
174 // rebuild datasetdefs from old values
8200ccd6 175 if ($olddef = optional_param('datasetdef', '', PARAM_RAW)) {
aeb15530
PS
176 $calcmin = optional_param('calcmin', '', PARAM_NUMBER);
177 $calclength = optional_param('calclength', '', PARAM_INT);
b003b818 178 $calcmax = optional_param('calcmax', '', PARAM_NUMBER);
aeb15530 179 $oldoptions = optional_param('defoptions', '', PARAM_RAW);
8200ccd6
TH
180 $newdatasetvalues = false;
181 $sizeofolddef = count($olddef);
182 for ($key = 1; $key <= $sizeofolddef; $key++) {
183 $def = $olddef[$key];
184 $this->datasetdefs[$def]= new stdClass();
06f80c6c 185 $this->datasetdefs[$def]->type = 1;
186 $this->datasetdefs[$def]->category = 0;
8200ccd6
TH
187 $this->datasetdefs[$def]->options = $oldoptions[$key];
188 $this->datasetdefs[$def]->calcmin = $calcmin[$key];
189 $this->datasetdefs[$def]->calcmax = $calcmax[$key];
190 $this->datasetdefs[$def]->calclength = $calclength[$key];
06f80c6c 191 //then compare with new values
8200ccd6
TH
192 if (preg_match('~^(uniform|loguniform):([^:]*):([^:]*):([0-9]*)$~',
193 $this->datasetdefs[$def]->options, $regs)) {
194 if ($this->datasetdefs[$def]->calcmin != $regs[2]||
195 $this->datasetdefs[$def]->calcmax != $regs[3] ||
196 $this->datasetdefs[$def]->calclength != $regs[4]) {
197 $newdatasetvalues = true;
aeb15530 198 }
06f80c6c 199 }
8200ccd6
TH
200 $this->datasetdefs[$def]->options = "uniform:" .
201 $this->datasetdefs[$def]->calcmin . ":" .
202 $this->datasetdefs[$def]->calcmax . ":" .
203 $this->datasetdefs[$def]->calclength;
06f80c6c 204 }
8200ccd6 205 }
aeb15530 206 // detect new datasets
8200ccd6
TH
207 $newdataset = false;
208 foreach ($mandatorydatasets as $datasetname) {
209 if (!isset($this->datasetdefs["1-0-$datasetname"])) {
210 $key = "1-0-$datasetname";
211 $this->datasetdefs[$key] = new stdClass();
212 $this->datasetdefs[$key]->type = 1;
213 $this->datasetdefs[$key]->category = 0;
214 $this->datasetdefs[$key]->name = $datasetname;
215 $this->datasetdefs[$key]->options = "uniform:1.0:10.0:1";
216 $newdataset = true;
217 } else {
218 $this->datasetdefs["1-0-$datasetname"]->name = $datasetname;
219 }
83a15d02 220 }
8200ccd6
TH
221 // remove obsolete datasets
222 $datasettoremove = false;
223 foreach ($this->datasetdefs as $defkey => $datasetdef) {
224 if (!isset($datasetdef->name)) {
225 $datasettoremove = true;
226 unset($this->datasetdefs[$defkey]);
227 }
83a15d02 228 }
06f80c6c 229 }
83a15d02 230 } // handle reload
231 // create items if $newdataset and noofitems > 0 and !$newdatasetvalues
232 // eliminate any items if $newdatasetvalues
233 // eliminate any items if $datasettoremove, $newdataset, $newdatasetvalues
8200ccd6
TH
234 if ($datasettoremove ||$newdataset ||$newdatasetvalues) {
235 foreach ($this->datasetdefs as $defkey => $datasetdef) {
83a15d02 236 $datasetdef->itemcount = 0;
237 unset($datasetdef->items);
238 }
239 }
8200ccd6
TH
240 $maxnumber = -1;
241 if ("" != optional_param('addbutton', '', PARAM_TEXT)) {
06f80c6c 242 $maxnumber = optional_param('selectadd', '', PARAM_INT); //FIXME: sloppy coding
83a15d02 243 foreach ($this->datasetdefs as $defid => $datasetdef) {
244 $datasetdef->itemcount = $maxnumber;
245 unset($datasetdef->items);
8200ccd6 246 for ($numberadded = 1; $numberadded <= $maxnumber; $numberadded++) {
0ff4bd08 247 $datasetitem = new stdClass();
83a15d02 248 $datasetitem->itemnumber = $numberadded;
249 $datasetitem->id = 0;
8200ccd6
TH
250 $datasetitem->value = $this->qtypeobj->generate_dataset_item(
251 $datasetdef->options);
252 $this->datasetdefs[$defid]->items[$numberadded] = $datasetitem;
253 }
254 }
255 $this->maxnumber = $maxnumber;
256 } else {
0735b509 257 // Handle reload dataset items
8200ccd6
TH
258 if ("" != optional_param('definition', '', PARAM_NOTAGS) &&
259 !($datasettoremove ||$newdataset ||$newdatasetvalues)) {
83a15d02 260 $i = 1;
aeb15530
PS
261 $fromformdefinition = optional_param('definition', '', PARAM_NOTAGS);
262 $fromformnumber = optional_param('number', '', PARAM_INT);
263 $fromformitemid = optional_param('itemid', '', PARAM_INT);
83a15d02 264 ksort($fromformdefinition);
aeb15530 265
8200ccd6 266 foreach ($fromformdefinition as $key => $defid) {
83a15d02 267 $addeditem = new stdClass();
8200ccd6 268 $addeditem->id = $fromformitemid[$i];
83a15d02 269 $addeditem->value = $fromformnumber[$i];
270 $addeditem->itemnumber = ceil($i / count($this->datasetdefs));
8200ccd6
TH
271 $this->datasetdefs[$defid]->items[$addeditem->itemnumber] = $addeditem;
272 $this->datasetdefs[$defid]->itemcount = $i;
83a15d02 273 $i++;
274 }
275 }
8200ccd6 276 if (isset($addeditem->itemnumber) && $this->maxnumber < $addeditem->itemnumber) {
83a15d02 277 $this->maxnumber = $addeditem->itemnumber;
8200ccd6 278 if (!empty($this->datasetdefs)) {
83a15d02 279 foreach ($this->datasetdefs as $datasetdef) {
8200ccd6 280 $datasetdef->itemcount = $this->maxnumber;
83a15d02 281 }
282 }
283 }
284 }
285
8200ccd6 286 parent::__construct($submiturl, $question, $category, $contexts, $formeditable);
83a15d02 287 }
288
8200ccd6
TH
289 public function get_per_answer_fields($mform, $label, $gradeoptions,
290 &$repeatedoptions, &$answersoption) {
291 $repeated = parent::get_per_answer_fields($mform, $label, $gradeoptions,
292 $repeatedoptions, $answersoption);
83a15d02 293 $mform->setType('answer', PARAM_NOTAGS);
294 $addrepeated = array();
8200ccd6
TH
295 $addrepeated[] = $mform->createElement('text', 'tolerance',
296 get_string('tolerance', 'qtype_calculated'));
83a15d02 297 $repeatedoptions['tolerance']['type'] = PARAM_NUMBER;
298 $repeatedoptions['tolerance']['default'] = 0.01;
8200ccd6
TH
299 $addrepeated[] = $mform->createElement('select', 'tolerancetype',
300 get_string('tolerancetype', 'qtype_numerical'), $this->qtypeobj->tolerance_types());
301 $addrepeated[] = $mform->createElement('select', 'correctanswerlength',
302 get_string('correctanswershows', 'qtype_calculated'), range(0, 9));
83a15d02 303 $repeatedoptions['correctanswerlength']['default'] = 2;
304
8200ccd6
TH
305 $answerlengthformats = array(
306 '1' => get_string('decimalformat', 'qtype_numerical'),
efe3e87b 307 '2' => get_string('significantfiguresformat', 'qtype_calculated')
8200ccd6
TH
308 );
309 $addrepeated[] = $mform->createElement('select', 'correctanswerformat',
310 get_string('correctanswershowsformat', 'qtype_calculated'), $answerlengthformats);
83a15d02 311 array_splice($repeated, 3, 0, $addrepeated);
5e8a85aa 312 $repeated[1]->setLabel(get_string('correctanswerformula', 'qtype_calculated').'=');
83a15d02 313
314 return $repeated;
315 }
316
317 /**
318 * Add question-type specific form fields.
319 *
320 * @param MoodleQuickForm $mform the form being built.
321 */
c7df5006 322 protected function definition_inner($mform) {
83a15d02 323 $strquestionlabel = $this->qtypeobj->comment_header($this->nonemptyanswer);
2fa83505 324 $label = get_string("sharedwildcards", "qtype_calculated");
b003b818 325 $mform->addElement('hidden', 'synchronize', 0);
83a15d02 326 $mform->addElement('hidden', 'initialcategory', 1);
d18e0fe6 327 $mform->setType('initialcategory', PARAM_INT);
83a15d02 328 $mform->addElement('hidden', 'reload', 1);
d18e0fe6 329 $mform->setType('reload', PARAM_INT);
8200ccd6
TH
330 $addfieldsname = 'updatequestion value';
331 $addstring = get_string("updatecategory", "qtype_calculated");
a31697ba 332 $mform->registerNoSubmitButton($addfieldsname);
83a15d02 333
83a15d02 334 $this->add_per_answer_fields($mform, get_string('answerhdr', 'qtype_calculated', '{no}'),
92111e8d 335 question_bank::fraction_options(), 1, 1);
83a15d02 336
efe3e87b
TH
337 $this->add_unit_options($mform, $this);
338 $this->add_unit_fields($mform, $this);
b130270d 339 $this->add_interactive_settings();
aeb15530 340
8200ccd6
TH
341 $label = "<div class='mdl-align'></div><div class='mdl-align'>" .
342 get_string('wildcardrole', 'qtype_calculatedsimple') . "</div>";
83a15d02 343 $mform->addElement('html', "<div class='mdl-align'>&nbsp;</div>");
8200ccd6
TH
344 // explaining the role of datasets so other strings can be shortened
345 $mform->addElement('html', $label);
83a15d02 346
8200ccd6
TH
347 $mform->addElement('submit', 'analyzequestion',
348 get_string('findwildcards', 'qtype_calculatedsimple'));
83a15d02 349 $mform->registerNoSubmitButton('analyzequestion');
350 $mform->closeHeaderBefore('analyzequestion');
8200ccd6 351 if ("" != optional_param('analyzequestion', '', PARAM_RAW)) {
83a15d02 352
353 $this->wizarddisplay = true;
83a15d02 354
8200ccd6 355 } else {
83a15d02 356 $this->wizwarddisplay = false;
357 }
8200ccd6 358 if ($this->maxnumber != -1) {
83a15d02 359 $this->noofitems = $this->maxnumber;
360 } else {
361 $this->noofitems = 0;
362 }
8200ccd6 363 if (!empty($this->datasetdefs)) {//So there are some datadefs
fe6ce234 364 // we put them on the page
0735b509 365 $key = 0;
8200ccd6
TH
366 $mform->addElement('header', 'additemhdr',
367 get_string('wildcardparam', 'qtype_calculatedsimple'));
0735b509 368 $idx = 1;
8200ccd6 369 if (!empty($this->datasetdefs)) {// unnecessary test
0735b509 370 $j = (($this->noofitems) * count($this->datasetdefs))+1;//
8200ccd6
TH
371 foreach ($this->datasetdefs as $defkey => $datasetdef) {
372 $mform->addElement('static', "na[$j]",
373 get_string('param', 'qtype_calculated', $datasetdef->name));
0735b509 374 $this->qtypeobj->custom_generator_tools_part($mform, $idx, $j);
375 $mform->addElement('hidden', "datasetdef[$idx]");
376 $mform->setType("datasetdef[$idx]", PARAM_RAW);
b003b818 377 $mform->addElement('hidden', "defoptions[$idx]");
aeb15530 378 $mform->setType("defoptions[$idx]", PARAM_RAW);
0735b509 379 $idx++;
380 $mform->addElement('static', "divider[$j]", '', '<hr />');
381 $j++;
382 }
383 }
8200ccd6 384 //this should be done before the elements are created and stored as $this->formdata;
0735b509 385 //fill out all data sets and also the fields for the next item to add.
fe6ce234
DC
386 /*Here we do already the values error analysis so that
387 * we could force all wild cards values display if there is an error in values.
388 * as using a , in a number */
389 $this->numbererrors = array();
8200ccd6 390 if (!empty($this->datasetdefs)) {
fe6ce234 391 $j = $this->noofitems * count($this->datasetdefs);
8200ccd6 392 for ($itemnumber = $this->noofitems; $itemnumber >= 1; $itemnumber--) {
fe6ce234 393 $data = array();
8200ccd6 394 $numbererrors = array();
0ff4bd08 395 $comment = new stdClass();
fe6ce234 396 $comment->stranswers = array();
8200ccd6 397 $comment->outsidelimit = false;
fe6ce234
DC
398 $comment->answers = array();
399
8200ccd6
TH
400 foreach ($this->datasetdefs as $defid => $datasetdef) {
401 if (isset($datasetdef->items[$itemnumber])) {
fe6ce234 402 $this->formdata["definition[$j]"] = $defid;
8200ccd6
TH
403 $this->formdata["itemid[$j]"] =
404 $datasetdef->items[$itemnumber]->id;
fe6ce234 405 $data[$datasetdef->name] = $datasetdef->items[$itemnumber]->value;
8200ccd6
TH
406 $this->formdata["number[$j]"] = $number =
407 $datasetdef->items[$itemnumber]->value;
408 if (! is_numeric($number)) {
0ff4bd08 409 $a = new stdClass();
8200ccd6
TH
410 $a->name = '{'.$datasetdef->name.'}';
411 $a->value = $datasetdef->items[$itemnumber]->value;
412 if (stristr($number, ',')) {
413 $this->numbererrors["number[$j]"] =
414 get_string('nocommaallowed', 'qtype_calculated');
fe6ce234 415 $numbererrors .= $this->numbererrors['number['.$j.']']."<br />";
aeb15530 416
8200ccd6
TH
417 } else {
418 $this->numbererrors["number[$j]"] =
419 get_string('notvalidnumber', 'qtype_calculated', $a);
0735b509 420 $numbererrors .= $this->numbererrors['number['.$j.']']."<br />";
fe6ce234 421 }
8200ccd6 422 } else if (stristr($number, 'x')) { // hexa will pass the test
0ff4bd08 423 $a = new stdClass();
8200ccd6
TH
424 $a->name = '{'.$datasetdef->name.'}';
425 $a->value = $datasetdef->items[$itemnumber]->value;
426 $this->numbererrors['number['.$j.']'] =
427 get_string('hexanotallowed', 'qtype_calculated', $a);
fe6ce234 428 $numbererrors .= $this->numbererrors['number['.$j.']']."<br />";
8200ccd6 429 } else if (is_nan($number)) {
0ff4bd08 430 $a = new stdClass();
8200ccd6
TH
431 $a->name = '{'.$datasetdef->name.'}';
432 $a->value = $datasetdef->items[$itemnumber]->value;
433 $this->numbererrors["number[$j]"] =
434 get_string('notvalidnumber', 'qtype_calculated', $a);
fe6ce234 435 $numbererrors .= $this->numbererrors['number['.$j.']']."<br />";
0735b509 436 }
0735b509 437 }
fe6ce234
DC
438 $j--;
439 }
8200ccd6 440 if ($this->noofitems != 0) {
fe6ce234
DC
441 if (empty($numbererrors)) {
442 if (!isset($this->question->id)) {
8200ccd6 443 $this->question->id = 0;
fe6ce234 444 }
8200ccd6
TH
445 $this->question->questiontext = !empty($this->question->questiontext) ?
446 $this->question->questiontext : '';
447 $comment = $this->qtypeobj->comment_on_datasetitems(
448 $this->qtypeobj, $this->question->id,
449 $this->question->questiontext, $this->nonemptyanswer,
450 $data, $itemnumber);
fe6ce234 451 if ($comment->outsidelimit) {
8200ccd6 452 $this->outsidelimit = $comment->outsidelimit;
0735b509 453 }
8200ccd6 454 $totalcomment = '';
fe6ce234
DC
455
456 foreach ($this->nonemptyanswer as $key => $answer) {
457 $totalcomment .= $comment->stranswers[$key].'<br/>';
458 }
459
8200ccd6 460 $this->formdata['answercomment['.$itemnumber.']'] = $totalcomment;
fe6ce234 461 }
0735b509 462 }
fe6ce234
DC
463 }
464 $this->formdata['selectdelete'] = '1';
465 $this->formdata['selectadd'] = '1';
466 $j = $this->noofitems * count($this->datasetdefs)+1;
467 $data = array(); // data for comment_on_datasetitems later
8200ccd6
TH
468 $idx = 1;
469 foreach ($this->datasetdefs as $defid => $datasetdef) {
0735b509 470 $this->formdata["datasetdef[$idx]"] = $defid;
471 $idx++;
472 }
8200ccd6
TH
473 $this->formdata = $this->qtypeobj->custom_generator_set_data(
474 $this->datasetdefs, $this->formdata);
fe6ce234
DC
475 }
476
fe6ce234 477 $addoptions = Array();
8200ccd6
TH
478 $addoptions['1'] = '1';
479 for ($i = 10; $i <= 100; $i += 10) {
480 $addoptions["$i"] = "$i";
fe6ce234
DC
481 }
482 $showoptions = Array();
8200ccd6
TH
483 $showoptions['1'] = '1';
484 $showoptions['2'] = '2';
485 $showoptions['5'] = '5';
486 for ($i = 10; $i <= 100; $i += 10) {
487 $showoptions["$i"] = "$i";
fe6ce234
DC
488 }
489 $mform->closeHeaderBefore('additemhdr');
490 $addgrp = array();
8200ccd6
TH
491 $addgrp[] = $mform->createElement('submit', 'addbutton',
492 get_string('generatenewitemsset', 'qtype_calculatedsimple'));
493 $addgrp[] = $mform->createElement('select', "selectadd", '', $addoptions);
494 $addgrp[] = $mform->createElement('static', "stat", '',
495 get_string('newsetwildcardvalues', 'qtype_calculatedsimple'));
fe6ce234
DC
496 $mform->addGroup($addgrp, 'addgrp', '', ' ', false);
497 $mform->registerNoSubmitButton('addbutton');
498 $mform->closeHeaderBefore('addgrp');
499 $addgrp1 = array();
8200ccd6
TH
500 $addgrp1[] = $mform->createElement('submit', 'showbutton',
501 get_string('showitems', 'qtype_calculatedsimple'));
502 $addgrp1[] = $mform->createElement('select', "selectshow", '', $showoptions);
503 $addgrp1[] = $mform->createElement('static', "stat", '',
504 get_string('setwildcardvalues', 'qtype_calculatedsimple'));
fe6ce234
DC
505 $mform->addGroup($addgrp1, 'addgrp1', '', ' ', false);
506 $mform->registerNoSubmitButton('showbutton');
507 $mform->closeHeaderBefore('addgrp1');
508 $mform->addElement('static', "divideradd", '', '');
509 if ($this->noofitems == 0) {
8200ccd6
TH
510 $mform->addElement('static', 'warningnoitems', '', '<span class="error">' .
511 get_string('youmustaddatleastonevalue', 'qtype_calculatedsimple') .
512 '</span>');
fe6ce234 513 $mform->closeHeaderBefore('warningnoitems');
8200ccd6
TH
514 } else {
515 $mform->addElement('header', 'additemhdr1',
516 get_string('wildcardvalues', 'qtype_calculatedsimple'));
fe6ce234 517 $mform->closeHeaderBefore('additemhdr1');
8200ccd6
TH
518 if (!empty($this->numbererrors) || $this->outsidelimit) {
519 $mform->addElement('static', "alert", '', '<span class="error">' .
520 get_string('useadvance', 'qtype_calculatedsimple').'</span>');
0735b509 521 }
522
8200ccd6
TH
523 $mform->addElement('submit', 'updatedatasets',
524 get_string('updatewildcardvalues', 'qtype_calculatedsimple'));
fe6ce234 525 $mform->registerNoSubmitButton('updatedatasets');
8200ccd6 526 $mform->setAdvanced("updatedatasets", true);
aeb15530 527
8200ccd6 528 //--------------------------------------------------------------
fe6ce234 529 $j = $this->noofitems * count($this->datasetdefs);
8200ccd6
TH
530 $k = 1;
531 if ("" != optional_param('selectshow', '', PARAM_INT)) {
fe6ce234
DC
532 $k = optional_param('selectshow', '', PARAM_INT);
533 }
aeb15530 534
8200ccd6
TH
535 for ($i = $this->noofitems; $i >= 1; $i--) {
536 foreach ($this->datasetdefs as $defkey => $datasetdef) {
537 if ($k > 0 || $this->outsidelimit || !empty($this->numbererrors)) {
538 $mform->addElement('text', "number[$j]", get_string(
539 'wildcard', 'qtype_calculatedsimple', $datasetdef->name));
540 $mform->setAdvanced("number[$j]", true);
541 if (!empty($this->numbererrors['number['.$j.']'])) {
542 $mform->addElement('static', "numbercomment[$j]", '',
543 '<span class="error">' .
544 $this->numbererrors['number['.$j.']'] . '</span>');
545 $mform->setAdvanced("numbercomment[$j]", true);
fe6ce234 546 }
8200ccd6
TH
547 } else {
548 $mform->addElement('hidden', "number[$j]", get_string(
549 'wildcard', 'qtype_calculatedsimple', $datasetdef->name));
fe6ce234
DC
550 }
551 $mform->setType("number[$j]", PARAM_NUMBER);
83a15d02 552
fe6ce234
DC
553 $mform->addElement('hidden', "itemid[$j]");
554 $mform->setType("itemid[$j]", PARAM_INT);
a31697ba 555
fe6ce234
DC
556 $mform->addElement('hidden', "definition[$j]");
557 $mform->setType("definition[$j]", PARAM_NOTAGS);
83a15d02 558
fe6ce234
DC
559 $j--;
560 }
8200ccd6
TH
561 if (!empty($strquestionlabel) && ($k > 0 || $this->outsidelimit ||
562 !empty($this->numbererrors))) {
563 $mform->addElement('static', "answercomment[$i]", "<b>" .
564 get_string('setno', 'qtype_calculatedsimple', $i) .
565 "</b>&nbsp;&nbsp;" . $strquestionlabel);
aeb15530 566
fe6ce234 567 }
8200ccd6 568 if ($k > 0 || $this->outsidelimit || !empty($this->numbererrors)) {
fe6ce234 569 $mform->addElement('static', "divider1[$j]", '', '<hr />');
aeb15530 570
fe6ce234 571 }
8200ccd6 572 $k--;
fe6ce234
DC
573 }
574 }
8200ccd6
TH
575 } else {
576 $mform->addElement('static', 'warningnowildcards', '', '<span class="error">' .
577 get_string('atleastonewildcard', 'qtype_calculatedsimple') . '</span>');
fe6ce234 578 $mform->closeHeaderBefore('warningnowildcards');
83a15d02 579 }
83a15d02 580
8200ccd6
TH
581 //----------------------------------------------------------------------
582 // Non standard name for button element needed so not using add_action_buttons
583 // hidden elements
83a15d02 584
585 $mform->addElement('hidden', 'id');
586 $mform->setType('id', PARAM_INT);
587
588 $mform->addElement('hidden', 'courseid');
589 $mform->setType('courseid', PARAM_INT);
590 $mform->setDefault('courseid', 0);
591
592 $mform->addElement('hidden', 'cmid');
593 $mform->setType('cmid', PARAM_INT);
594 $mform->setDefault('cmid', 0);
8200ccd6
TH
595 if (!empty($this->question->id)) {
596 if ($this->question->formoptions->cansaveasnew) {
597 $mform->addElement('header', 'additemhdr',
598 get_string('converttocalculated', 'qtype_calculatedsimple'));
fe6ce234 599 $mform->closeHeaderBefore('additemhdr');
aeb15530 600
8200ccd6
TH
601 $mform->addElement('checkbox', 'convert', '',
602 get_string('willconverttocalculated', 'qtype_calculatedsimple'));
fe6ce234 603 $mform->setDefault('convert', 0);
83a15d02 604
83a15d02 605 }
fe6ce234 606 }
83a15d02 607 }
608
8200ccd6 609 public function data_preprocessing($question) {
fe6ce234
DC
610 $answer = $this->answer;
611 $default_values = array();
612 if (count($answer)) {
613 $key = 0;
8200ccd6
TH
614 foreach ($answer as $answer) {
615 $default_values['answer['.$key.']'] = $answer->answer;
fe6ce234
DC
616 $default_values['fraction['.$key.']'] = $answer->fraction;
617 $default_values['tolerance['.$key.']'] = $answer->tolerance;
618 $default_values['tolerancetype['.$key.']'] = $answer->tolerancetype;
619 $default_values['correctanswerlength['.$key.']'] = $answer->correctanswerlength;
620 $default_values['correctanswerformat['.$key.']'] = $answer->correctanswerformat;
621
622 // prepare draft files
623 $draftid = file_get_submitted_draft_itemid('feedback['.$key.']');
624 $default_values['feedback['.$key.']']['text'] = file_prepare_draft_area(
625 $draftid, // draftid
626 $this->context->id, // context
627 'question', // component
628 'answerfeedback', // filarea
629 !empty($answer->id)?(int)$answer->id:null, // itemid
630 $this->fileoptions, // options
631 !empty($answer->feedback)?$answer->feedback:'' // text
632 );
8200ccd6
TH
633 $default_values['feedback['.$key.']']['format'] = !empty($answer->feedbackformat) ?
634 $answer->feedbackformat : editors_get_preferred_format();
fe6ce234
DC
635 $default_values['feedback['.$key.']']['itemid'] = $draftid;
636
637 $key++;
b003b818 638 }
fe6ce234 639 }
8200ccd6 640 $default_values['synchronize'] = 0;
83a15d02 641
642 $formdata = array();
643 $fromform = new stdClass();
8200ccd6 644 //this should be done before the elements are created and stored as $this->formdata;
83a15d02 645 //fill out all data sets and also the fields for the next item to add.
8200ccd6 646 $question = (object)((array)$question + $default_values+$this->formdata);
83a15d02 647
efe3e87b
TH
648 $question = $this->data_preprocessing_units($question);
649 $question = $this->data_preprocessing_unit_options($question);
650
fe6ce234 651 return $question;
83a15d02 652 }
653
8200ccd6 654 public function qtype() {
83a15d02 655 return 'calculatedsimple';
656 }
657
8200ccd6 658 public function validation($data, $files) {
83a15d02 659 $errors = parent::validation($data, $files);
83a15d02 660
e6d76583
TH
661 if (empty($data['definition'])) {
662 $errors['selectadd'] = get_string('youmustaddatleastonevalue', 'qtype_calculatedsimple');
663 }
664
83a15d02 665 return $errors;
666 }
667}