Completed
Pull Request — 1.11.x (#1285)
by José
478:06 queued 439:54
created

MoodleImport::traverseArray()   A

Complexity

Conditions 4
Paths 4

Size

Total Lines 11
Code Lines 7

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 4
eloc 7
c 1
b 0
f 0
nc 4
nop 2
dl 0
loc 11
rs 9.2
1
<?php
2
/* For licensing terms, see /license.txt */
3
4
/**
5
 * Class MoodleImport
6
 *
7
 * @author José Loguercio <[email protected]>
8
 * @package chamilo.library
9
 */
10
11
class MoodleImport
12
{
13
    /**
14
     * Read and validate the moodleFile
15
     *
16
     * @param resource $uploadedFile *.* mbz file moodle course backup
17
     * @return bool
18
     */
19
    public function readMoodleFile($uploadedFile)
20
    {
21
        $file = $uploadedFile['tmp_name'];
22
23
        if (is_file($file) && is_readable($file)) {
24
            $package = new PclZip($file);
25
            $packageContent = $package->listContent();
26
            $mainFileKey = 0;
27
            foreach ($packageContent as $index => $value) {
28
                if ($value['filename'] == 'moodle_backup.xml') {
29
                    $mainFileKey = $index;
30
                    break;
31
                }
32
            }
33
34
            if (!$mainFileKey) {
35
                Display::addFlash(Display::return_message(get_lang('FailedToImportThisIsNotAMoodleFile'), 'error'));
36
            }
37
38
            $folder = api_get_unique_id();
39
            $destinationDir = api_get_path(SYS_ARCHIVE_PATH).$folder;
40
            $coursePath = api_get_path(SYS_COURSE_PATH).api_get_course_path().'/';
41
            $courseInfo = api_get_course_info();
42
43
            mkdir($destinationDir, api_get_permissions_for_new_directories(), true);
44
45
            $package->extract(
46
                PCLZIP_OPT_PATH,
47
                $destinationDir
48
            );
49
50
            $xml = @file_get_contents($destinationDir.'/moodle_backup.xml');
51
52
            $doc = new DOMDocument();
53
            $res = @$doc->loadXML($xml);
54
            if ($res) {
55
                $activities = $doc->getElementsByTagName('activity');
56
                foreach ($activities as $activity) {
57
                    if ($activity->childNodes->length) {
58
                        $currentItem = [];
59
60
                        foreach ($activity->childNodes as $item) {
61
                            $currentItem[$item->nodeName] = $item->nodeValue;
62
                        }
63
64
                        $moduleName = isset($currentItem['modulename']) ? $currentItem['modulename'] : false;
65
                        switch ($moduleName) {
66
                            case 'forum':
67
                                require_once '../forum/forumfunction.inc.php';
68
                                $catForumValues = [];
69
70
                                // Read the current forum module xml.
71
                                $moduleDir = $currentItem['directory'];
72
                                $moduleXml = @file_get_contents($destinationDir.'/'.$moduleDir.'/'.$moduleName.'.xml');
73
                                $moduleValues = $this->readForumModule($moduleXml);
74
75
                                // Create a Forum category based on Moodle forum type.
76
                                $catForumValues['forum_category_title'] = $moduleValues['type'];
77
                                $catForumValues['forum_category_comment'] = '';
78
                                $catId = store_forumcategory($catForumValues);
79
                                $forumValues = [];
80
                                $forumValues['forum_title'] = $moduleValues['name'];
81
                                $forumValues['forum_image'] = '';
82
                                $forumValues['forum_comment'] = $moduleValues['intro'];
83
                                $forumValues['forum_category'] = $catId;
84
85
                                store_forum($forumValues);
86
                                break;
87
                            case 'quiz':
0 ignored issues
show
Coding Style introduced by
The case body in a switch statement must start on the line following the statement.

According to the PSR-2, the body of a case statement must start on the line immediately following the case statement.

switch ($expr) {
case "A":
    doSomething(); //right
    break;
case "B":

    doSomethingElse(); //wrong
    break;

}

To learn more about the PSR-2 coding standard, please refer to the PHP-Fig.

Loading history...
88
89
                                // Read the current quiz module xml.
90
                                // The quiz case is the very complicate process of all the import.
91
                                // Please if you want to review the script, try to see the readingXML functions.
92
                                // The readingXML functions in this clases do all the mayor work here.
93
94
                                $moduleDir = $currentItem['directory'];
95
                                $moduleXml = @file_get_contents($destinationDir.'/'.$moduleDir.'/'.$moduleName.'.xml');
96
                                $questionsXml = @file_get_contents($destinationDir.'/questions.xml');
97
                                $moduleValues = $this->readQuizModule($moduleXml);
98
99
                                // At this point we got all the prepared resources from Moodle file
100
                                // $moduleValues variable contains all the necesary info to the quiz import
101
                                // var_dump($moduleValues); // <-- uncomment this to see the final array
102
103
                                // Lets do this ...
104
                                $exercise = new Exercise();
105
                                $exercise->updateTitle(Exercise::format_title_variable($moduleValues['name']));
106
                                $exercise->updateDescription($moduleValues['intro']);
107
                                $exercise->updateAttempts($moduleValues['attempts_number']);
108
                                $exercise->updateFeedbackType(0);
109
110
                                // Match shuffle question with chamilo
111
                                switch ($moduleValues['shufflequestions']) {
112
                                    case '0':
113
                                        $exercise->setRandom(0);
114
                                        break;
115
                                    case '1':
116
                                        $exercise->setRandom(-1);
117
                                        break;
118
                                    default:
119
                                        $exercise->setRandom(0);
120
                                }
121
                                $exercise->updateRandomAnswers($moduleValues['shuffleanswers']);
122
                                // @todo divide to minutes
123
                                $exercise->updateExpiredTime($moduleValues['timelimit']);
124
125
                                if ($moduleValues['questionsperpage'] == 1) {
126
                                    $exercise->updateType(2);
127
                                } else {
128
                                    $exercise->updateType(1);
129
                                }
130
131
                                // Create the new Quiz
132
                                $exercise->save();
133
134
                                // Ok, we got the Quiz and create it, now its time to add the Questions
135
                                foreach ($moduleValues['question_instances'] as $index => $question) {
136
                                    $questionsValues = $this->readMainQuestionsXml($questionsXml, $question['questionid']);
137
                                    $moduleValues['question_instances'][$index] = $questionsValues;
138
                                    // Set Question Type from Moodle XML element <qtype>
139
                                    $qType = $moduleValues['question_instances'][$index]['qtype'];
140
                                    // Add the matched chamilo question type to the array
141
                                    $moduleValues['question_instances'][$index]['chamilo_qtype'] = $this->matchMoodleChamiloQuestionTypes($qType);
142
                                    $questionInstance = Question::getInstance($moduleValues['question_instances'][$index]['chamilo_qtype']);
143
                                    if ($questionInstance) {
144
                                        $questionInstance->updateTitle($moduleValues['question_instances'][$index]['name']);
145
                                        $questionInstance->updateDescription($moduleValues['question_instances'][$index]['questiontext']);
146
                                        $questionInstance->updateLevel(1);
147
                                        $questionInstance->updateCategory(0);
148
149
                                        //Save normal question if NOT media
150
                                        if ($questionInstance->type != MEDIA_QUESTION) {
151
                                            $questionInstance->save($exercise->id);
152
153
                                            // modify the exercise
154
                                            $exercise->addToList($questionInstance->id);
155
                                            $exercise->update_question_positions();
156
                                        }
157
158
                                        $questionList = $moduleValues['question_instances'][$index]['plugin_qtype_'.$qType.'_question'];
159
                                        $currentQuestion = $moduleValues['question_instances'][$index];
160
161
                                        $result = $this->processAnswers($questionList, $qType, $questionInstance, $currentQuestion);
162
                                    }
163
                                }
164
165
                                break;
166
                            case 'resource':
167
                                // Read the current resource module xml.
168
                                $moduleDir = $currentItem['directory'];
169
                                $moduleXml = @file_get_contents($destinationDir.'/'.$moduleDir.'/'.$moduleName.'.xml');
170
                                $filesXml = @file_get_contents($destinationDir.'/files.xml');
171
                                $moduleValues = $this->readResourceModule($moduleXml);
172
                                $mainFileModuleValues = $this->readMainFilesXml($filesXml, $moduleValues['contextid']);
173
                                $fileInfo = array_merge($moduleValues, $mainFileModuleValues, $currentItem);
174
                                $documentPath = $coursePath.'document/';
175
                                $currentResourceFilePath = $destinationDir.'/files/';
176
                                $dirs = new RecursiveDirectoryIterator($currentResourceFilePath);
177
                                foreach (new RecursiveIteratorIterator($dirs) as $file) {
178
                                    if (is_file($file) && strpos($file, $fileInfo['contenthash']) !== false) {
179
                                        $files = [];
180
                                        $files['file']['name'] = $fileInfo['filename'];
181
                                        $files['file']['tmp_name'] = $file->getPathname();
182
                                        $files['file']['type'] = $fileInfo['mimetype'];
183
                                        $files['file']['error'] = 0;
184
                                        $files['file']['size'] = $fileInfo['filesize'];
185
                                        $files['file']['from_file'] = true;
186
                                        $files['file']['move_file'] = true;
187
                                        $_POST['language'] = $courseInfo['language'];
188
                                        $_POST['moodle_import'] = true;
189
190
                                        DocumentManager::upload_document(
191
                                            $files,
192
                                            '/',
193
                                            $fileInfo['title'],
194
                                            '',
195
                                            null,
196
                                            null,
197
                                            true,
198
                                            true
199
                                        );
200
                                    }
201
                                }
202
203
                                break;
204
                            case 'url':
205
                                // Read the current url module xml.
206
                                $moduleDir = $currentItem['directory'];
207
                                $moduleXml = @file_get_contents($destinationDir.'/'.$moduleDir.'/'.$moduleName.'.xml');
208
                                $moduleValues = $this->readUrlModule($moduleXml);
209
                                $_POST['title'] = $moduleValues['name'];
210
                                $_POST['url'] = $moduleValues['externalurl'];
211
                                $_POST['description'] = $moduleValues['intro'];
212
                                $_POST['category_id'] = 0;
213
                                $_POST['target'] = '_blank';
214
215
                                Link::addlinkcategory("link");
216
                                break;
217
                        }
218
                    }
219
                }
220
            } else {
221
                return false;
222
            }
223
        } else {
224
            return false;
225
        }
226
227
        removeDir($destinationDir);
228
        return $packageContent[$mainFileKey];
229
    }
230
231
    /**
232
     * Read and validate the forum module XML
233
     *
234
     * @param resource $moduleXml XML file
235
     * @return mixed | array if is a valid xml file, false otherwise
236
     */
237 View Code Duplication
    public function readForumModule($moduleXml)
238
    {
239
        $moduleDoc = new DOMDocument();
240
        $moduleRes = @$moduleDoc->loadXML($moduleXml);
241
        if ($moduleRes) {
242
            $activities = $moduleDoc->getElementsByTagName('forum');
243
            $currentItem = [];
244
            foreach ($activities as $activity) {
245
                if ($activity->childNodes->length) {
246
                    foreach ($activity->childNodes as $item) {
247
                        $currentItem[$item->nodeName] = $item->nodeValue;
248
                    }
249
                }
250
            }
251
252
            return $currentItem;
253
        }
254
255
        return false;
256
    }
257
258
    /**
259
     * Read and validate the resource module XML
260
     *
261
     * @param resource $moduleXml XML file
262
     * @return mixed | array if is a valid xml file, false otherwise
263
     */
264
    public function readResourceModule($moduleXml)
265
    {
266
        $moduleDoc = new DOMDocument();
267
        $moduleRes = @$moduleDoc->loadXML($moduleXml);
268
        if ($moduleRes) {
269
            $activities = $moduleDoc->getElementsByTagName('resource');
270
            $mainActivity = $moduleDoc->getElementsByTagName('activity');
271
            $contextId = $mainActivity->item(0)->getAttribute('contextid');
272
            $currentItem = [];
273
            foreach ($activities as $activity) {
274
                if ($activity->childNodes->length) {
275
                    foreach ($activity->childNodes as $item) {
276
                        $currentItem[$item->nodeName] = $item->nodeValue;
277
                    }
278
                }
279
            }
280
281
            $currentItem['contextid'] = $contextId;
282
            return $currentItem;
283
        }
284
285
        return false;
286
    }
287
288
    /**
289
     * Read and validate the url module XML
290
     *
291
     * @param resource $moduleXml XML file
292
     * @return mixed | array if is a valid xml file, false otherwise
293
     */
294 View Code Duplication
    public function readUrlModule($moduleXml)
295
    {
296
        $moduleDoc = new DOMDocument();
297
        $moduleRes = @$moduleDoc->loadXML($moduleXml);
298
        if ($moduleRes) {
299
            $activities = $moduleDoc->getElementsByTagName('url');
300
            $currentItem = [];
301
            foreach ($activities as $activity) {
302
                if ($activity->childNodes->length) {
303
                    foreach ($activity->childNodes as $item) {
304
                        $currentItem[$item->nodeName] = $item->nodeValue;
305
                    }
306
                }
307
            }
308
309
            return $currentItem;
310
        }
311
312
        return false;
313
    }
314
315
    /**
316
     * Read and validate the quiz module XML
317
     *
318
     * @param resource $moduleXml XML file
319
     * @return mixed | array if is a valid xml file, false otherwise
320
     */
321
    public function readQuizModule($moduleXml)
322
    {
323
        $moduleDoc = new DOMDocument();
324
        $moduleRes = @$moduleDoc->loadXML($moduleXml);
325
        if ($moduleRes) {
326
            $activities = $moduleDoc->getElementsByTagName('quiz');
327
            $currentItem = [];
328
            foreach ($activities as $activity) {
329
                if ($activity->childNodes->length) {
330
                    foreach ($activity->childNodes as $item) {
331
                        $currentItem[$item->nodeName] = $item->nodeValue;
332
                    }
333
                }
334
            }
335
336
            $questions = $moduleDoc->getElementsByTagName('question_instance');
337
338
            $questionList = [];
339
            $counter = 0;
340
            foreach ($questions as $question) {
341
                if ($question->childNodes->length) {
342
                    foreach ($question->childNodes as $item) {
343
                        $questionList[$counter][$item->nodeName] = $item->nodeValue;
344
                    }
345
                    $counter++;
346
                }
347
348
            }
349
            $currentItem['question_instances'] = $questionList;
350
            return $currentItem;
351
        }
352
353
        return false;
354
    }
355
356
    /**
357
     * Search the current file resource in main Files XML
358
     *
359
     * @param resource $filesXml XML file
360
     * @param int $contextId
361
     * @return mixed | array if is a valid xml file, false otherwise
362
     */
363
    public function readMainFilesXml($filesXml, $contextId)
364
    {
365
        $moduleDoc = new DOMDocument();
366
        $moduleRes = @$moduleDoc->loadXML($filesXml);
367
        if ($moduleRes) {
368
            $activities = $moduleDoc->getElementsByTagName('file');
369
            $currentItem = [];
370
            foreach ($activities as $activity) {
371
                if ($activity->childNodes->length) {
372
                    $isThisItemThatIWant = false;
373
                    foreach ($activity->childNodes as $item) {
374
                        if (!$isThisItemThatIWant && $item->nodeName == 'contenthash') {
375
                            $currentItem['contenthash'] = $item->nodeValue;
376
                        }
377
                        if ($item->nodeName == 'contextid' && intval($item->nodeValue) == intval($contextId) && !$isThisItemThatIWant) {
378
                            $isThisItemThatIWant = true;
379
                            continue;
380
                        }
381
382
                        if ($isThisItemThatIWant && $item->nodeName == 'filename') {
383
                            $currentItem['filename'] = $item->nodeValue;
384
                        }
385
386
                        if ($isThisItemThatIWant && $item->nodeName == 'filesize') {
387
                            $currentItem['filesize'] = $item->nodeValue;
388
                        }
389
390
                        if ($isThisItemThatIWant && $item->nodeName == 'mimetype' && $item->nodeValue == 'document/unknown') {
391
                            break;
392
                        }
393
394
                        if ($isThisItemThatIWant && $item->nodeName == 'mimetype' && $item->nodeValue !== 'document/unknown') {
395
                            $currentItem['mimetype'] = $item->nodeValue;
396
                            break 2;
397
                        }
398
                    }
399
                }
400
            }
401
402
            return $currentItem;
403
        }
404
405
        return false;
406
    }
407
408
    /**
409
     * Search the current quiestion resource in main Questions XML
410
     *
411
     * @param resource $questionsXml XML file
412
     * @param int $questionId
413
     * @return mixed | array if is a valid xml file, false otherwise
414
     */
415
    public function readMainQuestionsXml($questionsXml, $questionId)
416
    {
417
        $moduleDoc = new DOMDocument();
418
        $moduleRes = @$moduleDoc->loadXML($questionsXml);
419
        if ($moduleRes) {
420
            $questions = $moduleDoc->getElementsByTagName('question');
421
            $currentItem = [];
422
            foreach ($questions as $question) {
423
                if (intval($question->getAttribute('id')) == $questionId) {
424
                    if ($question->childNodes->length) {
425
                        $currentItem['questionid'] = $questionId;
426
                        $questionType = '';
427
                        foreach ($question->childNodes as $item) {
428
                            $currentItem[$item->nodeName] = $item->nodeValue;
429
                            if ($item->nodeName == 'qtype') {
430
                                $questionType = $item->nodeValue;
431
                            }
432
433
                            if ($item->nodeName == 'plugin_qtype_'.$questionType.'_question') {
434
                                $answer = $item->getElementsByTagName($this->getQuestionTypeAnswersTag($questionType));
435
                                $currentItem['plugin_qtype_'.$questionType.'_question'] = [];
436
                                for ($i = 0; $i <= $answer->length - 1; $i++) {
437
                                    $currentItem['plugin_qtype_'.$questionType.'_question'][$i]['answerid'] = $answer->item($i)->getAttribute('id');
438
                                    foreach ($answer->item($i)->childNodes as $properties) {
439
                                        $currentItem['plugin_qtype_'.$questionType.'_question'][$i][$properties->nodeName] = $properties->nodeValue;
440
                                    }
441
                                }
442
443
                                $typeValues = $item->getElementsByTagName($this->getQuestionTypeOptionsTag($questionType));
444
                                for ($i = 0; $i <= $typeValues->length - 1; $i++) {
445
                                    foreach ($typeValues->item($i)->childNodes as $properties) {
446
                                        $currentItem[$questionType.'_values'][$properties->nodeName] = $properties->nodeValue;
447
                                        if ($properties->nodeName == 'sequence') {
448
                                            $sequence = $properties->nodeValue;
449
                                            $sequenceIds = explode(',', $sequence);
450
                                            foreach ($sequenceIds as $qId) {
451
                                                $questionMatch = $this->readMainQuestionsXml($questionsXml, $qId);
452
                                                $currentItem['plugin_qtype_'.$questionType.'_question'][] = $questionMatch;
453
                                            }
454
                                        }
455
                                    }
456
                                }
457
                            }
458
                        }
459
                    }
460
                }
461
            }
462
463
            $this->traverseArray($currentItem, ['#text', 'question_hints', 'tags']);
464
            return $currentItem;
465
        }
466
467
        return false;
468
    }
469
470
    /**
471
     * return the correct question type options tag
472
     *
473
     * @param string $questionType name
474
     * @return string question type tag
475
     */
476
    public function getQuestionTypeOptionsTag($questionType)
477
    {
478
        switch ($questionType) {
479
            case 'match':
480
            case 'ddmatch':
481
                return 'matchoptions';
482
                break;
483
            default:
484
                return $questionType;
485
                break;
486
        }
487
    }
488
489
    /**
490
     * return the correct question type answers tag
491
     *
492
     * @param string $questionType name
493
     * @return string question type tag
494
     */
495
    public function getQuestionTypeAnswersTag($questionType)
496
    {
497
        switch ($questionType) {
498
            case 'match':
499
            case 'ddmatch':
500
                return 'match';
501
                break;
502
            default:
503
                return 'answer';
504
                break;
505
        }
506
    }
507
508
    /**
509
     *
510
     * @param string $moodleQuestionType
511
     * @return integer Chamilo question type
512
     */
513
    public function matchMoodleChamiloQuestionTypes($moodleQuestionType)
514
    {
515
        switch ($moodleQuestionType) {
516
            case 'multichoice':
517
                return UNIQUE_ANSWER;
518
                break;
519
            case 'multianswer':
520
            case 'shortanswer':
521
            case 'match':
522
                return FILL_IN_BLANKS;
523
                break;
524
            case 'essay':
525
                return FREE_ANSWER;
526
                break;
527
            case 'truefalse':
528
                return MULTIPLE_ANSWER_TRUE_FALSE;
529
            break;
530
        }
531
    }
532
533
    /**
534
     * Process Moodle Answers to Chamilo
535
     *
536
     * @param array $questionList
537
     * @param string $questionType
538
     * @param object $questionInstance Question/Answer instance
539
     * @param array $currentQuestion
540
     * @return integer db response
541
     */
542
    public function processAnswers($questionList, $questionType, $questionInstance, $currentQuestion)
543
    {
544
        switch ($questionType) {
545
            case 'multichoice':
546
                $objAnswer = new Answer($questionInstance->id);
547
                $questionWeighting = 0;
548
                foreach ($questionList as $slot => $answer) {
549
                    $this->processUniqueAnswer($objAnswer, $answer, $slot + 1, $questionWeighting);
550
                }
551
552
                // saves the answers into the data base
553
                $objAnswer->save();
554
                // sets the total weighting of the question
555
                $questionInstance->updateWeighting($questionWeighting);
556
                $questionInstance->save();
557
558
                return true;
559
                break;
560
            case 'multianswer':
0 ignored issues
show
Coding Style introduced by
There must be a comment when fall-through is intentional in a non-empty case body
Loading history...
561
                $objAnswer = new Answer($questionInstance->id);
562
563
                $placeholder = $currentQuestion['questiontext'];
564
565
                $optionsValues = [];
566
567
                foreach ($questionList as $slot => $subQuestion) {
568
                    $qtype = $subQuestion['qtype'];
569
                    $optionsValues[] = $this->processFillBlanks($objAnswer, $subQuestion, $subQuestion['plugin_qtype_'.$qtype.'_question'], $placeholder, $slot + 1);
570
                }
571
572
                $answerOptionsWeight = '::';
573
                $answerOptionsSize = '';
574
                $questionWeighting = 0;
575
                foreach ($optionsValues as $index => $value) {
576
                    $questionWeighting += $value['weight'];
577
                    $answerOptionsWeight .= $value['weight'].',';
578
                    $answerOptionsSize .= $value['size'].',';
579
                }
580
581
                $answerOptionsWeight = substr($answerOptionsWeight, 0, -1);
582
                $answerOptionsSize = substr($answerOptionsSize, 0, -1);
583
584
                $suffleAnswers = isset($subQuestion[$qtype.'_values']['shuffleanswers']) ? $subQuestion[$qtype.'_values']['shuffleanswers'] : false;
585
586
                if ($suffleAnswers) {
587
                    $answerOptions = $answerOptionsWeight.':'.$answerOptionsSize.':0@'.$suffleAnswers;
588
                } else {
589
                    $answerOptions = $answerOptionsWeight.':'.$answerOptionsSize.':0@';
590
                }
591
592
                $placeholder = $placeholder.$answerOptions;
593
594
                $questionInstance->updateWeighting($questionWeighting);
595
                $questionInstance->updateDescription('');
596
                $questionInstance->save();
597
                $objAnswer->createAnswer($placeholder, 0, '', 0, 1);
598
                $objAnswer->save();
599
            case 'shortanswer':
600
            case 'match':
601
            case 'ddmatch':
602
                // Not Supported Yet
603
                return false;
604
                break;
605
            case 'essay':
606
                $questionWeighting = $currentQuestion['defaultmark'];
607
                $questionInstance->updateWeighting($questionWeighting);
608
                $questionInstance->save();
609
                break;
610
            case 'truefalse':
611
                // Not Supported Yet
612
                return false;
613
                break;
614
            default:
615
                return false;
616
                break;
617
        }
618
    }
619
620
    /**
621
     * Process Chamilo Unique Answer
622
     *
623
     * @param object $objAnswer
624
     * @param array $answerValues
625
     * @param integer $position
626
     * @param integer $questionWeighting
627
     * @return integer db response
628
     */
629
    public function processUniqueAnswer($objAnswer, $answerValues, $position, &$questionWeighting)
630
    {
631
        $correct = intval($answerValues['fraction']) ? intval($answerValues['fraction']) : 0;
632
        $answer = $answerValues['answertext'];
633
        $comment = $answerValues['feedback'];
634
        $weighting = $answerValues['fraction'];
635
        $weighting = abs($weighting);
636
        if ($weighting > 0) {
637
            $questionWeighting += $weighting;
638
        }
639
        $goodAnswer =  $correct ? true : false;
640
641
        $objAnswer->createAnswer(
642
            $answer,
643
            $goodAnswer,
644
            $comment,
645
            $weighting,
646
            $position,
647
            null,
648
            null,
649
            ''
650
        );
651
    }
652
653
    /**
654
     * Process Chamilo FillBlanks
655
     *
656
     * @param object $objAnswer
657
     * @param array $question
658
     * @param array $answerValues
659
     * @param string $placeholder
660
     * @param integer $position
661
     * @return integer db response
662
     */
663
    public function processFillBlanks($objAnswer, $question, $answerValues, &$placeholder, $position)
664
    {
665
        switch ($question['qtype']) {
666
            case 'multichoice':
667
                $optionsValues = [];
668
669
                $correctAnswer = '';
670
                $othersAnswer = '';
671
                foreach ($answerValues as $answer) {
672
                    $correct = intval($answer['fraction']);
673
                    if ($correct) {
674
                        $correctAnswer .= $answer['answertext'].'|';
675
                        $optionsValues['weight'] = $answer['fraction'];
676
                        $optionsValues['size'] = '200';
677
                    } else {
678
                        $othersAnswer .= $answer['answertext'].'|';
679
                    }
680
                }
681
                $currentAnswers = $correctAnswer.$othersAnswer;
682
                $currentAnswers = '['.substr($currentAnswers, 0, -1).']';
683
                $placeholder = str_replace("{#$position}", $currentAnswers, $placeholder);
684
685
                return $optionsValues;
686
687
                break;
688
            case 'shortanswer':
689
                $optionsValues = [];
690
691
                $correctAnswer = '';
692
693
                foreach ($answerValues as $answer) {
694
                    $correct = intval($answer['fraction']);
695
                    if ($correct) {
696
                        $correctAnswer .= $answer['answertext'];
697
                        $optionsValues['weight'] = $answer['fraction'];
698
                        $optionsValues['size'] = '200';
699
                    }
700
                }
701
702
                $currentAnswers = '['.$correctAnswer.']';
703
                $placeholder = str_replace("{#$position}", $currentAnswers, $placeholder);
704
705
                return $optionsValues;
706
707
                break;
708
            default:
709
                return false;
710
                break;
711
        }
712
    }
713
714
715
    /**
716
     * Litle utility to delete the unuseful tags
717
     *
718
     * @param $array
719
     * @param $keys
720
     */
721
    public function traverseArray(&$array, $keys) {
722
        foreach ($array as $key => &$value) {
723
            if (is_array($value)) {
724
                $this->traverseArray($value, $keys);
725
            } else {
726
                if (in_array($key, $keys)){
727
                    unset($array[$key]);
728
                }
729
            }
730
        }
731
    }
732
733
}