ILIAS  trunk Revision v11.0_alpha-3011-gc6b235a2e85
class.ilPCTableGUI.php
Go to the documentation of this file.
1<?php
2
26{
27 protected \ILIAS\COPage\Dom\DomUtil $dom_util;
28 protected \ILIAS\COPage\PC\PCDefinition $pc_definition;
29 protected \ILIAS\COPage\Xsl\XslManager $xsl;
31 protected ilTabsGUI $tabs;
32 protected ilObjUser $user;
33
34 public function __construct(
35 ilPageObject $a_pg_obj,
36 ?ilPageContent $a_content_obj,
37 string $a_hier_id,
38 string $a_pc_id = ""
39 ) {
40 global $DIC;
41
42 $this->tabs = $DIC->tabs();
43 $this->ctrl = $DIC->ctrl();
44 $this->lng = $DIC->language();
45 $this->tpl = $DIC["tpl"];
46 $this->user = $DIC->user();
47 parent::__construct($a_pg_obj, $a_content_obj, $a_hier_id, $a_pc_id);
48 $this->setCharacteristics(array("StandardTable" => $this->lng->txt("cont_StandardTable")));
49 $this->tool_context = $DIC->globalScreen()->tool()->context();
50 $this->xsl = $DIC->copage()->internal()->domain()->xsl();
51 $this->pc_definition = $DIC
52 ->copage()
53 ->internal()
54 ->domain()
55 ->pc()
56 ->definition();
57 $this->dom_util = $DIC->copage()->internal()->domain()->domUtil();
58 }
59
60 public function setBasicTableCellStyles(): void
61 {
62 $this->setCharacteristics(array("Cell1" => "Cell1", "Cell2" => "Cell2",
63 "Cell3" => "Cell3", "Cell4" => "Cell4"));
64 }
65
69 public function executeCommand()
70 {
71 $this->getCharacteristicsOfCurrentStyle(["table"]); // scorm-2004
72
73 // get next class that processes or forwards current command
74 $next_class = $this->ctrl->getNextClass($this);
75
76 // get current command
77 $cmd = $this->ctrl->getCmd();
78
79 switch ($next_class) {
80 default:
81 $this->$cmd();
82 break;
83 }
84 return "";
85 }
86
87 public function setTabs(
88 string $data_tab_txt_key = ""
89 ): void {
90 $ilTabs = $this->tabs;
91 $ilCtrl = $this->ctrl;
93
94 $ilTabs->setBackTarget(
95 "",
96 ""
97 );
98
99 return;
100
101 $ilTabs->setBackTarget(
102 $lng->txt("pg"),
103 (string) $this->ctrl->getParentReturn($this)
104 );
105
106 if ($data_tab_txt_key == "") {
107 $data_tab_txt_key = "cont_table_edit_cells";
108 }
109
110 $ilTabs->addTarget(
111 $data_tab_txt_key,
112 $ilCtrl->getLinkTarget($this, "editData"),
113 "editData",
114 get_class($this)
115 );
116
117 $ilTabs->addTarget(
118 "cont_table_properties",
119 $ilCtrl->getLinkTarget($this, "editProperties"),
120 "editProperties",
121 get_class($this)
122 );
123
124 $ilTabs->addTarget(
125 "cont_table_cell_properties",
126 $ilCtrl->getLinkTarget($this, "editCellStyle"),
127 "editCellStyle",
128 get_class($this)
129 );
130 }
131
132 public function setCellPropertiesSubTabs(): void
133 {
134 $ilTabs = $this->tabs;
135 $ilCtrl = $this->ctrl;
136
137 $ilTabs->addSubTabTarget(
138 "cont_style",
139 $ilCtrl->getLinkTarget($this, "editCellStyle"),
140 "editCellStyle",
141 get_class($this)
142 );
143
144 $ilTabs->addSubTabTarget(
145 "cont_width",
146 $ilCtrl->getLinkTarget($this, "editCellWidth"),
147 "editCellWidth",
148 get_class($this)
149 );
150
151 $ilTabs->addSubTabTarget(
152 "cont_alignment",
153 $ilCtrl->getLinkTarget($this, "editCellAlignment"),
154 "editCellAlignment",
155 get_class($this)
156 );
157
158 $ilTabs->addSubTabTarget(
159 "cont_span",
160 $ilCtrl->getLinkTarget($this, "editCellSpan"),
161 "editCellSpan",
162 get_class($this)
163 );
164 }
165
166 public function getTemplateOptions(string $a_type = ""): array
167 {
168 return parent::getTemplateOptions("table");
169 }
170
171 public function edit(): void
172 {
173 $this->ctrl->redirect($this, "editData");
174 }
175
176 public function editProperties(): void
177 {
178 $tpl = $this->tpl;
179
180 $this->displayValidationError();
181 $this->setTabs();
182
183 $this->initPropertiesForm();
184 $this->getPropertiesFormValues();
185 $html = $this->form->getHTML();
186 $html .= "<br />" . $this->renderTable("");
187 $tpl->setContent($html);
188 }
189
190 protected function getFormTitle(string $a_mode = "edit"): string
191 {
192 if ($a_mode === "create") {
193 return $this->lng->txt("cont_insert_table");
194 }
195 return $this->lng->txt("cont_table_properties");
196 }
197
198 public function initPropertiesForm(
199 string $a_mode = "edit"
200 ): void {
201 $a_seleted_value = "";
202 $ilCtrl = $this->ctrl;
204 $ilUser = $this->user;
205
206 $this->form = new ilPropertyFormGUI();
207 $this->form->setFormAction($ilCtrl->getFormAction($this));
208 $this->form->setTitle($this->getFormTitle($a_mode));
209
210 if ($a_mode == "create") {
211 $nr = array();
212 for ($i = 1; $i <= 20; $i++) {
213 $nr[$i] = $i;
214 }
215
216 // cols
217 $cols = new ilSelectInputGUI($this->lng->txt("cont_nr_cols"), "nr_cols");
218 $cols->setOptions($nr);
219 $cols->setValue(2);
220 $this->form->addItem($cols);
221
222 // rows
223 $rows = new ilSelectInputGUI($this->lng->txt("cont_nr_rows"), "nr_rows");
224 $rows->setOptions($nr);
225 $rows->setValue(2);
226 $this->form->addItem($rows);
227 }
228
229 // width
230 $width = new ilTextInputGUI($this->lng->txt("cont_table_width"), "width");
231 $width->setSize(6);
232 $width->setMaxLength(6);
233 $this->form->addItem($width);
234
235 /*
236 // border
237 $border = new ilTextInputGUI($this->lng->txt("cont_table_border"), "border");
238 $border->setInfo($this->lng->txt("cont_table_border_info"));
239 $border->setValue("1px");
240 $border->setSize(6);
241 $border->setMaxLength(6);
242 $this->form->addItem($border);
243
244 // padding
245 $padding = new ilTextInputGUI($this->lng->txt("cont_table_cellpadding"), "padding");
246 $padding->setInfo($this->lng->txt("cont_table_cellpadding_info"));
247 $padding->setValue("2px");
248 $padding->setSize(6);
249 $padding->setMaxLength(6);
250 $this->form->addItem($padding);
251
252 // spacing (deprecated, only hidden)
253 $spacing = new ilHiddenInputGUI("spacing");
254 $spacing->setValue("0px");
255 $this->form->addItem($spacing);*/
256
257 // table templates and table classes
258 $char_prop = new ilSelectInputGUI(
259 $this->lng->txt("cont_characteristic_table"),
260 "characteristic"
261 );
262 $chars = $this->getCharacteristics();
263 $templates = $this->getTemplateOptions();
264 $chars = array_merge($templates, $chars);
265 if (is_object($this->content_obj)) {
266 if (($chars[$a_seleted_value] ?? "") == "" && ($this->content_obj->getClass() != "")) {
267 $chars = array_merge(
268 array($this->content_obj->getClass() => $this->content_obj->getClass()),
269 $chars
270 );
271 }
272 }
273 $options = [];
274 foreach ($chars as $k => $char) {
275 if (strpos($k, ":") > 0) {
276 $t = explode(":", $k);
277 $html = $this->style->lookupTemplatePreview($t[1]) . '<div style="clear:both;" class="small">' . $char . "</div>";
278 } else {
279 $html = '<table class="ilc_table_' . $k . '"><tr><td class="small">' .
280 $char . '</td></tr></table>';
281 }
282 //$char_prop->addOption($k, $char, $html);
283 $options[$k] = $char;
284 }
285 $char_prop->setOptions($options);
286 $char_prop->setValue("StandardTable");
287 $this->form->addItem($char_prop);
288
289 $nr = array();
290 for ($i = 0; $i <= 3; $i++) {
291 $nr[$i] = $i;
292 }
293
294 // row header
295 $rh = new ilSelectInputGUI($this->lng->txt("cont_nr_row_header"), "row_header");
296 $rh->setOptions($nr);
297 $rh->setValue(1);
298 $this->form->addItem($rh);
299
300 // row footer
301 $rf = new ilSelectInputGUI($this->lng->txt("cont_nr_row_footer"), "row_footer");
302 $rf->setOptions($nr);
303 $rf->setValue(0);
304 $this->form->addItem($rf);
305
306 // col header
307 $ch = new ilSelectInputGUI($this->lng->txt("cont_nr_col_header"), "col_header");
308 $ch->setOptions($nr);
309 $ch->setValue(0);
310 $this->form->addItem($ch);
311
312 // col footer
313 $cf = new ilSelectInputGUI($this->lng->txt("cont_nr_col_footer"), "col_footer");
314 $cf->setOptions($nr);
315 $cf->setValue(0);
316 $this->form->addItem($cf);
317
318 if ($a_mode == "create") {
319 // first row style
320 $fr_style = new ilSelectInputGUI(
321 $this->lng->txt("cont_first_row_style"),
322 "first_row_style"
323 );
324 $this->setBasicTableCellStyles();
325 $this->getCharacteristicsOfCurrentStyle(["table_cell"]);
326 $chars = $this->getCharacteristics();
327 $options = array_merge(array("" => $this->lng->txt("none")), $chars);
328 $fr_style->setOptions($options);
329
330 $fr_style->setValue("");
331 $this->form->addItem($fr_style);
332 }
333
334 // alignment
335 $align_opts = array("Left" => $lng->txt("cont_left"),
336 "Right" => $lng->txt("cont_right"), "Center" => $lng->txt("cont_center"),
337 "LeftFloat" => $lng->txt("cont_left_float"),
338 "RightFloat" => $lng->txt("cont_right_float"));
339 $align = new ilSelectInputGUI($this->lng->txt("cont_align"), "align");
340 $align->setOptions($align_opts);
341 $align->setValue("Center");
342 $this->form->addItem($align);
343
344 // caption
345 $caption = new ilTextInputGUI($this->lng->txt("cont_caption"), "caption");
346 $caption->setSize(60);
347 $this->form->addItem($caption);
348
349 // caption align
350 $ca_opts = array("top" => $lng->txt("cont_top"),
351 "bottom" => $lng->txt("cont_bottom"));
352 $ca = new ilSelectInputGUI(
353 $this->lng->txt("cont_align"),
354 "cap_align"
355 );
356 $ca->setOptions($ca_opts);
357 $caption->addSubItem($ca);
358
359 // import
360 if ($a_mode == "create") {
361 // import table
362 $import = new ilRadioGroupInputGUI($this->lng->txt("cont_paste_table"), "import_type");
363 $op = new ilRadioOption($this->lng->txt("cont_html_table"), "html");
364 $import->addOption($op);
365 $op2 = new ilRadioOption($this->lng->txt("cont_spreadsheet_table"), "spreadsheet");
366
367 $import_data = new ilTextAreaInputGUI("", "import_table");
368 $import_data->setRows(8);
369 $import_data->setCols(50);
370 $op2->addSubItem($import_data);
371
372 $import->addOption($op2);
373 $import->setValue("html");
374 $this->form->addItem($import);
375 }
376
377 // language
378 if ($this->getCurrentTextLang() != "") {
379 $s_lang = $this->getCurrentTextLang();
380 } else {
381 $s_lang = $ilUser->getLanguage();
382 }
383 $languages = [];
384 foreach ($this->lom_services->dataHelper()->getAllLanguages() as $language) {
385 $languages[$language->value()] = $language->presentableLabel();
386 }
387 $language = new ilSelectInputGUI($this->lng->txt("language"), "language");
388 $language->setOptions($languages);
389 $language->setValue($s_lang);
390 $this->form->addItem($language);
391
392 if ($a_mode == "create") {
393 $this->form->addCommandButton("create", $lng->txt("save"));
394 $this->form->addCommandButton("cancelCreate", $lng->txt("cancel"));
395 } else {
396 $this->form->addCommandButton("saveProperties", $lng->txt("save"));
397 $this->form->addCommandButton("editData", $lng->txt("close"));
398 }
399 }
400
401 public function getPropertiesFormValues(): void
402 {
403 $values = array();
404 $values["width"] = $this->content_obj->getWidth();
405 //$values["border"] = $this->content_obj->getBorder();
406 //$values["padding"] = $this->content_obj->getCellPadding();
407 //$values["spacing"] = $this->content_obj->getCellSpacing();
408 $values["row_header"] = $this->content_obj->getHeaderRows();
409 $values["row_footer"] = $this->content_obj->getFooterRows();
410 $values["col_header"] = $this->content_obj->getHeaderCols();
411 $values["col_footer"] = $this->content_obj->getFooterCols();
412 if ($this->content_obj->getTemplate() != "") {
413 $values["characteristic"] = "t:" .
414 ilObjStyleSheet::_lookupTemplateIdByName($this->getStyleId(), $this->content_obj->getTemplate()) . ":" .
415 $this->content_obj->getTemplate();
416 } else {
417 $values["characteristic"] = $this->content_obj->getClass();
418 }
419 $values["align"] = $this->content_obj->getHorizontalAlign();
420 $values["caption"] = $this->content_obj->getCaption();
421 $values["cap_align"] = $this->content_obj->getCaptionAlign();
422 $values["language"] = $this->content_obj->getLanguage();
423
424 $this->form->setValuesByArray($values);
425
426 $ca = $this->form->getItemByPostVar("cap_align");
427 $ca->setValue($this->content_obj->getCaptionAlign());
428 }
429
430 public function renderTable(
431 string $a_mode = "table_edit",
432 string $a_submode = ""
433 ): string {
434 $template_xml = "";
435 $tab_node = $this->content_obj->getDomNode();
436 $tab_node->setAttribute("Enabled", "True");
437 $content = $this->dom_util->dump($tab_node);
438
439 $trans = $this->pg_obj->getLanguageVariablesXML();
440 $mobs = $this->pg_obj->getMultimediaXML();
441 if ($this->getStyleId() > 0) {
442 if (ilObject::_lookupType($this->getStyleId()) == "sty") {
443 $style = new ilObjStyleSheet($this->getStyleId());
444 $template_xml = $style->getTemplateXML();
445 }
446 }
447
448 $content = $content . $mobs . $trans . $template_xml;
449
451 $tab = $this->content_obj;
453 $content,
454 $a_mode,
455 $a_submode,
456 $tab,
457 !$this->pg_obj->getPageConfig()->getPreventHTMLUnmasking(),
458 $this->getPage()
459 );
460 }
461
462 public static function _renderTable(
463 string $content,
464 string $a_mode = "table_edit",
465 string $a_submode = "",
466 ?ilPCTable $a_table_obj = null,
467 bool $unmask = true,
468 ?ilPageObject $page_object = null
469 ): string {
470 global $DIC;
471
472 $ilUser = $DIC->user();
473 $xsl = $DIC->copage()->internal()->domain()->xsl();
474 $pc_definition = $DIC->copage()->internal()->domain()->pc()->definition();
475
476 $content = "<dummy>" . $content . "</dummy>";
477
478 $wb_path = ilFileUtils::getWebspaceDir("output") . "/";
479 $enlarge_path = ilUtil::getImagePath("media/enlarge.svg");
480 $params = array('mode' => $a_mode,
481 'webspace_path' => $wb_path, 'enlarge_path' => $enlarge_path);
482 $output = $xsl->process($content, $params);
483
484 // unmask user html
485 if ($unmask) {
486 $output = str_replace("&lt;", "<", $output);
487 $output = str_replace("&gt;", ">", $output);
488 $output = str_replace("&amp;", "&", $output);
489 }
490
491 if ($a_mode == "table_edit" && !is_null($a_table_obj)) {
492 switch ($a_submode) {
493 case "style":
494 $output = ilPCTableGUI::_addStyleCheckboxes($output, $a_table_obj);
495 break;
496
497 case "alignment":
498 $output = ilPCTableGUI::_addAlignmentCheckboxes($output, $a_table_obj);
499 break;
500
501 case "width":
502 $output = ilPCTableGUI::_addWidthInputs($output, $a_table_obj);
503 break;
504
505 case "span":
506 $output = ilPCTableGUI::_addSpanInputs($output, $a_table_obj);
507 break;
508 }
509 }
510
511 // for all page components...
512 if (isset($page_object)) {
513 $defs = $pc_definition->getPCDefinitions();
514 foreach ($defs as $def) {
515 $pc_class = $def["pc_class"];
516 $pc_obj = new $pc_class($page_object);
517
518 // post xsl page content modification by pc elements
519 $output = $pc_obj->modifyPageContentPostXsl($output, "presentation", false);
520 }
521 }
522
523 return $output;
524 }
525
529 public static function _addStyleCheckboxes(
530 string $a_output,
531 ilPCTable $a_table
532 ): string {
533 global $DIC;
534
535 $lng = $DIC->language();
536
537 $classes = $a_table->getAllCellClasses();
538
539 foreach ($classes as $k => $v) {
540 if ($v == "") {
541 $v = $lng->txt("none");
542 }
543 if (substr($v, 0, 4) == "ilc_") {
544 $v = substr($v, 4);
545 }
546 $check = $lng->txt("cont_style") . ": " .
547 '<input type="checkbox" value="1"' .
548 ' name="target[' . $k . ']">' . '</input> ' . $v;
549
550 $a_output = str_replace("{{{{{TableEdit;" . $k . "}}}}}", $check, $a_output);
551 }
552 return $a_output;
553 }
554
558 public static function _addAlignmentCheckboxes(
559 string $a_output,
560 ilPCTable $a_table
561 ): string {
562 global $DIC;
563
564 $lng = $DIC->language();
565
566 $classes = $a_table->getAllCellAlignments();
567
568 foreach ($classes as $k => $v) {
569 if ($v == "") {
570 $v = $lng->txt("default");
571 }
572 $check = $lng->txt("cont_alignment") . ": " .
573 '<input type="checkbox" value="1"' .
574 ' name="target[' . $k . ']">' . '</input> ' . $v;
575
576 $a_output = str_replace("{{{{{TableEdit;" . $k . "}}}}}", $check, $a_output);
577 }
578 return $a_output;
579 }
580
584 public static function _addWidthInputs(
585 string $a_output,
586 ilPCTable $a_table
587 ): string {
588 global $DIC;
589
590 $lng = $DIC->language();
591
592 $widths = $a_table->getAllCellWidths();
593
594 foreach ($widths as $k => $v) {
595 $check = $lng->txt("cont_width") . ": " .
596 '<input class="small" type="text" size="5" maxlength="10"' .
597 ' name="width[' . $k . ']" value="' . $v . '">' . '</input>';
598
599 $a_output = str_replace("{{{{{TableEdit;" . $k . "}}}}}", $check, $a_output);
600 }
601 return $a_output;
602 }
603
607 public static function _addSpanInputs(
608 string $a_output,
609 ilPCTable $a_table
610 ): string {
611 global $DIC;
612
613 $lng = $DIC->language();
614
615 $spans = $a_table->getAllCellSpans();
616
617 foreach ($spans as $k => $v) {
618 // colspans
619 $selects = '<div style="white-space:nowrap;">' . $lng->txt("cont_colspan") . ": " .
620 '<select class="small" name="colspan[' . $k . ']">';
621 for ($i = 1; $i <= $v["max_x"] - $v["x"] + 1; $i++) {
622 $sel_str = ($i == $v["colspan"])
623 ? 'selected="selected"'
624 : '';
625 $selects .= '<option value="' . $i . '" ' . $sel_str . '>' . $i . '</option>';
626 }
627 $selects .= "</select></div>";
628
629 // rowspans
630 $selects .= '<div style="margin-top:3px; white-space:nowrap;">' . $lng->txt("cont_rowspan") . ": " .
631 '<select class="small" name="rowspan[' . $k . ']">';
632 for ($i = 1; $i <= $v["max_y"] - $v["y"] + 1; $i++) {
633 $sel_str = ($i == $v["rowspan"])
634 ? 'selected="selected"'
635 : '';
636 $selects .= '<option value="' . $i . '" ' . $sel_str . '>' . $i . '</option>';
637 }
638 $selects .= "</select></div>";
639
640 $a_output = str_replace("{{{{{TableEdit;" . $k . "}}}}}", $selects, $a_output);
641 }
642 return $a_output;
643 }
644
645 public function editCellStyle(): void
646 {
647 $ilCtrl = $this->ctrl;
648 $tpl = $this->tpl;
650 $ilTabs = $this->tabs;
651
652 $this->displayValidationError();
653 $this->setTabs();
654 $this->setCellPropertiesSubTabs();
655 $ilTabs->setSubTabActive("cont_style");
656
657 // edit form
658 $form = new ilPropertyFormGUI();
659 $form->setFormAction($ilCtrl->getFormAction($this));
660 $form->setTitle($this->lng->txt("cont_table_cell_properties"));
661
662 // first row style
663 $style = new ilSelectInputGUI(
664 $this->lng->txt("cont_style"),
665 "style"
666 );
667 $this->setBasicTableCellStyles();
668 $this->getCharacteristicsOfCurrentStyle(["table_cell"]); // scorm-2004
669 $chars = $this->getCharacteristics(); // scorm-2004
670 $options = array_merge(array("" => $this->lng->txt("none")), $chars); // scorm-2004
671 $style->setOptions($options);
672
673 $style->setValue("");
674 $style->setInfo($lng->txt("cont_set_tab_style_info"));
675 $form->addItem($style);
676 $form->setKeepOpen(true);
677
678 $form->addCommandButton("setStyles", $lng->txt("cont_set_styles"));
679
680 $html = $form->getHTML();
681 $html .= "<br />" . $this->renderTable("table_edit", "style") . "</form>";
682 $tpl->setContent($html);
683 }
684
685 public function editCellWidth(): void
686 {
687 $ilCtrl = $this->ctrl;
688 $tpl = $this->tpl;
690 $ilTabs = $this->tabs;
691
692 $this->displayValidationError();
693 $this->setTabs();
694 $this->setCellPropertiesSubTabs();
695 $ilTabs->setSubTabActive("cont_width");
696 $ilTabs->setTabActive("cont_table_cell_properties");
697
698 $ctpl = new ilTemplate("tpl.table_cell_properties.html", true, true, "components/ILIAS/COPage");
699 $ctpl->setVariable("BTN_NAME", "setWidths");
700 $ctpl->setVariable("BTN_TEXT", $lng->txt("cont_save_widths"));
701 $ctpl->setVariable("FORMACTION", $ilCtrl->getFormAction($this));
702
703 $html = $ctpl->get();
704 $html .= "<br />" . $this->renderTable("table_edit", "width") . "</form>";
705 $tpl->setContent($html);
706 }
707
708 public function editCellSpan(): void
709 {
710 $ilCtrl = $this->ctrl;
711 $tpl = $this->tpl;
713 $ilTabs = $this->tabs;
714
715 $this->displayValidationError();
716 $this->setTabs();
717 $this->setCellPropertiesSubTabs();
718 $ilTabs->setSubTabActive("cont_span");
719 $ilTabs->setTabActive("cont_table_cell_properties");
720
721 $ctpl = new ilTemplate("tpl.table_cell_properties.html", true, true, "components/ILIAS/COPage");
722 $ctpl->setVariable("BTN_NAME", "setSpans");
723 $ctpl->setVariable("BTN_TEXT", $lng->txt("cont_save_spans"));
724 $ctpl->setVariable("FORMACTION", $ilCtrl->getFormAction($this));
725
726 $html = $ctpl->get();
727 $html .= "<br />" . $this->renderTable("table_edit", "span") . "</form>";
728 $tpl->setContent($html);
729 }
730
734 public function setStyles(): void
735 {
737
738 $target = $this->request->getStringArray("target");
739 if (count($target)) {
740 foreach ($target as $k => $value) {
741 if ($value > 0) {
742 $cid = explode(":", $k);
743 $this->content_obj->setTDClass(
744 ilUtil::stripSlashes($cid[0]),
745 $this->request->getString("style"),
746 ilUtil::stripSlashes($cid[1])
747 );
748 }
749 }
750 }
751 $this->updated = $this->pg_obj->update();
752 $this->tpl->setOnScreenMessage('success', $lng->txt("msg_obj_modified"), true);
753 $this->ctrl->redirect($this, "editCellStyle");
754 }
755
759 public function setWidths(): void
760 {
762
763 $widths = $this->request->getStringArray("width");
764 if (count($widths) > 0) {
765 foreach ($widths as $k => $width) {
766 $cid = explode(":", $k);
767 $this->content_obj->setTDWidth(
768 ilUtil::stripSlashes($cid[0]),
769 ilUtil::stripSlashes($width),
770 ilUtil::stripSlashes($cid[1])
771 );
772 }
773 }
774 $this->updated = $this->pg_obj->update();
775 $this->tpl->setOnScreenMessage('success', $lng->txt("msg_obj_modified"), true);
776 $this->ctrl->redirect($this, "editCellWidth");
777 }
778
782 public function setSpans(): void
783 {
785
786 $colspans = $this->request->getStringArray("colspan");
787 $rowspans = $this->request->getStringArray("rowspan");
788 $cs = [];
789 $rs = [];
790 if (count($colspans) > 0) {
791 foreach ($colspans as $k => $span) {
792 $cs[$k] = $span;
793 $rs[$k] = $rowspans[$k];
794 }
795 $this->content_obj->setTDSpans($cs, $rs);
796 }
797 $this->updated = $this->pg_obj->update();
798 $this->tpl->setOnScreenMessage('success', $lng->txt("msg_obj_modified"), true);
799 $this->ctrl->redirect($this, "editCellSpan");
800 }
801
805 public function setProperties(): void
806 {
807 $this->initPropertiesForm();
808 $this->form->checkInput();
809
810 // mask html
811 $caption = $this->form->getInput("caption");
812 $caption = str_replace("&", "&amp;", $caption);
813 $caption = str_replace("<", "&lt;", $caption);
814 $caption = str_replace(">", "&gt;", $caption);
815
816 $this->content_obj->setLanguage($this->form->getInput("language"));
817 $this->content_obj->setWidth($this->form->getInput("width"));
818 //$this->content_obj->setBorder($this->form->getInput("border"));
819 //$this->content_obj->setCellSpacing($this->form->getInput("spacing"));
820 //$this->content_obj->setCellPadding($this->form->getInput("padding"));
821 $this->content_obj->setHorizontalAlign($this->form->getInput("align"));
822 $this->content_obj->setHeaderRows($this->form->getInput("row_header"));
823 $this->content_obj->setHeaderCols($this->form->getInput("col_header"));
824 $this->content_obj->setFooterRows($this->form->getInput("row_footer"));
825 $this->content_obj->setFooterCols($this->form->getInput("col_footer"));
826 if (strpos($this->form->getInput("characteristic"), ":") > 0) {
827 $t = explode(":", $this->form->getInput("characteristic"));
828 $this->content_obj->setTemplate($t[2]);
829 $this->content_obj->setClass("");
830 } else {
831 $this->content_obj->setClass($this->form->getInput("characteristic"));
832 $this->content_obj->setTemplate("");
833 }
834 $this->content_obj->setCaption(
835 $caption,
836 $this->form->getInput("cap_align")
837 );
838 }
839
843 public function saveProperties(): void
844 {
845 $this->setProperties();
846 $this->updated = $this->pg_obj->update();
847 if ($this->updated === true) {
848 $this->tpl->setOnScreenMessage('success', $this->lng->txt("msg_obj_modified"), true);
849 $this->ctrl->redirect($this, "editProperties");
850 } else {
851 $this->pg_obj->addHierIDs();
852 $this->edit();
853 }
854 }
855
856 public function rightAlign(): void
857 {
858 $this->content_obj->setHorizontalAlign("Right");
859 $this->updateAndReturn();
860 }
861
862 public function leftAlign(): void
863 {
864 $this->content_obj->setHorizontalAlign("Left");
865 $this->updateAndReturn();
866 }
867
868 public function centerAlign(): void
869 {
870 $this->content_obj->setHorizontalAlign("Center");
871 $this->updateAndReturn();
872 }
873
874 public function leftFloatAlign(): void
875 {
876 $this->content_obj->setHorizontalAlign("LeftFloat");
877 $this->updateAndReturn();
878 }
879
880 public function rightFloatAlign(): void
881 {
882 $this->content_obj->setHorizontalAlign("RightFloat");
883 $this->updateAndReturn();
884 }
885
886 public function insert(): void
887 {
888 $tpl = $this->tpl;
889
890 $this->displayValidationError();
891 $this->initPropertiesForm("create");
892 $html = $this->form->getHTML();
893 $tpl->setContent($html);
894 }
895
896 public function getNewTableObject(): ilPCTable
897 {
898 return new ilPCTable($this->getPage());
899 }
900
904 public function create(): void
905 {
906 $this->content_obj = $this->getNewTableObject();
907 $this->content_obj->create($this->pg_obj, $this->hier_id, $this->pc_id);
908
909 $this->initPropertiesForm("create");
910 $this->form->checkInput();
911
912 $import_table = trim($this->form->getInput("import_table"));
913
914 // import xhtml or spreadsheet table
915 if (!empty($import_table)) {
916 switch ($this->form->getInput("import_type")) {
917 // xhtml import
918
919 // spreadsheet
920 case "spreadsheet":
921 $this->content_obj->importSpreadsheet($this->form->getInput("language"), $import_table);
922 break;
923 }
924 } else {
925 $this->content_obj->addRows(
926 $this->form->getInput("nr_rows"),
927 $this->form->getInput("nr_cols")
928 );
929 }
930
931 $this->setProperties();
932
933 $frtype = $this->form->getInput("first_row_style");
934 if ($frtype != "") {
935 $this->content_obj->setFirstRowStyle($frtype);
936 }
937
938 $this->updated = $this->pg_obj->update();
939
940 if ($this->updated === true) {
941 $this->afterCreation();
942 } else {
943 $this->insert();
944 }
945 }
946
947 public function afterCreation(): void
948 {
949 $this->ctrl->returnToParent($this, "jump" . $this->hier_id);
950 }
951
952
953 //
954 // Edit cell alignments
955 //
956
957 public function editCellAlignment(): void
958 {
959 $ilCtrl = $this->ctrl;
960 $tpl = $this->tpl;
962 $ilTabs = $this->tabs;
963
964 $this->displayValidationError();
965 $this->setTabs();
966 $this->setCellPropertiesSubTabs();
967 $ilTabs->setSubTabActive("cont_alignment");
968 $ilTabs->setTabActive("cont_table_cell_properties");
969
970 // edit form
971 $form = new ilPropertyFormGUI();
972 $form->setFormAction($ilCtrl->getFormAction($this));
973 $form->setTitle($this->lng->txt("cont_table_cell_properties"));
974
975 // alignment
976 $options = array(
977 "" => $lng->txt("default"),
978 "Left" => $lng->txt("cont_left"),
979 "Center" => $lng->txt("cont_center"),
980 "Right" => $lng->txt("cont_right")
981 );
982 $si = new ilSelectInputGUI($lng->txt("cont_alignment"), "alignment");
983 $si->setOptions($options);
984 $si->setInfo($lng->txt(""));
985 $form->addItem($si);
986
987 $form->setKeepOpen(true);
988
989 $form->addCommandButton("setAlignment", $lng->txt("cont_set_alignment"));
990
991 $html = $form->getHTML();
992 $html .= "<br />" . $this->renderTable("table_edit", "alignment") . "</form>";
993 $tpl->setContent($html);
994 }
995
999 public function setAlignment(): void
1000 {
1001 $lng = $this->lng;
1002
1003 $targets = $this->request->getStringArray("target");
1004 if (count($targets) > 0) {
1005 foreach ($targets as $k => $value) {
1006 if ($value > 0) {
1007 $cid = explode(":", $k);
1008 $this->content_obj->setTDAlignment(
1009 ilUtil::stripSlashes($cid[0]),
1010 $this->request->getString("alignment"),
1011 ilUtil::stripSlashes($cid[1])
1012 );
1013 }
1014 }
1015 }
1016 $this->updated = $this->pg_obj->update();
1017 $this->tpl->setOnScreenMessage('success', $lng->txt("msg_obj_modified"), true);
1018
1019 $this->ctrl->redirect($this, "editCellAlignment");
1020 }
1021
1022
1026 public function editData(): void
1027 {
1028 $this->setTabs();
1029
1030 $this->displayValidationError();
1031 $this->initEditor();
1032 $this->tpl->addJavaScript("assets/js/AdvancedSelectionList.js");
1033 $this->tpl->addCss(ilObjStyleSheet::getBaseContentStylePath());
1034 $this->tpl->setContent($this->getEditDataTable(true));
1035 }
1036
1037 public function getEditDataTable(bool $initial = false): string
1038 {
1039 $ilCtrl = $this->ctrl;
1040
1042 $pc_tab = $this->content_obj;
1043
1044 $dtpl = new ilTemplate("tpl.tabledata2.html", true, true, "components/ILIAS/COPage");
1045 $dtpl->setVariable("FORMACTION", $this->ctrl->getFormAction($this, "tableAction"));
1046 $dtpl->setVariable("HIERID", $this->hier_id);
1047 $dtpl->setVariable("PCID", $this->pc_id);
1048 $class = $pc_tab->getClass();
1049 if ($class === "") {
1050 $class = "StandardTable";
1051 }
1052 $template_classes = [];
1053 if ($this->getStyleId() > 0 && $pc_tab->getTemplate() != "") {
1054 $id = ilObjStyleSheet::_lookupTemplateIdByName($this->getStyleId(), $pc_tab->getTemplate());
1055 $style = new ilObjStyleSheet($this->getStyleId());
1056 if ($id) {
1057 $template_classes = $style->getTemplateClasses($id);
1058 if ($template_classes["table"] !== "") {
1059 $class = $template_classes["table"];
1060 }
1061 }
1062 }
1063 $dtpl->setVariable("TABLE_CLASS", "ilc_table" . $class);
1064
1065 $dtpl->setVariable(
1066 "WYSIWYG_ACTION",
1067 $ilCtrl->getFormAction($this, "updateJS")
1068 );
1069
1070 // get all rows
1071 $path = "//PageContent[@HierId='" . $this->getHierId() . "']" .
1072 "/Table/TableRow";
1073 $nodes = $this->dom_util->path($this->dom, $path);
1074 $i = 0;
1075 $total_rows = count($nodes);
1076 foreach ($nodes as $node) {
1077 $path2 = "//PageContent[@HierId='" . $this->getHierId() . "']" .
1078 "/Table/TableRow[$i+1]/TableData";
1079 $nodes2 = $this->dom_util->path($this->dom, $path2);
1080 // if this is the first row -> col icons
1081 if ($i == 0) {
1082 $total_cols = count($nodes2);
1083 $j = 0;
1084 foreach ($nodes2 as $node2) {
1085 if ($j == 0) {
1086 $dtpl->touchBlock("empty_td");
1087 }
1088
1089 $move_forward = false;
1090 $move_backward = false;
1091 if ($j == 0) {
1092 if (count($nodes2) == 1) {
1093 //
1094 } else {
1095 $move_forward = true;
1096 }
1097 } elseif ($j == (count($nodes2) - 1)) {
1098 $move_backward = true;
1099 } else {
1100 $move_forward = true;
1101 $move_backward = true;
1102 }
1103 $dtpl->setCurrentBlock("col_icon");
1104 $dtpl->setVariable("NR_COLUMN", $j + 1);
1105 $dtpl->setVariable("PCID_COLUMN", $node2->getAttribute("PCID"));
1106 $dtpl->setVariable("COLUMN_CAPTION", $this->getColumnCaption($j + 1));
1107 $dtpl->parseCurrentBlock();
1108 $j++;
1109 }
1110 $dtpl->setCurrentBlock("row");
1111 $dtpl->parseCurrentBlock();
1112 }
1113
1114 $j = 0;
1115 foreach ($nodes2 as $node2) {
1116 // first col: row icons
1117 if ($j == 0) {
1118 if ($i == 0) {
1119 if (count($nodes) == 1) {
1120 $move_type = "none";
1121 } else {
1122 $move_type = "forward";
1123 }
1124 } elseif ($i == (count($nodes) - 1)) {
1125 $move_type = "backward";
1126 } else {
1127 $move_type = "both";
1128 }
1129 $dtpl->setCurrentBlock("row_icon");
1130 $dtpl->setVariable("NR_ROW", $i + 1);
1131 $dtpl->setVariable("PCID_ROW", $node2->getAttribute("PCID"));
1132 $dtpl->setVariable("ROW_CAPTION", $i + 1);
1133 $dtpl->parseCurrentBlock();
1134 }
1135
1136 // cell
1137 if ($node2->getAttribute("Hidden") != "Y") {
1138 //if ($this->content_obj->getType() == "dtab") {
1139 $dtpl->touchBlock("cell_type");
1140 //$dtpl->setCurrentBlock("cell_type");
1141 //$dtpl->parseCurrentBlock();
1142 //}
1143
1144 $dtpl->setCurrentBlock("cell");
1145
1146 $dtpl->setVariable("PAR_TA_NAME", "cell[" . $i . "][" . $j . "]");
1147 $dtpl->setVariable("PAR_TA_ID", "cell_" . $i . "_" . $j);
1148 $dtpl->setVariable("PAR_ROW", (string) $i);
1149 $dtpl->setVariable("PAR_COLUMN", (string) $j);
1150
1151 // which tag to use?
1152 $tag = "td";
1153 // only from template
1154 if (false) {
1155 $tag = "th";
1156 }
1157 $dtpl->setVariable("CELL_TAG", "td");
1158
1159 // which class to use?
1160 $node_class = $node2->getAttribute("Class");
1161 $class = $this->getCellClass(
1162 $i,
1163 $j,
1164 $node_class,
1165 $template_classes,
1166 $total_rows,
1167 $total_cols
1168 );
1169 if ($class !== "") {
1170 $dtpl->setVariable("CELL_CLASS", "ilc_table_cell_" . $class);
1171 }
1172
1173 $dtpl->setVariable(
1174 "PAR_TA_CONTENT",
1175 $this->getCellContent($i, $j)
1176 );
1177
1178 $cs = $node2->getAttribute("ColSpan");
1179 $width = (int) $node2->getAttribute("Width");
1180 $rs = $node2->getAttribute("RowSpan");
1181 if ($width > 0) {
1182 $dtpl->setVariable("WIDTH", $width);
1183 }
1184 $align = (string) $node2->getAttribute("HorizontalAlign");
1185 if ($align !== "") {
1186 $dtpl->setVariable("ALIGN", $align);
1187 }
1188 $dtpl->setVariable("HEIGHT", "80");
1189 if ($cs > 1) {
1190 $dtpl->setVariable("COLSPAN", 'colspan="' . $cs . '"');
1191 //$dtpl->setVariable("WIDTH", (140 + ($cs - 1) * 146));
1192 }
1193 if ($rs > 1) {
1194 $dtpl->setVariable("ROWSPAN", 'rowspan="' . $rs . '"');
1195 //$dtpl->setVariable("HEIGHT", (80 + ($rs - 1) * 86));
1196 }
1197 $dtpl->parseCurrentBlock();
1198 }
1199 $j++;
1200 }
1201 $dtpl->setCurrentBlock("row");
1202 $dtpl->parseCurrentBlock();
1203 $i++;
1204 }
1205 $dtpl->setVariable("TXT_ACTION", $this->lng->txt("cont_table"));
1206
1207 // add int link parts
1208 $dtpl->setCurrentBlock("int_link_prep");
1209 $dtpl->setVariable(
1210 "INT_LINK_PREP",
1212 $ilCtrl->getLinkTargetByClass(
1213 array("ilpageeditorgui", "ilinternallinkgui"),
1214 "",
1215 false,
1216 true,
1217 false
1218 )
1219 )
1220 );
1221 $dtpl->parseCurrentBlock();
1222
1223 $html = $dtpl->get();
1224 if ($initial) {
1225 $html .= $this->getEditorScriptTag();
1226 }
1227
1228 return $html;
1229 }
1230
1231 protected function getCellClass(
1232 int $i,
1233 int $j,
1234 string $node_class,
1235 array $template_classes,
1236 int $total_rows,
1237 int $total_cols
1238 ) {
1239 $class = "";
1241 $pc_tab = $this->content_obj;
1242
1243 // ["col_foot"] ["row_foot"]
1244
1245 if (($template_classes["even_row"] ?? "") !== "") {
1246 if ($i % 2 == 1) {
1247 $class = $template_classes["even_row"];
1248 }
1249 }
1250
1251 if (($template_classes["odd_row"] ?? "") !== "") {
1252 if ($i % 2 == 0) {
1253 $class = $template_classes["odd_row"];
1254 }
1255 }
1256
1257 if (($template_classes["even_col"] ?? "") !== "") {
1258 if ($j % 2 == 1) {
1259 $class = $template_classes["even_col"];
1260 }
1261 }
1262
1263 if (($template_classes["odd_col"] ?? "") !== "") {
1264 if ($j % 2 == 0) {
1265 $class = $template_classes["odd_col"];
1266 }
1267 }
1268
1269 if (($template_classes["row_foot"] ?? "") !== "") {
1270 if ($i + $pc_tab->getFooterRows() >= $total_rows) {
1271 $class = $template_classes["row_foot"];
1272 }
1273 }
1274
1275 if (($template_classes["col_foot"] ?? "") !== "") {
1276 if ($j + $pc_tab->getFooterCols() >= $total_cols) {
1277 $class = $template_classes["col_foot"];
1278 }
1279 }
1280
1281 if (($template_classes["row_head"] ?? "") !== "") {
1282 if ($i < $pc_tab->getHeaderRows()) {
1283 $class = $template_classes["row_head"];
1284 }
1285 }
1286
1287 if (($template_classes["col_head"] ?? "") !== "") {
1288 if ($j < $pc_tab->getHeaderCols()) {
1289 $class = $template_classes["col_head"];
1290 }
1291 }
1292
1293 if ($class === "") {
1294 if ($i < $pc_tab->getHeaderRows()) {
1295 $class = "StandardHeader";
1296 }
1297 }
1298
1299 if ($class === "") {
1300 $class = "StandardCell1";
1301 }
1302
1303
1304 if ($node_class !== "") {
1305 $class = $node_class;
1306 }
1307 return $class;
1308 }
1309
1310 protected function getColumnCaption(int $nr): string
1311 {
1312 $cap = "";
1313 $base = 26;
1314 while ($nr > 0) {
1315 $chr = ($nr - 1) % $base;
1316 $cap = chr($chr + 65) . $cap;
1317 $nr = ($nr - 1 - $chr) / $base;
1318 }
1319 return $cap;
1320 }
1321
1322 protected function getCellContent(int $i, int $j): string
1323 {
1324 $tab_node = $this->content_obj->getDomNode();
1325 $cnt_i = 0;
1326 $content = "";
1327 $template_xml = "";
1328 // get correct cell and dump content of all its childrem
1329 foreach ($tab_node->firstChild->childNodes as $child) {
1330 if ($i == $cnt_i) {
1331 $cnt_j = 0;
1332 foreach ($child->childNodes as $child2) {
1333 if ($j == $cnt_j) {
1334 foreach ($child2->childNodes as $cell_content_node) {
1335 $content .= $this->dom_util->dump($cell_content_node);
1336 }
1337 }
1338 $cnt_j++;
1339 }
1340 }
1341 $cnt_i++;
1342 }
1343 $trans = $this->pg_obj->getLanguageVariablesXML();
1344 $mobs = $this->pg_obj->getMultimediaXML();
1345 if ($this->getStyleId() > 0) {
1346 if (ilObject::_lookupType($this->getStyleId()) == "sty") {
1347 $style = new ilObjStyleSheet($this->getStyleId());
1348 $template_xml = $style->getTemplateXML();
1349 }
1350 }
1351
1352 $content = $content . $mobs . $trans . $template_xml;
1353
1354 return $this->renderCell(
1355 $content,
1356 !$this->pg_obj->getPageConfig()->getPreventHTMLUnmasking(),
1357 $this->getPage()
1358 );
1359 }
1360
1364 protected function renderCell(
1365 $content,
1366 $unmask = true,
1367 $page_object = null
1368 ): string {
1369 global $DIC;
1370
1371 $ilUser = $DIC->user();
1372 $content = "<dummy>" . $content . "</dummy>";
1373
1374 $wb_path = ilFileUtils::getWebspaceDir("output") . "/";
1375 $enlarge_path = ilUtil::getImagePath("media/enlarge.svg");
1376 $params = array('webspace_path' => $wb_path, 'enlarge_path' => $enlarge_path);
1377 $output = $this->xsl->process($content, $params);
1378
1379 // unmask user html
1380 if ($unmask) {
1381 $output = str_replace("&lt;", "<", $output);
1382 $output = str_replace("&gt;", ">", $output);
1383 $output = str_replace("&amp;", "&", $output);
1384 }
1385
1386 // for all page components...
1387 if (isset($page_object)) {
1388 $defs = $this->pc_definition->getPCDefinitions();
1389 foreach ($defs as $def) {
1390 $pc_class = $def["pc_class"];
1391 $pc_obj = new $pc_class($page_object);
1392
1393 // post xsl page content modification by pc elements
1394 $output = $pc_obj->modifyPageContentPostXsl((string) $output, "presentation", false);
1395 }
1396 }
1397
1398
1399 return $output;
1400 }
1401}
$id
plugin.php for ilComponentBuildPluginInfoObjectiveTest::testAddPlugins
Definition: plugin.php:23
$check
Definition: buildRTE.php:81
static getWebspaceDir(string $mode="filesystem")
get webspace directory
setFormAction(string $a_formaction)
setKeepOpen(bool $a_keepopen)
static getInitHTML(string $a_url)
Get initialisation HTML to use internal link editing.
txt(string $a_topic, string $a_default_lang_fallback_mod="")
gets the text for a given topic if the topic is not in the list, the topic itself with "-" will be re...
Class ilObjStyleSheet.
static _lookupTemplateIdByName(int $a_style_id, string $a_name)
Lookup table template preview.
User class.
static _lookupType(int $id, bool $reference=false)
This file is part of ILIAS, a powerful learning management system published by ILIAS open source e-Le...
getCellContent(int $i, int $j)
__construct(ilPageObject $a_pg_obj, ?ilPageContent $a_content_obj, string $a_hier_id, string $a_pc_id="")
static _addSpanInputs(string $a_output, ilPCTable $a_table)
Add span inputs.
create()
create new table in dom and update page in db
getTemplateOptions(string $a_type="")
Get table templates.
setStyles()
Set cell styles.
ILIAS COPage PC PCDefinition $pc_definition
initPropertiesForm(string $a_mode="edit")
editData()
Edit data of table.
ILIAS COPage Xsl XslManager $xsl
setProperties()
Set properties from input form.
static _addStyleCheckboxes(string $a_output, ilPCTable $a_table)
Add style checkboxes in edit mode.
getFormTitle(string $a_mode="edit")
ilPropertyFormGUI $form
saveProperties()
save table properties in db and return to page edit screen
static _addAlignmentCheckboxes(string $a_output, ilPCTable $a_table)
Add alignment checkboxes in edit mode.
setSpans()
Set cell spans.
setWidths()
Set cell widths.
static _addWidthInputs(string $a_output, ilPCTable $a_table)
Add width inputs.
ILIAS COPage Dom DomUtil $dom_util
static _renderTable(string $content, string $a_mode="table_edit", string $a_submode="", ?ilPCTable $a_table_obj=null, bool $unmask=true, ?ilPageObject $page_object=null)
setTabs(string $data_tab_txt_key="")
renderCell( $content, $unmask=true, $page_object=null)
Static render table function.
setAlignment()
Set cell alignments.
This file is part of ILIAS, a powerful learning management system published by ILIAS open source e-Le...
getAllCellClasses()
Get all cell classes.
getAllCellSpans()
Get all cell spans.
getAllCellWidths()
Get all cell widths.
User Interface for Editing of Page Content Objects (Paragraphs, Tables, ...)
getCharacteristicsOfCurrentStyle(array $a_type)
Get characteristics of current style and call setCharacteristics, if style is given.
setCharacteristics(array $a_chars)
Content object of ilPageObject (see ILIAS DTD).
Class ilPageObject Handles PageObjects of ILIAS Learning Modules (see ILIAS DTD)
This class represents a property form user interface.
addCommandButton(string $a_cmd, string $a_text, string $a_id="")
This class represents a property in a property form.
This class represents an option in a radio group.
This class represents a selection list property in a property form.
This file is part of ILIAS, a powerful learning management system published by ILIAS open source e-Le...
special template class to simplify handling of ITX/PEAR
This class represents a text area property in a property form.
This class represents a text property in a property form.
static getImagePath(string $image_name, string $module_path="", string $mode="output", bool $offline=false)
get image path (for images located in a template directory)
static stripSlashes(string $a_str, bool $a_strip_html=true, string $a_allow="")
if(! $DIC->user() ->getId()||!ilLTIConsumerAccess::hasCustomProviderCreationAccess()) $params
Definition: ltiregstart.php:31
$path
Definition: ltiservices.php:30
__construct(Container $dic, ilPlugin $plugin)
@inheritDoc
form( $class_path, string $cmd, string $submit_caption="")
global $lng
Definition: privfeed.php:31
global $DIC
Definition: shib_login.php:26