ILIAS  release_6 Revision v6.24-5-g0c8bfefb3b8
All Data Structures Namespaces Files Functions Variables Modules Pages
class.assImagemapQuestion.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 require_once './Modules/TestQuestionPool/classes/class.assQuestion.php';
5 require_once './Modules/Test/classes/inc.AssessmentConstants.php';
6 require_once './Modules/TestQuestionPool/interfaces/interface.ilObjQuestionScoringAdjustable.php';
7 require_once './Modules/TestQuestionPool/interfaces/interface.ilObjAnswerScoringAdjustable.php';
8 require_once './Modules/TestQuestionPool/interfaces/interface.iQuestionCondition.php';
9 require_once './Modules/TestQuestionPool/classes/class.ilUserQuestionResult.php';
10 
25 {
26  // hey: prevPassSolutions - wtf is imagemap ^^
27  public $currentSolution = array();
28  // hey.
29 
30  const MODE_SINGLE_CHOICE = 0;
32 
34  public $answers;
35 
38 
41 
43  public $coords;
44 
46  protected $is_multiple_choice = false;
47 
62  public function __construct(
63  $title = "",
64  $comment = "",
65  $author = "",
66  $owner = -1,
67  $question = "",
68  $image_filename = ""
69  ) {
71  $this->image_filename = $image_filename;
72  $this->answers = array();
73  $this->coords = array();
74  }
75 
82  {
83  $this->is_multiple_choice = $is_multiple_choice;
84  }
85 
91  public function getIsMultipleChoice()
92  {
94  }
95 
102  public function isComplete()
103  {
104  if (strlen($this->title)
105  && ($this->author)
106  && ($this->question)
107  && ($this->image_filename)
108  && (count($this->answers))
109  && ($this->getMaximumPoints() > 0)
110  ) {
111  return true;
112  }
113  return false;
114  }
115 
125  public function saveToDb($original_id = "")
126  {
130  parent::saveToDb($original_id);
131  }
132 
133  public function saveAnswerSpecificDataToDb()
134  {
135  global $DIC;
136  $ilDB = $DIC['ilDB'];
137  $ilDB->manipulateF(
138  "DELETE FROM qpl_a_imagemap WHERE question_fi = %s",
139  array( "integer" ),
140  array( $this->getId() )
141  );
142 
143  // Anworten wegschreiben
144  foreach ($this->answers as $key => $value) {
145  $answer_obj = $this->answers[$key];
146  $answer_obj->setOrder($key);
147  $next_id = $ilDB->nextId('qpl_a_imagemap');
148  $ilDB->manipulateF(
149  "INSERT INTO qpl_a_imagemap (answer_id, question_fi, answertext, points, aorder, coords, area, points_unchecked) VALUES (%s, %s, %s, %s, %s, %s, %s, %s)",
150  array( "integer", "integer", "text", "float", "integer", "text", "text", "float" ),
151  array( $next_id, $this->id, $answer_obj->getAnswertext(
152  ), $answer_obj->getPoints(), $answer_obj->getOrder(
153  ), $answer_obj->getCoords(), $answer_obj->getArea(
154  ), $answer_obj->getPointsUnchecked() )
155  );
156  }
157  }
158 
160  {
161  global $DIC;
162  $ilDB = $DIC['ilDB'];
163 
164  $ilDB->manipulateF(
165  "DELETE FROM " . $this->getAdditionalTableName() . " WHERE question_fi = %s",
166  array( "integer" ),
167  array( $this->getId() )
168  );
169 
170  $ilDB->manipulateF(
171  "INSERT INTO " . $this->getAdditionalTableName(
172  ) . " (question_fi, image_file, is_multiple_choice) VALUES (%s, %s, %s)",
173  array( "integer", "text", 'integer' ),
174  array(
175  $this->getId(),
176  $this->image_filename,
177  (int) $this->is_multiple_choice
178  )
179  );
180  }
181 
187  public function duplicate($for_test = true, $title = "", $author = "", $owner = "", $testObjId = null)
188  {
189  if ($this->id <= 0) {
190  // The question has not been saved. It cannot be duplicated
191  return;
192  }
193  // duplicate the question in database
194  $this_id = $this->getId();
195  $thisObjId = $this->getObjId();
196 
197  $clone = $this;
198  include_once("./Modules/TestQuestionPool/classes/class.assQuestion.php");
200  $clone->id = -1;
201 
202  if ((int) $testObjId > 0) {
203  $clone->setObjId($testObjId);
204  }
205 
206  if ($title) {
207  $clone->setTitle($title);
208  }
209  if ($author) {
210  $clone->setAuthor($author);
211  }
212  if ($owner) {
213  $clone->setOwner($owner);
214  }
215  if ($for_test) {
216  $clone->saveToDb($original_id);
217  } else {
218  $clone->saveToDb();
219  }
220 
221  // copy question page content
222  $clone->copyPageOfQuestion($this_id);
223  // copy XHTML media objects
224  $clone->copyXHTMLMediaObjectsOfQuestion($this_id);
225  // duplicate the image
226  $clone->duplicateImage($this_id, $thisObjId);
227 
228  $clone->onDuplicate($thisObjId, $this_id, $clone->getObjId(), $clone->getId());
229 
230  return $clone->id;
231  }
232 
240  public function copyObject($target_questionpool_id, $title = "")
241  {
242  if ($this->id <= 0) {
243  // The question has not been saved. It cannot be duplicated
244  return;
245  }
246  // duplicate the question in database
247  $clone = $this;
248  include_once("./Modules/TestQuestionPool/classes/class.assQuestion.php");
250  $clone->id = -1;
251  $source_questionpool_id = $this->getObjId();
252  $clone->setObjId($target_questionpool_id);
253  if ($title) {
254  $clone->setTitle($title);
255  }
256  $clone->saveToDb();
257 
258  // copy question page content
259  $clone->copyPageOfQuestion($original_id);
260  // copy XHTML media objects
261  $clone->copyXHTMLMediaObjectsOfQuestion($original_id);
262  // duplicate the image
263  $clone->copyImage($original_id, $source_questionpool_id);
264 
265  $clone->onCopy($source_questionpool_id, $original_id, $clone->getObjId(), $clone->getId());
266 
267  return $clone->id;
268  }
269 
270  public function createNewOriginalFromThisDuplicate($targetParentId, $targetQuestionTitle = "")
271  {
272  if ($this->id <= 0) {
273  // The question has not been saved. It cannot be duplicated
274  return;
275  }
276 
277  include_once("./Modules/TestQuestionPool/classes/class.assQuestion.php");
278 
279  $sourceQuestionId = $this->id;
280  $sourceParentId = $this->getObjId();
281 
282  // duplicate the question in database
283  $clone = $this;
284  $clone->id = -1;
285 
286  $clone->setObjId($targetParentId);
287 
288  if ($targetQuestionTitle) {
289  $clone->setTitle($targetQuestionTitle);
290  }
291 
292  $clone->saveToDb();
293  // copy question page content
294  $clone->copyPageOfQuestion($sourceQuestionId);
295  // copy XHTML media objects
296  $clone->copyXHTMLMediaObjectsOfQuestion($sourceQuestionId);
297  // duplicate the image
298  $clone->copyImage($sourceQuestionId, $sourceParentId);
299 
300  $clone->onCopy($sourceParentId, $sourceQuestionId, $clone->getObjId(), $clone->getId());
301 
302  return $clone->id;
303  }
304 
305  public function duplicateImage($question_id, $objectId = null)
306  {
307  global $DIC;
308  $ilLog = $DIC['ilLog'];
309 
310  $imagepath = $this->getImagePath();
311  $imagepath_original = str_replace("/$this->id/images", "/$question_id/images", $imagepath);
312 
313  if ((int) $objectId > 0) {
314  $imagepath_original = str_replace("/$this->obj_id/", "/$objectId/", $imagepath_original);
315  }
316 
317  if (!file_exists($imagepath)) {
318  ilUtil::makeDirParents($imagepath);
319  }
320  $filename = $this->getImageFilename();
321 
322  // #18755
323  if (!file_exists($imagepath_original . $filename)) {
324  $ilLog->write("Could not find an image map file when trying to duplicate image: " . $imagepath_original . $filename);
325  $imagepath_original = str_replace("/$this->obj_id/", "/$objectId/", $imagepath_original);
326  $ilLog->write("Using fallback source directory:" . $imagepath_original);
327  }
328 
329  if (!file_exists($imagepath_original . $filename) || !copy($imagepath_original . $filename, $imagepath . $filename)) {
330  $ilLog->write("Could not duplicate image for image map question: " . $imagepath_original . $filename);
331  }
332  }
333 
334  public function copyImage($question_id, $source_questionpool)
335  {
336  $imagepath = $this->getImagePath();
337  $imagepath_original = str_replace("/$this->id/images", "/$question_id/images", $imagepath);
338  $imagepath_original = str_replace("/$this->obj_id/", "/$source_questionpool/", $imagepath_original);
339  if (!file_exists($imagepath)) {
340  ilUtil::makeDirParents($imagepath);
341  }
342  $filename = $this->getImageFilename();
343  if (!copy($imagepath_original . $filename, $imagepath . $filename)) {
344  print "image could not be copied!!!! ";
345  }
346  }
347 
357  public function loadFromDb($question_id)
358  {
359  global $DIC;
360  $ilDB = $DIC['ilDB'];
361 
362  $result = $ilDB->queryF(
363  "SELECT qpl_questions.*, " . $this->getAdditionalTableName() . ".* FROM qpl_questions LEFT JOIN " . $this->getAdditionalTableName() . " ON " . $this->getAdditionalTableName() . ".question_fi = qpl_questions.question_id WHERE qpl_questions.question_id = %s",
364  array("integer"),
365  array($question_id)
366  );
367  if ($result->numRows() == 1) {
368  $data = $ilDB->fetchAssoc($result);
369  $this->setId($question_id);
370  $this->setObjId($data["obj_fi"]);
371  $this->setTitle($data["title"]);
372  $this->setComment($data["description"]);
373  $this->setOriginalId($data["original_id"]);
374  $this->setNrOfTries($data['nr_of_tries']);
375  $this->setAuthor($data["author"]);
376  $this->setPoints($data["points"]);
377  $this->setOwner($data["owner"]);
378  $this->setIsMultipleChoice($data["is_multiple_choice"] == self::MODE_MULTIPLE_CHOICE);
379  include_once("./Services/RTE/classes/class.ilRTE.php");
380  $this->setQuestion(ilRTE::_replaceMediaObjectImageSrc($data["question_text"], 1));
381  $this->setImageFilename($data["image_file"]);
382  $this->setEstimatedWorkingTime(substr($data["working_time"], 0, 2), substr($data["working_time"], 3, 2), substr($data["working_time"], 6, 2));
383 
384  try {
388  }
389 
390  try {
391  $this->setAdditionalContentEditingMode($data['add_cont_edit_mode']);
392  } catch (ilTestQuestionPoolException $e) {
393  }
394 
395  $result = $ilDB->queryF(
396  "SELECT * FROM qpl_a_imagemap WHERE question_fi = %s ORDER BY aorder ASC",
397  array("integer"),
398  array($question_id)
399  );
400  include_once "./Modules/TestQuestionPool/classes/class.assAnswerImagemap.php";
401  if ($result->numRows() > 0) {
402  while ($data = $ilDB->fetchAssoc($result)) {
403  array_push($this->answers, new ASS_AnswerImagemap($data["answertext"], $data["points"], $data["aorder"], $data["coords"], $data["area"], $data['question_fi'], $data['points_unchecked']));
404  }
405  }
406  }
407  parent::loadFromDb($question_id);
408  }
409 
416  public function uploadImagemap(array $shapes)
417  {
418  $added = 0;
419 
420  if (count($shapes) > 0) {
421  foreach ($shapes as $shape) {
422  $this->addAnswer($shape->getAnswertext(), 0.0, count($this->answers), $shape->getCoords(), $shape->getArea());
423  $added++;
424  }
425  }
426 
427  return $added;
428  }
429 
430  public function getImageFilename()
431  {
432  return $this->image_filename;
433  }
434 
442  public function setImageFilename($image_filename, $image_tempfilename = "")
443  {
444  if (!empty($image_filename)) {
445  $image_filename = str_replace(" ", "_", $image_filename);
446  $this->image_filename = $image_filename;
447  }
448  if (!empty($image_tempfilename)) {
449  $imagepath = $this->getImagePath();
450  if (!file_exists($imagepath)) {
451  ilUtil::makeDirParents($imagepath);
452  }
453  if (!ilUtil::moveUploadedFile($image_tempfilename, $image_filename, $imagepath . $image_filename)) {
454  $this->ilias->raiseError("The image could not be uploaded!", $this->ilias->error_obj->MESSAGE);
455  }
456  global $DIC;
457  $ilLog = $DIC['ilLog'];
458  $ilLog->write("gespeichert: " . $imagepath . $image_filename);
459  }
460  }
461 
471  public function get_imagemap_contents($href = "#")
472  {
473  $imagemap_contents = "<map name=\"" . $this->title . "\"> ";
474  for ($i = 0; $i < count($this->answers); $i++) {
475  $imagemap_contents .= "<area alt=\"" . $this->answers[$i]->getAnswertext() . "\" ";
476  $imagemap_contents .= "shape=\"" . $this->answers[$i]->getArea() . "\" ";
477  $imagemap_contents .= "coords=\"" . $this->answers[$i]->getCoords() . "\" ";
478  $imagemap_contents .= "href=\"$href&selimage=" . $this->answers[$i]->getOrder() . "\" /> ";
479  }
480  $imagemap_contents .= "</map>";
481  return $imagemap_contents;
482  }
483 
498  public function addAnswer(
499  $answertext = "",
500  $points = 0.0,
501  $order = 0,
502  $coords = "",
503  $area = "",
504  $points_unchecked = 0.0
505  ) {
506  include_once "./Modules/TestQuestionPool/classes/class.assAnswerImagemap.php";
507  if (array_key_exists($order, $this->answers)) {
508  // Insert answer
509  $answer = new ASS_AnswerImagemap($answertext, $points, $order, $coords, $area, -1, $points_unchecked);
510  for ($i = count($this->answers) - 1; $i >= $order; $i--) {
511  $this->answers[$i + 1] = $this->answers[$i];
512  $this->answers[$i + 1]->setOrder($i + 1);
513  }
514  $this->answers[$order] = $answer;
515  } else {
516  // Append answer
517  $answer = new ASS_AnswerImagemap($answertext, $points, count($this->answers), $coords, $area, -1, $points_unchecked);
518  array_push($this->answers, $answer);
519  }
520  }
521 
531  public function getAnswerCount()
532  {
533  return count($this->answers);
534  }
535 
547  public function getAnswer($index = 0)
548  {
549  if ($index < 0) {
550  return null;
551  }
552  if (count($this->answers) < 1) {
553  return null;
554  }
555  if ($index >= count($this->answers)) {
556  return null;
557  }
558  return $this->answers[$index];
559  }
560 
570  public function &getAnswers()
571  {
572  return $this->answers;
573  }
574 
585  public function deleteArea($index = 0)
586  {
587  if ($index < 0) {
588  return;
589  }
590  if (count($this->answers) < 1) {
591  return;
592  }
593  if ($index >= count($this->answers)) {
594  return;
595  }
596  unset($this->answers[$index]);
597  $this->answers = array_values($this->answers);
598  for ($i = 0; $i < count($this->answers); $i++) {
599  if ($this->answers[$i]->getOrder() > $index) {
600  $this->answers[$i]->setOrder($i);
601  }
602  }
603  }
604 
613  public function flushAnswers()
614  {
615  $this->answers = array();
616  }
617 
626  public function getMaximumPoints()
627  {
628  $points = 0;
629  foreach ($this->answers as $key => $value) {
630  if ($this->is_multiple_choice) {
631  if ($value->getPoints() > $value->getPointsUnchecked()) {
632  $points += $value->getPoints();
633  } else {
634  $points += $value->getPointsUnchecked();
635  }
636  } else {
637  if ($value->getPoints() > $points) {
638  $points = $value->getPoints();
639  }
640  }
641  }
642  return $points;
643  }
644 
655  public function calculateReachedPoints($active_id, $pass = null, $authorizedSolution = true, $returndetails = false)
656  {
657  if ($returndetails) {
658  throw new ilTestException('return details not implemented for ' . __METHOD__);
659  }
660 
661  global $DIC;
662  $ilDB = $DIC['ilDB'];
663 
664  $found_values = array();
665  if (is_null($pass)) {
666  $pass = $this->getSolutionMaxPass($active_id);
667  }
668  $result = $this->getCurrentSolutionResultSet($active_id, $pass, $authorizedSolution);
669  while ($data = $ilDB->fetchAssoc($result)) {
670  if (strcmp($data["value1"], "") != 0) {
671  array_push($found_values, $data["value1"]);
672  }
673  }
674 
675  $points = $this->calculateReachedPointsForSolution($found_values);
676 
677  return $points;
678  }
679 
681  {
682  $solutionData = $previewSession->getParticipantsSolution();
683 
684  $reachedPoints = $this->calculateReachedPointsForSolution(is_array($solutionData) ? array_values($solutionData) : array());
685  $reachedPoints = $this->deductHintPointsFromReachedPoints($previewSession, $reachedPoints);
686 
687  return $this->ensureNonNegativePoints($reachedPoints);
688  }
689 
690  public function isAutosaveable()
691  {
692  return false; // #15217
693  }
694 
703  public function saveWorkingData($active_id, $pass = null, $authorized = true)
704  {
705  global $DIC;
706  $ilDB = $DIC['ilDB'];
707 
708  if (is_null($pass)) {
709  include_once "./Modules/Test/classes/class.ilObjTest.php";
710  $pass = ilObjTest::_getPass($active_id);
711  }
712 
713  $solutionSelectionChanged = false;
714 
715  $this->getProcessLocker()->executeUserSolutionUpdateLockOperation(function () use (&$solutionSelectionChanged, $ilDB, $active_id, $pass, $authorized) {
716  if ($authorized) {
717  // remove the dummy record of the intermediate solution
718  $this->deleteDummySolutionRecord($active_id, $pass);
719 
720  // delete the authorized solution and make the intermediate solution authorized (keeping timestamps)
721  $this->removeCurrentSolution($active_id, $pass, true);
722  $this->updateCurrentSolutionsAuthorization($active_id, $pass, true, true);
723 
724  $solutionSelectionChanged = true;
725  } else {
727  $active_id,
728  $pass,
729  $this->is_multiple_choice
730  );
731 
732  if ($this->isReuseSolutionSelectionRequest()) {
733  $selection = $this->getReuseSolutionSelectionParameter();
734 
735  foreach ($selection as $selectedIndex) {
736  $this->saveCurrentSolution($active_id, $pass, (int) $selectedIndex, null, $authorized);
737  $solutionSelectionChanged = true;
738  }
739  } elseif ($this->isRemoveSolutionSelectionRequest()) {
740  $selection = $this->getRemoveSolutionSelectionParameter();
741 
742  $this->deleteSolutionRecordByValues($active_id, $pass, $authorized, array(
743  'value1' => (int) $selection
744  ));
745 
746  $solutionSelectionChanged = true;
747  } elseif ($this->isAddSolutionSelectionRequest()) {
748  $selection = $this->getAddSolutionSelectionParameter();
749 
750  if ($this->is_multiple_choice) {
751  $this->deleteSolutionRecordByValues($active_id, $pass, $authorized, array(
752  'value1' => (int) $_GET['selImage']
753  ));
754  } else {
755  $this->removeCurrentSolution($active_id, $pass, $authorized);
756  }
757 
758  $this->saveCurrentSolution($active_id, $pass, $_GET['selImage'], null, $authorized);
759 
760  $solutionSelectionChanged = true;
761  }
762  }
763  });
764 
765  require_once 'Modules/Test/classes/class.ilObjAssessmentFolder.php';
767  if ($solutionSelectionChanged) {
768  assQuestion::logAction($this->lng->txtlng("assessment", "log_user_entered_values", ilObjAssessmentFolder::_getLogLanguage()), $active_id, $this->getId());
769  } else {
770  assQuestion::logAction($this->lng->txtlng("assessment", "log_user_not_entered_values", ilObjAssessmentFolder::_getLogLanguage()), $active_id, $this->getId());
771  }
772  }
773 
774  return true;
775  }
776 
777  protected function savePreviewData(ilAssQuestionPreviewSession $previewSession)
778  {
779  $solution = $previewSession->getParticipantsSolution();
780 
781  if ($this->is_multiple_choice && strlen($_GET['remImage'])) {
782  unset($solution[(int) $_GET['remImage']]);
783  }
784 
785  if (strlen($_GET['selImage'])) {
786  if (!$this->is_multiple_choice) {
787  $solution = array();
788  }
789 
790  $solution[(int) $_GET['selImage']] = (int) $_GET['selImage'];
791  }
792 
793  $previewSession->setParticipantsSolution($solution);
794  }
795 
796  public function syncWithOriginal()
797  {
798  if ($this->getOriginalId()) {
799  parent::syncWithOriginal();
800  }
801  }
802 
811  public function getQuestionType()
812  {
813  return "assImagemapQuestion";
814  }
815 
824  public function getAdditionalTableName()
825  {
826  return "qpl_qst_imagemap";
827  }
828 
837  public function getAnswerTableName()
838  {
839  return "qpl_a_imagemap";
840  }
841 
846  public function getRTETextWithMediaObjects()
847  {
848  $text = parent::getRTETextWithMediaObjects();
849  foreach ($this->answers as $index => $answer) {
850  $text .= $this->feedbackOBJ->getSpecificAnswerFeedbackContent($this->getId(), 0, $index);
851  }
852  return $text;
853  }
854 
858  public function setExportDetailsXLS($worksheet, $startrow, $active_id, $pass)
859  {
860  parent::setExportDetailsXLS($worksheet, $startrow, $active_id, $pass);
861 
862  $solution = $this->getSolutionValues($active_id, $pass);
863 
864  $i = 1;
865  foreach ($this->getAnswers() as $id => $answer) {
866  $worksheet->setCell($startrow + $i, 0, $answer->getArea() . ": " . $answer->getCoords());
867  $worksheet->setBold($worksheet->getColumnCoord(0) . ($startrow + $i));
868 
869  $cellValue = 0;
870  foreach ($solution as $solIndex => $sol) {
871  if ($sol['value1'] == $id) {
872  $cellValue = 1;
873  break;
874  }
875  }
876 
877  $worksheet->setCell($startrow + $i, 1, $cellValue);
878 
879  $i++;
880  }
881 
882  return $startrow + $i + 1;
883  }
884 
888  public function deleteImage()
889  {
890  $file = $this->getImagePath() . $this->getImageFilename();
891  @unlink($file);
892  $this->flushAnswers();
893  $this->image_filename = "";
894  }
895 
899  public function toJSON()
900  {
901  include_once("./Services/RTE/classes/class.ilRTE.php");
902  $result = array();
903  $result['id'] = (int) $this->getId();
904  $result['type'] = (string) $this->getQuestionType();
905  $result['title'] = (string) $this->getTitle();
906  $result['question'] = $this->formatSAQuestion($this->getQuestion());
907  $result['nr_of_tries'] = (int) $this->getNrOfTries();
908  $result['shuffle'] = (bool) $this->getShuffle();
909  $result['is_multiple'] = (bool) $this->getIsMultipleChoice();
910  $result['feedback'] = array(
911  'onenotcorrect' => $this->formatSAQuestion($this->feedbackOBJ->getGenericFeedbackTestPresentation($this->getId(), false)),
912  'allcorrect' => $this->formatSAQuestion($this->feedbackOBJ->getGenericFeedbackTestPresentation($this->getId(), true))
913  );
914  $result['image'] = (string) $this->getImagePathWeb() . $this->getImageFilename();
915 
916  $answers = array();
917  $order = 0;
918  foreach ($this->getAnswers() as $key => $answer_obj) {
919  array_push($answers, array(
920  "answertext" => (string) $answer_obj->getAnswertext(),
921  "points" => (float) $answer_obj->getPoints(),
922  "points_unchecked" => (float) $answer_obj->getPointsUnchecked(),
923  "order" => (int) $order,
924  "coords" => $answer_obj->getCoords(),
925  "state" => $answer_obj->getState(),
926  "area" => $answer_obj->getArea(),
927  "feedback" => $this->formatSAQuestion(
928  $this->feedbackOBJ->getSpecificAnswerFeedbackExportPresentation($this->getId(), 0, $key)
929  )
930  ));
931  $order++;
932  }
933  $result['answers'] = $answers;
934 
935  $mobs = ilObjMediaObject::_getMobsOfObject("qpl:html", $this->getId());
936  $result['mobs'] = $mobs;
937 
938  return json_encode($result);
939  }
940 
945  protected function calculateReachedPointsForSolution($found_values)
946  {
947  $points = 0;
948  if (count($found_values) > 0) {
949  foreach ($this->answers as $key => $answer) {
950  if (in_array($key, $found_values)) {
951  $points += $answer->getPoints();
952  } elseif ($this->getIsMultipleChoice()) {
953  $points += $answer->getPointsUnchecked();
954  }
955  }
956  return $points;
957  }
958  return $points;
959  }
960 
969  public function getOperators($expression)
970  {
971  require_once "./Modules/TestQuestionPool/classes/class.ilOperatorsExpressionMapping.php";
973  }
974 
979  public function getExpressionTypes()
980  {
981  return array(
986  );
987  }
988 
997  public function getUserQuestionResult($active_id, $pass)
998  {
1000  global $DIC;
1001  $ilDB = $DIC['ilDB'];
1002  $result = new ilUserQuestionResult($this, $active_id, $pass);
1003 
1004  $maxStep = $this->lookupMaxStep($active_id, $pass);
1005 
1006  if ($maxStep !== null) {
1007  $data = $ilDB->queryF(
1008  "SELECT value1+1 as value1 FROM tst_solutions WHERE active_fi = %s AND pass = %s AND question_fi = %s AND step = %s",
1009  array("integer", "integer", "integer", "integer"),
1010  array($active_id, $pass, $this->getId(), $maxStep)
1011  );
1012  } else {
1013  $data = $ilDB->queryF(
1014  "SELECT value1+1 as value1 FROM tst_solutions WHERE active_fi = %s AND pass = %s AND question_fi = %s AND step IS NULL",
1015  array("integer", "integer", "integer"),
1016  array($active_id, $pass, $this->getId())
1017  );
1018  }
1019 
1020  while ($row = $ilDB->fetchAssoc($data)) {
1021  $result->addKeyValue($row["value1"], $row["value1"]);
1022  }
1023 
1024  $points = $this->calculateReachedPoints($active_id, $pass);
1025  $max_points = $this->getMaximumPoints();
1026 
1027  $result->setReachedPercentage(($points / $max_points) * 100);
1028 
1029  return $result;
1030  }
1031 
1040  public function getAvailableAnswerOptions($index = null)
1041  {
1042  if ($index !== null) {
1043  return $this->getAnswer($index);
1044  } else {
1045  return $this->getAnswers();
1046  }
1047  }
1048 
1049  // hey: prevPassSolutions - wtf is imagemap ^^
1050  public function getTestOutputSolutions($activeId, $pass)
1051  {
1052  $solution = parent::getTestOutputSolutions($activeId, $pass);
1053 
1054  $this->currentSolution = array();
1055  foreach ($solution as $record) {
1056  $this->currentSolution[] = $record['value1'];
1057  }
1058 
1059  return $solution;
1060  }
1062  {
1063  if (!$this->isAddSolutionSelectionRequest()) {
1064  return null;
1065  }
1066 
1067  return $_GET["selImage"];
1068  }
1069  protected function isAddSolutionSelectionRequest()
1070  {
1071  if (!isset($_GET["selImage"])) {
1072  return false;
1073  }
1074 
1075  if (!strlen($_GET["selImage"])) {
1076  return false;
1077  }
1078 
1079  return true;
1080  }
1082  {
1083  if (!$this->isRemoveSolutionSelectionRequest()) {
1084  return null;
1085  }
1086 
1087  return $_GET["remImage"];
1088  }
1090  {
1091  if (!$this->is_multiple_choice) {
1092  return false;
1093  }
1094 
1095  if (!isset($_GET["remImage"])) {
1096  return false;
1097  }
1098 
1099  if (!strlen($_GET["remImage"])) {
1100  return false;
1101  }
1102 
1103  return true;
1104  }
1106  {
1107  if (!$this->isReuseSolutionSelectionRequest()) {
1108  return null;
1109  }
1110 
1111  return assQuestion::explodeKeyValues($_GET["reuseSelection"]);
1112  }
1113  protected function isReuseSolutionSelectionRequest()
1114  {
1115  if (!$this->getTestPresentationConfig()->isPreviousPassSolutionReuseAllowed()) {
1116  return false;
1117  }
1118 
1119  if (!isset($_GET["reuseSelection"])) {
1120  return false;
1121  }
1122 
1123  if (!strlen($_GET["reuseSelection"])) {
1124  return false;
1125  }
1126 
1127  if (!preg_match('/\d(,\d)*/', $_GET["reuseSelection"])) {
1128  return false;
1129  }
1130 
1131  return true;
1132  }
1133  // hey.
1134 }
static makeDirParents($a_dir)
Create a new directory and all parent directories.
static logAction($logtext="", $active_id="", $question_id="")
Logs an action into the Test&Assessment log.
getId()
Gets the id of the assQuestion object.
static _getMobsOfObject($a_type, $a_id, $a_usage_hist_nr=0, $a_lang="-")
get mobs of object
static _getOriginalId($question_id)
Returns the original id of a question.
formatSAQuestion($a_q)
Format self assessment question.
calculateReachedPointsForSolution($found_values)
Class iQuestionCondition.
forceExistingIntermediateSolution($activeId, $passIndex, $considerDummyRecordCreation)
static _getPass($active_id)
Retrieves the actual pass of a given user for a given test.
$data
Definition: storeScorm.php:23
$result
savePreviewData(ilAssQuestionPreviewSession $previewSession)
$_GET["client_id"]
duplicate($for_test=true, $title="", $author="", $owner="", $testObjId=null)
Duplicates an assImagemapQuestion.
Class for true/false or yes/no answers.
Abstract basic class which is to be extended by the concrete assessment question type classes...
getOperators($expression)
Get all available operations for a specific question.
ensureNonNegativePoints($points)
deleteDummySolutionRecord($activeId, $passIndex)
__construct( $title="", $comment="", $author="", $owner=-1, $question="", $image_filename="")
assImagemapQuestion constructor
getSolutionValues($active_id, $pass=null, $authorized=true)
Loads solutions of a given user from the database an returns it.
setId($id=-1)
Sets the id of the assQuestion object.
getImagePathWeb()
Returns the web image path for web accessable images of a question.
getSolutionMaxPass($active_id)
Returns the maximum pass a users question solution.
setEstimatedWorkingTime($hour=0, $min=0, $sec=0)
Sets the estimated working time of a question from given hour, minute and second. ...
getUserQuestionResult($active_id, $pass)
Get the user solution for a question by active_id and the test pass.
deleteArea($index=0)
Deletes an answer.
setNrOfTries($a_nr_of_tries)
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...
getObjId()
Get the object id of the container object.
getShuffle()
Gets the shuffle flag.
Base Exception for all Exceptions relating to Modules/Test.
$index
Definition: metadata.php:128
getIsMultipleChoice()
Returns true, if the imagemap question is a multiplechoice question.
static _getLogLanguage()
retrieve the log language for assessment logging
calculateReachedPoints($active_id, $pass=null, $authorizedSolution=true, $returndetails=false)
Returns the points, a learner has reached answering the question.
getTestOutputSolutions($activeId, $pass)
setAuthor($author="")
Sets the authors name of the assQuestion object.
static _enabledAssessmentLogging()
check wether assessment logging is enabled or not
getImagePath($question_id=null, $object_id=null)
Returns the image path for web accessable images of a question.
getAnswer($index=0)
Returns an answer.
saveToDb($original_id="")
Saves an assImagemapQuestion object to a database.
uploadImagemap(array $shapes)
Uploads an image map and takes over the areas.
$mobs
toJSON()
Returns a JSON representation of the question.
Class ilUserQuestionResult.
updateCurrentSolutionsAuthorization($activeId, $pass, $authorized, $keepTime=false)
saveCurrentSolution($active_id, $pass, $value1, $value2, $authorized=true, $tstamp=null)
static moveUploadedFile($a_file, $a_name, $a_target, $a_raise_errors=true, $a_mode="move_uploaded")
move uploaded file
static explodeKeyValues($keyValues)
Interface ilObjAnswerScoringAdjustable.
getQuestion()
Gets the question string of the question object.
deleteImage()
Deletes the image file.
redirection script todo: (a better solution should control the processing via a xml file) ...
Class for image map questions.
getAvailableAnswerOptions($index=null)
If index is null, the function returns an array with all anwser options Else it returns the specific ...
getRTETextWithMediaObjects()
Collects all text in the question which could contain media objects which were created with the Rich ...
isComplete()
Returns true, if a imagemap question is complete for use.
createNewOriginalFromThisDuplicate($targetParentId, $targetQuestionTitle="")
copyImage($question_id, $source_questionpool)
getMaximumPoints()
Returns the maximum points, a learner can reach answering the question.
duplicateImage($question_id, $objectId=null)
$filename
Definition: buildRTE.php:89
setIsMultipleChoice($is_multiple_choice)
Set true if the Imagemapquestion is a multiplechoice Question.
getExpressionTypes()
Get all available expression types for a specific question.
saveWorkingData($active_id, $pass=null, $authorized=true)
Saves the learners input of the question to the database.
deductHintPointsFromReachedPoints(ilAssQuestionPreviewSession $previewSession, $reachedPoints)
setPoints($a_points)
Sets the maximum available points for the question.
saveQuestionDataToDb($original_id="")
addAnswer( $answertext="", $points=0.0, $order=0, $coords="", $area="", $points_unchecked=0.0)
Adds a possible answer for a imagemap question.
saveAdditionalQuestionDataToDb()
Saves a record to the question types additional data table.
& getAnswers()
Returns the answer array.
copyObject($target_questionpool_id, $title="")
Copies an assImagemapQuestion object.
getAnswerCount()
Returns the number of answers.
setQuestion($question="")
Sets the question string of the question object.
Interface ilObjQuestionScoringAdjustable.
removeCurrentSolution($active_id, $pass, $authorized=true)
__construct(Container $dic, ilPlugin $plugin)
setExportDetailsXLS($worksheet, $startrow, $active_id, $pass)
{}
deleteSolutionRecordByValues($activeId, $passIndex, $authorized, $matchValues)
getTestPresentationConfig()
Get the test question configuration (initialised once)
setImageFilename($image_filename, $image_tempfilename="")
Sets the image file name.
global $ilDB
setOriginalId($original_id)
$DIC
Definition: xapitoken.php:46
getCurrentSolutionResultSet($active_id, $pass, $authorized=true)
Get a restulset for the current user solution for a this question by active_id and pass...
setLifecycle(ilAssQuestionLifecycle $lifecycle)
saveAnswerSpecificDataToDb()
Saves the answer specific records into a question types answer table.
getAnswerTableName()
Returns the name of the answer table in the database.
getTitle()
Gets the title string of the assQuestion object.
getQuestionType()
Returns the question type of the question.
flushAnswers()
Deletes all answers.
setTitle($title="")
Sets the title string of the assQuestion object.
setObjId($obj_id=0)
Set the object id of the container object.
calculateReachedPointsFromPreviewSession(ilAssQuestionPreviewSession $previewSession)
loadFromDb($question_id)
Loads a assImagemapQuestion object from a database.
setComment($comment="")
Sets the comment string of the assQuestion object.
get_imagemap_contents($href="#")
Gets the imagemap file contents.
getAdditionalTableName()
Returns the name of the additional question data table in the database.
$i
Definition: metadata.php:24
setOwner($owner="")
Sets the creator/owner ID of the assQuestion object.