ILIAS  release_5-3 Revision v5.3.23-19-g915713cf615
class.assFormulaQuestion.php
Go to the documentation of this file.
1 <?php
2 /* Copyright (c) 1998-2013 ILIAS open source, Extended GPL, see docs/LICENSE */
3 
4 include_once "./Modules/TestQuestionPool/classes/class.assQuestion.php";
5 include_once "./Modules/TestQuestionPool/classes/class.assFormulaQuestionResult.php";
6 include_once "./Modules/TestQuestionPool/classes/class.assFormulaQuestionVariable.php";
7 include_once "./Modules/TestQuestionPool/classes/class.ilUnitConfigurationRepository.php";
8 include_once "./Modules/Test/classes/inc.AssessmentConstants.php";
9 include_once "./Modules/TestQuestionPool/interfaces/interface.iQuestionCondition.php";
10 require_once './Modules/TestQuestionPool/classes/class.ilUserQuestionResult.php';
11 
20 {
21  private $variables;
22  private $results;
23  private $resultunits;
24 
28  private $unitrepository;
29 
41  public function __construct(
42  $title = "",
43  $comment = "",
44  $author = "",
45  $owner = -1,
46  $question = ""
47  ) {
48  parent::__construct($title, $comment, $author, $owner, $question);
49  $this->variables = array();
50  $this->results = array();
51  $this->resultunits = array();
52  $this->unitrepository = new ilUnitConfigurationRepository(0);
53  }
54 
55  public function clearVariables()
56  {
57  $this->variables = array();
58  }
59 
60  public function getVariables()
61  {
62  return $this->variables;
63  }
64 
65  public function getVariable($variable)
66  {
67  if (array_key_exists($variable, $this->variables)) {
68  return $this->variables[$variable];
69  }
70  return null;
71  }
72 
73  public function addVariable($variable)
74  {
75  $this->variables[$variable->getVariable()] = $variable;
76  }
77 
78  public function clearResults()
79  {
80  $this->results = array();
81  }
82 
83  public function getResults()
84  {
85  return $this->results;
86  }
87 
88  public function getResult($result)
89  {
90  if (array_key_exists($result, $this->results)) {
91  return $this->results[$result];
92  }
93  return null;
94  }
95 
96  public function addResult($result)
97  {
98  $this->results[$result->getResult()] = $result;
99  }
100 
101  public function addResultUnits($result, $unit_ids)
102  {
103  $this->resultunits[$result->getResult()] = array();
104  if ((!is_object($result)) || (!is_array($unit_ids))) {
105  return;
106  }
107  foreach ($unit_ids as $id) {
108  if (is_numeric($id) && ($id > 0)) {
109  $this->resultunits[$result->getResult()][$id] = $this->getUnitrepository()->getUnit($id);
110  }
111  }
112  }
113 
114  public function addResultUnit($result, $unit)
115  {
116  if (is_object($result) && is_object($unit)) {
117  if (!is_array($this->resultunits[$result->getResult()])) {
118  $this->resultunits[$result->getResult()] = array();
119  }
120  $this->resultunits[$result->getResult()][$unit->getId()] = $unit;
121  }
122  }
123 
124  public function getResultUnits($result)
125  {
126  if (array_key_exists($result->getResult(), $this->resultunits)) {
127  return $this->resultunits[$result->getResult()];
128  } else {
129  return array();
130  }
131  }
132 
133  public function hasResultUnit($result, $unit_id)
134  {
135  if (array_key_exists($result->getResult(), $this->resultunits)) {
136  if (array_key_exists($unit_id, $this->resultunits[$result->getResult()])) {
137  return true;
138  }
139  }
140 
141  return false;
142  }
143 
144  public function parseQuestionText()
145  {
146  $this->clearResults();
147  $this->clearVariables();
148  if (preg_match_all("/(\\\$v\\d+)/ims", $this->getQuestion(), $matches)) {
149  foreach ($matches[1] as $variable) {
150  $varObj = new assFormulaQuestionVariable($variable, 0, 0, null, 0);
151  $this->addVariable($varObj);
152  }
153  }
154 
155  if (preg_match_all("/(\\\$r\\d+)/ims", $this->getQuestion(), $rmatches)) {
156  foreach ($rmatches[1] as $result) {
157  $resObj = new assFormulaQuestionResult($result, null, null, 0, -1, null, 1, 1, true);
158  $this->addResult($resObj);
159  }
160  }
161  }
162 
163  public function checkForDuplicateVariables()
164  {
165  if (preg_match_all("/(\\\$v\\d+)/ims", $this->getQuestion(), $matches)) {
166  if ((count(array_unique($matches[1]))) != count($matches[1])) {
167  return false;
168  }
169  }
170  return true;
171  }
172 
173  public function checkForDuplicateResults()
174  {
175  if (preg_match_all("/(\\\$r\\d+)/ims", $this->getQuestion(), $rmatches)) {
176  if ((count(array_unique($rmatches[1]))) != count($rmatches[1])) {
177  return false;
178  }
179  }
180  return true;
181  }
182 
187  public function fetchAllResults($questionText)
188  {
189  $resObjects = array();
190  $matches = null;
191 
192  if (preg_match_all("/(\\\$r\\d+)/ims", $questionText, $matches)) {
193  foreach ($matches[1] as $resultKey) {
194  $resObjects[] = $this->getResult($resultKey);
195  }
196  }
197 
198  return $resObjects;
199  }
200 
205  public function fetchAllVariables($questionText)
206  {
207  $varObjects = array();
208  $matches = null;
209 
210  if (preg_match_all("/(\\\$v\\d+)/ims", $questionText, $matches)) {
211  foreach ($matches[1] as $variableKey) {
212  $varObjects[] = $this->getVariable($variableKey);
213  }
214  }
215 
216  return $varObjects;
217  }
218 
223  public function hasRequiredVariableSolutionValues(array $userSolution)
224  {
225  foreach ($this->fetchAllVariables($this->getQuestion()) as $varObj) {
226  if (!isset($userSolution[$varObj->getVariable()])) {
227  return false;
228  }
229 
230  if (!strlen($userSolution[$varObj->getVariable()])) {
231  return false;
232  }
233  }
234 
235  return true;
236  }
237 
242  {
243  foreach ($this->fetchAllResults($this->getQuestion()) as $resObj) {
244  $resObj->findValidRandomVariables($this->getVariables(), $this->getResults());
245  }
246 
247  $variableSolutionValues = array();
248 
249  foreach ($this->fetchAllVariables($this->getQuestion()) as $varObj) {
250  $variableSolutionValues[$varObj->getVariable()] = $varObj->getValue();
251  }
252 
253  return $variableSolutionValues;
254  }
255 
264  public function substituteVariables(array $userdata, $graphicalOutput = false, $forsolution = false, $result_output = false)
265  {
266  if ((count($this->results) == 0) && (count($this->variables) == 0)) {
267  return false;
268  }
269 
270  $text = $this->getQuestion();
271 
272  foreach ($this->fetchAllVariables($this->getQuestion()) as $varObj) {
273  if (isset($userdata[$varObj->getVariable()]) && strlen($userdata[$varObj->getVariable()])) {
274  $varObj->setValue($userdata[$varObj->getVariable()]);
275  }
276 
277  $unit = (is_object($varObj->getUnit())) ? $varObj->getUnit()->getUnit() : "";
278  $val = (strlen($varObj->getValue()) > 8) ? strtoupper(sprintf("%e", $varObj->getValue())) : $varObj->getValue();
279 
280  $text = preg_replace("/\\$" . substr($varObj->getVariable(), 1) . "(?![0-9]+)/", $val . " " . $unit . "\\1", $text);
281  }
282 
283  if (preg_match_all("/(\\\$r\\d+)/ims", $this->getQuestion(), $rmatches)) {
284  foreach ($rmatches[1] as $result) {
285  $resObj = $this->getResult($result);
286  $value = "";
287  $frac_helper = '';
288  $user_data[$result]['result_type'] = $resObj->getResultType();
289 
290  if (
291  $resObj->getResultType() == assFormulaQuestionResult::RESULT_FRAC ||
292  $resObj->getResultType() == assFormulaQuestionResult::RESULT_CO_FRAC
293  ) {
294  $is_frac = true;
295  }
296  if (is_array($userdata)) {
297  if (is_array($userdata[$result])) {
298  if (false && $forsolution && $result_output) { // fix for mantis #25956
299  $value_org = $resObj->calculateFormula($this->getVariables(), $this->getResults(), parent::getId());
300  $value = sprintf("%." . $resObj->getPrecision() . "f", $value_org);
301  if ($is_frac) {
303  if (is_array($value)) {
304  $frac_helper = $value[1];
305  $value = $value[0];
306  }
307  }
308  } else {
309  if ($forsolution) {
310  $value = $userdata[$result]["value"];
311  } else {
312  $value = ' value="' . $userdata[$result]["value"] . '"';
313  }
314  }
315  }
316  } else {
317  if ($forsolution) {
318  $value = $resObj->calculateFormula($this->getVariables(), $this->getResults(), parent::getId());
319  $value = sprintf("%." . $resObj->getPrecision() . "f", $value);
320 
321  if ($is_frac) {
323  if (is_array($value)) {
324  $frac_helper = $value[1];
325  $value = $value[0];
326  }
327  $value = ' value="' . $value . '"';
328  }
329  } else {
330  // Precision fix for Preview by tjoussen
331  // If all default values are set, this function is called in getPreview
332  $use_precision = !($userdata == null && $graphicalOutput == false && $forsolution == false && $result_output == false);
333 
334  $val = $resObj->calculateFormula($this->getVariables(), $this->getResults(), parent::getId(), $use_precision);
335 
336  if ($resObj->getResultType() == assFormulaQuestionResult::RESULT_FRAC
337  ||$resObj->getResultType() == assFormulaQuestionResult::RESULT_CO_FRAC) {
338  $val = $resObj->convertDecimalToCoprimeFraction($val);
339  if (is_array($val)) {
340  $frac_helper = $val[1];
341  $val = $val[0];
342  }
343  } else {
344  $val = sprintf("%." . $resObj->getPrecision() . "f", $val);
345  $val = (strlen($val) > 8) ? strtoupper(sprintf("%e", $val)) : $val;
346  }
347  $value = ' value="' . $val . '"';
348  }
349  }
350 
351  if ($forsolution) {
352  $input = '<span class="ilc_qinput_TextInput solutionbox">' . ilUtil::prepareFormOutput($value) . '</span>';
353  } else {
354  $input = '<input class="ilc_qinput_TextInput" type="text" spellcheck="false" autocomplete="off" autocorrect="off" autocapitalize="off" name="result_' . $result . '"' . $value . ' />';
355  }
356 
357  $units = "";
358  if (count($this->getResultUnits($resObj)) > 0) {
359  if ($forsolution) {
360  if (is_array($userdata)) {
361  foreach ($this->getResultUnits($resObj) as $unit) {
362  if ($userdata[$result]["unit"] == $unit->getId()) {
363  $units = $unit->getUnit();
364  }
365  }
366  } else {
367  if ($resObj->getUnit()) {
368  $units = $resObj->getUnit()->getUnit();
369  }
370  }
371  } else {
372  $units = '<select name="result_' . $result . '_unit">';
373  $units .= '<option value="-1">' . $this->lng->txt("select_unit") . '</option>';
374  foreach ($this->getResultUnits($resObj) as $unit) {
375  $units .= '<option value="' . $unit->getId() . '"';
376  if ((is_array($userdata[$result])) && (strlen($userdata[$result]["unit"]))) {
377  if ($userdata[$result]["unit"] == $unit->getId()) {
378  $units .= ' selected="selected"';
379  }
380  }
381  $units .= '>' . $unit->getUnit() . '</option>';
382  }
383  $units .= '</select>';
384  }
385  } else {
386  $units = "";
387  }
388  switch ($resObj->getResultType()) {
390  $units .= ' ' . $this->lng->txt('expected_result_type') . ': ' . $this->lng->txt('result_dec');
391  break;
393  if (strlen($frac_helper)) {
394  $units .= ' &asymp; ' . $frac_helper . ', ';
395  } elseif (is_array($userdata) && isset($userdata[$result]) && strlen($userdata[$result]["frac_helper"])) {
396  if (!preg_match('-/-', $value)) {
397  $units .= ' &asymp; ' . $userdata[$result]["frac_helper"] . ', ';
398  }
399  }
400  $units .= ' ' . $this->lng->txt('expected_result_type') . ': ' . $this->lng->txt('result_frac');
401  break;
403  if (strlen($frac_helper)) {
404  $units .= ' &asymp; ' . $frac_helper . ', ';
405  } elseif (is_array($userdata) && isset($userdata[$result]) && strlen($userdata[$result]["frac_helper"])) {
406  if (!preg_match('-/-', $value)) {
407  $units .= ' &asymp; ' . $userdata[$result]["frac_helper"] . ', ';
408  }
409  }
410  $units .= ' ' . $this->lng->txt('expected_result_type') . ': ' . $this->lng->txt('result_co_frac');
411  break;
413  break;
414  }
415  $checkSign = "";
416  if ($graphicalOutput) {
417  $resunit = null;
418  $user_value = '';
419  if (is_array($userdata) && is_array($userdata[$result])) {
420  if ($userdata[$result]["unit"] > 0) {
421  $resunit = $this->getUnitrepository()->getUnit($userdata[$result]["unit"]);
422  }
423 
424  if (isset($userdata[$result]["value"])) {
425  $user_value = $userdata[$result]["value"];
426  }
427  }
428 
429  $template = new ilTemplate("tpl.il_as_qpl_formulaquestion_output_solution_image.html", true, true, 'Modules/TestQuestionPool');
430 
431  if ($resObj->isCorrect($this->getVariables(), $this->getResults(), $user_value, $resunit)) {
432  $template->setCurrentBlock("icon_ok");
433  $template->setVariable("ICON_OK", ilUtil::getImagePath("icon_ok.svg"));
434  $template->setVariable("TEXT_OK", $this->lng->txt("answer_is_right"));
435  $template->parseCurrentBlock();
436  } else {
437  $template->setCurrentBlock("icon_not_ok");
438  $template->setVariable("ICON_NOT_OK", ilUtil::getImagePath("icon_not_ok.svg"));
439  $template->setVariable("TEXT_NOT_OK", $this->lng->txt("answer_is_wrong"));
440  $template->parseCurrentBlock();
441  }
442  $checkSign = $template->get();
443  }
444  $resultOutput = "";
445  if ($result_output) {
446  $template = new ilTemplate("tpl.il_as_qpl_formulaquestion_output_solution_result.html", true, true, 'Modules/TestQuestionPool');
447 
448  if (is_array($userdata)) {
449  $found = $resObj->getResultInfo($this->getVariables(), $this->getResults(), $userdata[$resObj->getResult()]["value"], $userdata[$resObj->getResult()]["unit"], $this->getUnitrepository()->getUnits());
450  } else {
451  $found = $resObj->getResultInfo($this->getVariables(), $this->getResults(), $resObj->calculateFormula($this->getVariables(), $this->getResults(), parent::getId()), is_object($resObj->getUnit()) ? $resObj->getUnit()->getId() : null, $this->getUnitrepository()->getUnits());
452  }
453  $resulttext = "(";
454  if ($resObj->getRatingSimple()) {
455  if ($frac_helper) {
456  $resulttext .="n/a";
457  } else {
458  $resulttext .= $found['points'] . " " . (($found['points'] == 1) ? $this->lng->txt('point') : $this->lng->txt('points'));
459  }
460  } else {
461  $resulttext .= $this->lng->txt("rated_sign") . " " . (($found['sign']) ? $found['sign'] : 0) . " " . (($found['sign'] == 1) ? $this->lng->txt('point') : $this->lng->txt('points')) . ", ";
462  $resulttext .= $this->lng->txt("rated_value") . " " . (($found['value']) ? $found['value'] : 0) . " " . (($found['value'] == 1) ? $this->lng->txt('point') : $this->lng->txt('points')) . ", ";
463  $resulttext .= $this->lng->txt("rated_unit") . " " . (($found['unit']) ? $found['unit'] : 0) . " " . (($found['unit'] == 1) ? $this->lng->txt('point') : $this->lng->txt('points'));
464  }
465 
466  $resulttext .= ")";
467  $template->setVariable("RESULT_OUTPUT", $resulttext);
468 
469  $resultOutput = $template->get();
470  }
471  $text = preg_replace("/\\\$" . substr($result, 1) . "(?![0-9]+)/", $input . " " . $units . " " . $checkSign . " " . $resultOutput . " " . "\\1", $text);
472  }
473  }
474  return $text;
475  }
476 
483  public function canUseAdvancedRating($result)
484  {
485  $result_units = $this->getResultUnits($result);
486  $resultunit = $result->getUnit();
487  $similar_units = 0;
488  foreach ($result_units as $unit) {
489  if (is_object($resultunit)) {
490  if ($resultunit->getId() != $unit->getId()) {
491  if ($resultunit->getBaseUnit() && $unit->getBaseUnit()) {
492  if ($resultunit->getBaseUnit() == $unit->getBaseUnit()) {
493  return false;
494  }
495  }
496  if ($resultunit->getBaseUnit()) {
497  if ($resultunit->getBaseUnit() == $unit->getId()) {
498  return false;
499  }
500  }
501  if ($unit->getBaseUnit()) {
502  if ($unit->getBaseUnit() == $resultunit->getId()) {
503  return false;
504  }
505  }
506  }
507  }
508  }
509  return true;
510  }
511 
516  public function isComplete()
517  {
518  if (($this->title) and ($this->author) and ($this->question) and ($this->getMaximumPoints() > 0)) {
519  return true;
520  } else {
521  return false;
522  }
523  }
524 
529  public function saveToDb($original_id = "")
530  {
531  global $ilDB;
532 
534  // save variables
535  $affectedRows = $ilDB->manipulateF(
536  "
537  DELETE FROM il_qpl_qst_fq_var
538  WHERE question_fi = %s",
539  array("integer"),
540  array($this->getId())
541  );
542 
543  foreach ($this->variables as $variable) {
544  $next_id = $ilDB->nextId('il_qpl_qst_fq_var');
545  $ilDB->insert(
546  'il_qpl_qst_fq_var',
547  array(
548  'variable_id' => array('integer', $next_id),
549  'question_fi' => array('integer', $this->getId()),
550  'variable' => array('text', $variable->getVariable()),
551  'range_min' => array('float', ((strlen($variable->getRangeMin())) ? $variable->getRangeMin() : 0.0)),
552  'range_max' => array('float', ((strlen($variable->getRangeMax())) ? $variable->getRangeMax() : 0.0)),
553  'unit_fi' => array('integer', (is_object($variable->getUnit()) ? (int) $variable->getUnit()->getId() : 0)),
554  'varprecision' => array('integer', (int) $variable->getPrecision()),
555  'intprecision' => array('integer', (int) $variable->getIntprecision()),
556  'range_min_txt' => array('text', $variable->getRangeMinTxt()),
557  'range_max_txt' => array('text', $variable->getRangeMaxTxt())
558  )
559  );
560  }
561  // save results
562  $affectedRows = $ilDB->manipulateF(
563  "DELETE FROM il_qpl_qst_fq_res WHERE question_fi = %s",
564  array("integer"),
565  array($this->getId())
566  );
567 
568  foreach ($this->results as $result) {
569  $next_id = $ilDB->nextId('il_qpl_qst_fq_res');
570  if (is_object($result->getUnit())) {
571  $tmp_result_unit = $result->getUnit()->getId();
572  } else {
573  $tmp_result_unit = null;
574  }
575 
576  $formula = str_replace(",", ".", $result->getFormula());
577 
578  $ilDB->insert("il_qpl_qst_fq_res", array(
579  "result_id" => array("integer", $next_id),
580  "question_fi" => array("integer", $this->getId()),
581  "result" => array("text", $result->getResult()),
582  "range_min" => array("float", ((strlen($result->getRangeMin())) ? $result->getRangeMin() : 0)),
583  "range_max" => array("float", ((strlen($result->getRangeMax())) ? $result->getRangeMax() : 0)),
584  "tolerance" => array("float", ((strlen($result->getTolerance())) ? $result->getTolerance() : 0)),
585  "unit_fi" => array("integer", (int) $tmp_result_unit),
586  "formula" => array("clob", $formula),
587  "resprecision" => array("integer", $result->getPrecision()),
588  "rating_simple" => array("integer", ($result->getRatingSimple()) ? 1 : 0),
589  "rating_sign" => array("float", ($result->getRatingSimple()) ? 0 : $result->getRatingSign()),
590  "rating_value" => array("float", ($result->getRatingSimple()) ? 0 : $result->getRatingValue()),
591  "rating_unit" => array("float", ($result->getRatingSimple()) ? 0 : $result->getRatingUnit()),
592  "points" => array("float", $result->getPoints()),
593  "result_type" => array('integer', (int) $result->getResultType()),
594  "range_min_txt" => array("text", $result->getRangeMinTxt()),
595  "range_max_txt" => array("text", $result->getRangeMaxTxt())
596 
597  ));
598  }
599  // save result units
600  $affectedRows = $ilDB->manipulateF(
601  "DELETE FROM il_qpl_qst_fq_res_unit WHERE question_fi = %s",
602  array("integer"),
603  array($this->getId())
604  );
605  foreach ($this->results as $result) {
606  foreach ($this->getResultUnits($result) as $unit) {
607  $next_id = $ilDB->nextId('il_qpl_qst_fq_res_unit');
608  $affectedRows = $ilDB->manipulateF(
609  "INSERT INTO il_qpl_qst_fq_res_unit (result_unit_id, question_fi, result, unit_fi) VALUES (%s, %s, %s, %s)",
610  array('integer', 'integer', 'text', 'integer'),
611  array(
612  $next_id,
613  $this->getId(),
614  $result->getResult(),
615  $unit->getId()
616  )
617  );
618  }
619  }
620 
621  parent::saveToDb();
622  }
623 
628  public function loadFromDb($question_id)
629  {
630  global $ilDB;
631 
632  $result = $ilDB->queryF(
633  "SELECT qpl_questions.* FROM qpl_questions WHERE question_id = %s",
634  array('integer'),
635  array($question_id)
636  );
637  if ($result->numRows() == 1) {
638  $data = $ilDB->fetchAssoc($result);
639  $this->setId($question_id);
640  $this->setTitle($data["title"]);
641  $this->setComment($data["description"]);
642  $this->setSuggestedSolution($data["solution_hint"]);
643  $this->setPoints($data['points']);
644  $this->setOriginalId($data["original_id"]);
645  $this->setObjId($data["obj_fi"]);
646  $this->setAuthor($data["author"]);
647  $this->setOwner($data["owner"]);
648 
649  try {
650  $this->setAdditionalContentEditingMode($data['add_cont_edit_mode']);
651  } catch (ilTestQuestionPoolException $e) {
652  }
653 
654  $this->unitrepository = new ilUnitConfigurationRepository($question_id);
655 
656  include_once("./Services/RTE/classes/class.ilRTE.php");
657  $this->setQuestion(ilRTE::_replaceMediaObjectImageSrc($data["question_text"], 1));
658  $this->setEstimatedWorkingTime(substr($data["working_time"], 0, 2), substr($data["working_time"], 3, 2), substr($data["working_time"], 6, 2));
659 
660  // load variables
661  $result = $ilDB->queryF(
662  "SELECT * FROM il_qpl_qst_fq_var WHERE question_fi = %s",
663  array('integer'),
664  array($question_id)
665  );
666  if ($result->numRows() > 0) {
667  while ($data = $ilDB->fetchAssoc($result)) {
668  $varObj = new assFormulaQuestionVariable($data["variable"], $data["range_min"], $data["range_max"], $this->getUnitrepository()->getUnit($data["unit_fi"]), $data["varprecision"], $data["intprecision"]);
669  $varObj->setRangeMinTxt($data['range_min_txt']);
670  $varObj->setRangeMaxTxt($data['range_max_txt']);
671  $this->addVariable($varObj);
672  }
673  }
674  // load results
675  $result = $ilDB->queryF(
676  "SELECT * FROM il_qpl_qst_fq_res WHERE question_fi = %s",
677  array('integer'),
678  array($question_id)
679  );
680  if ($result->numRows() > 0) {
681  while ($data = $ilDB->fetchAssoc($result)) {
682  $resObj = new assFormulaQuestionResult($data["result"], $data["range_min"], $data["range_max"], $data["tolerance"], $this->getUnitrepository()->getUnit($data["unit_fi"]), $data["formula"], $data["points"], $data["resprecision"], $data["rating_simple"], $data["rating_sign"], $data["rating_value"], $data["rating_unit"]);
683  $resObj->setResultType($data['result_type']);
684  $resObj->setRangeMinTxt($data['range_min_txt']);
685  $resObj->setRangeMaxTxt($data['range_max_txt']);
686  $this->addResult($resObj);
687  }
688  }
689 
690  // load result units
691  $result = $ilDB->queryF(
692  "SELECT * FROM il_qpl_qst_fq_res_unit WHERE question_fi = %s",
693  array('integer'),
694  array($question_id)
695  );
696  if ($result->numRows() > 0) {
697  while ($data = $ilDB->fetchAssoc($result)) {
698  $unit = $this->getUnitrepository()->getUnit($data["unit_fi"]);
699  $resObj = $this->getResult($data["result"]);
700  $this->addResultUnit($resObj, $unit);
701  }
702  }
703  }
704  parent::loadFromDb($question_id);
705  }
706 
711  public function duplicate($for_test = true, $title = "", $author = "", $owner = "", $testObjId = null)
712  {
713  if ($this->id <= 0) {
714  // The question has not been saved. It cannot be duplicated
715  return;
716  }
717  // duplicate the question in database
718  $this_id = $this->getId();
719  $thisObjId = $this->getObjId();
720 
721  $clone = $this;
722  include_once("./Modules/TestQuestionPool/classes/class.assQuestion.php");
724  $clone->id = -1;
725 
726  if ((int) $testObjId > 0) {
727  $clone->setObjId($testObjId);
728  }
729 
730  if ($title) {
731  $clone->setTitle($title);
732  }
733 
734  if ($author) {
735  $clone->setAuthor($author);
736  }
737  if ($owner) {
738  $clone->setOwner($owner);
739  }
740 
741  if ($for_test) {
742  $clone->saveToDb($original_id);
743  } else {
744  $clone->saveToDb();
745  }
746 
747  $clone->unitrepository->cloneUnits($this_id, $clone->getId());
748 
749  // copy question page content
750  $clone->copyPageOfQuestion($this_id);
751  // copy XHTML media objects
752  $clone->copyXHTMLMediaObjectsOfQuestion($this_id);
753  $clone->onDuplicate($thisObjId, $this_id, $clone->getObjId(), $clone->getId());
754 
755  return $clone->id;
756  }
757 
762  public function copyObject($target_questionpool_id, $title = "")
763  {
764  if ($this->id <= 0) {
765  // The question has not been saved. It cannot be duplicated
766  return;
767  }
768  // duplicate the question in database
769  $clone = $this;
770  include_once("./Modules/TestQuestionPool/classes/class.assQuestion.php");
772  $clone->id = -1;
773  $source_questionpool_id = $this->getObjId();
774  $clone->setObjId($target_questionpool_id);
775  if ($title) {
776  $clone->setTitle($title);
777  }
778  $clone->saveToDb();
779 
780  $clone->unitrepository->cloneUnits($original_id, $clone->getId());
781 
782  // copy question page content
783  $clone->copyPageOfQuestion($original_id);
784  // copy XHTML media objects
785  $clone->copyXHTMLMediaObjectsOfQuestion($original_id);
786 
787  $clone->onCopy($source_questionpool_id, $original_id, $clone->getObjId(), $clone->getId());
788 
789  return $clone->id;
790  }
791 
792  public function createNewOriginalFromThisDuplicate($targetParentId, $targetQuestionTitle = "")
793  {
794  if ($this->id <= 0) {
795  // The question has not been saved. It cannot be duplicated
796  return;
797  }
798 
799  include_once("./Modules/TestQuestionPool/classes/class.assQuestion.php");
800 
801  $sourceQuestionId = $this->id;
802  $sourceParentId = $this->getObjId();
803 
804  // duplicate the question in database
805  $clone = $this;
806  $clone->id = -1;
807 
808  $clone->setObjId($targetParentId);
809 
810  if ($targetQuestionTitle) {
811  $clone->setTitle($targetQuestionTitle);
812  }
813 
814  $clone->saveToDb();
815  // copy question page content
816  $clone->copyPageOfQuestion($sourceQuestionId);
817  // copy XHTML media objects
818  $clone->copyXHTMLMediaObjectsOfQuestion($sourceQuestionId);
819 
820  $clone->onCopy($sourceParentId, $sourceQuestionId, $clone->getObjId(), $clone->getId());
821 
822  return $clone->id;
823  }
824 
829  public function getMaximumPoints()
830  {
831  $points = 0;
832  foreach ($this->results as $result) {
833  $points += $result->getPoints();
834  }
835  return $points;
836  }
837 
846  public function calculateReachedPoints($active_id, $pass = null, $authorizedSolution = true, $returndetails = false)
847  {
848  if (is_null($pass)) {
849  $pass = $this->getSolutionMaxPass($active_id);
850  }
851  $solutions =&$this->getSolutionValues($active_id, $pass, $authorizedSolution);
852  $user_solution = array();
853  foreach ($solutions as $idx => $solution_value) {
854  if (preg_match("/^(\\\$v\\d+)$/", $solution_value["value1"], $matches)) {
855  $user_solution[$matches[1]] = $solution_value["value2"];
856  $varObj = $this->getVariable($solution_value["value1"]);
857  $varObj->setValue($solution_value["value2"]);
858  } elseif (preg_match("/^(\\\$r\\d+)$/", $solution_value["value1"], $matches)) {
859  if (!array_key_exists($matches[1], $user_solution)) {
860  $user_solution[$matches[1]] = array();
861  }
862  $user_solution[$matches[1]]["value"] = $solution_value["value2"];
863  } elseif (preg_match("/^(\\\$r\\d+)_unit$/", $solution_value["value1"], $matches)) {
864  if (!array_key_exists($matches[1], $user_solution)) {
865  $user_solution[$matches[1]] = array();
866  }
867  $user_solution[$matches[1]]["unit"] = $solution_value["value2"];
868  }
869  }
870  //vd($this->getResults());
871  $points = 0;
872  foreach ($this->getResults() as $result) {
873  //vd($user_solution[$result->getResult()]["value"]);
874  $points += $result->getReachedPoints($this->getVariables(), $this->getResults(), $user_solution[$result->getResult()]["value"], $user_solution[$result->getResult()]["unit"], $this->unitrepository->getUnits());
875  }
876 
877  return $points;
878  }
879 
881  {
882  $user_solution = $previewSession->getParticipantsSolution();
883 
884  $points = 0;
885  foreach ($this->getResults() as $result) {
886  $v = isset($user_solution[$result->getResult()]) ? $user_solution[$result->getResult()] : null;
887  $u = isset($user_solution[$result->getResult() . '_unit']) ? $user_solution[$result->getResult() . '_unit'] : null;
888 
889  $points += $result->getReachedPoints(
890  $this->getVariables(),
891  $this->getResults(),
892  $v,
893  $u,
894  $this->unitrepository->getUnits()
895  );
896  }
897 
898  $reachedPoints = $this->deductHintPointsFromReachedPoints($previewSession, $points);
899 
900  return $this->ensureNonNegativePoints($reachedPoints);
901  }
902 
903  protected function isValidSolutionResultValue($submittedValue)
904  {
905  $submittedValue = str_replace(',', '.', $submittedValue);
906 
907  if (is_numeric($submittedValue)) {
908  return true;
909  }
910 
911  if (preg_match('/^[-+]{0,1}\d+\/\d+$/', $submittedValue)) {
912  return true;
913  }
914 
915  return false;
916  }
917 
925  public function saveWorkingData($active_id, $pass = null, $authorized = true)
926  {
927  global $ilDB;
928 
929  if (is_null($pass)) {
930  include_once "./Modules/Test/classes/class.ilObjTest.php";
931  $pass = ilObjTest::_getPass($active_id);
932  }
933 
934  $entered_values = false;
935 
936  $this->getProcessLocker()->executeUserSolutionUpdateLockOperation(function () use (&$entered_values, $ilDB, $active_id, $pass, $authorized) {
937  $solutionSubmit = $this->getSolutionSubmit();
938  foreach ($solutionSubmit as $key => $value) {
939  $matches = null;
940  if (preg_match("/^result_(\\\$r\\d+)$/", $key, $matches)) {
941  if (strlen($value)) {
942  $entered_values = true;
943  }
944 
945  $queryResult = "SELECT solution_id FROM tst_solutions WHERE active_fi = %s AND pass = %s AND question_fi = %s AND authorized = %s AND " . $ilDB->like('value1', 'clob', $matches[1]);
946 
947  if ($this->getStep() !== null) {
948  $queryResult .= " AND step = " . $ilDB->quote((int) $this->getStep(), 'integer') . " ";
949  }
950 
951  $result = $ilDB->queryF(
952  $queryResult,
953  array('integer', 'integer', 'integer', 'integer'),
954  array($active_id, $pass, $this->getId(), (int) $authorized)
955  );
956  if ($result->numRows()) {
957  while ($row = $ilDB->fetchAssoc($result)) {
958  $ilDB->manipulateF(
959  "DELETE FROM tst_solutions WHERE solution_id = %s AND authorized = %s",
960  array('integer', 'integer'),
961  array($row['solution_id'], (int) $authorized)
962  );
963  }
964  }
965 
966  $this->saveCurrentSolution($active_id, $pass, $matches[1], str_replace(",", ".", $value), $authorized);
967  } elseif (preg_match("/^result_(\\\$r\\d+)_unit$/", $key, $matches)) {
968  $queryResultUnit = "SELECT solution_id FROM tst_solutions WHERE active_fi = %s AND pass = %s AND question_fi = %s AND authorized = %s AND " . $ilDB->like('value1', 'clob', $matches[1] . "_unit");
969 
970  if ($this->getStep() !== null) {
971  $queryResultUnit .= " AND step = " . $ilDB->quote((int) $this->getStep(), 'integer') . " ";
972  }
973 
974  $result = $ilDB->queryF(
975  $queryResultUnit,
976  array('integer', 'integer', 'integer', 'integer'),
977  array($active_id, $pass, $this->getId(), (int) $authorized)
978  );
979  if ($result->numRows()) {
980  while ($row = $ilDB->fetchAssoc($result)) {
981  $ilDB->manipulateF(
982  "DELETE FROM tst_solutions WHERE solution_id = %s AND authorized = %s",
983  array('integer', 'integer'),
984  array($row['solution_id'], (int) $authorized)
985  );
986  }
987  }
988 
989  $this->saveCurrentSolution($active_id, $pass, $matches[1] . "_unit", $value, $authorized);
990  }
991  }
992  });
993 
994  if ($entered_values) {
995  include_once("./Modules/Test/classes/class.ilObjAssessmentFolder.php");
997  assQuestion::logAction($this->lng->txtlng("assessment", "log_user_entered_values", ilObjAssessmentFolder::_getLogLanguage()), $active_id, $this->getId());
998  }
999  } else {
1000  include_once("./Modules/Test/classes/class.ilObjAssessmentFolder.php");
1002  assQuestion::logAction($this->lng->txtlng("assessment", "log_user_not_entered_values", ilObjAssessmentFolder::_getLogLanguage()), $active_id, $this->getId());
1003  }
1004  }
1005 
1006  return true;
1007  }
1008 
1009  // fau: testNav - overridden function lookupForExistingSolutions (specific for formula question: don't lookup variables)
1016  public function lookupForExistingSolutions($activeId, $pass)
1017  {
1018  global $ilDB;
1019 
1020  $return = array(
1021  'authorized' => false,
1022  'intermediate' => false
1023  );
1024 
1025  $query = "
1026  SELECT authorized, COUNT(*) cnt
1027  FROM tst_solutions
1028  WHERE active_fi = " . $ilDB->quote($activeId, 'integer') . "
1029  AND question_fi = " . $ilDB->quote($this->getId(), 'integer') . "
1030  AND pass = " . $ilDB->quote($pass, 'integer') . "
1031  AND value1 like '\$r%'
1032  AND value2 is not null
1033  AND value2 <> ''
1034  ";
1035 
1036  if ($this->getStep() !== null) {
1037  $query .= " AND step = " . $ilDB->quote((int) $this->getStep(), 'integer') . " ";
1038  }
1039 
1040  $query .= "
1041  GROUP BY authorized
1042  ";
1043 
1044  $result = $ilDB->query($query);
1045 
1046  while ($row = $ilDB->fetchAssoc($result)) {
1047  if ($row['authorized']) {
1048  $return['authorized'] = $row['cnt'] > 0;
1049  } else {
1050  $return['intermediate'] = $row['cnt'] > 0;
1051  }
1052  }
1053  return $return;
1054  }
1055  // fau.
1056 
1057  // fau: testNav - Remove an existing solution (specific for formula question: don't delete variables)
1064  public function removeExistingSolutions($activeId, $pass)
1065  {
1066  global $ilDB;
1067 
1068  $query = "
1069  DELETE FROM tst_solutions
1070  WHERE active_fi = " . $ilDB->quote($activeId, 'integer') . "
1071  AND question_fi = " . $ilDB->quote($this->getId(), 'integer') . "
1072  AND pass = " . $ilDB->quote($pass, 'integer') . "
1073  AND value1 like '\$r%'
1074  ";
1075 
1076  if ($this->getStep() !== null) {
1077  $query .= " AND step = " . $ilDB->quote((int) $this->getStep(), 'integer') . " ";
1078  }
1079 
1080  return $ilDB->manipulate($query);
1081  }
1082  // fau.
1083 
1084  protected function savePreviewData(ilAssQuestionPreviewSession $previewSession)
1085  {
1086  $userSolution = $previewSession->getParticipantsSolution();
1087 
1088  foreach ($this->getSolutionSubmit() as $key => $val) {
1089  $matches = null;
1090 
1091  if (preg_match("/^result_(\\\$r\\d+)$/", $key, $matches)) {
1092  $userSolution[$matches[1]] = $val;
1093  } elseif (preg_match("/^result_(\\\$r\\d+)_unit$/", $key, $matches)) {
1094  $userSolution[$matches[1] . "_unit"] = $val;
1095  }
1096  }
1097 
1098  $previewSession->setParticipantsSolution($userSolution);
1099  }
1100 
1104  protected function reworkWorkingData($active_id, $pass, $obligationsAnswered, $authorized)
1105  {
1106  // nothing to rework!
1107  }
1108 
1113  public function getQuestionType()
1114  {
1115  return "assFormulaQuestion";
1116  }
1117 
1122  public function getAdditionalTableName()
1123  {
1124  return "";
1125  }
1126 
1131  public function getAnswerTableName()
1132  {
1133  return "";
1134  }
1135 
1141  public function deleteAnswers($question_id)
1142  {
1143  global $ilDB;
1144 
1145  $affectedRows = $ilDB->manipulateF(
1146  "DELETE FROM il_qpl_qst_fq_var WHERE question_fi = %s",
1147  array('integer'),
1148  array($question_id)
1149  );
1150 
1151  $affectedRows = $ilDB->manipulateF(
1152  "DELETE FROM il_qpl_qst_fq_res WHERE question_fi = %s",
1153  array('integer'),
1154  array($question_id)
1155  );
1156 
1157  $affectedRows = $ilDB->manipulateF(
1158  "DELETE FROM il_qpl_qst_fq_res_unit WHERE question_fi = %s",
1159  array('integer'),
1160  array($question_id)
1161  );
1162 
1163  $affectedRows = $ilDB->manipulateF(
1164  "DELETE FROM il_qpl_qst_fq_ucat WHERE question_fi = %s",
1165  array('integer'),
1166  array($question_id)
1167  );
1168 
1169  $affectedRows = $ilDB->manipulateF(
1170  "DELETE FROM il_qpl_qst_fq_unit WHERE question_fi = %s",
1171  array('integer'),
1172  array($question_id)
1173  );
1174  }
1175 
1180  public function getRTETextWithMediaObjects()
1181  {
1182  $text = parent::getRTETextWithMediaObjects();
1183  return $text;
1184  }
1185 
1189  public function setExportDetailsXLS($worksheet, $startrow, $active_id, $pass)
1190  {
1191  parent::setExportDetailsXLS($worksheet, $startrow, $active_id, $pass);
1192 
1193  $solution = $this->getSolutionValues($active_id, $pass);
1194 
1195  $i = 1;
1196  foreach ($solution as $solutionvalue) {
1197  $worksheet->setCell($startrow + $i, 0, $solutionvalue["value1"]);
1198  $worksheet->setBold($worksheet->getColumnCoord(0) . ($startrow + $i));
1199  if (strpos($solutionvalue["value1"], "_unit")) {
1200  $unit = $this->getUnitrepository()->getUnit($solutionvalue["value2"]);
1201  if (is_object($unit)) {
1202  $worksheet->setCell($startrow + $i, 1, $unit->getUnit());
1203  }
1204  } else {
1205  $worksheet->setCell($startrow + $i, 1, $solutionvalue["value2"]);
1206  }
1207  if (preg_match("/(\\\$v\\d+)/", $solutionvalue["value1"], $matches)) {
1208  $var = $this->getVariable($solutionvalue["value1"]);
1209  if (is_object($var) && (is_object($var->getUnit()))) {
1210  $worksheet->setCell($startrow + $i, 2, $var->getUnit()->getUnit());
1211  }
1212  }
1213  $i++;
1214  }
1215 
1216  return $startrow + $i + 1;
1217  }
1218 
1224  public function getBestSolution($solutions)
1225  {
1226  $user_solution = array();
1227 
1228  foreach ($solutions as $idx => $solution_value) {
1229  if (preg_match("/^(\\\$v\\d+)$/", $solution_value["value1"], $matches)) {
1230  $user_solution[$matches[1]] = $solution_value["value2"];
1231  $varObj = $this->getVariable($matches[1]);
1232  $varObj->setValue($solution_value["value2"]);
1233  } elseif (preg_match("/^(\\\$r\\d+)$/", $solution_value["value1"], $matches)) {
1234  if (!array_key_exists($matches[1], $user_solution)) {
1235  $user_solution[$matches[1]] = array();
1236  }
1237  $user_solution[$matches[1]]["value"] = $solution_value["value2"];
1238  } elseif (preg_match("/^(\\\$r\\d+)_unit$/", $solution_value["value1"], $matches)) {
1239  if (!array_key_exists($matches[1], $user_solution)) {
1240  $user_solution[$matches[1]] = array();
1241  }
1242  $user_solution[$matches[1]]["unit"] = $solution_value["value2"];
1243  }
1244  }
1245  foreach ($this->getResults() as $result) {
1246  $resVal = $result->calculateFormula($this->getVariables(), $this->getResults(), parent::getId(), false);
1247 
1248  if (is_object($result->getUnit())) {
1249  $user_solution[$result->getResult()]["unit"] = $result->getUnit()->getId();
1250  $user_solution[$result->getResult()]["value"] = $resVal;
1251  } elseif ($result->getUnit() == null) {
1252  $unit_factor = 1;
1253  // there is no fix result_unit, any "available unit" is accepted
1254 
1255  $available_units = $result->getAvailableResultUnits(parent::getId());
1256  $result_name = $result->getResult();
1257 
1258  if ($available_units[$result_name] != null) {
1259  $check_unit = in_array($user_solution[$result_name]['unit'], $available_units[$result_name]);
1260  }
1261 
1262  if ($check_unit == true) {
1263  //get unit-factor
1264  $unit_factor = assFormulaQuestionUnit::lookupUnitFactor($user_solution[$result_name]['unit']);
1265  }
1266 
1267  $user_solution[$result->getResult()]["value"] = round(ilMath::_div($resVal, $unit_factor), 55);
1268  }
1269  if ($result->getResultType() == assFormulaQuestionResult::RESULT_CO_FRAC
1270  || $result->getResultType() == assFormulaQuestionResult::RESULT_FRAC) {
1272  if (is_array($value)) {
1273  $user_solution[$result->getResult()]["value"] = $value[0];
1274  $user_solution[$result->getResult()]["frac_helper"] = $value[1];
1275  } else {
1276  $user_solution[$result->getResult()]["value"] = $value;
1277  $user_solution[$result->getResult()]["frac_helper"] = null;
1278  }
1279  } elseif ($result->getPrecision() > 0) {
1280  $user_solution[$result->getResult()]["value"] = round(
1281  $user_solution[$result->getResult()]["value"],
1282  $result->getPrecision()
1283  );
1284  } else {
1285  $user_solution[$result->getResult()]["value"] = round(
1286  $user_solution[$result->getResult()]["value"]
1287  );
1288  }
1289  }
1290  return $user_solution;
1291  }
1292 
1293  public function setId($id = -1)
1294  {
1295  parent::setId($id);
1296  $this->unitrepository->setConsumerId($this->getId());
1297  }
1298 
1302  public function __get($value)
1303  {
1304  switch ($value) {
1305  case "resultunits":
1306  return $this->resultunits;
1307  break;
1308  default:
1309  return parent::__get($value);
1310  break;
1311  }
1312  }
1313 
1318  {
1319  $this->unitrepository = $unitrepository;
1320  }
1321 
1325  public function getUnitrepository()
1326  {
1327  return $this->unitrepository;
1328  }
1329 
1333  protected function getSolutionSubmit()
1334  {
1335  $solutionSubmit = array();
1336  foreach ($_POST as $k => $v) {
1337  if (preg_match("/^result_(\\\$r\\d+)$/", $k)) {
1338  $solutionSubmit[$k] = $v;
1339  } elseif (preg_match("/^result_(\\\$r\\d+)_unit$/", $k)) {
1340  $solutionSubmit[$k] = $v;
1341  }
1342  }
1343  return $solutionSubmit;
1344  }
1345 
1346  public function validateSolutionSubmit()
1347  {
1348  foreach ($this->getSolutionSubmit() as $key => $value) {
1349  if (preg_match("/^result_(\\\$r\\d+)$/", $key)) {
1350  if (strlen($value) && !$this->isValidSolutionResultValue($value)) {
1351  ilUtil::sendFailure($this->lng->txt("err_no_numeric_value"), true);
1352  return false;
1353  }
1354  } elseif (preg_match("/^result_(\\\$r\\d+)_unit$/", $key)) {
1355  continue;
1356  }
1357  }
1358 
1359  return true;
1360  }
1361 
1370  public function getOperators($expression)
1371  {
1372  require_once "./Modules/TestQuestionPool/classes/class.ilOperatorsExpressionMapping.php";
1374  }
1375 
1380  public function getExpressionTypes()
1381  {
1382  return array(
1386  );
1387  }
1388 
1397  public function getUserQuestionResult($active_id, $pass)
1398  {
1400  global $ilDB;
1401  $result = new ilUserQuestionResult($this, $active_id, $pass);
1402 
1403  $maxStep = $this->lookupMaxStep($active_id, $pass);
1404 
1405  if ($maxStep !== null) {
1406  $data = $ilDB->queryF(
1407  "SELECT value1, value2 FROM tst_solutions WHERE active_fi = %s AND pass = %s AND question_fi = %s AND step = %s",
1408  array("integer", "integer", "integer",'integer'),
1409  array($active_id, $pass, $this->getId(), $maxStep)
1410  );
1411  } else {
1412  $data = $ilDB->queryF(
1413  "SELECT value1, value2 FROM tst_solutions WHERE active_fi = %s AND pass = %s AND question_fi = %s",
1414  array("integer", "integer", "integer"),
1415  array($active_id, $pass, $this->getId())
1416  );
1417  }
1418 
1419  while ($row = $ilDB->fetchAssoc($data)) {
1420  if (strstr($row["value1"], '$r') && $row["value2"] != null) {
1421  $result->addKeyValue(str_replace('$r', "", $row["value1"]), $row["value2"]);
1422  }
1423  }
1424 
1425  $points = $this->calculateReachedPoints($active_id, $pass);
1426  $max_points = $this->getMaximumPoints();
1427 
1428  $result->setReachedPercentage(($points/$max_points) * 100);
1429 
1430  return $result;
1431  }
1432 
1441  public function getAvailableAnswerOptions($index = null)
1442  {
1443  if ($index !== null) {
1444  return $this->getResult('$r' . ($index+1));
1445  } else {
1446  return $this->getResults();
1447  }
1448  }
1449 }
getAvailableAnswerOptions($index=null)
If index is null, the function returns an array with all anwser options Else it returns the specific ...
static logAction($logtext="", $active_id="", $question_id="")
Logs an action into the Test&Assessment log.
addResultUnits($result, $unit_ids)
getId()
Gets the id of the assQuestion object.
static prepareFormOutput($a_str, $a_strip=false)
prepares string output for html forms public
static _getOriginalId($question_id)
Returns the original id of a question.
$worksheet
setSuggestedSolution($solution_id="", $subquestion_index=0, $is_import=false)
Sets a suggested solution for the question.
Class iQuestionCondition.
static _getPass($active_id)
Retrieves the actual pass of a given user for a given test.
$result
$template
saveToDb($original_id="")
Saves a assFormulaQuestion object to a database public.
duplicate($for_test=true, $title="", $author="", $owner="", $testObjId=null)
Duplicates an assFormulaQuestion public.
substituteVariables(array $userdata, $graphicalOutput=false, $forsolution=false, $result_output=false)
Abstract basic class which is to be extended by the concrete assessment question type classes...
lookupForExistingSolutions($activeId, $pass)
Lookup if an authorized or intermediate solution exists.
getAdditionalTableName()
Returns the name of the additional question data table in the database.
setExportDetailsXLS($worksheet, $startrow, $active_id, $pass)
{}
ensureNonNegativePoints($points)
getSolutionValues($active_id, $pass=null, $authorized=true)
Loads solutions of a given user from the database an returns it.
Class ilUnitConfigurationRepository.
$userdata
Definition: demo.php:48
getSolutionMaxPass($active_id)
Returns the maximum pass a users question solution.
static _div($left_operand, $right_operand, $scale=50)
Class for single choice questions assFormulaQuestion is a class for single choice questions...
setEstimatedWorkingTime($hour=0, $min=0, $sec=0)
Sets the estimated working time of a question from given hour, minute and second. ...
getAnswerTableName()
Returns the name of the answer table in the database.
$index
Definition: metadata.php:60
getRTETextWithMediaObjects()
Collects all text in the question which could contain media objects which were created with the Rich ...
getUserQuestionResult($active_id, $pass)
Get the user solution for a question by active_id and the test pass.
setAdditionalContentEditingMode($additinalContentEditingMode)
setter for additional content editing mode for this question
static _replaceMediaObjectImageSrc($a_text, $a_direction=0, $nic=IL_INST_ID)
Replaces image source from mob image urls with the mob id or replaces mob id with the correct image s...
getOperators($expression)
Get all available operations for a specific question.
getObjId()
Get the object id of the container object.
__construct( $title="", $comment="", $author="", $owner=-1, $question="")
assFormulaQuestion constructor The constructor takes possible arguments an creates an instance of the...
static _getLogLanguage()
retrieve the log language for assessment logging
setAuthor($author="")
Sets the authors name of the assQuestion object.
static _enabledAssessmentLogging()
check wether assessment logging is enabled or not
Class ilUserQuestionResult.
saveCurrentSolution($active_id, $pass, $value1, $value2, $authorized=true, $tstamp=null)
static getImagePath($img, $module_path="", $mode="output", $offline=false)
get image path (for images located in a template directory)
getBestSolution($solutions)
Returns the best solution for a given pass of a participant.
deleteAnswers($question_id)
Deletes datasets from answers tables.
hasRequiredVariableSolutionValues(array $userSolution)
__get($value)
Object getter.
special template class to simplify handling of ITX/PEAR
saveWorkingData($active_id, $pass=null, $authorized=true)
Saves the learners input of the question to the database.
$text
Definition: errorreport.php:18
loadFromDb($question_id)
Loads a assFormulaQuestion object from a database.
getQuestion()
Gets the question string of the question object.
calculateReachedPoints($active_id, $pass=null, $authorizedSolution=true, $returndetails=false)
Returns the points, a learner has reached answering the question The points are calculated from the g...
isValidSolutionResultValue($submittedValue)
$query
canUseAdvancedRating($result)
Check if advanced rating can be used for a result.
createNewOriginalFromThisDuplicate($targetParentId, $targetQuestionTitle="")
Create styles array
The data for the language used.
copyObject($target_questionpool_id, $title="")
Copies an assFormulaQuestion object public.
static sendFailure($a_info="", $a_keep=false)
Send Failure Message to Screen.
deductHintPointsFromReachedPoints(ilAssQuestionPreviewSession $previewSession, $reachedPoints)
setPoints($a_points)
Sets the maximum available points for the question.
saveQuestionDataToDb($original_id="")
getQuestionType()
Returns the question type of the question.
setQuestion($question="")
Sets the question string of the question object.
isComplete()
Returns true, if the question is complete for use.
global $ilDB
setOriginalId($original_id)
calculateReachedPointsFromPreviewSession(ilAssQuestionPreviewSession $previewSession)
$i
Definition: disco.tpl.php:19
hasResultUnit($result, $unit_id)
getExpressionTypes()
Get all available expression types for a specific question.
removeExistingSolutions($activeId, $pass)
Remove an existing solution without removing the variables.
setTitle($title="")
Sets the title string of the assQuestion object.
reworkWorkingData($active_id, $pass, $obligationsAnswered, $authorized)
{}
setObjId($obj_id=0)
Set the object id of the container object.
setUnitrepository($unitrepository)
$key
Definition: croninfo.php:18
setComment($comment="")
Sets the comment string of the assQuestion object.
$_POST["username"]
static convertDecimalToCoprimeFraction($decimal_value, $tolerance=1.e-9)
getMaximumPoints()
Returns the maximum points, a learner can reach answering the question.
setOwner($owner="")
Sets the creator/owner ID of the assQuestion object.
savePreviewData(ilAssQuestionPreviewSession $previewSession)