1<?php
2
3declare(strict_types=1);
4
5/**
6 * Class ilObjLearningSequenceGUI
7 *
8 * @ilCtrl_isCalledBy ilObjLearningSequenceGUI: ilRepositoryGUI
9 * @ilCtrl_isCalledBy ilObjLearningSequenceGUI: ilAdministrationGUI
10 * @ilCtrl_Calls ilObjLearningSequenceGUI: ilPermissionGUI
11 * @ilCtrl_Calls ilObjLearningSequenceGUI: ilInfoScreenGUI
12 * @ilCtrl_Calls ilObjLearningSequenceGUI: ilCommonActionDispatcherGUI
13 * @ilCtrl_Calls ilObjLearningSequenceGUI: ilColumnGUI
14 * @ilCtrl_Calls ilObjLearningSequenceGUI: ilObjectCopyGUI
15 * @ilCtrl_Calls ilObjLearningSequenceGUI: ilExportGUI
16 * @ilCtrl_Calls ilObjLearningSequenceGUI: ilContainerLinkListGUI
17 * @ilCtrl_Calls ilObjLearningSequenceGUI: ilObjLearningSequenceSettingsGUI
18 * @ilCtrl_Calls ilObjLearningSequenceGUI: ilObjLearningSequenceContentGUI
19 * @ilCtrl_Calls ilObjLearningSequenceGUI: ilObjLearningSequenceLearnerGUI
20 * @ilCtrl_Calls ilObjLearningSequenceGUI: ilLearningSequenceMembershipGUI
21 * @ilCtrl_Calls ilObjLearningSequenceGUI: ilLearningProgressGUI
22 *
23 * @ilCtrl_Calls ilObjLearningSequenceGUI: ilObjLearningModuleGUI
24 * @ilCtrl_Calls ilObjLearningSequenceGUI: ilObjFileBasedLMGUI
25 * @ilCtrl_Calls ilObjLearningSequenceGUI: ilObjSAHSLearningModuleGUI
26 * @ilCtrl_Calls ilObjLearningSequenceGUI: ilObjContentPageGUI
27 * @ilCtrl_Calls ilObjLearningSequenceGUI: ilObjExerciseGUI
28 * @ilCtrl_Calls ilObjLearningSequenceGUI: ilObjFileGUI
29 * @ilCtrl_Calls ilObjLearningSequenceGUI: ilObjIndividualAssessmentGUI
30 * @ilCtrl_Calls ilObjLearningSequenceGUI: ilIndividualAssessmentSettingsGUI
31 * @ilCtrl_Calls ilObjLearningSequenceGUI: ilObjTestGUI
32 * @ilCtrl_Calls ilObjLearningSequenceGUI: ilObjSurveyGUI
33
34 */
35class ilObjLearningSequenceGUI extends ilContainerGUI
36{
37    const CMD_VIEW = "view";
38    const CMD_LEARNER_VIEW = "learnerView";
39    const CMD_CONTENT = "manageContent";
40
41    const CMD_MEMBERS = "members";
42    const CMD_MANAGE_MEMBERS = "participants";
43    const CMD_MEMBERS_GALLERY = "jump2UsersGallery";
44
45    const CMD_INFO = "showSummary";
46    const CMD_INFO_SCREEN = "infoScreen";
47    const CMD_SETTINGS = "settings";
48    const CMD_PERMISSIONS = "perm";
49    const CMD_LP = "learningProgress";
50    const CMD_EXPORT = "export";
51    const CMD_IMPORT = "importFile";
52    const CMD_CREATE = "create";
53    const CMD_SAVE = "save";
54    const CMD_CANCEL = "cancel";
55    const CMD_UNPARTICIPATE = "unparticipate";
56    const CMD_ADD_TO_DESK = "addToDesk";
57    const CMD_REMOVE_FROM_DESK = "removeFromDesk";
58    const CMD_LINK = "link";
59    const CMD_CANCEL_LINK = "cancelMoveLink";
60    const CMD_CUT = "cut";
61    const CMD_CANCEL_CUT = "cancelCut";
62    const CMD_CUT_SHOWTREE = "showPasteTree";
63    const CMD_CUT_CLIPBOARD = "keepObjectsInClipboard";
64    const CMD_DELETE = "delete";
65    const CMD_CANCEL_DELETE = "cancelDelete";
66    const CMD_DELETE_CONFIRMED = "confirmedDelete";
67    const CMD_PERFORM_PASTE = 'performPasteIntoMultipleObjects';
68    const CMD_SHOW_TRASH = 'trash';
69    const CMD_UNDELETE = 'undelete';
70
71    const TAB_VIEW_CONTENT = "view_content";
72    const TAB_MANAGE = "manage";
73    const TAB_CONTENT_MAIN = "manage_content_maintab";
74    const TAB_INFO = "show_summary";
75    const TAB_SETTINGS = "settings";
76    const TAB_PERMISSIONS = "perm_settings";
77    const TAB_MEMBERS = "members";
78    const TAB_LP = "learning_progress";
79    const TAB_EXPORT = "export";
80
81    const MAIL_ALLOWED_ALL = 1;
82    const MAIL_ALLOWED_TUTORS = 2;
83
84    const ACCESS_READ = 'read';
85    const ACCESS_VISIBLE = 'visible';
86
87    public $object;
88
89    public static function _goto(string $target)
90    {
91        global $DIC;
92
93        $request = $DIC->http()->request();
94        $lng = $DIC->language();
95        $err = $DIC['ilErr'];
96
97        $targetParameters = explode('_', $target);
98        $id = (int) $targetParameters[0];
99
100        if (!self::isAccessible($id)) {
101            $err->raiseError($lng->txt('msg_no_perm_read'), $err->FATAL);
102        }
103
104        if (self::hasAccess(self::ACCESS_READ, $id)) {
105            $params = ['ref_id' => $id];
106
107            if (isset($request->getQueryParams()['gotolp'])) {
108                $params['gotolp'] = 1;
109            }
110
111            self::forwardByClass(
112                ilRepositoryGUI::class,
113                [ilRepositoryGUI::class, ilObjLearningSequenceGUI::class],
114                $params,
115                self::CMD_VIEW
116            );
117        }
118
119        if (self::hasAccess(self::ACCESS_VISIBLE, $id)) {
120            ilObjectGUI::_gotoRepositoryNode($target, 'infoScreen');
121        }
122
123        if (self::hasAccess(self::ACCESS_READ, ROOT_FOLDER_ID)) {
124            ilUtil::sendInfo(sprintf(
125                $lng->txt('msg_no_perm_read_item'),
126                ilObject::_lookupTitle(ilObject::_lookupObjId($id))
127            ), true);
128
129            self::forwardByClass(ilRepositoryGUI::class, [ilRepositoryGUI::class], ['ref_id' => ROOT_FOLDER_ID]);
130        }
131    }
132
133    protected static function isAccessible(int $id) : bool
134    {
135        return $id > 0 && (
136            self::hasAccess(self::ACCESS_READ, $id) ||
137                self::hasAccess(self::ACCESS_VISIBLE, $id) ||
138                self::hasAccess(self::ACCESS_READ, ROOT_FOLDER_ID)
139        );
140    }
141
142    protected static function hasAccess(string $mode, int $id) : bool
143    {
144        global $DIC;
145        return $DIC->access()->checkAccess($mode, '', $id);
146    }
147
148    protected static function forwardByClass(string $base_class, array $classes, array $params, string $cmd = '')
149    {
150        global $DIC;
151        $ctrl = $DIC->ctrl();
152        $target_class = end($classes);
153
154        $ctrl->setTargetScript('ilias.php');
155        $ctrl->initBaseClass($base_class);
156
157        foreach ($params as $key => $value) {
158            $ctrl->setParameterByClass($target_class, $key, $value);
159        }
160
161        $ctrl->redirectByClass($classes, $cmd);
162    }
163
164    public function __construct()
165    {
166        $this->ref_id = (int) $_GET['ref_id'];
167        parent::__construct([], $this->ref_id, true, false);
168
169        $this->obj_type = ilObjLearningSequence::OBJ_TYPE;
170
171        global $DIC;
172        $this->ctrl = $DIC['ilCtrl'];
173        $this->lng = $DIC['lng'];
174        $this->user = $DIC['ilUser'];
175        $this->tabs = $DIC['ilTabs'];
176        $this->toolbar = $DIC['ilToolbar'];
177        $this->help = $DIC['ilHelp'];
178        $this->settings = $DIC['ilSetting'];
179        $this->access = $DIC['ilAccess'];
180        $this->rbac_review = $DIC['rbacreview'];
181        $this->ui_factory = $DIC['ui.factory'];
182        $this->ui_renderer = $DIC['ui.renderer'];
183
184        $this->log = $DIC["ilLoggerFactory"]->getRootLogger();
185        $this->app_event_handler = $DIC['ilAppEventHandler'];
186        $this->navigation_history = $DIC['ilNavigationHistory'];
187        $this->obj_definition = $DIC['objDefinition'];
188        $this->tpl = $DIC["tpl"];
189        $this->obj_service = $DIC->object();
190        $this->toolbar = $DIC['ilToolbar'];
191
192        $this->help->setScreenIdComponent($this->obj_type);
193        $this->lng->loadLanguageModule($this->obj_type);
194
195        $this->object = $this->getObject();
196        $this->data_factory = new \ILIAS\Data\Factory();
197    }
198
199    protected function recordLearningSequenceRead()
200    {
201        ilChangeEvent::_recordReadEvent(
202            $this->object->getType(),
203            $this->object->getRefId(),
204            $this->object->getId(),
205            $this->user->getId()
206        );
207    }
208
209    public function executeCommand()
210    {
211        $next_class = $this->ctrl->getNextClass($this);
212        $cmd = $this->ctrl->getCmd();
213        $tpl = $this->tpl;
214
215        parent::prepareOutput();
216        $this->addToNavigationHistory();
217        //showRepTree is from containerGUI;
218        //LSO will attach allowed subitems to whitelist
219        //see: $this::getAdditionalWhitelistTypes
220
221        $in_player = (
222            $next_class === 'ilobjlearningsequencelearnergui'
223            && $cmd === 'view'
224        );
225
226        $tpl->setPermanentLink("lso", $this->ref_id);
227
228        switch ($next_class) {
229            case "ilcommonactiondispatchergui":
230                $gui = ilCommonActionDispatcherGUI::getInstanceFromAjaxCall();
231                $this->ctrl->forwardCommand($gui);
232                break;
233            case "ilinfoscreengui":
234                $this->info($cmd);
235                break;
236            case "ilpermissiongui":
237                $this->permissions($cmd);
238                break;
239            case "ilobjlearningsequencesettingsgui":
240                $this->settings($cmd);
241                break;
242            case "ilobjlearningsequencecontentgui":
243                $this->manageContent($cmd);
244                break;
245            case "ilobjlearningsequencelearnergui":
246                $this->learnerView($cmd);
247                break;
248            case "illearningsequencemembershipgui":
249                $this->manage_members($cmd);
250                break;
251            case 'ilmailmembersearchgui':
252                $this->mail();
253                break;
254            case 'illearningprogressgui':
255                $this->learningProgress($cmd);
256                break;
257            case 'ilexportgui':
258                $this->export();
259                break;
260            case 'ilobjectcopygui':
261                $cp = new ilObjectCopyGUI($this);
262                $cp->setType('lso');
263                $this->ctrl->forwardCommand($cp);
264                break;
265            case 'ilobjindividualassessmentgui':
266                $struct = ['ilrepositorygui','ilobjindividualassessmentgui'];
267                if ($cmd === 'edit') {
268                    $struct[] = 'ilindividualassessmentsettingsgui';
269                }
270                $this->ctrl->redirectByClass($struct, $cmd);
271                break;
272            case 'ilobjtestgui':
273                $struct = ['ilrepositorygui','ilobjtestgui'];
274                $this->ctrl->redirectByClass($struct, $cmd);
275                break;
276
277            case false:
278                if ($cmd === '') {
279                    $cmd = self::CMD_VIEW;
280                }
281
282                switch ($cmd) {
283                    case self::CMD_IMPORT:
284                        $this->importFileObject();
285                        break;
286                    case self::CMD_INFO:
287                    case self::CMD_INFO_SCREEN:
288                        $this->info();
289                        break;
290                    case self::CMD_VIEW:
291                    case self::CMD_LEARNER_VIEW:
292                    case self::CMD_CONTENT:
293                    case self::CMD_MEMBERS:
294                    case self::CMD_SETTINGS:
295                    case self::CMD_SAVE:
296                    case self::CMD_CREATE:
297                    case self::CMD_LP:
298                    case self::CMD_UNPARTICIPATE:
299                        $this->$cmd();
300                        break;
301                    case self::CMD_CANCEL:
302                        if ($this->getCreationMode()) {
303                            $this->cancelCreation();
304                        }
305                        break;
306                    case self::CMD_REMOVE_FROM_DESK:
307                        $this->removeFromDeskObject();
308                        $this->view();
309                        break;
310                    case self::CMD_ADD_TO_DESK:
311                        $this->addToDeskObject();
312                        $this->view();
313                        break;
314                    case self::CMD_CUT:
315                        $this->cutObject();
316                        break;
317                    case self::CMD_CUT_SHOWTREE:
318                        $this->showPasteTreeObject();
319                        break;
320                    case self::CMD_CUT_CLIPBOARD:
321                        $this->keepObjectsInClipboardObject();
322                        break;
323                    case self::CMD_LINK:
324                        $this->linkObject();
325                        break;
326                    case self::CMD_DELETE:
327                        $this->deleteObject();
328                        break;
329                    case self::CMD_DELETE_CONFIRMED:
330                        $this->confirmedDeleteObject();
331                        break;
332                    case self::CMD_PERFORM_PASTE:
333                        $this->performPasteIntoMultipleObjectsObject();
334                        break;
335                    case self::CMD_SHOW_TRASH:
336                        $this->trashObject();
337                        break;
338                    case self::CMD_UNDELETE:
339                        $this->undeleteObject();
340                        break;
341
342                    case self::CMD_CANCEL_CUT:
343                    case self::CMD_CANCEL_DELETE:
344                    case self::CMD_CANCEL_LINK:
345                        $cmd = self::CMD_CONTENT;
346                        $this->$cmd();
347                        break;
348
349                    default:
350                        throw new ilException("ilObjLearningSequenceGUI: Invalid command '$cmd'");
351                }
352                break;
353            default:
354                throw new ilException("ilObjLearningSequenceGUI: Can't forward to next class $next_class");
355        }
356
357        if (!$in_player) {
358            $this->addHeaderAction();
359        }
360    }
361
362    public function addToNavigationHistory()
363    {
364        if (
365            !$this->getCreationMode() &&
366            $this->access->checkAccess('read', '', $this->ref_id)
367        ) {
368            $link = ilLink::_getLink($this->ref_id, $this->obj_type);
369            $this->navigation_history->addItem($this->ref_id, $link, $this->obj_type);
370        }
371    }
372
373    protected function info(string $cmd = self::CMD_INFO)
374    {
375        $this->tabs->setTabActive(self::TAB_INFO);
376        $this->ctrl->setCmdClass('ilinfoscreengui');
377        $this->ctrl->setCmd($cmd);
378        $info = new ilInfoScreenGUI($this);
379        $this->ctrl->forwardCommand($info);
380    }
381
382    protected function permissions(string $cmd = self::CMD_PERMISSIONS)
383    {
384        $this->tabs->setTabActive(self::TAB_PERMISSIONS);
385        $perm_gui = new ilPermissionGUI($this);
386        $this->ctrl->setCmd($cmd);
387        $this->ctrl->forwardCommand($perm_gui);
388    }
389
390    protected function settings(string $cmd = self::CMD_SETTINGS)
391    {
392        $this->tabs->activateTab(self::TAB_SETTINGS);
393        $gui = new ilObjLearningSequenceSettingsGUI(
394            $this->getObject(),
395            $this->ctrl,
396            $this->lng,
397            $this->tpl,
398            $this->obj_service
399        );
400        $this->ctrl->setCmd($cmd);
401        $this->ctrl->forwardCommand($gui);
402    }
403
404    protected function view()
405    {
406        $this->tabs->clearSubTabs();
407        if ($this->checkAccess("write")) {
408            $this->manageContent(self::CMD_CONTENT);
409            return;
410        }
411        if ($this->checkAccess("read")) {
412            $this->learnerView(self::CMD_LEARNER_VIEW);
413            $this->recordLearningSequenceRead();
414            return;
415        }
416        $this->info(self::CMD_INFO);
417        $this->recordLearningSequenceRead();
418    }
419
420    protected function manageContent(string $cmd = self::CMD_CONTENT)
421    {
422        $this->tabs->activateTab(self::TAB_CONTENT_MAIN);
423        $this->addSubTabsForContent($cmd);
424        $this->tabs->activateSubTab(self::TAB_MANAGE);
425
426        $gui = new ilObjLearningSequenceContentGUI(
427            $this,
428            $this->ctrl,
429            $this->tpl,
430            $this->lng,
431            $this->access,
432            new ilConfirmationGUI(),
433            new LSItemOnlineStatus()
434        );
435        $this->ctrl->setCmd($cmd);
436        $this->ctrl->forwardCommand($gui);
437    }
438
439    protected function learnerView(string $cmd = self::CMD_LEARNER_VIEW)
440    {
441        $this->tabs->activateTab(self::TAB_CONTENT_MAIN);
442        $this->addSubTabsForContent($cmd);
443        $this->tabs->activateSubTab(self::TAB_VIEW_CONTENT);
444
445        $gui = $this->object->getLocalDI()["gui.learner"];
446
447        $this->ctrl->setCmd($cmd);
448        $this->ctrl->forwardCommand($gui);
449    }
450
451    protected function members()
452    {
453        $may_manage_members = $this->checkAccess("edit_members");
454        $this->ctrl->setCmdClass('ilLearningSequenceMembershipGUI');
455        if ($may_manage_members) {
456            $this->manage_members(self::CMD_MANAGE_MEMBERS);
457        } else {
458            $this->manage_members(self::CMD_MEMBERS_GALLERY);
459        }
460    }
461
462    protected function manage_members(string $cmd = self::CMD_MANAGE_MEMBERS)
463    {
464        $this->tabs->setTabActive(self::TAB_MEMBERS);
465
466        $ms_gui = new ilLearningSequenceMembershipGUI(
467            $this,
468            $this->getObject(),
469            $this->getTrackingObject(),
470            ilPrivacySettings::_getInstance(),
471            $this->lng,
472            $this->ctrl,
473            $this->access,
474            $this->rbac_review,
475            $this->settings,
476            $this->toolbar
477        );
478
479        $this->ctrl->setCmd($cmd);
480        $this->ctrl->forwardCommand($ms_gui);
481    }
482
483    protected function learningProgress(string $cmd = self::CMD_LP)
484    {
485        $this->tabs->setTabActive(self::TAB_LP);
486
487        $for_user = $this->user->getId();
488
489        if ($_GET['user_id']) {
490            $for_user = $_GET['user_id'];
491        }
492
493        $lp_gui = new ilLearningProgressGUI(
494            ilLearningProgressGUI::LP_CONTEXT_REPOSITORY,
495            $this->getObject()->getRefId(),
496            $for_user
497        );
498
499        if ($cmd === self::CMD_LP) {
500            $cmd = '';
501        }
502
503        $this->ctrl->setCmd($cmd);
504        $this->ctrl->forwardCommand($lp_gui);
505    }
506
507    protected function export()
508    {
509        $this->tabs->setTabActive(self::TAB_EXPORT);
510        $gui = new ilExportGUI($this);
511        $gui->addFormat("xml");
512
513        $this->ctrl->forwardCommand($gui);
514    }
515
516    protected function initDidacticTemplate(ilPropertyFormGUI $form)
517    {
518        return $form;
519    }
520
521    protected function create()
522    {
523        parent::createObject();
524    }
525
526    protected function save()
527    {
528        parent::saveObject();
529    }
530
531    protected function afterSave(ilObject $new_object)
532    {
533        $participant = new ilLearningSequenceParticipants(
534            (int) $new_object->getId(),
535            $this->log,
536            $this->app_event_handler,
537            $this->settings
538        );
539
540        $participant->add($this->user->getId(), IL_LSO_ADMIN);
541        $participant->updateNotification($this->user->getId(), $this->settings->get('mail_lso_admin_notification', true));
542
543
544        $settings = new \ilContainerSortingSettings($new_object->getId());
545        $settings->setSortMode(\ilContainer::SORT_MANUAL);
546        $settings->setSortDirection(\ilContainer::SORT_DIRECTION_ASC);
547        $settings->setSortNewItemsOrder(\ilContainer::SORT_NEW_ITEMS_ORDER_CREATION);
548        $settings->setSortNewItemsPosition(\ilContainer::SORT_NEW_ITEMS_POSITION_BOTTOM);
549        $settings->save();
550
551        ilUtil::sendSuccess($this->lng->txt('object_added'), true);
552        $this->ctrl->setParameter($this, "ref_id", $new_object->getRefId());
553        ilUtil::redirect(
554            $this->getReturnLocation(
555                "save",
556                $this->ctrl->getLinkTarget($this, self::CMD_SETTINGS, "", false, false)
557            )
558        );
559    }
560
561    public function unparticipate()
562    {
563        if ($this->checkAccess('unparticipate')) {
564            $usr_id = (int) $this->user->getId();
565            $this->getObject()->getLSRoles()->leave($usr_id);
566            $this->learnerView();
567        }
568    }
569
570    protected function removeMember(int $usr_id)
571    {
572        $this->ls_object->leave($usr_id);
573    }
574
575    public function getTabs()
576    {
577        if ($this->checkAccess("read")) {
578            $this->tabs->addTab(
579                self::TAB_CONTENT_MAIN,
580                $this->lng->txt(self::TAB_CONTENT_MAIN),
581                $this->ctrl->getLinkTarget($this, self::CMD_VIEW, "", false, false)
582            );
583        }
584
585        if ($this->checkAccess("read") || $this->checkAccess("visible")) {
586            $this->tabs->addTab(
587                self::TAB_INFO,
588                $this->lng->txt(self::TAB_INFO),
589                $this->getLinkTarget(self::CMD_INFO)
590            );
591        }
592
593        if ($this->checkAccess("write")) {
594            $this->tabs->addTab(
595                self::TAB_SETTINGS,
596                $this->lng->txt(self::TAB_SETTINGS),
597                $this->getLinkTarget(self::CMD_SETTINGS)
598            );
599        }
600
601        if ($this->checkAccess("read")) {
602            if ($this->checkAccess("manage_members")
603                || (
604                    $this->getObject()->getLSSettings()->getMembersGallery()
605                    &&
606                    $this->getObject()->getLSRoles()->isMember((int) $this->user->getId())
607                )
608            ) {
609                $this->tabs->addTab(
610                    self::TAB_MEMBERS,
611                    $this->lng->txt(self::TAB_MEMBERS),
612                    $this->ctrl->getLinkTarget($this, self::CMD_MEMBERS, "", false, false)
613                );
614            }
615        }
616
617        if (ilObjUserTracking::_enabledLearningProgress() && $this->checkLPAccess()) {
618            $this->tabs->addTab(
619                self::TAB_LP,
620                $this->lng->txt(self::TAB_LP),
621                $this->getLinkTarget(self::CMD_LP)
622            );
623        }
624
625        if ($this->checkAccess("write")) {
626            $this->tabs->addTab(
627                self::TAB_EXPORT,
628                $this->lng->txt(self::TAB_EXPORT),
629                $this->ctrl->getLinkTargetByClass("ilexportgui", "")
630            );
631        }
632
633        if ($this->checkAccess("edit_permission")) {
634            $this->tabs->addTab(
635                self::TAB_PERMISSIONS,
636                $this->lng->txt(self::TAB_PERMISSIONS),
637                $this->getLinkTarget(self::CMD_PERMISSIONS)
638            );
639        }
640    }
641
642    public function renderObject()
643    {
644        // disables this method in ilContainerGUI
645    }
646
647    protected function addSubTabsForContent()
648    {
649        $this->tabs->addSubTab(
650            self::TAB_VIEW_CONTENT,
651            $this->lng->txt(self::TAB_VIEW_CONTENT),
652            $this->getLinkTarget(self::CMD_LEARNER_VIEW)
653        );
654
655        if ($this->checkAccess("write")) {
656            $this->tabs->addSubTab(
657                self::TAB_MANAGE,
658                $this->lng->txt(self::TAB_MANAGE),
659                $this->getLinkTarget(self::CMD_CONTENT)
660            );
661        }
662    }
663
664    protected function checkAccess($which) : bool
665    {
666        return $this->access->checkAccess($which, "", $this->ref_id);
667    }
668
669    protected function checkLPAccess()
670    {
671        $ref_id = $this->getObject()->getRefId();
672        $is_participant = ilLearningSequenceParticipants::_isParticipant($ref_id, $this->user->getId());
673
674        $lp_access = ilLearningProgressAccess::checkAccess($ref_id, $is_participant);
675        $may_edit_lp_settings = $this->checkAccess('edit_learning_progress');
676
677        return ($lp_access || $may_edit_lp_settings);
678    }
679
680    protected function getLinkTarget(string $cmd) : string
681    {
682        $class = $this->getClassForTabs($cmd);
683        $class_path = [
684            strtolower('ilObjLearningSequenceGUI'),
685            $class
686        ];
687        return $this->ctrl->getLinkTargetByClass($class_path, $cmd);
688    }
689
690    protected function getClassForTabs(string $cmd) : string
691    {
692        switch ($cmd) {
693            case self::CMD_CONTENT:
694                return 'ilObjLearningSequenceContentGUI';
695            case self::CMD_LEARNER_VIEW:
696                return 'ilObjLearningSequenceLearnerGUI';
697            case self::CMD_SETTINGS:
698                return 'ilObjLearningSequenceSettingsGUI';
699            case self::CMD_INFO:
700                return 'ilInfoScreenGUI';
701            case self::CMD_PERMISSIONS:
702                return 'ilPermissionGUI';
703            case self::CMD_LP:
704                return 'ilLearningProgressGUI';
705        }
706
707        throw new InvalidArgumentException('cannot resolve class for command: ' . $cmd);
708    }
709
710    public function createMailSignature()
711    {
712        $link = chr(13) . chr(10) . chr(13) . chr(10);
713        $link .= $this->lng->txt('lso_mail_permanent_link');
714        $link .= chr(13) . chr(10) . chr(13) . chr(10);
715        $link .= ilLink::_getLink($this->object->getRefId());
716
717        return rawurlencode(base64_encode($link));
718    }
719
720    public function getObject()
721    {
722        if ($this->object === null) {
723            $this->object = ilObjLearningSequence::getInstanceByRefId($this->ref_id);
724        }
725
726        return $this->object;
727    }
728
729    protected function getTrackingObject() : ilObjUserTracking
730    {
731        return new ilObjUserTracking();
732    }
733
734    /**
735     * @return [role_id] => title
736     */
737    public function getLocalRoles() : array
738    {
739        $local_roles = $this->object->getLocalLearningSequenceRoles(false);
740        $lso_member = $this->object->getDefaultMemberRole();
741        $lso_roles = array();
742
743        if (in_array($lso_member, $local_roles)) {
744            $lso_roles[$lso_member] = ilObjRole::_getTranslation(array_search($lso_member, $local_roles));
745            unset($local_roles[$lso_roles[$lso_member]]);
746        }
747
748        foreach ($local_roles as $title => $role_id) {
749            $lso_roles[$role_id] = ilObjRole::_getTranslation($title);
750        }
751
752        return $lso_roles;
753    }
754
755    /**
756     * append additional types to ilRepositoryExplorerGUI's whitelist
757     */
758    protected function getAdditionalWhitelistTypes() : array
759    {
760        $types = array_filter(
761            array_keys($this->obj_definition->getSubObjects('lso', false)),
762            function ($type) {
763                return $type !== 'rolf';
764            }
765        );
766
767        return $types;
768    }
769
770    public function addCustomData($a_data)
771    {
772        $res_data = array();
773        foreach ($a_data as $usr_id => $user_data) {
774            $res_data[$usr_id] = $user_data;
775            $udf_data = new ilUserDefinedData($usr_id);
776
777            foreach ($udf_data->getAll() as $field => $value) {
778                list($f, $field_id) = explode('_', $field);
779                $res_data[$usr_id]['udf_' . $field_id] = (string) $value;
780            }
781        }
782
783        return $res_data;
784    }
785}
786