aboutsummaryrefslogtreecommitdiff
path: root/app
diff options
context:
space:
mode:
authorMarcus Eibrink-Lunzenauer <lunzenauer@elan-ev.de>2025-07-10 09:14:44 +0000
committerRon Lucke <lucke@elan-ev.de>2025-07-10 11:14:44 +0200
commit1f5b6ce81987ed5a03279265ca881ecb4bac0832 (patch)
treeaff162afb291f206a490c0eb2d4ec98d29e3e140 /app
parent7f557a0d69924597be5ca6b3aa8495ed26460429 (diff)
STEP 3263: Block- und Abschnittstypen standortspezifisch deaktivieren. (zweite Version)
Closes #3263 Merge request studip/studip!4206
Diffstat (limited to 'app')
-rw-r--r--app/controllers/admin/courseware.php139
-rw-r--r--app/views/admin/courseware/elements.php101
2 files changed, 229 insertions, 11 deletions
diff --git a/app/controllers/admin/courseware.php b/app/controllers/admin/courseware.php
index 964ff4d..1af8e8c 100644
--- a/app/controllers/admin/courseware.php
+++ b/app/controllers/admin/courseware.php
@@ -1,28 +1,146 @@
<?php
+use Courseware\BlockTypes\BlockType;
+use Courseware\ContainerTypes\ContainerType;
+
+/**
+ * @SuppressWarnings(PHPMD.CamelCaseClassName)
+ * @SuppressWarnings(PHPMD.CamelCaseMethodName)
+ * @SuppressWarnings(PHPMD.StaticAccess)
+ */
class Admin_CoursewareController extends AuthenticatedController
{
+ /**
+ * @SuppressWarnings(PHPMD.Superglobals)
+ */
public function before_filter(&$action, &$args)
{
parent::before_filter($action, $args);
$GLOBALS['perm']->check('root');
- PageLayout::setTitle(_('Coursewareverwaltung'));
- Navigation::activateItem('/admin/locations/courseware');
}
public function index_action()
{
- $this->setSidebar();
+ PageLayout::setTitle(_('Courseware Vorlagen'));
+ Navigation::activateItem('/admin/locations/courseware_templates');
+ $this->setIndexSidebar();
}
- private function setSidebar()
+ public function elements_action(): void
{
- $sidebar = Sidebar::Get();
- $views = new TemplateWidget(
- _('Ansichten'),
- $this->get_template_factory()->open('admin/courseware/admin_view_widget')
+ PageLayout::setTitle(_('Courseware Inhaltselemente'));
+ Navigation::activateItem('/admin/locations/courseware_elements');
+
+ $this->blockTypes = BlockType::getBlockTypes();
+ usort($this->blockTypes, fn($blockTypeA, $blockTypeB) => $blockTypeA::getTitle() <=> $blockTypeB::getTitle());
+
+ $this->containerTypes = ContainerType::getContainerTypes();
+
+ usort(
+ $this->containerTypes,
+ fn($containerTypeA, $containerTypeB) => $containerTypeA::getTitle() <=> $containerTypeB::getTitle()
+ );
+ }
+
+ public function activate_block_types_action()
+ {
+ CSRFProtection::verifyUnsafeRequest();
+
+ $requestedBlockTypes = $this->validateBlockTypes();
+ $changed = array_sum(array_map(fn($blockType) => $blockType::activate() ? 1 : 0, $requestedBlockTypes));
+
+ PageLayout::postSuccess(
+ sprintf(
+ ngettext('Block-Typ erfolgreich aktiviert.', '%d Block-Typen erfolgreich aktiviert.', $changed),
+ $changed
+ )
);
- $sidebar->addWidget($views)->addLayoutCSSClass('courseware-admin-view-widget');
+ $this->redirect($this->action_url('elements'));
+ }
+
+ public function deactivate_block_types_action()
+ {
+ CSRFProtection::verifyUnsafeRequest();
+
+ $requestedBlockTypes = $this->validateBlockTypes();
+ $changed = array_sum(array_map(fn($blockType) => $blockType::deactivate() ? 1 : 0, $requestedBlockTypes));
+
+ PageLayout::postSuccess(
+ sprintf(
+ ngettext('Block-Typ erfolgreich deaktiviert.', '%d Block-Typen erfolgreich deaktiviert.', $changed),
+ $changed
+ )
+ );
+ $this->redirect($this->action_url('elements'));
+ }
+
+ private function validateBlockTypes(): iterable
+ {
+ $requestedBlockTypes = Request::getArray('block_types');
+ $diff = array_diff($requestedBlockTypes, BlockType::getBlockTypes());
+ if (count($diff)) {
+ throw new Trails\Exception(400);
+ }
+
+ return $requestedBlockTypes;
+ }
+
+ public function activate_container_types_action()
+ {
+ CSRFProtection::verifyUnsafeRequest();
+
+ $requestedContainerTypes = $this->validateContainerTypes();
+ $changed = array_sum(
+ array_map(fn($containerType) => $containerType::activate() ? 1 : 0, $requestedContainerTypes)
+ );
+
+ PageLayout::postSuccess(
+ sprintf(
+ ngettext('Container-Typ erfolgreich aktiviert.', '%d Container-Typen erfolgreich aktiviert.', $changed),
+ $changed
+ )
+ );
+ $this->redirect($this->action_url('elements'));
+ }
+
+ /**
+ */
+ public function deactivate_container_types_action()
+ {
+ CSRFProtection::verifyUnsafeRequest();
+
+ $requestedContainerTypes = $this->validateContainerTypes();
+ $changed = array_sum(
+ array_map(fn($containerType) => $containerType::deactivate() ? 1 : 0, $requestedContainerTypes)
+ );
+
+ PageLayout::postSuccess(
+ sprintf(
+ ngettext(
+ 'Container-Typ erfolgreich deaktiviert.',
+ '%d Container-Typen erfolgreich deaktiviert.',
+ $changed
+ ),
+ $changed
+ )
+ );
+ $this->redirect($this->action_url('elements'));
+ }
+
+ private function validateContainerTypes(): iterable
+ {
+ $requestedContainerTypes = Request::getArray('container_types');
+ $diff = array_diff($requestedContainerTypes, ContainerType::getContainerTypes());
+ if (count($diff)) {
+ throw new Trails\Exception(400);
+ }
+
+ return $requestedContainerTypes;
+ }
+
+ private function setIndexSidebar()
+ {
+ $sidebar = Sidebar::Get();
$views = new TemplateWidget(
_('Aktionen'),
@@ -30,5 +148,4 @@ class Admin_CoursewareController extends AuthenticatedController
);
$sidebar->addWidget($views)->addLayoutCSSClass('courseware-admin-action-widget');
}
-
-} \ No newline at end of file
+}
diff --git a/app/views/admin/courseware/elements.php b/app/views/admin/courseware/elements.php
new file mode 100644
index 0000000..59a1c0f
--- /dev/null
+++ b/app/views/admin/courseware/elements.php
@@ -0,0 +1,101 @@
+<form method="post" action="<?= URLHelper::getLink('dispatch.php/admin/courseware/container_types') ?>">
+ <?= CSRFProtection::tokenTag() ?>
+ <table class="default sortable-table cw-admin-container-types">
+ <caption>
+ <?= _('Abschnittstypen') ?>
+ </caption>
+ <colgroup>
+ <col style="width: 5%">
+ <col style="width: 35%">
+ <col style="width: 60%">
+ </colgroup>
+ <thead>
+ <tr>
+ <th><?= _('Aktiv') ?></th>
+ <th data-sort="text"><?= _('Container-Typ') ?></th>
+ <th data-sort="text"><?= _('Beschreibung') ?></th>
+ </tr>
+ </thead>
+ <tbody>
+ <? foreach ($containerTypes as $containerType) { ?>
+ <? $isActivated = $containerType::isActivated(); ?>
+ <tr>
+ <td>
+ <label>
+ <? $formaction = $isActivated ? URLHelper::getURL(
+ 'dispatch.php/admin/courseware/deactivate_container_types',
+ ['container_types' => [$containerType]]
+ ) :
+ URLHelper::getURL('dispatch.php/admin/courseware/activate_container_types', [
+ 'container_types' => [$containerType],
+ ])
+ ?>
+ <span
+ class="sr-only"><? printf(_('Abschnittstyp "%s" %s'), $containerType::getTitle(), $isActivated ? _('deaktivieren') : _('aktivieren')) ?></span>
+ <button class="undecorated"
+ formaction="<?= $formaction ?>"><?= Icon::create($isActivated ? 'checkbox-checked' : 'checkbox-unchecked') ?></button>
+ </label>
+ </td>
+ <td data-sort-value="<?= htmlReady(strtolower($containerType::getType())) ?>">
+ <span><?= htmlReady($containerType::getTitle()) ?></span>
+ <span>(<?= htmlReady($containerType::getType()) ?>)</span>
+ </td>
+ <td data-sort-value="<?= htmlReady(strtolower($containerType::getDescription())) ?>">
+ <p>
+ <?= htmlReady($containerType::getDescription()) ?>
+ </p>
+ </td>
+ </tr>
+ <? } ?>
+ </tbody>
+ </table>
+</form>
+<form method="post" action="<?= URLHelper::getLink('dispatch.php/admin/courseware/block_types') ?>">
+ <?= CSRFProtection::tokenTag() ?>
+ <table class="default sortable-table cw-admin-block-types">
+ <caption><?= _('Blocktypen') ?></caption>
+ <colgroup>
+ <col style="width: 5%">
+ <col style="width: 35%">
+ <col style="width: 60%">
+ </colgroup>
+ <thead>
+ <tr>
+ <th><?= _('Aktiv') ?></th>
+ <th data-sort="text"><?= _('Block-Typ') ?></th>
+ <th data-sort="text"><?= _('Beschreibung') ?></th>
+ </tr>
+ </thead>
+ <tbody>
+ <? foreach ($blockTypes as $blockType) { ?>
+ <? $isActivated = $blockType::isActivated(); ?>
+ <tr>
+ <td>
+ <label>
+ <? $formaction = $isActivated ? URLHelper::getURL(
+ 'dispatch.php/admin/courseware/deactivate_block_types',
+ ['block_types' => [$blockType]]
+ ) : URLHelper::getURL(
+ 'dispatch.php/admin/courseware/activate_block_types',
+ ['block_types' => [$blockType]]
+ ) ?>
+ <span
+ class="sr-only"><? printf(_('Blocktyp "%s" %s'), $blockType::getTitle(), $isActivated ? _('deaktivieren') : _('aktivieren')) ?></span>
+ <button class="undecorated"
+ formaction="<?= $formaction ?>"><?= Icon::create($isActivated ? 'checkbox-checked' : 'checkbox-unchecked') ?></button>
+ </label>
+ </td>
+ <td data-sort-value="<?= htmlReady(strtolower($blockType::getType())) ?>">
+ <span><?= htmlReady($blockType::getTitle()) ?></span>
+ <span>(<?= htmlReady($blockType::getType()) ?>)</span>
+ </td>
+ <td data-sort-value="<?= htmlReady(strtolower($blockType::getDescription())) ?>">
+ <p>
+ <?= htmlReady($blockType::getDescription()) ?>
+ </p>
+ </td>
+ </tr>
+ <? } ?>
+ </tbody>
+ </table>
+</form> \ No newline at end of file