ILIAS  release_5-1 Revision 5.0.0-5477-g43f3e3fab5f
class.ilQTIParser.php
Go to the documentation of this file.
1<?php
2/*
3 +-----------------------------------------------------------------------------+
4 | ILIAS open source |
5 +-----------------------------------------------------------------------------+
6 | Copyright (c) 1998-2001 ILIAS open source, University of Cologne |
7 | |
8 | This program is free software; you can redistribute it and/or |
9 | modify it under the terms of the GNU General Public License |
10 | as published by the Free Software Foundation; either version 2 |
11 | of the License, or (at your option) any later version. |
12 | |
13 | This program is distributed in the hope that it will be useful, |
14 | but WITHOUT ANY WARRANTY; without even the implied warranty of |
15 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
16 | GNU General Public License for more details. |
17 | |
18 | You should have received a copy of the GNU General Public License |
19 | along with this program; if not, write to the Free Software |
20 | Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. |
21 +-----------------------------------------------------------------------------+
22*/
23
24include_once("./Services/Xml/classes/class.ilSaxParser.php");
25include_once 'Modules/TestQuestionPool/classes/questions/LogicalAnswerCompare/class.ilAssQuestionTypeList.php';
26
27define ("IL_MO_PARSE_QTI", 1);
28define ("IL_MO_VERIFY_QTI", 2);
29
40{
41 var $lng;
43 var $path;
44 var $items;
45 var $item;
46 var $depth;
53
58
68 var $flow;
85 var $in_assessment = FALSE;
90 var $in_objectives = FALSE;
91
92 var $founditems = array();
93 var $verifyroot = false;
100
108 protected $in_prensentation_material = false;
109
113 protected $ignoreItemsEnabled = false;
114
118 public function isIgnoreItemsEnabled()
119 {
121 }
122
127 {
128 $this->ignoreItemsEnabled = $ignoreItemsEnabled;
129 }
130
138 // TODO: The following line gets me an parse error in PHP 4, but I found no hint that pass-by-reference is forbidden in PHP 4 ????
139 function ilQTIParser($a_xml_file, $a_mode = IL_MO_PARSE_QTI, $a_qpl_id = 0, $a_import_idents = "")
140 {
141 global $lng;
142
143 $this->setParserMode($a_mode);
144
145 parent::ilSaxParser($a_xml_file);
146
147 $this->qpl_id = $a_qpl_id;
148 $this->import_idents = array();
149 if (is_array($a_import_idents))
150 {
151 $this->import_idents =& $a_import_idents;
152 }
153
154 $this->lng =& $lng;
155 $this->hasRootElement = FALSE;
156 $this->import_mapping = array();
157 $this->assessments = array();
158 $this->assessment = NULL;
159 $this->section = NULL;
160 $this->path = array();
161 $this->items = array();
162 $this->item = NULL;
163 $this->depth = array();
164 $this->do_nothing = FALSE;
165 $this->qti_element = "";
166 $this->in_presentation = FALSE;
167 $this->in_objectives = FALSE;
168 $this->in_reponse = FALSE;
169 $this->render_type = NULL;
170 $this->render_hotspot = NULL;
171 $this->response_label = NULL;
172 $this->material = NULL;
173 $this->response = NULL;
174 $this->assessmentcontrol = NULL;
175 $this->objectives = NULL;
176 $this->matimage = NULL;
177 $this->resprocessing = NULL;
178 $this->outcomes = NULL;
179 $this->decvar = NULL;
180 $this->respcondition = NULL;
181 $this->setvar = NULL;
182 $this->displayfeedback = NULL;
183 $this->itemfeedback = NULL;
184 $this->flow_mat = array();
185 $this->question_counter = 1;
186 $this->flow = 0;
187 $this->gap_index = 0;
188 $this->presentation = NULL;
189 $this->mattext = NULL;
190 $this->matapplet = NULL;
191 $this->sametag = FALSE;
192 $this->in_assessment = FALSE;
193 $this->characterbuffer = "";
194 $this->metadata = array("label" => "", "entry" => "");
195 }
196
197 function setTestObject(&$a_tst_object)
198 {
199 $this->tst_object =& $a_tst_object;
200 if (is_object($a_tst_object))
201 {
202 $this->tst_id = $this->tst_object->getId();
203 }
204 }
205
206 function setParserMode($a_mode = IL_MO_PARSE_QTI)
207 {
208 $this->parser_mode = $a_mode;
209 $this->founditems = array();
210 $this->verifyroot = false;
211 $this->verifyqticomment = 0;
212 $this->verifymetadatafield = 0;
213 $this->verifyfieldlabel = 0;
214 $this->verifyfieldentry = 0;
215 $this->verifyfieldlabeltext = "";
216 $this->verifyfieldentrytext = "";
217 $this->question_counter = 1;
218 }
219
225 function setHandlers($a_xml_parser)
226 {
227 xml_set_object($a_xml_parser,$this);
228 xml_set_element_handler($a_xml_parser,'handlerBeginTag','handlerEndTag');
229 xml_set_character_data_handler($a_xml_parser,'handlerCharacterData');
230 }
231
232 function startParsing()
233 {
234 $this->question_counter = 1;
235 parent::startParsing();
236 return FALSE;
237 }
238
239 function getParent($a_xml_parser)
240 {
241 if ($this->depth[$a_xml_parser] > 0)
242 {
243 return $this->path[$this->depth[$a_xml_parser]-1];
244 }
245 else
246 {
247 return "";
248 }
249 }
250
254 function handlerBeginTag($a_xml_parser,$a_name,$a_attribs)
255 {
256 switch ($this->parser_mode)
257 {
258 case IL_MO_PARSE_QTI:
259 $this->handlerParseBeginTag($a_xml_parser, $a_name, $a_attribs);
260 break;
261 case IL_MO_VERIFY_QTI:
262 $this->handlerVerifyBeginTag($a_xml_parser, $a_name, $a_attribs);
263 break;
264 }
265 }
266
270 function handlerParseBeginTag($a_xml_parser,$a_name,$a_attribs)
271 {
272 if ($this->do_nothing) return;
273 $this->sametag = FALSE;
274 $this->characterbuffer = "";
275 $this->depth[$a_xml_parser]++;
276 $this->path[$this->depth[$a_xml_parser]] = strtolower($a_name);
277 $this->qti_element = $a_name;
278
279 switch (strtolower($a_name))
280 {
281 case "assessment":
282 include_once ("./Services/QTI/classes/class.ilQTIAssessment.php");
283 $this->assessment =& $this->assessments[array_push($this->assessments, new ilQTIAssessment())-1];
284 $this->in_assessment = TRUE;
285 if (is_array($a_attribs))
286 {
287 foreach ($a_attribs as $attribute => $value)
288 {
289 switch (strtolower($attribute))
290 {
291 case "title":
292 $this->assessment->setTitle($value);
293 break;
294 case "ident":
295 $this->assessment->setIdent($value);
296 break;
297 }
298 }
299 }
300 break;
301 case "assessmentcontrol":
302 include_once ("./Services/QTI/classes/class.ilQTIAssessmentcontrol.php");
303 $this->assessmentcontrol = new ilQTIAssessmentcontrol();
304 if (is_array($a_attribs))
305 {
306 foreach ($a_attribs as $attribute => $value)
307 {
308 switch (strtolower($attribute))
309 {
310 case "solutionswitch":
311 $this->assessmentcontrol->setSolutionswitch($value);
312 break;
313 case "hintswitch":
314 $this->assessmentcontrol->setHintswitch($value);
315 break;
316 case "feedbackswitch":
317 $this->assessmentcontrol->setFeedbackswitch($value);
318 break;
319 }
320 }
321 }
322 break;
323 case "objectives":
324 include_once ("./Services/QTI/classes/class.ilQTIObjectives.php");
325 $this->objectives = new ilQTIObjectives();
326 $this->in_objectives = TRUE;
327 break;
328 case 'presentation_material':
329 require_once 'Services/QTI/classes/class.ilQTIPresentationMaterial.php';
330 $this->prensentation_material = new ilQTIPresentationMaterial();
331 $this->in_prensentation_material = TRUE;
332 break;
333 case "section":
334 include_once ("./Services/QTI/classes/class.ilQTISection.php");
335 $this->section = new ilQTISection();
336 break;
337 case "itemmetadata":
338 $this->in_itemmetadata = TRUE;
339 break;
340 case "qtimetadatafield":
341 $this->metadata = array("label" => "", "entry" => "");
342 break;
343 case "flow":
344 include_once ("./Services/QTI/classes/class.ilQTIFlow.php");
345 $this->flow++;
346 break;
347 case "flow_mat":
348 include_once ("./Services/QTI/classes/class.ilQTIFlowMat.php");
349 array_push($this->flow_mat, new ilQTIFlowMat());
350 break;
351 case "itemfeedback":
352 include_once ("./Services/QTI/classes/class.ilQTIItemfeedback.php");
353 $this->itemfeedback = new ilQTIItemfeedback();
354 if (is_array($a_attribs))
355 {
356 foreach ($a_attribs as $attribute => $value)
357 {
358 switch (strtolower($attribute))
359 {
360 case "ident":
361 $this->itemfeedback->setIdent($value);
362 break;
363 case "view":
364 $this->itemfeedback->setView($value);
365 break;
366 }
367 }
368 }
369 break;
370 case "displayfeedback":
371 include_once ("./Services/QTI/classes/class.ilQTIDisplayfeedback.php");
372 $this->displayfeedback = new ilQTIDisplayfeedback();
373 if (is_array($a_attribs))
374 {
375 foreach ($a_attribs as $attribute => $value)
376 {
377 switch (strtolower($attribute))
378 {
379 case "feedbacktype":
380 $this->displayfeedback->setFeedbacktype($value);
381 break;
382 case "linkrefid":
383 $this->displayfeedback->setLinkrefid($value);
384 break;
385 }
386 }
387 }
388 break;
389 case "setvar":
390 include_once ("./Services/QTI/classes/class.ilQTISetvar.php");
391 $this->setvar = new ilQTISetvar();
392 if (is_array($a_attribs))
393 {
394 foreach ($a_attribs as $attribute => $value)
395 {
396 switch (strtolower($attribute))
397 {
398 case "action":
399 $this->setvar->setAction($value);
400 break;
401 case "varname":
402 $this->setvar->setVarname($value);
403 break;
404 }
405 }
406 }
407 break;
408 case "conditionvar":
409 include_once ("./Services/QTI/classes/class.ilQTIConditionvar.php");
410 $this->conditionvar = new ilQTIConditionvar();
411 break;
412 case "not":
413 if ($this->conditionvar != NULL)
414 {
415 $this->conditionvar->addNot();
416 }
417 break;
418 case "and":
419 if ($this->conditionvar != NULL)
420 {
421 $this->conditionvar->addAnd();
422 }
423 break;
424 case "or":
425 if ($this->conditionvar != NULL)
426 {
427 $this->conditionvar->addOr();
428 }
429 break;
430 case "varequal":
431 include_once("./Services/QTI/classes/class.ilQTIResponseVar.php");
432 $this->responsevar = new ilQTIResponseVar(RESPONSEVAR_EQUAL);
433 if (is_array($a_attribs))
434 {
435 foreach ($a_attribs as $attribute => $value)
436 {
437 switch (strtolower($attribute))
438 {
439 case "case":
440 $this->responsevar->setCase($value);
441 break;
442 case "respident":
443 $this->responsevar->setRespident($value);
444 break;
445 case "index":
446 $this->responsevar->setIndex($value);
447 break;
448 }
449 }
450 }
451 break;
452 case "varlt":
453 include_once("./Services/QTI/classes/class.ilQTIResponseVar.php");
454 $this->responsevar = new ilQTIResponseVar(RESPONSEVAR_LT);
455 if (is_array($a_attribs))
456 {
457 foreach ($a_attribs as $attribute => $value)
458 {
459 switch (strtolower($attribute))
460 {
461 case "respident":
462 $this->responsevar->setRespident($value);
463 break;
464 case "index":
465 $this->responsevar->setIndex($value);
466 break;
467 }
468 }
469 }
470 break;
471 case "varlte":
472 include_once("./Services/QTI/classes/class.ilQTIResponseVar.php");
473 $this->responsevar = new ilQTIResponseVar(RESPONSEVAR_LTE);
474 if (is_array($a_attribs))
475 {
476 foreach ($a_attribs as $attribute => $value)
477 {
478 switch (strtolower($attribute))
479 {
480 case "respident":
481 $this->responsevar->setRespident($value);
482 break;
483 case "index":
484 $this->responsevar->setIndex($value);
485 break;
486 }
487 }
488 }
489 break;
490 case "vargt":
491 include_once("./Services/QTI/classes/class.ilQTIResponseVar.php");
492 $this->responsevar = new ilQTIResponseVar(RESPONSEVAR_GT);
493 if (is_array($a_attribs))
494 {
495 foreach ($a_attribs as $attribute => $value)
496 {
497 switch (strtolower($attribute))
498 {
499 case "respident":
500 $this->responsevar->setRespident($value);
501 break;
502 case "index":
503 $this->responsevar->setIndex($value);
504 break;
505 }
506 }
507 }
508 break;
509 case "vargte":
510 include_once("./Services/QTI/classes/class.ilQTIResponseVar.php");
511 $this->responsevar = new ilQTIResponseVar(RESPONSEVAR_GTE);
512 if (is_array($a_attribs))
513 {
514 foreach ($a_attribs as $attribute => $value)
515 {
516 switch (strtolower($attribute))
517 {
518 case "respident":
519 $this->responsevar->setRespident($value);
520 break;
521 case "index":
522 $this->responsevar->setIndex($value);
523 break;
524 }
525 }
526 }
527 break;
528 case "varsubset":
529 include_once("./Services/QTI/classes/class.ilQTIResponseVar.php");
530 $this->responsevar = new ilQTIResponseVar(RESPONSEVAR_SUBSET);
531 if (is_array($a_attribs))
532 {
533 foreach ($a_attribs as $attribute => $value)
534 {
535 switch (strtolower($attribute))
536 {
537 case "respident":
538 $this->responsevar->setRespident($value);
539 break;
540 case "setmatch":
541 $this->responsevar->setSetmatch($value);
542 break;
543 case "index":
544 $this->responsevar->setIndex($value);
545 break;
546 }
547 }
548 }
549 break;
550 case "varinside":
551 include_once("./Services/QTI/classes/class.ilQTIResponseVar.php");
552 $this->responsevar = new ilQTIResponseVar(RESPONSEVAR_INSIDE);
553 if (is_array($a_attribs))
554 {
555 foreach ($a_attribs as $attribute => $value)
556 {
557 switch (strtolower($attribute))
558 {
559 case "respident":
560 $this->responsevar->setRespident($value);
561 break;
562 case "areatype":
563 $this->responsevar->setAreatype($value);
564 break;
565 case "index":
566 $this->responsevar->setIndex($value);
567 break;
568 }
569 }
570 }
571 break;
572 case "varsubstring":
573 include_once("./Services/QTI/classes/class.ilQTIResponseVar.php");
574 $this->responsevar = new ilQTIResponseVar(RESPONSEVAR_SUBSTRING);
575 if (is_array($a_attribs))
576 {
577 foreach ($a_attribs as $attribute => $value)
578 {
579 switch (strtolower($attribute))
580 {
581 case "case":
582 $this->responsevar->setCase($value);
583 break;
584 case "respident":
585 $this->responsevar->setRespident($value);
586 break;
587 case "index":
588 $this->responsevar->setIndex($value);
589 break;
590 }
591 }
592 }
593 break;
594 case "respcondition":
595 include_once("./Services/QTI/classes/class.ilQTIRespcondition.php");
596 $this->respcondition = new ilQTIRespcondition();
597 if (is_array($a_attribs))
598 {
599 foreach ($a_attribs as $attribute => $value)
600 {
601 switch (strtolower($attribute))
602 {
603 case "continue":
604 $this->respcondition->setContinue($value);
605 break;
606 case "title":
607 $this->respcondition->setTitle($value);
608 break;
609 }
610 }
611 }
612 break;
613 case "outcomes":
614 include_once("./Services/QTI/classes/class.ilQTIOutcomes.php");
615 $this->outcomes = new ilQTIOutcomes();
616 break;
617 case "decvar":
618 include_once("./Services/QTI/classes/class.ilQTIDecvar.php");
619 $this->decvar = new ilQTIDecvar();
620 if (is_array($a_attribs))
621 {
622 foreach ($a_attribs as $attribute => $value)
623 {
624 switch (strtolower($attribute))
625 {
626 case "varname":
627 $this->decvar->setVarname($value);
628 break;
629 case "vartype":
630 $this->decvar->setVartype($value);
631 break;
632 case "defaultval":
633 $this->decvar->setDefaultval($value);
634 break;
635 case "minvalue":
636 $this->decvar->setMinvalue($value);
637 break;
638 case "maxvalue":
639 $this->decvar->setMaxvalue($value);
640 break;
641 case "members":
642 $this->decvar->setMembers($value);
643 break;
644 case "cutvalue":
645 $this->decvar->setCutvalue($value);
646 break;
647 }
648 }
649 }
650 break;
651 case "matimage":
652 include_once("./Services/QTI/classes/class.ilQTIMatimage.php");
653 $this->matimage = new ilQTIMatimage();
654 if (is_array($a_attribs))
655 {
656 foreach ($a_attribs as $attribute => $value)
657 {
658 switch (strtolower($attribute))
659 {
660 case "imagtype":
661 $this->matimage->setImagetype($value);
662 break;
663 case "label":
664 $this->matimage->setLabel($value);
665 break;
666 case "height":
667 $this->matimage->setHeight($value);
668 break;
669 case "width":
670 $this->matimage->setWidth($value);
671 break;
672 case "uri":
673 $this->matimage->setUri($value);
674 break;
675 case "embedded":
676 $this->matimage->setEmbedded($value);
677 break;
678 case "x0":
679 $this->matimage->setX0($value);
680 break;
681 case "y0":
682 $this->matimage->setY0($value);
683 break;
684 case "entityref":
685 $this->matimage->setEntityref($value);
686 break;
687 }
688 }
689 }
690 if (!$this->matimage->getEmbedded() && strlen($this->matimage->getUri()))
691 {
692 $this->matimage->setContent(@file_get_contents(dirname($this->xml_file) . '/'. $this->matimage->getUri()));
693 }
694 break;
695 case "material":
696 include_once("./Services/QTI/classes/class.ilQTIMaterial.php");
697 $this->material = new ilQTIMaterial();
698 $this->material->setFlow($this->flow);
699 if (is_array($a_attribs))
700 {
701 foreach ($a_attribs as $attribute => $value)
702 {
703 switch (strtolower($attribute))
704 {
705 case "label":
706 $this->material->setLabel($value);
707 break;
708 }
709 }
710 }
711 break;
712 case "mattext":
713 include_once ("./Services/QTI/classes/class.ilQTIMattext.php");
714 $this->mattext = new ilQTIMattext();
715 if (is_array($a_attribs))
716 {
717 foreach ($a_attribs as $attribute => $value)
718 {
719 switch (strtolower($attribute))
720 {
721 case "texttype":
722 $this->mattext->setTexttype($value);
723 break;
724 case "label":
725 $this->mattext->setLabel($value);
726 break;
727 case "charset":
728 $this->mattext->setCharset($value);
729 break;
730 case "uri":
731 $this->mattext->setUri($value);
732 break;
733 case "xml:space":
734 $this->mattext->setXmlspace($value);
735 break;
736 case "xml:lang":
737 $this->mattext->setXmllang($value);
738 break;
739 case "entityref":
740 $this->mattext->setEntityref($value);
741 break;
742 case "height":
743 $this->mattext->setHeight($value);
744 break;
745 case "width":
746 $this->mattext->setWidth($value);
747 break;
748 case "x0":
749 $this->mattext->setX0($value);
750 break;
751 case "y0":
752 $this->mattext->setY0($value);
753 break;
754 }
755 }
756 }
757 break;
758 case "matapplet":
759 include_once ("./Services/QTI/classes/class.ilQTIMatapplet.php");
760 $this->matapplet = New ilQTIMatapplet();
761 if (is_array($a_attribs))
762 {
763 foreach ($a_attribs as $attribute => $value)
764 {
765 switch (strtolower($attribute))
766 {
767 case "label":
768 $this->matapplet->setLabel($value);
769 break;
770 case "uri":
771 $this->matapplet->setUri($value);
772 break;
773 case "y0":
774 $this->matapplet->setY0($value);
775 break;
776 case "height":
777 $this->matapplet->setHeight($value);
778 break;
779 case "width":
780 $this->matapplet->setWidth($value);
781 break;
782 case "x0":
783 $this->matapplet->setX0($value);
784 break;
785 case "embedded":
786 $this->matapplet->setEmbedded($value);
787 break;
788 case "entityref":
789 $this->matapplet->setEntityref($value);
790 break;
791 }
792 }
793 }
794 break;
795 case "questestinterop":
796 $this->hasRootElement = TRUE;
797 break;
798 case "qticomment":
799 break;
800 case "objectbank":
801 // not implemented yet
802 break;
803 case "section":
804 if ($this->assessment != NULL)
805 {
806 $this->assessment->addSection($this->section);
807 }
808 $this->section = NULL;
809 break;
810 case "presentation":
811 $this->in_presentation = TRUE;
812 include_once ("./Services/QTI/classes/class.ilQTIPresentation.php");
813 $this->presentation = new ilQTIPresentation();
814 break;
815 case "response_label":
816 if ($this->render_type != NULL)
817 {
818 include_once("./Services/QTI/classes/class.ilQTIResponseLabel.php");
819 $this->response_label = new ilQTIResponseLabel();
820 foreach ($a_attribs as $attribute => $value)
821 {
822 switch (strtolower($attribute))
823 {
824 case "rshuffle":
825 $this->response_label->setRshuffle($value);
826 break;
827 case "rarea":
828 $this->response_label->setRarea($value);
829 break;
830 case "rrange":
831 $this->response_label->setRrange($value);
832 break;
833 case "labelrefid":
834 $this->response_label->setLabelrefid($value);
835 break;
836 case "ident":
837 $this->response_label->setIdent($value);
838 break;
839 case "match_group":
840 $this->response_label->setMatchGroup($value);
841 break;
842 case "match_max":
843 $this->response_label->setMatchMax($value);
844 break;
845 }
846 }
847 }
848 break;
849 case "render_choice":
850 if ($this->in_response)
851 {
852 include_once("./Services/QTI/classes/class.ilQTIRenderChoice.php");
853 $this->render_type = new ilQTIRenderChoice();
854 foreach ($a_attribs as $attribute => $value)
855 {
856 switch (strtolower($attribute))
857 {
858 case "shuffle":
859 $this->render_type->setShuffle($value);
860 break;
861 }
862 }
863 }
864 break;
865 case "render_hotspot":
866 if ($this->in_response)
867 {
868 include_once("./Services/QTI/classes/class.ilQTIRenderHotspot.php");
869 $this->render_type = new ilQTIRenderHotspot();
870 foreach ($a_attribs as $attribute => $value)
871 {
872 switch (strtolower($attribute))
873 {
874 case "showdraw":
875 $this->render_type->setShuffle($value);
876 break;
877 case "minnumber":
878 $this->render_type->setMinnumber($value);
879 break;
880 case "maxnumber":
881 $this->render_type->setMaxnumber($value);
882 break;
883 }
884 }
885 }
886 break;
887 case "render_fib":
888 if ($this->in_response)
889 {
890 include_once("./Services/QTI/classes/class.ilQTIRenderFib.php");
891 $this->render_type = new ilQTIRenderFib();
892 foreach ($a_attribs as $attribute => $value)
893 {
894 switch (strtolower($attribute))
895 {
896 case "encoding":
897 $this->render_type->setEncoding($value);
898 break;
899 case "fibtype":
900 $this->render_type->setFibtype($value);
901 break;
902 case "rows":
903 $this->render_type->setRows($value);
904 break;
905 case "maxchars":
906 $this->render_type->setMaxchars($value);
907 break;
908 case "prompt":
909 $this->render_type->setPrompt($value);
910 break;
911 case "columns":
912 $this->render_type->setColumns($value);
913 break;
914 case "charset":
915 $this->render_type->setCharset($value);
916 break;
917 case "maxnumber":
918 $this->render_type->setMaxnumber($value);
919 break;
920 case "minnumber":
921 $this->render_type->setMinnumber($value);
922 break;
923 }
924 }
925 }
926 break;
927 case "response_lid":
928 // Ordering Terms and Definitions or
929 // Ordering Terms and Pictures or
930 // Multiple choice single response or
931 // Multiple choice multiple response
932 case "response_xy":
933 // Imagemap question
934 case "response_str":
935 // Close question
936 case "response_num":
937 case "response_grp":
938 // Matching terms and definitions
939 // Matching terms and images
940 include_once "./Services/QTI/classes/class.ilQTIResponse.php";
941 switch (strtolower($a_name))
942 {
943 case "response_lid":
944 $response_type = RT_RESPONSE_LID;
945 break;
946 case "response_xy":
947 $response_type = RT_RESPONSE_XY;
948 break;
949 case "response_str":
950 $response_type = RT_RESPONSE_STR;
951 break;
952 case "response_num":
953 $response_type = RT_RESPONSE_NUM;
954 break;
955 case "response_grp":
956 $response_type = RT_RESPONSE_GRP;
957 break;
958 }
959 $this->in_response = TRUE;
960 $this->response = new ilQTIResponse($response_type);
961 $this->response->setFlow($this->flow);
962 if (is_array($a_attribs))
963 {
964 foreach ($a_attribs as $attribute => $value)
965 {
966 switch (strtolower($attribute))
967 {
968 case "ident":
969 $this->response->setIdent($value);
970 break;
971 case "rtiming":
972 $this->response->setRTiming($value);
973 break;
974 case "rcardinality":
975 $this->response->setRCardinality($value);
976 break;
977 case "numtype":
978 $this->response->setNumtype($value);
979 break;
980 }
981 }
982 }
983 break;
984 case "item":
985 include_once("./Services/QTI/classes/class.ilQTIItem.php");
986 $this->gap_index = 0;
987 $this->item =& $this->items[array_push($this->items, new ilQTIItem())-1];
988 if (is_array($a_attribs))
989 {
990 foreach ($a_attribs as $attribute => $value)
991 {
992 switch (strtolower($attribute))
993 {
994 case "ident":
995 $this->item->setIdent($value);
996 $this->item->setIliasSourceNic(
997 $this->fetchSourceNicFromItemIdent($value)
998 );
999 if( $this->isIgnoreItemsEnabled() )
1000 {
1001 $this->do_nothing = true;
1002 }
1003 elseif (count($this->import_idents) > 0)
1004 {
1005 if (!in_array($value, $this->import_idents))
1006 {
1007 $this->do_nothing = TRUE;
1008 }
1009 }
1010 break;
1011 case "title":
1012 $this->item->setTitle($value);
1013 break;
1014 case "maxattempts":
1015 $this->item->setMaxattempts($value);
1016 break;
1017 }
1018 }
1019 }
1020 break;
1021 case "resprocessing":
1022 include_once("./Services/QTI/classes/class.ilQTIResprocessing.php");
1023 $this->resprocessing = new ilQTIResprocessing();
1024 if (is_array($a_attribs))
1025 {
1026 foreach ($a_attribs as $attribute => $value)
1027 {
1028 switch (strtolower($attribute))
1029 {
1030 case "scoremodel":
1031 $this->resprocessing->setScoremodel($value);
1032 break;
1033 }
1034 }
1035 }
1036 break;
1037 }
1038 }
1039
1043 function handlerEndTag($a_xml_parser,$a_name)
1044 {
1045 switch ($this->parser_mode)
1046 {
1047 case IL_MO_PARSE_QTI:
1048 $this->handlerParseEndTag($a_xml_parser, $a_name);
1049 break;
1050 case IL_MO_VERIFY_QTI:
1051 $this->handlerVerifyEndTag($a_xml_parser, $a_name);
1052 break;
1053 }
1054 }
1055
1059 function handlerParseEndTag($a_xml_parser,$a_name)
1060 {
1061 if (($this->do_nothing) && (strcmp(strtolower($a_name), "item") != 0)) return;
1062 switch (strtolower($a_name))
1063 {
1064 case "assessment":
1065 if (is_object($this->tst_object))
1066 {
1067 $this->tst_object->fromXML($this->assessment);
1068 }
1069 $this->in_assessment = FALSE;
1070 break;
1071 case "assessmentcontrol":
1072 $this->assessment->addAssessmentcontrol($this->assessmentcontrol);
1073 $this->assessmentcontrol = NULL;
1074 break;
1075 case "objectives":
1076 if (strcmp(strtolower($this->getParent($a_xml_parser)), "assessment") == 0)
1077 {
1078 $this->assessment->addObjectives($this->objectives);
1079 }
1080 $this->in_objectives = FALSE;
1081 break;
1082 case 'presentation_material':
1083 $this->assessment->setPresentationMaterial($this->prensentation_material);
1084 $this->in_prensentation_material = FALSE;
1085 break;
1086 case "itemmetadata":
1087 $this->in_itemmetadata = FALSE;
1088 break;
1089 case "qtimetadatafield":
1090 // handle only specific ILIAS metadata
1091 switch ($this->metadata["label"])
1092 {
1093 case "ILIAS_VERSION":
1094 if ($this->item != NULL)
1095 {
1096 $this->item->setIliasSourceVersion(
1097 $this->fetchNumericVersionFromVersionDateString($this->metadata["entry"])
1098 );
1099 }
1100 break;
1101 case "QUESTIONTYPE":
1102 if ($this->item != NULL)
1103 {
1104 $this->item->setQuestiontype($this->metadata["entry"]);
1105 }
1106 break;
1107 case "AUTHOR":
1108 if ($this->item != NULL)
1109 {
1110 $this->item->setAuthor($this->metadata["entry"]);
1111 }
1112 default:
1113 if ($this->item != NULL)
1114 {
1115 $this->item->addMetadata($this->metadata);
1116 }
1117 break;
1118 }
1119 if ($this->in_assessment)
1120 {
1121 $this->assessment->addQtiMetadata($this->metadata);
1122 }
1123 $this->metadata = array("label" => "", "entry" => "");
1124 break;
1125 case "flow":
1126 $this->flow--;
1127 break;
1128 case "flow_mat":
1129 if (count($this->flow_mat))
1130 {
1131 $flow_mat = array_pop($this->flow_mat);
1132 if (count($this->flow_mat))
1133 {
1134 $this->flow_mat[count($this->flow_mat)-1]->addFlow_mat($flow_mat);
1135 }
1136 else if($this->in_prensentation_material)
1137 {
1138 $this->prensentation_material->addFlowMat($flow_mat);
1139 }
1140 else if ($this->itemfeedback != NULL)
1141 {
1142 $this->itemfeedback->addFlow_mat($flow_mat);
1143 }
1144 else if ($this->response_label != NULL)
1145 {
1146 $this->response_label->addFlow_mat($flow_mat);
1147 }
1148 }
1149 break;
1150 case "itemfeedback":
1151 if ($this->item != NULL)
1152 {
1153 if ($this->itemfeedback != NULL)
1154 {
1155 $this->item->addItemfeedback($this->itemfeedback);
1156 }
1157 }
1158 $this->itemfeedback = NULL;
1159 break;
1160 case "displayfeedback":
1161 if ($this->respcondition != NULL)
1162 {
1163 if ($this->displayfeedback != NULL)
1164 {
1165 $this->respcondition->addDisplayfeedback($this->displayfeedback);
1166 }
1167 }
1168 $this->displayfeedback = NULL;
1169 break;
1170 case "setvar":
1171 if ($this->respcondition != NULL)
1172 {
1173 if ($this->setvar != NULL)
1174 {
1175 $this->respcondition->addSetvar($this->setvar);
1176 }
1177 }
1178 $this->setvar = NULL;
1179 break;
1180 case "conditionvar":
1181 if ($this->respcondition != NULL)
1182 {
1183 $this->respcondition->setConditionvar($this->conditionvar);
1184 }
1185 $this->conditionvar = NULL;
1186 break;
1187 case "varequal":
1188 case "varlt":
1189 case "varlte":
1190 case "vargt":
1191 case "vargte":
1192 case "varsubset":
1193 case "varinside":
1194 case "varsubstring":
1195 if ($this->conditionvar != NULL)
1196 {
1197 if ($this->responsevar != NULL)
1198 {
1199 $this->conditionvar->addResponseVar($this->responsevar);
1200 }
1201 }
1202 $this->responsevar = NULL;
1203 break;
1204 case "respcondition":
1205 if ($this->resprocessing != NULL)
1206 {
1207 $this->resprocessing->addRespcondition($this->respcondition);
1208 }
1209 $this->respcondition = NULL;
1210 break;
1211 case "outcomes":
1212 if ($this->resprocessing != NULL)
1213 {
1214 $this->resprocessing->setOutcomes($this->outcomes);
1215 }
1216 $this->outcomes = NULL;
1217 break;
1218 case "decvar":
1219 if ($this->outcomes != NULL)
1220 {
1221 $this->outcomes->addDecvar($this->decvar);
1222 }
1223 $this->decvar = NULL;
1224 break;
1225 case "presentation":
1226 $this->in_presentation = FALSE;
1227 if ($this->presentation != NULL)
1228 {
1229 if ($this->item != NULL)
1230 {
1231 $this->item->setPresentation($this->presentation);
1232 }
1233 }
1234 $this->presentation = NULL;
1235 break;
1236 case "response_label":
1237 if ($this->render_type != NULL)
1238 {
1239 $this->render_type->addResponseLabel($this->response_label);
1240 $this->response_label = NULL;
1241 }
1242 break;
1243 case "render_choice":
1244 case "render_hotspot":
1245 case "render_fib":
1246 if ($this->in_response)
1247 {
1248 if ($this->response != NULL)
1249 {
1250 if ($this->render_type != NULL)
1251 {
1252 $this->response->setRenderType($this->render_type);
1253 $this->render_type = NULL;
1254 }
1255 }
1256 }
1257 break;
1258 case "response_lid":
1259 case "response_xy":
1260 case "response_str":
1261 case "response_num":
1262 case "response_grp":
1263 $this->gap_index++;
1264 if ($this->presentation != NULL)
1265 {
1266 if ($this->response != NULL)
1267 {
1268 $this->presentation->addResponse($this->response);
1269 if ($this->item != NULL)
1270 {
1271 $this->item->addPresentationitem($this->response);
1272 }
1273 }
1274 }
1275 $this->response = NULL;
1276 $this->in_response = FALSE;
1277 break;
1278 case "item":
1279 if ($this->do_nothing)
1280 {
1281 $this->do_nothing = FALSE;
1282 return;
1283 }
1284 if (strlen($this->item->getQuestionType()))
1285 {
1286 // this is an ILIAS QTI question
1287 }
1288 else
1289 {
1290 // this is a QTI question which wasn't generated by ILIAS
1291 }
1292 global $ilDB;
1293 global $ilUser;
1294 // save the item directly to save memory
1295 // the database id's of the created items are exported. if the import fails
1296 // ILIAS can delete the already imported items
1297
1298 // problems: the object id of the parent questionpool is not yet known. must be set later
1299 // the complete flag must be calculated?
1300 $qt = $this->item->determineQuestionType();
1301 $presentation = $this->item->getPresentation();
1302
1304 {
1305 return;
1306 }
1307
1308 include_once "./Modules/TestQuestionPool/classes/class.assQuestion.php";
1310 $question = new $qt();
1311 $fbt = str_replace('ass', 'ilAss', $qt).'Feedback';
1312 $question->feedbackOBJ = new $fbt(
1313 $question, $GLOBALS['ilCtrl'], $GLOBALS['ilDB'], $GLOBALS['lng']
1314 );
1315 $question->fromXML($this->item, $this->qpl_id, $this->tst_id, $this->tst_object, $this->question_counter, $this->import_mapping);
1316 break;
1317 case "material":
1318 if ($this->material)
1319 {
1320 $mat = $this->material->getMaterial(0);
1321 if ((strcmp($mat["type"], "mattext") == 0) && (strcmp($mat["material"]->getLabel(), "suggested_solution") == 0))
1322 {
1323 $this->item->addSuggestedSolution($mat["material"], $this->gap_index);
1324 }
1325 if ($this->in_objectives)
1326 {
1327 $this->objectives->addMaterial($this->material);
1328 }
1329 else if (($this->render_type != NULL) && (strcmp(strtolower($this->getParent($a_xml_parser)), "render_hotspot") == 0))
1330 {
1331 $this->render_type->addMaterial($this->material);
1332 }
1333 else if (count($this->flow_mat) && (strcmp(strtolower($this->getParent($a_xml_parser)), "flow_mat") == 0))
1334 {
1335 $this->flow_mat[count($this->flow_mat)-1]->addMaterial($this->material);
1336 }
1337 else if ($this->itemfeedback != NULL)
1338 {
1339 $this->itemfeedback->addMaterial($this->material);
1340 }
1341 else if ($this->response_label != NULL)
1342 {
1343 $this->response_label->addMaterial($this->material);
1344 }
1345 else if ($this->response != NULL)
1346 {
1347 if ($this->response->hasRendering())
1348 {
1349 $this->response->setMaterial2($this->material);
1350 }
1351 else
1352 {
1353 $this->response->setMaterial1($this->material);
1354 }
1355 }
1356 elseif (($this->in_presentation) && (!$this->in_response))
1357 {
1358 if (!is_object($this->item->getQuestiontext()))
1359 {
1360 $this->item->setQuestiontext($this->material);
1361 }
1362 $this->presentation->addMaterial($this->material);
1363 }
1364 else if ($this->presentation != NULL)
1365 {
1366 $this->presentation->addMaterial($this->material);
1367 if ($this->item != NULL)
1368 {
1369 $this->item->addPresentationitem($this->material);
1370 }
1371 }
1372 }
1373 $this->material = NULL;
1374 break;
1375 case "matimage";
1376
1377 if( !$this->isMatImageAvailable() )
1378 {
1379 break;
1380 }
1381
1382 if( $this->virusDetected($this->matimage->getRawContent()) )
1383 {
1384 break;
1385 }
1386
1387 require_once 'Services/QTI/classes/class.ilQtiMatImageSecurity.php';
1388 $matImageSecurity = new ilQtiMatImageSecurity($this->matimage);
1389 $matImageSecurity->sanitizeLabel();
1390
1391 if( !$matImageSecurity->validate() )
1392 {
1393 break;
1394 }
1395
1396 $this->material->addMatimage($this->matimage);
1397 $this->matimage = NULL;
1398 break;
1399
1400 // add support for matbreak element
1401 case "matbreak":
1402 $this->mattext = new ilQTIMattext();
1403 $this->mattext->setContent('<br />');
1404 $this->material->addMattext($this->mattext);
1405 $this->mattext = NULL;
1406 break;
1407 case "resprocessing":
1408 if ($this->item != NULL)
1409 {
1410 $this->item->addResprocessing($this->resprocessing);
1411 }
1412 $this->resprocessing = NULL;
1413 break;
1414 case "mattext":
1415 if ($this->material != NULL)
1416 {
1417 $this->material->addMattext($this->mattext);
1418 }
1419 $this->mattext = NULL;
1420 break;
1421 case "matapplet":
1422 if ($this->material != NULL)
1423 {
1424 $this->material->addMatapplet($this->matapplet);
1425 }
1426 $this->matapplet = NULL;
1427 break;
1428 }
1429 $this->depth[$a_xml_parser]--;
1430 }
1431
1435 function handlerCharacterData($a_xml_parser,$a_data)
1436 {
1437 switch ($this->parser_mode)
1438 {
1439 case IL_MO_PARSE_QTI:
1440 $this->handlerParseCharacterData($a_xml_parser, $a_data);
1441 break;
1442 case IL_MO_VERIFY_QTI:
1443 $this->handlerVerifyCharacterData($a_xml_parser, $a_data);
1444 break;
1445 }
1446 }
1447
1451 function handlerParseCharacterData($a_xml_parser,$a_data)
1452 {
1453 if ($this->do_nothing) return;
1454 $this->characterbuffer .= $a_data;
1455 $a_data = $this->characterbuffer;
1456 switch ($this->qti_element)
1457 {
1458 case "fieldlabel":
1459 $this->metadata["label"] = $a_data;
1460 break;
1461 case "fieldentry":
1462 $this->metadata["entry"] = $a_data;
1463 break;
1464 case "response_label":
1465 if ($this->response_label != NULL)
1466 {
1467 $this->response_label->setContent($a_data);
1468 }
1469 break;
1470 case "setvar":
1471 if ($this->setvar != NULL)
1472 {
1473 $this->setvar->setContent($a_data);
1474 }
1475 break;
1476 case "displayfeedback":
1477 if ($this->displayfeedback != NULL)
1478 {
1479 $this->displayfeedback->setContent($a_data);
1480 }
1481 break;
1482 case "varequal":
1483 case "varlt":
1484 case "varlte":
1485 case "vargt":
1486 case "vargte":
1487 case "varsubset":
1488 case "varinside":
1489 case "varsubstring":
1490 if ($this->responsevar != NULL)
1491 {
1492 $this->responsevar->setContent($a_data);
1493 }
1494 break;
1495 case "decvar":
1496 if (strlen($a_data))
1497 {
1498 if ($this->decvar != NULL)
1499 {
1500 $this->decvar->setContent($a_data);
1501 }
1502 }
1503 break;
1504 case "mattext":
1505 if ($this->mattext != NULL)
1506 {
1507 $this->mattext->setContent($a_data);
1508 }
1509 break;
1510 case "matapplet":
1511 if ($this->matapplet != NULL)
1512 {
1513 $this->matapplet->setContent($a_data);
1514 }
1515 break;
1516 case "matimage":
1517 if ($this->matimage != NULL)
1518 {
1519 $this->matimage->setContent($a_data);
1520 }
1521 break;
1522 case "duration":
1523 switch ($this->getParent($a_xml_parser))
1524 {
1525 case "assessment":
1526 // to be done
1527 break;
1528 case "section":
1529 // to be done
1530 break;
1531 case "item":
1532 $this->item->setDuration($a_data);
1533 break;
1534 }
1535 break;
1536 case "qticomment":
1537 switch ($this->getParent($a_xml_parser))
1538 {
1539 case "item":
1540 $this->item->setComment($a_data);
1541 break;
1542 case "assessment":
1543 $this->assessment->setComment($a_data);
1544 break;
1545 default:
1546 break;
1547 }
1548 break;
1549 }
1550 $this->sametag = TRUE;
1551 }
1552
1556 function handlerVerifyBeginTag($a_xml_parser,$a_name,$a_attribs)
1557 {
1558 switch (strtolower($a_name))
1559 {
1560 case "questestinterop":
1561 $this->verifyroot = true;
1562 break;
1563 case "qtimetadatafield":
1564 $this->verifymetadatafield = 1;
1565 break;
1566 case "fieldlabel":
1567 $this->verifyfieldlabeltext = "";
1568 if ($this->verifymetadatafield == 1) $this->verifyfieldlabel = 1;
1569 break;
1570 case "fieldentry":
1571 $this->verifyfieldentrytext = "";
1572 if ($this->verifymetadatafield == 1) $this->verifyfieldentry = 1;
1573 break;
1574 case "item":
1575 $title = "";
1576 if (is_array($a_attribs))
1577 {
1578 foreach ($a_attribs as $attribute => $value)
1579 {
1580 switch (strtolower($attribute))
1581 {
1582 case "title":
1583 $title = $value;
1584 break;
1585 }
1586 }
1587 }
1588 array_push($this->founditems, array("title" => "$title", "type" => "", "ident" => $a_attribs["ident"]));
1589 break;
1590 case "response_lid":
1591 if (strlen($this->founditems[count($this->founditems)-1]["type"]) == 0)
1592 {
1593 // test for non ILIAS generated question types
1594 if (is_array($a_attribs))
1595 {
1596 foreach ($a_attribs as $attribute => $value)
1597 {
1598 switch (strtolower($attribute))
1599 {
1600 case "rcardinality":
1601 include_once "./Services/QTI/classes/class.ilQTIItem.php";
1602 switch (strtolower($value))
1603 {
1604 case "single":
1605 $this->founditems[count($this->founditems)-1]["type"] = QT_MULTIPLE_CHOICE_SR;
1606 break;
1607 case "multiple":
1608 $this->founditems[count($this->founditems)-1]["type"] = QT_MULTIPLE_CHOICE_MR;
1609 break;
1610 case "ordered":
1611 $this->founditems[count($this->founditems)-1]["type"] = QT_ORDERING;
1612 break;
1613 }
1614 break;
1615 }
1616 }
1617 }
1618 }
1619 break;
1620 case "response_str":
1621 if (strlen($this->founditems[count($this->founditems)-1]["type"]) == 0)
1622 {
1623 // test for non ILIAS generated question types
1624 if (is_array($a_attribs))
1625 {
1626 foreach ($a_attribs as $attribute => $value)
1627 {
1628 switch (strtolower($attribute))
1629 {
1630 case "rcardinality":
1631 include_once "./Services/QTI/classes/class.ilQTIItem.php";
1632 switch (strtolower($value))
1633 {
1634 case "single":
1635 $this->founditems[count($this->founditems)-1]["type"] = QT_CLOZE;
1636 break;
1637 case "ordered":
1638 $this->founditems[count($this->founditems)-1]["type"] = QT_TEXT;
1639 break;
1640 }
1641 break;
1642 }
1643 }
1644 }
1645 }
1646 break;
1647 case "response_xy":
1648 if (strlen($this->founditems[count($this->founditems)-1]["type"]) == 0)
1649 {
1650 $this->founditems[count($this->founditems)-1]["type"] = QT_IMAGEMAP;
1651 }
1652 break;
1653 case "response_num":
1654 if (strlen($this->founditems[count($this->founditems)-1]["type"]) == 0)
1655 {
1656 $this->founditems[count($this->founditems)-1]["type"] = QT_NUMERIC;
1657 }
1658 break;
1659 case "response_grp":
1660 if (strlen($this->founditems[count($this->founditems)-1]["type"]) == 0)
1661 {
1662 $this->founditems[count($this->founditems)-1]["type"] = QT_MATCHING;
1663 }
1664 break;
1665 case "qticomment":
1666 // check for "old" ILIAS qti format (not well formed)
1667 $this->verifyqticomment = 1;
1668 break;
1669 case "presentation":
1670 if (is_array($a_attribs))
1671 {
1672 foreach ($a_attribs as $attribute => $value)
1673 {
1674 switch (strtolower($attribute))
1675 {
1676 case "label":
1677 $this->founditems[count($this->founditems)-1]["title"] = $value;
1678 break;
1679 }
1680 }
1681 }
1682 break;
1683 }
1684 }
1685
1689 function handlerVerifyEndTag($a_xml_parser,$a_name)
1690 {
1691 switch (strtolower($a_name))
1692 {
1693 case "qticomment":
1694 // check for "old" ILIAS qti format (not well formed)
1695 $this->verifyqticomment = 0;
1696 break;
1697 case "qtimetadatafield":
1698 $this->verifymetadatafield = 0;
1699 if (strcmp($this->verifyfieldlabeltext, "QUESTIONTYPE") == 0)
1700 {
1701 $this->founditems[count($this->founditems)-1]["type"] = $this->verifyfieldentrytext;
1702 }
1703 break;
1704 case "fieldlabel":
1705 $this->verifyfieldlabel = 0;
1706 break;
1707 case "fieldentry":
1708 $this->verifyfieldentry = 0;
1709 break;
1710 }
1711 }
1712
1716 function handlerVerifyCharacterData($a_xml_parser,$a_data)
1717 {
1718 if ($this->verifyqticomment == 1)
1719 {
1720 if (preg_match("/Questiontype\=(.*)/", $a_data, $matches))
1721 {
1722 if (count($this->founditems))
1723 {
1724 $this->founditems[count($this->founditems)-1]["type"] = $matches[1];
1725 }
1726 }
1727 }
1728 else if ($this->verifyfieldlabel == 1)
1729 {
1730 $this->verifyfieldlabeltext = $a_data;
1731 }
1732 else if ($this->verifyfieldentry == 1)
1733 {
1734 $this->verifyfieldentrytext = $a_data;
1735 }
1736 }
1737
1738 function &getFoundItems()
1739 {
1740 return $this->founditems;
1741 }
1742
1748 {
1749 if (!is_array($this->import_mapping))
1750 {
1751 return array();
1752 }
1753 else
1754 {
1755 return $this->import_mapping;
1756 }
1757 }
1758
1759 function setXMLContent($a_xml_content)
1760 {
1761 $a_xml_content = $this->cleanInvalidXmlChars($a_xml_content);
1762
1763 return parent::setXMLContent($a_xml_content);
1764 }
1765
1766 function openXMLFile()
1767 {
1768 $xmlContent = file_get_contents($this->xml_file);
1769 $xmlContent = $this->cleanInvalidXmlChars($xmlContent);
1770 file_put_contents($this->xml_file, $xmlContent);
1771
1772 return parent::openXMLFile();
1773 }
1774
1775 protected function fetchNumericVersionFromVersionDateString($versionDateString)
1776 {
1777 $matches = null;
1778
1779 if( preg_match('/^(\d+\.\d+\.\d+) .*$/', $versionDateString, $matches) )
1780 {
1781 return $matches[1];
1782 }
1783
1784 return null;
1785 }
1786
1787 protected function fetchSourceNicFromItemIdent($itemIdent)
1788 {
1789 $matches = null;
1790
1791 if( preg_match('/^il_(\d+?)_qst_\d+$/', $itemIdent, $matches) )
1792 {
1793 return $matches[1];
1794 }
1795
1796 return null;
1797 }
1798
1799 protected function cleanInvalidXmlChars($xmlContent)
1800 {
1801 // http://www.w3.org/TR/xml/#charsets
1802
1803 // DOES ACTUALLY KILL CONTENT, SHOULD CLEAN NON ESCAPED ILLEGAL CHARS, DON'T KNOW
1804 //$reg = '/[^\x09\x0A\x0D\x20-\uD7FF\uE000-\uFFFD\u10000-\u10FFFF]/';
1805 //$xmlContent = preg_replace($reg, '', $xmlContent);
1806
1807 // remove illegal chars escaped to html entities
1808 $needles = array();
1809 for($i = 0x00, $max = 0x08; $i <= $max; $i += 0x01)
1810 {
1811 $needles[] = "&#{$i};";
1812 }
1813 for($i = 0x0b, $max = 0x0c; $i <= $max; $i += 0x01)
1814 {
1815 $needles[] = "&#{$i};";
1816 }
1817 for($i = 0x0e, $max = 0x1f; $i <= $max; $i += 0x01)
1818 {
1819 $needles[] = "&#{$i};";
1820 }
1821 for($i = 0xd800, $max = 0xdfff; $i <= $max; $i += 0x0001)
1822 {
1823 $needles[] = "&#{$i};";
1824 }
1825 for($i = 0xfffe, $max = 0xffff; $i <= $max; $i += 0x0001)
1826 {
1827 $needles[] = "&#{$i};";
1828 }
1829 $reg = '/('.implode('|', $needles).')/';
1830 $xmlContent = preg_replace($reg, '', $xmlContent);
1831
1832 return $xmlContent;
1833 }
1834
1835 protected function isMatImageAvailable()
1836 {
1837 if( !$this->material )
1838 {
1839 return false;
1840 }
1841
1842 if( !$this->matimage )
1843 {
1844 return false;
1845 }
1846
1847 return true;
1848 }
1849
1850 protected function virusDetected($buffer)
1851 {
1852 require_once 'Services/VirusScanner/classes/class.ilVirusScannerFactory.php';
1854
1855 if( $vs === null )
1856 {
1857 return false; // no virus scan, no virus detected
1858 }
1859
1860 return (bool)$vs->scanBuffer($buffer);
1861 }
1862}
const QT_CLOZE
const QT_IMAGEMAP
const QT_MULTIPLE_CHOICE_MR
const QT_MATCHING
const QT_ORDERING
const QT_NUMERIC
const QT_MULTIPLE_CHOICE_SR
const QT_TEXT
const IL_MO_VERIFY_QTI
const IL_MO_PARSE_QTI
const RESPONSEVAR_GTE
const RESPONSEVAR_LT
const RESPONSEVAR_EQUAL
const RESPONSEVAR_LTE
const RESPONSEVAR_INSIDE
const RESPONSEVAR_SUBSTRING
const RESPONSEVAR_SUBSET
const RESPONSEVAR_GT
const RT_RESPONSE_LID
const RT_RESPONSE_XY
const RT_RESPONSE_STR
const RT_RESPONSE_NUM
const RT_RESPONSE_GRP
static _includeClass($question_type, $gui=0)
Include the php class file for a given question type.
static isImportable($questionTypeTag)
setHandlers($a_xml_parser)
set event handler should be overwritten by inherited class @access private
fetchNumericVersionFromVersionDateString($versionDateString)
handlerVerifyEndTag($a_xml_parser, $a_name)
handler for end of element verification
openXMLFile()
open xml file
ilQTIParser($a_xml_file, $a_mode=IL_MO_PARSE_QTI, $a_qpl_id=0, $a_import_idents="")
Constructor.
handlerEndTag($a_xml_parser, $a_name)
handler for end of element
getParent($a_xml_parser)
setXMLContent($a_xml_content)
virusDetected($buffer)
handlerParseEndTag($a_xml_parser, $a_name)
handler for end of element parser
startParsing()
stores xml data in array
getImportMapping()
get array of new created questions for import id
setTestObject(&$a_tst_object)
handlerVerifyBeginTag($a_xml_parser, $a_name, $a_attribs)
handler for begin of element verification
setIgnoreItemsEnabled($ignoreItemsEnabled)
handlerParseCharacterData($a_xml_parser, $a_data)
handler for character data
cleanInvalidXmlChars($xmlContent)
setParserMode($a_mode=IL_MO_PARSE_QTI)
handlerParseBeginTag($a_xml_parser, $a_name, $a_attribs)
handler for begin of element parser
handlerVerifyCharacterData($a_xml_parser, $a_data)
handler for character data verification
handlerCharacterData($a_xml_parser, $a_data)
handler for character data
fetchSourceNicFromItemIdent($itemIdent)
handlerBeginTag($a_xml_parser, $a_name, $a_attribs)
handler for begin of element
Class ilQTIPresentationMaterial.
Base class for sax-based expat parsing extended classes need to overwrite the method setHandlers and ...
& _getInstance()
Constructor @access public.
$GLOBALS['PHPCAS_CLIENT']
This global variable is used by the interface class phpCAS.
Definition: CAS.php:276
QTI assessment class.
global $ilDB
global $ilUser
Definition: imgupload.php:15