ILIAS  trunk Revision v12.0_alpha-1338-g8f7e531aa3c
class.ilLMTOCExplorerGUI.php
Go to the documentation of this file.
1<?php
2
25{
26 protected string $lang;
27 protected int $highlight_node = 0;
28 protected bool $export_all_languages;
30 protected array $complete_tree = [];
31 protected array $activation_data = [];
32 protected ilSetting $lm_set;
34 protected int $focus_id = 0;
37
42 public function __construct(
43 $a_parent_obj,
44 string $a_parent_cmd,
46 string $a_lang = "-",
47 int $a_focus_id = 0,
48 bool $export_all_languages = false
49 ) {
50 global $DIC;
51
52 $this->service = $service;
53 $this->user = $DIC->user();
54 $this->lm = $service->getLearningModule();
55 $this->linker = $service->getLinker();
56 $this->tracker = $service->getTracker();
57
58 $exp_id = (!$this->getOfflineMode() && $this->lm->getProgressIcons())
59 ? "ilLMProgressTree"
60 : "";
61 parent::__construct($a_parent_obj, $a_parent_cmd, $this->lm, $exp_id);
62 $this->lm_set = new ilSetting("lm");
63 $this->lang = $a_lang;
64 if ($a_focus_id > 0) {
65 $sec_high = [];
66 foreach ($this->tree->getSubTree($this->tree->getNodeData($a_focus_id)) as $node) {
67 $sec_high[] = $node["child"];
68 }
69 $this->setSecondaryHighlightedNodes($sec_high);
70 }
71 if ($this->lm->getTOCMode() != "pages") {
72 $this->setTypeWhiteList(array("st", "du"));
73 }
74 $this->focus_id = $a_focus_id;
75 $this->export_all_languages = $export_all_languages;
76
77 $this->activation_repo = new ilPageActivationDBRepository();
78
79 $this->initTreeData();
80 }
81
82 protected function initTreeData(): void
83 {
84 $nodes = $this->tree->getCompleteTree();
85 foreach ($nodes as $node) {
86 $this->complete_tree["childs"][$node["parent"]][] = $node;
87 $this->complete_tree["parent"][$node["child"]] = $node["parent"];
88 $this->complete_tree["nodes"][$node["child"]] = $node;
89 }
90
91 $page_ids = array_column($this->complete_tree["nodes"], "child");
92 $this->activation_data = $this->activation_repo->get(
93 "lm",
94 $page_ids,
95 (bool) $this->lm_set->get("time_scheduled_page_activation"),
96 $this->lang
97 );
98 $this->initVisibilityData($this->tree->readRootId());
99 }
100
101 protected function initVisibilityData(
102 int $node_id
103 ): void {
104 $current_node = $this->complete_tree["nodes"][$node_id];
105
106 if (isset($this->complete_tree["childs"][$node_id])) {
107 foreach ($this->complete_tree["childs"][$node_id] as $node) {
108 $this->initVisibilityData($node["child"]);
109 }
110 }
111
112 // pages are visible if they are active or activation info should be shown
113 if ($current_node["type"] == "pg") {
114 $this->complete_tree["visibility"][$node_id] = ($this->activation_data[$node_id]["active"] ||
115 $this->activation_data[$node_id]["show_info"]);
116 } elseif ($current_node["type"] == "st") {
117 // make chapters visible as soon as there is one visible child
118 $this->complete_tree["visibility"][$node_id] = false;
119 if (isset($this->complete_tree["childs"][$node_id])) {
120 foreach ($this->complete_tree["childs"][$node_id] as $node) {
121 if (isset($this->complete_tree["visibility"][$node["child"]]) &&
122 $this->complete_tree["visibility"][$node["child"]]) {
123 $this->complete_tree["visibility"][$node_id] = true;
124 }
125 }
126 }
127 } else {
128 $this->complete_tree["visibility"][$node_id] = true;
129 }
130 }
131
132 public function getRootNode(): array
133 {
134 $root_id = $this->getTree()->readRootId();
135 if ($this->focus_id > 0 && $this->getTree()->isInTree($this->focus_id) &&
136 ilLMObject::_lookupType($this->focus_id) == "st") {
137 // $root_id = $this->focus_id;
138 }
139 return $this->getTree()->getNodeData($root_id);
140 }
141
142 public function setTracker(ilLMTracker $a_val): void
143 {
144 $this->tracker = $a_val;
145 }
146
147 public function getTracker(): ilLMTracker
148 {
149 return $this->tracker;
150 }
151
152 public function setHighlightNode(int $a_val): void
153 {
154 $this->highlight_node = $a_val;
155 }
156
157 public function getHighlightNode(): int
158 {
159 return $this->highlight_node;
160 }
161
165 public function isNodeHighlighted($a_node): bool
166 {
167 if ($a_node["child"] == $this->getHighlightNode()) {
168 return true;
169 }
170 return false;
171 }
172
176 public function getNodeContent($a_node): string
177 {
178 if ($a_node["type"] == "st") {
180 $a_node["child"],
182 $this->lm->isActiveNumbering(),
183 false,
184 false,
185 $this->lm->getId(),
186 $this->lang,
187 true
188 );
189 } elseif ($a_node["type"] == "pg") {
191 $a_node["child"],
192 $this->lm->getPageHeader(),
193 $this->lm->isActiveNumbering(),
194 (bool) $this->lm_set->get("time_scheduled_page_activation"),
195 true,
196 $this->lm->getId(),
197 $this->lang,
198 true
199 );
200 } elseif ($a_node["child"] == $this->getNodeId($this->getRootNode())) {
201 $content = $this->service->getPresentationStatus()->getLMPresentationTitle();
202 }
203
204 return $this->highlightContent($a_node, $content);
205 }
206
207 protected function highlightContent(array $node, string $content): string
208 {
209 if ($this->isNodeHighlighted($node)) {
210 $content = "<b>" . $content . "</b>";
211 }
212 $sec = $this->getSecondaryHighlightedNodes();
213 if (in_array($node["child"], $sec)) {
214 return "<span class='ilHighlighted'>" . $content . "</span>";
215 }
216 return $content;
217 }
218
219
223 public function getNodeIcon($a_node): string
224 {
225 // overwrite chapter icons with lp info?
226 if (!$this->getOfflineMode() && $a_node["type"] == "st") {
227 $icon = $this->checkLPIcon($a_node["child"]);
228 if ($icon != "") {
229 return $icon;
230 }
231 }
232 // use progress icons (does not depend on lp mode)
233 if (!$this->getOfflineMode() && $this->lm->getProgressIcons()) {
234 return $this->tracker->getIconForLMObject($a_node, $this->highlight_node);
235 }
236
237 if ($a_node["type"] == "du") {
238 $a_node["type"] = "lm";
239 }
240 $a_name = "standard/icon_" . $a_node["type"] . ".svg";
241 if ($a_node["type"] == "pg") {
242 $lm_set = new ilSetting("lm");
243 $active = ilLMPage::_lookupActive(
244 $a_node["child"],
245 $this->lm->getType(),
246 (bool) $lm_set->get("time_scheduled_page_activation")
247 );
248
249 // is page scheduled?
250 $img_sc = ($lm_set->get("time_scheduled_page_activation") &&
251 ilLMPage::_isScheduledActivation($a_node["child"], $this->lm->getType()) && !$active
252 && !$this->getOfflineMode())
253 ? "_sc"
254 : "";
255
256 $a_name = "standard/icon_pg" . $img_sc . ".svg";
257
258 if (!$active && !$this->getOfflineMode()) {
259 $a_name = "standard/icon_pg_d" . $img_sc . ".svg";
260 }
261 }
262
263 return ilUtil::getImagePath($a_name, false, "output", $this->getOfflineMode());
264 }
265
269 public function isNodeClickable($a_node): bool
270 {
271 $ilUser = $this->user;
272 $orig_node_id = $a_node["child"];
273
274 // if navigation is restricted based on correct answered questions
275 // check if we have preceeding pages including unsanswered/incorrect answered questions
276 if (!$this->getOfflineMode()) {
277 if ($this->lm->getRestrictForwardNavigation()) {
278 if ($this->getTracker()->hasPredIncorrectAnswers($orig_node_id)) {
279 return false;
280 }
281 }
282 }
283
284 if ($a_node["type"] == "st") {
285 if (!$this->getOfflineMode()) {
286 if ($this->lm->getTOCMode() != "pages") {
287 $a_node = $this->getTree()->fetchSuccessorNode($a_node["child"], "pg");
288 } else {
289 // faster, but needs pages to be in explorer
290 $a_node = $this->getSuccessorNode($a_node["child"], "pg");
291 }
292 if (($a_node["child"] ?? 0) == 0) {
293 return false;
294 }
295 } else {
296 // get next activated page
297 $found = false;
298 while (!$found) {
299 if ($this->lm->getTOCMode() != "pages") {
300 $a_node = $this->getTree()->fetchSuccessorNode($a_node["child"], "pg");
301 } else {
302 $a_node = $this->getSuccessorNode($a_node["child"], "pg");
303 }
304 $active = ilLMPage::_lookupActive(
305 $a_node["child"],
306 $this->lm->getType(),
307 (bool) $this->lm_set->get("time_scheduled_page_activation")
308 );
309
310 if ($a_node["child"] > 0 && !$active) {
311 $found = false;
312 } else {
313 $found = true;
314 }
315 }
316 if ($a_node["child"] <= 0) {
317 return false;
318 } else {
319 $path = $this->getTree()->getPathId($a_node["child"]);
320 if (!in_array($orig_node_id, $path)) {
321 return false;
322 }
323 }
324 }
325 }
326
327 return true;
328 }
329
330
334 public function getNodeIconAlt($a_node): string
335 {
336 return "";
337 }
338
342 public function getNodeHref($a_node): string
343 {
344 if (!$this->getOfflineMode()) {
345 return $this->linker->getLink("", $a_node["child"]);
346 }
347 // for offline, see build()
348 return "---";
349 }
350
351 public function build(
352 \ILIAS\UI\Component\Tree\Node\Factory $factory,
353 $a_node,
354 $environment = null
355 ): \ILIAS\UI\Component\Tree\Node\Node {
356 $node = parent::build($factory, $a_node, $environment);
357 if ($this->getOfflineMode()) {
358 if ($a_node["type"] !== "pg") {
359 // get next activated page
360 $found = false;
361 while (!$found) {
362 $a_node = $this->getTree()->fetchSuccessorNode($a_node["child"], "pg");
363 if (is_null($a_node)) {
364 return $node;
365 }
366 $active = ilLMPage::_lookupActive(
367 $a_node["child"],
368 $this->lm->getType(),
369 (bool) $this->lm_set->get("time_scheduled_page_activation")
370 );
371
372 if ($a_node["child"] > 0 && !$active) {
373 $found = false;
374 } else {
375 $found = true;
376 }
377 }
378 }
379
380 $lang_suffix = "";
381 if ($this->export_all_languages) {
382 if ($this->lang != "" && $this->lang != "-") {
383 $lang_suffix = "_" . $this->lang;
384 }
385 }
386
387 if ($nid = ilLMPageObject::getExportId($this->lm->getId(), $a_node["child"])) {
388 $target = "./lm_pg_" . $nid . $lang_suffix . ".html";
389 } else {
390 $target = "./lm_pg_" . $a_node["child"] . $lang_suffix . ".html";
391 }
392
393 $node = $node->withAdditionalOnLoadCode(function ($id) use ($target): string {
394 return "document.getElementById('$id').querySelector('a').addEventListener('click', (event) => { event.preventDefault(); window.location.href = '$target';});";
395 });
396 }
397
398 return $node;
399 }
400
401
405 public function isNodeVisible($a_node): bool
406 {
407 return (bool) $this->complete_tree["visibility"][$a_node["child"]];
408 }
409
410 //
411 // Learning Sequence TOC
412 //
413
414 public function renderLSToc(\LSTOCBuilder $toc): void
415 {
416 $this->renderLSTocNode($toc, null);
417 }
418
419 protected function renderLSTocNode(\LSTOCBuilder $toc, ?array $current_node = null): void
420 {
421 $root = false;
422 if ($current_node == 0) {
423 $root = true;
424 $current_node = $this->tree->getNodeData($this->tree->readRootId());
425 }
426
427 $children = $this->getChildren($current_node);
428 if (count($children) > 0) {
429 if ($root) {
430 $node_toc = $toc;
431 } else {
432 // current workaround
434 $node_icon = $this->getNodeIcon($current_node);
435 if (strpos($node_icon, "complete")) {
437 }
438
439 $node_toc = $toc->node($current_node["title"], $current_node["child"], $lp);
440 }
441 foreach ($this->getChildren($current_node) as $child) {
442 $this->renderLSTocNode($node_toc, $child);
443 }
444 $node_toc->end();
445 } else {
446 $highlight = $this->isNodeHighlighted($current_node);
447 $toc->item($current_node["title"], $current_node["child"], null, $highlight);
448 }
449 }
450}
$id
plugin.php for ilComponentBuildPluginInfoObjectiveTest::testAddPlugins
Definition: plugin.php:23
Class LSTOCBuilder.
node(string $label, ?int $parameter=null, ?int $lp=null)
Build a sub tree in the TOC.If a parameter is provided, the node in the TOC can be accessed itself....
item(string $label, int $parameter, $state=null, bool $current=false)
Build an entry in the TOC.The parameter will be appended to the command when updating the state....
setSecondaryHighlightedNodes(array $a_val)
Set secondary (background) highlighted nodes.
This file is part of ILIAS, a powerful learning management system published by ILIAS open source e-Le...
static getExportId(int $a_lm_id, int $a_lmobj_id, string $a_type="pg")
static _lookupType(int $a_obj_id, int $a_lm_id=0)
static _getPresentationTitle(int $a_pg_id, string $a_mode=self::CHAPTER_TITLE, bool $a_include_numbers=false, bool $a_time_scheduled_activation=false, bool $a_force_content=false, int $a_lm_id=0, string $a_lang="-", bool $a_include_short=false)
presentation title doesn't have to be page title, it may be chapter title + page title or chapter tit...
Learning module presentation linker.
Main service init and factory.
This file is part of ILIAS, a powerful learning management system published by ILIAS open source e-Le...
build(\ILIAS\UI\Component\Tree\Node\Factory $factory, $a_node, $environment=null)
setTracker(ilLMTracker $a_val)
ilLMPresentationLinker $linker
renderLSToc(\LSTOCBuilder $toc)
ilLMPresentationService $service
highlightContent(array $node, string $content)
__construct( $a_parent_obj, string $a_parent_cmd, ilLMPresentationService $service, string $a_lang="-", int $a_focus_id=0, bool $export_all_languages=false)
Constructor.
ilPageActivationDBRepository $activation_repo
renderLSTocNode(\LSTOCBuilder $toc, ?array $current_node=null)
This file is part of ILIAS, a powerful learning management system published by ILIAS open source e-Le...
This file is part of ILIAS, a powerful learning management system published by ILIAS open source e-Le...
static _isScheduledActivation(int $a_id, string $a_parent_type, string $a_lang="-")
Check whether page is activated by time schedule.
static _lookupActive(int $a_id, string $a_parent_type, bool $a_check_scheduled_activation=false, string $a_lang="-")
lookup activation status
ILIAS Setting Class.
static _getPresentationTitle(int $a_st_id, string $a_mode=self::CHAPTER_TITLE, bool $a_include_numbers=false, bool $a_time_scheduled_activation=false, bool $a_force_content=false, int $a_lm_id=0, string $a_lang="-", bool $a_include_short=false)
setTypeWhiteList(array $a_val)
Set type white list.
static getImagePath(string $image_name, string $module_path="", string $mode="output", bool $offline=false)
get image path (for images located in a template directory)
$path
Definition: ltiservices.php:30
__construct(Container $dic, ilPlugin $plugin)
@inheritDoc
Interface Observer \BackgroundTasks Contains several chained tasks and infos about them.
global $DIC
Definition: shib_login.php:26
$lm_set