aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMoritz Strohm <strohm@data-quest.de>2024-12-03 15:20:59 +0000
committerMoritz Strohm <strohm@data-quest.de>2024-12-03 15:20:59 +0000
commit2835b3b966dc60ebcf85e7bb77be9d85e24d9920 (patch)
treee2580e6295d48672af1142ec751dd5a1a3e0c049
parent60c88b927ed3d9409660832d16dadb527bd4506c (diff)
added GUI improvements to schedule, re #4421
Merge request studip/studip!3578
-rw-r--r--app/controllers/calendar/schedule.php136
-rw-r--r--app/views/calendar/schedule/_colour_selector.php18
-rw-r--r--app/views/calendar/schedule/course_info.php37
-rw-r--r--app/views/calendar/schedule/entry.php90
-rw-r--r--app/views/calendar/schedule/settings.php64
-rw-r--r--db/migrations/6.0.13_alter_schedule_table.php4
-rw-r--r--db/migrations/6.0.35_new_schedule_improvements.php75
-rw-r--r--lib/classes/calendar/Helper.php42
-rw-r--r--lib/models/calendar/ScheduleEntry.php24
-rw-r--r--resources/assets/stylesheets/scss/calendar.scss2
-rw-r--r--resources/assets/stylesheets/scss/my_courses.scss6
-rw-r--r--resources/assets/stylesheets/scss/schedule.scss17
-rw-r--r--resources/assets/stylesheets/studip.scss1
13 files changed, 436 insertions, 80 deletions
diff --git a/app/controllers/calendar/schedule.php b/app/controllers/calendar/schedule.php
index 8f5e6e5..5019660 100644
--- a/app/controllers/calendar/schedule.php
+++ b/app/controllers/calendar/schedule.php
@@ -72,13 +72,13 @@ class Calendar_ScheduleController extends AuthenticatedController
_('Neuer Termin'),
$this->url_for('calendar/schedule/entry/add'),
Icon::create('add'),
- ['data-dialog' => '']
+ ['data-dialog' => 'size=auto']
);
if ($show_hidden) {
$actions->addLink(
_('Ausgeblendete Veranstaltungen verstecken'),
$this->indexURL(['semester_id' => Request::get('semester_id')]),
- Icon::create('visibility-invisible')
+ Icon::create('visibility-visible')
)->asButton();
} else {
$actions->addLink(
@@ -87,7 +87,7 @@ class Calendar_ScheduleController extends AuthenticatedController
'show_hidden' => true,
'semester_id' => Request::get('semester_id'),
]),
- Icon::create('visibility-visible')
+ Icon::create('visibility-invisible')
)->asButton();
}
@@ -99,12 +99,40 @@ class Calendar_ScheduleController extends AuthenticatedController
);
$actions->addLink(
_('Einstellungen'),
- $this->url_for('settings/calendar'),
+ $this->url_for('calendar/schedule/settings'),
Icon::create('settings'),
['data-dialog' => 'size=auto;reload-on-close']
);
$sidebar->addWidget($actions);
+ $schedule_settings = UserConfig::get()->getValue('SCHEDULE_SETTINGS');
+ $size = $schedule_settings['size'] ?? 'medium';
+ if (Request::submitted('size')) {
+ $size = Request::option('size');
+ if (in_array($size, ['small', 'medium', 'large'])) {
+ //Set the new size in the schedule settings:
+ $schedule_settings['size'] = $size;
+ UserConfig::get()->store('SCHEDULE_SETTINGS', $schedule_settings);
+ } else {
+ $size = 'medium';
+ }
+ }
+ $views = new ViewsWidget();
+ $views->setTitle(_('Größe'));
+ $views->addLink(
+ _('Klein'),
+ $this->url_for('calendar/schedule/index', ['size' => 'small'])
+ )->setActive($size === 'small');
+ $views->addLink(
+ _('Mittel'),
+ $this->url_for('calendar/schedule/index', ['size' => 'medium'])
+ )->setActive($size === 'medium');
+ $views->addLink(
+ _('Groß'),
+ $this->url_for('calendar/schedule/index', ['size' => 'large'])
+ )->setActive($size === 'large');
+ $sidebar->addWidget($views);
+
$fullcalendar = \Studip\Calendar\Helper::getScheduleFullcalendar(
$semester->id ?? '',
Request::bool('show_hidden', false)
@@ -203,9 +231,23 @@ class Calendar_ScheduleController extends AuthenticatedController
);
$event_classes = ['schedule'];
- $event_title = $cycle_date->course->getFullName();
+ $event_title = $cycle_date->course->getFullName('number-name');
+
if ($course_membership) {
$event_classes[] = sprintf('course-color-%u', $course_membership->gruppe);
+
+ $lecturer_names = array_map(
+ fn($lecturer) => $lecturer->user->nachname,
+ CourseMember::findByCourseAndStatus($course_membership->seminar_id, 'dozent')
+ );
+ sort($lecturer_names);
+ $event_title = studip_interpolate(
+ '%{course_name} (%{lecturer_names})',
+ [
+ 'course_name' => $cycle_date->course->getFullName('number-name'),
+ 'lecturer_names' => implode(', ', $lecturer_names)
+ ]
+ );
} elseif ($schedule_course) {
$event_classes[] = 'marked-course';
$event_title = studip_interpolate(
@@ -274,9 +316,10 @@ class Calendar_ScheduleController extends AuthenticatedController
$this->entry->user_id = $GLOBALS['user']->id;
if (!Request::submitted('save')) {
//Provide good default values:
+ $this->entry->colour_id = 1;
if (Request::submitted('start')) {
//String format
- $this->entry->dow = Request::int('dow', date('N'));
+ $this->entry->dow = Request::int('dow',date('N'));
$this->entry->setFormattedStart(Request::get('start', date('H:00', strtotime('+1 hour'))));
$this->entry->setFormattedEnd(Request::get('end', date('H:00', strtotime('+2 hours'))));
} elseif (Request::submitted('begin')) {
@@ -284,10 +327,16 @@ class Calendar_ScheduleController extends AuthenticatedController
$begin = Request::get('begin');
$end = Request::get('end');
if ($begin && $end) {
- $this->entry->dow = date('N', $begin);
+ $this->entry->dow = intval(date('N', $begin));
$this->entry->setFormattedStart(date('H:i', $begin));
$this->entry->setFormattedEnd(date('H:i', $end));
}
+ } else {
+ $begin = time() + 3600;
+ $end = $begin + 3600;
+ $this->entry->dow = intval(date('N', $begin));
+ $this->entry->setFormattedStart(date('H:00', $begin));
+ $this->entry->setFormattedEnd(date('H:00', $end));
}
}
PageLayout::setTitle(_('Neuer Termin'));
@@ -338,6 +387,7 @@ class Calendar_ScheduleController extends AuthenticatedController
$this->entry->dow = Request::int('dow', date('N'));
$this->entry->setFormattedStart(Request::get('start'));
$this->entry->setFormattedEnd(Request::get('end'));
+ $this->entry->colour_id = Request::get('colour_id') ?? '';
$this->entry->label = Request::get('label', '');
$this->entry->content = Request::get('content', '');
@@ -589,4 +639,76 @@ class Calendar_ScheduleController extends AuthenticatedController
}
$this->redirect('calendar/schedule/index');
}
+
+ /**
+ * Shows the settings dialog for the schedule.
+ */
+ public function settings_action()
+ {
+ $user_config = UserConfig::get($GLOBALS['user']->id);
+ $this->schedule_settings = $user_config->getValue('SCHEDULE_SETTINGS');
+
+ //Provide good defaults:
+ $default_config = [
+ 'start_time' => '08:00',
+ 'end_time' => '20:00',
+ 'weekdays' => 5,
+ 'visible_days' => [1, 2, 3, 4, 5]
+ ];
+ if (
+ empty($this->schedule_settings['start_time'])
+ && empty($this->schedule_settings['end_time'])
+ && empty($this->schedule_settings['weekdays'])
+ && empty($this->schedule_settings['visible_days'])
+ ) {
+ //Use the defaults:
+ $this->schedule_settings = $default_config;
+ }
+ }
+
+ /**
+ * Saves the schedule settings from the settings dialog.
+ */
+ public function save_settings_action()
+ {
+ CSRFProtection::verifyUnsafeRequest();
+
+ $start_time = Request::get('start_time', '08:00');
+ $end_time = Request::get('end_time', '20:00');
+ $weekdays = Request::int('weekdays', 5);
+ $visible_days = Request::intArray('visible_days');
+ if ($start_time >= $end_time) {
+ PageLayout::postError(_('Die Startuhrzeit muss vor der Enduhrzeit liegen.'));
+ $this->redirect('calendar/schedule/settings');
+ return;
+ }
+ if (!in_array($weekdays, [5, 7])) {
+ PageLayout::postError(_('Der Stundenplan kann nur 5 oder 7 Tage anzeigen.'));
+ $this->redirect('calendar/schedule/settings');
+ return;
+ }
+ if (empty($visible_days)) {
+ PageLayout::postError(_('Es wurde kein Wochentag ausgewählt.'));
+ $this->redirect('calendar/schedule/settings');
+ return;
+ }
+
+
+ $schedule_settings = [
+ 'start_time' => $start_time,
+ 'end_time' => $end_time,
+ 'weekdays' => $weekdays,
+ 'visible_days' => $visible_days
+ ];
+
+ UserConfig::get($GLOBALS['user']->id)->store('SCHEDULE_SETTINGS', $schedule_settings);
+
+ PageLayout::postSuccess(_('Die Einstellungen wurden gespeichert.'));
+ if (Request::isDialog()) {
+ $this->response->add_header('X-Dialog-Close', '1');
+ } else {
+ $this->redirect('calendar/schedule/index');
+ }
+ $this->render_nothing();
+ }
}
diff --git a/app/views/calendar/schedule/_colour_selector.php b/app/views/calendar/schedule/_colour_selector.php
new file mode 100644
index 0000000..34758b2
--- /dev/null
+++ b/app/views/calendar/schedule/_colour_selector.php
@@ -0,0 +1,18 @@
+<?php
+/**
+ * @var string $selected_colour_id
+ */
+?>
+<? foreach ($GLOBALS['PERS_TERMIN_KAT'] as $colour_id => $data) : ?>
+ <td class="colour">
+ <input type="radio" name="colour_id" value="<?= htmlReady($colour_id) ?>"
+ aria-label="<?= sprintf(_('Farbe %s zuordnen'), htmlReady($colour_id)) ?>"
+ <?= $selected_colour_id === $colour_id ? 'checked' : '' ?>
+ id="colour-<?= htmlReady($colour_id) ?>">
+ <label for="colour-<?= htmlReady($colour_id) ?>"
+ style="background-color: <?= htmlReady($data['bgcolor']) ?>;">
+ <span class="colour-id"></span>
+ <span class="checked-icon"><?= Icon::create('accept', Icon::ROLE_INFO) ?></span>
+ </label>
+ </td>
+<? endforeach ?>
diff --git a/app/views/calendar/schedule/course_info.php b/app/views/calendar/schedule/course_info.php
index 7cfaeae..dd664ec 100644
--- a/app/views/calendar/schedule/course_info.php
+++ b/app/views/calendar/schedule/course_info.php
@@ -7,7 +7,6 @@
*/
?>
<? if ($course) : ?>
- <h2><?= htmlReady($course->getFullName()) ?></h2>
<form class="default" method="post" data-dialog="reload-on-close"
action="<?= $controller->link_for('calendar/schedule/course_info/' . $course->id) ?>">
<?= CSRFProtection::tokenTag() ?>
@@ -30,8 +29,10 @@
<fieldset>
<legend><?= _('Informationen') ?></legend>
<section>
- <h3><?= _('Veranstaltungsnummer') ?></h3>
- <p><?= htmlReady($course->veranstaltungsnummer) ?></p>
+ <? if ($course->veranstaltungsnummer) : ?>
+ <h3><?= _('Veranstaltungsnummer') ?></h3>
+ <p><?= htmlReady($course->veranstaltungsnummer) ?></p>
+ <? endif ?>
<h3><?= _('Lehrende') ?></h3>
<ul class="default">
<?
@@ -48,6 +49,22 @@
<h3><?= _('Veranstaltungszeiten') ?></h3>
<?= $course->getAllDatesInSemester()->toHtml() ?>
</section>
+ <section>
+ <?
+ $enrolment_info = $course->getEnrolmentInformation($GLOBALS['user']->id);
+ ?>
+ <? if ($enrolment_info->isEnrolmentAllowed()) : ?>
+ <a href="<?= URLHelper::getLink('dispatch.php/course/overview', ['cid' => $course->id]) ?>">
+ <?= _('Direkt zur Veranstaltung') ?>
+ <?= Icon::create('link-intern')->asImg(Icon::SIZE_INLINE, ['class' => 'text-bottom']) ?>
+ </a>
+ <? else : ?>
+ <a href="<?= URLHelper::getLink('dispatch.php/course/details', ['sem_id' => $course->id]) ?>">
+ <?= _('Direkt zur Veranstaltung') ?>
+ <?= Icon::create('link-intern')->asImg(Icon::SIZE_INLINE, ['class' => 'text-bottom']) ?>
+ </a>
+ <? endif ?>
+ </section>
</fieldset>
<div data-dialog-button>
<?= \Studip\Button::create(
@@ -68,20 +85,6 @@
['formaction' => $controller->url_for('calendar/schedule/hide_course/' . $course->id)]
) ?>
<? endif ?>
- <?php
- $enrolment_info = $course->getEnrolmentInformation($GLOBALS['user']->id);
- ?>
- <? if ($enrolment_info->isEnrolmentAllowed()) : ?>
- <?= \Studip\LinkButton::create(
- _('Direkt zur Veranstaltung'),
- URLHelper::getURL('dispatch.php/course/overview', ['cid' => $course->id])
- ) ?>
- <? else : ?>
- <?= \Studip\LinkButton::create(
- _('Direkt zur Veranstaltung'),
- URLHelper::getURL('dispatch.php/course/details', ['sem_id' => $course->id])
- ) ?>
- <? endif ?>
</div>
</form>
<? endif ?>
diff --git a/app/views/calendar/schedule/entry.php b/app/views/calendar/schedule/entry.php
index 676f073..561588a 100644
--- a/app/views/calendar/schedule/entry.php
+++ b/app/views/calendar/schedule/entry.php
@@ -4,48 +4,60 @@
* @var ScheduleEntry $entry The schedule entry to be created/modified.
*/
?>
-<form class="default" method="post" action="<?= $controller->link_for('calendar/schedule/entry/' . ($entry->isNew() ? 'add' : $entry->id)) ?>"
+<form class="default schedule-entry" method="post"
+ action="<?= $controller->link_for('calendar/schedule/entry/' . ($entry->isNew() ? 'add' : $entry->id)) ?>"
data-dialog="reload-on-close">
<?= CSRFProtection::tokenTag() ?>
<fieldset>
+ <legend><?= _('Farbe') ?></legend>
+ <table class="default colour-selector">
+ <tr>
+ <?= $this->render_partial(
+ 'calendar/schedule/_colour_selector',
+ ['selected_colour_id' => $entry->colour_id]
+ ) ?>
+ </tr>
+ </table>
+ </fieldset>
+ <fieldset>
<legend><?= _('Zeit') ?></legend>
- <section class="flex-row">
- <label>
- <?= _('Wochentag') ?>
- <select name="dow">
- <option value="1" <?= $entry->dow === 1 ? 'selected' : '' ?>>
- <?= _('Montag') ?>
- </option>
- <option value="2" <?= $entry->dow === 2 ? 'selected' : '' ?>>
- <?= _('Dienstag') ?>
- </option>
- <option value="3" <?= $entry->dow === 3 ? 'selected' : '' ?>>
- <?= _('Mittwoch') ?>
- </option>
- <option value="4" <?= $entry->dow === 4 ? 'selected' : '' ?>>
- <?= _('Donnerstag') ?>
- </option>
- <option value="5" <?= $entry->dow === 5 ? 'selected' : '' ?>>
- <?= _('Freitag') ?>
- </option>
- <option value="6" <?= $entry->dow === 6 ? 'selected' : '' ?>>
- <?= _('Samstag') ?>
- </option>
- <option value="7" <?= $entry->dow === 7 ? 'selected' : '' ?>>
- <?= _('Sonntag') ?>
- </option>
- </select>
- </label>
- <label>
- <?= _('Startuhrzeit') ?>
- <input type="text" class="has-time-picker" name="start"
- value="<?= htmlReady($entry->getFormattedStart()) ?>">
- </label>
- <label>
- <?= _('Enduhrzeit') ?>
- <input type="text" class="has-time-picker" name="end"
- value="<?= htmlReady($entry->getFormattedEnd()) ?>">
- </label>
+ <section class="hgroup nowrap">
+ <label>
+ <?= _('Wochentag') ?>
+ <select name="dow" class="size-s">
+ <option value="1" <?= $entry->dow === 1 ? 'selected' : '' ?>>
+ <?= _('Montag') ?>
+ </option>
+ <option value="2" <?= $entry->dow === 2 ? 'selected' : '' ?>>
+ <?= _('Dienstag') ?>
+ </option>
+ <option value="3" <?= $entry->dow === 3 ? 'selected' : '' ?>>
+ <?= _('Mittwoch') ?>
+ </option>
+ <option value="4" <?= $entry->dow === 4 ? 'selected' : '' ?>>
+ <?= _('Donnerstag') ?>
+ </option>
+ <option value="5" <?= $entry->dow === 5 ? 'selected' : '' ?>>
+ <?= _('Freitag') ?>
+ </option>
+ <option value="6" <?= $entry->dow === 6 ? 'selected' : '' ?>>
+ <?= _('Samstag') ?>
+ </option>
+ <option value="7" <?= $entry->dow === 7 ? 'selected' : '' ?>>
+ <?= _('Sonntag') ?>
+ </option>
+ </select>
+ </label>
+ <label>
+ <?= _('Anfang') ?>
+ <input type="text" class="has-time-picker size-s" name="start"
+ value="<?= htmlReady($entry->getFormattedStart()) ?>">
+ </label>
+ <label>
+ <?= _('Ende') ?>
+ <input type="text" class="has-time-picker size-s" name="end"
+ value="<?= htmlReady($entry->getFormattedEnd()) ?>">
+ </label>
</section>
</fieldset>
<fieldset>
@@ -60,7 +72,7 @@
</label>
</fieldset>
<div data-dialog-button>
- <?= \Studip\Button::create(
+ <?= \Studip\Button::createAccept(
_('Speichern'),
'save',
['formaction' => $controller->url_for('calendar/schedule/save_entry/' . ($entry->isNew() ? 'add' : $entry->id))]
diff --git a/app/views/calendar/schedule/settings.php b/app/views/calendar/schedule/settings.php
new file mode 100644
index 0000000..6c03ba6
--- /dev/null
+++ b/app/views/calendar/schedule/settings.php
@@ -0,0 +1,64 @@
+<?php
+/**
+ * @var StudipController $controller
+ * @var array $schedule_settings
+ */
+?>
+<form class="default" method="post" action="<?= $controller->link_for('calendar/schedule/save_settings') ?>"
+ <?= Request::isDialog() ? 'data-dialog="reload-on-close"' : '' ?>>
+ <?= CSRFProtection::tokenTag() ?>
+ <fieldset>
+ <legend><?= _('Zeiten') ?></legend>
+ <label>
+ <?= _('Anfang') ?>
+ <select name="start_time" aria-label="<?= _('Anfang des Stundenplans') ?>" class="size-s">
+ <? for ($i = 0; $i < 24; $i += 1): ?>
+ <? $value = sprintf('%02u:00', $i); ?>
+ <option value="<?= htmlReady($value) ?>"
+ <?= $schedule_settings['start_time'] === $value ? 'selected' : '' ?>>
+ <?= studip_interpolate('%{time} Uhr', ['time' => $value]) ?>
+ </option>
+ <? endfor ?>
+ </select>
+ </label>
+ <label>
+ <?= _('Ende') ?>
+ <select name="end_time" aria-label="<?= _('Ende des Stundenplans') ?>" class="size-s">
+ <? for ($i = 0; $i < 24; $i += 1): ?>
+ <? $value = sprintf('%02u:00', $i); ?>
+ <option value="<?= $value ?>"
+ <?= $schedule_settings['end_time'] === $value ? 'selected' : '' ?>>
+ <?= studip_interpolate('%{time} Uhr', ['time' => $value]) ?>
+ </option>
+ <? endfor ?>
+ </select>
+ </label>
+ <label>
+ <input type="radio" name="weekdays" value="7"
+ <?= $schedule_settings['weekdays'] === 7 ? 'checked' : '' ?>>
+ <?= _('Alle Wochentage im Stundenplan anzeigen.') ?>
+ </label>
+ <label>
+ <input type="radio" name="weekdays" value="5"
+ <?= $schedule_settings['weekdays'] === 5 ? 'checked' : '' ?>>
+ <?= _('Nur Montag bis Freitag im Stundenplan anzeigen.') ?>
+ </label>
+ </fieldset>
+ <fieldset>
+ <legend><?= _('Wochentage') ?></legend>
+ <section class="hgroup">
+ <? for ($i = 1; $i < 8; $i++) : ?>
+ <label>
+ <input type="checkbox" name="visible_days[]" value="<?= $i ?>"
+ <?= in_array($i, $schedule_settings['visible_days']) ? 'checked' : '' ?>>
+ <?= getWeekday($i, false) ?>
+ </label>
+ <? endfor ?>
+ </section>
+ </fieldset>
+ <div data-dialog-button>
+ <?= \Studip\Button::createAccept(_('Speichern')) ?>
+ <?= \Studip\Button::createCancel(_('Abbrechen')) ?>
+ </div>
+</form>
+
diff --git a/db/migrations/6.0.13_alter_schedule_table.php b/db/migrations/6.0.13_alter_schedule_table.php
index d27bf81..ecd692f 100644
--- a/db/migrations/6.0.13_alter_schedule_table.php
+++ b/db/migrations/6.0.13_alter_schedule_table.php
@@ -16,7 +16,7 @@ class AlterScheduleTable extends Migration
$db->exec(
"ALTER TABLE `schedule_entries`
- DROP COLUMN color,
+ RENAME COLUMN color TO colour_id,
CHANGE COLUMN start start_time SMALLINT(6) NOT NULL,
CHANGE COLUMN end end_time SMALLINT(6) NOT NULL,
CHANGE COLUMN day dow TINYINT(1) NOT NULL,
@@ -51,7 +51,7 @@ class AlterScheduleTable extends Migration
$db->exec(
"ALTER TABLE `schedule_entries`
- ADD COLUMN color TINYINT(4) NULL DEFAULT NULL,
+ RENAME COLUMN colour_id TO color,
CHANGE COLUMN start_time start SMALLINT(6) NOT NULL,
CHANGE COLUMN end_time end SMALLINT(6) NOT NULL,
CHANGE COLUMN dow day TINYINT(1) NOT NULL,
diff --git a/db/migrations/6.0.35_new_schedule_improvements.php b/db/migrations/6.0.35_new_schedule_improvements.php
new file mode 100644
index 0000000..2a038b9
--- /dev/null
+++ b/db/migrations/6.0.35_new_schedule_improvements.php
@@ -0,0 +1,75 @@
+<?php
+
+
+class NewScheduleImprovements extends Migration
+{
+ public function description()
+ {
+ return 'A bugfix migration to add colours to personal schedule entries again and to migrate schedule configurations.';
+ }
+
+ protected function up()
+ {
+ $db = DBManager::get();
+ $db->exec(
+ "ALTER TABLE `schedule_entries`
+ ADD COLUMN IF NOT EXISTS `colour_id` TINYINT(3) NOT NULL DEFAULT 0"
+ );
+
+ //Migrate the content of schedule configuration entries:
+
+ $fetch_stmt = $db->prepare(
+ "SELECT `range_id`, `value`
+ FROM `config_values`
+ WHERE `field` = 'SCHEDULE_SETTINGS'"
+ );
+ $update_stmt = $db->prepare(
+ "UPDATE `config_values`
+ SET `value` = :new_value, `chdate` = UNIX_TIMESTAMP()
+ WHERE `field` = 'SCHEDULE_SETTINGS'
+ AND `range_id` = :range_id"
+ );
+ $delete_stmt = $db->prepare(
+ "DELETE FROM `config_values`
+ WHERE `field` = 'SCHEDULE_SETTINGS'
+ AND `range_id` = :range_id"
+ );
+
+ $fetch_stmt->execute();
+ while ($row = $fetch_stmt->fetch(PDO::FETCH_ASSOC)) {
+ $old_config = json_decode($row['value'], true);
+ if (is_array($old_config)) {
+ //Convert the configuration:
+ $new_config = [
+ 'start_time' => sprintf('%02u:00', $old_config['glb_start_time']),
+ 'end_time' => sprintf('%02u:00', $old_config['glb_end_time']),
+ 'semester_id' => $old_config['semester_id']
+ ];
+ if (count($old_config['glb_days']) === 7) {
+ $new_config['weekdays'] = 7;
+ } else {
+ $new_config['weekdays'] = 5;
+ }
+ //Convert the visible days array:
+ $visible_days = [];
+ if (is_array($old_config['glb_days'])) {
+ foreach ($old_config['glb_days'] as $day) {
+ if ($day == 0) {
+ $visible_days[] = 7;
+ } else {
+ $visible_days[] = (int) $day;
+ }
+ }
+ }
+ $new_config['visible_days'] = $visible_days;
+ $update_stmt->execute([
+ 'range_id' => $row['range_id'],
+ 'new_value' => json_encode($new_config)
+ ]);
+ } else {
+ //Delete the configuration:
+ $delete_stmt->execute(['range_id' => $old_config['range_id']]);
+ }
+ }
+ }
+}
diff --git a/lib/classes/calendar/Helper.php b/lib/classes/calendar/Helper.php
index 004e2f5..8be9891 100644
--- a/lib/classes/calendar/Helper.php
+++ b/lib/classes/calendar/Helper.php
@@ -128,7 +128,31 @@ class Helper
if (!$semester_id) {
$semester_id = \Semester::findCurrent()?->id ?? '';
}
- $calendar_settings = \User::findCurrent()->getConfiguration()->CALENDAR_SETTINGS ?? [];
+ $schedule_settings = \UserConfig::get($GLOBALS['user']->id)->getValue('SCHEDULE_SETTINGS') ?? [];
+ $slot_duration = '00:30:00';
+ if (!empty($schedule_settings['size']) && in_array($schedule_settings['size'], ['small', 'large'])) {
+ if ($schedule_settings['size'] === 'small') {
+ $slot_duration = '01:00:00';
+ } elseif ($schedule_settings['size'] === 'large') {
+ $slot_duration = '00:15:00';
+ }
+ }
+
+ //Determine the value of the hiddenDays config.
+ $hidden_days = [1, 2, 3, 4, 5, 6, 7];
+ $hidden_days = array_diff(
+ $hidden_days,
+ $schedule_settings['visible_days'] ?? [1, 2, 3, 4, 5, 6, 7]
+ );
+
+ $fullcalendar_hidden_days = [];
+ foreach ($hidden_days as $day) {
+ if ($day === 7) {
+ $fullcalendar_hidden_days[] = 0;
+ } else {
+ $fullcalendar_hidden_days[] = $day;
+ }
+ }
return new \Studip\Fullcalendar(
_('Stundenplan'),
@@ -136,8 +160,8 @@ class Helper
'editable' => true,
'selectable' => true,
'dialog_size' => 'auto',
- 'minTime' => sprintf('%02u:00', $calendar_settings['start'] ?? 8),
- 'maxTime' => sprintf('%02u:00', $calendar_settings['end'] ?? 20),
+ 'minTime' => $schedule_settings['start_time'] ?? '08:00',
+ 'maxTime' => $schedule_settings['end_time'] ?? '20:00',
'allDaySlot' => false,
'header' => [
'left' => '',
@@ -145,13 +169,19 @@ class Helper
],
'views' => [
'timeGridWeek' => [
- 'columnHeaderFormat' => ['weekday' => 'long'],
- 'weekends' => $calendar_settings['type_week'] === 'LONG',
- 'slotDuration' => self::getCalendarSlotDuration('week'),
+ 'columnHeaderFormat' => ['weekday' => 'short'],
+ 'weekends' => !empty($schedule_settings['weekdays']) && $schedule_settings['weekdays'] === 7,
+ 'slotDuration' => $slot_duration
]
],
'defaultView' => 'timeGridWeek',
'defaultDate' => date('Y-m-d'),
+ 'slotLabelFormat' => [
+ 'hour' => 'numeric',
+ 'minute' => '2-digit',
+ 'omitZeroMinute' => false
+ ],
+ 'hiddenDays' => $fullcalendar_hidden_days,
'timeGridEventMinHeight' => 20,
'eventSources' => [
[
diff --git a/lib/models/calendar/ScheduleEntry.php b/lib/models/calendar/ScheduleEntry.php
index f1e23fd..638f9e7 100644
--- a/lib/models/calendar/ScheduleEntry.php
+++ b/lib/models/calendar/ScheduleEntry.php
@@ -17,6 +17,7 @@
* @property string $start_time database column
* @property string $end_time database column
* @property string $dow database column
+ * @property string $colour_id database column
* @property string $label database column
* @property string $content database column
* @property string $user_id database column
@@ -216,7 +217,7 @@ class ScheduleEntry extends SimpleORMap implements Event
*/
public function getDescription(): string
{
- return $this->content;
+ return $this->getValue('content');
}
/**
@@ -298,13 +299,24 @@ class ScheduleEntry extends SimpleORMap implements Event
*/
public function toEventData(string $user_id): \Studip\Calendar\EventData
{
+ $title = $this->label;
+
+ $description = $this->getDescription();
+ if ($description) {
+ if ($this->label) {
+ $title = $this->label . ': ' . $description;
+ } else {
+ $title = $description;
+ }
+ }
+ $event_classes = ['schedule-entry'];
return new \Studip\Calendar\EventData(
$this->getBegin(),
$this->getEnd(),
- $this->label,
- ['schedule-entry'],
- '#000000',
- '#ffffff',
+ $title,
+ $event_classes,
+ $GLOBALS['PERS_TERMIN_KAT'][$this->colour_id]['fgcolor'] ?? '#000000',
+ $GLOBALS['PERS_TERMIN_KAT'][$this->colour_id]['bgcolor'] ?? '#ffffff',
$this->isWritable($user_id),
self::class,
$this->id,
@@ -317,7 +329,7 @@ class ScheduleEntry extends SimpleORMap implements Event
],
[],
'',
- '#000000',
+ $GLOBALS['PERS_TERMIN_KAT'][$this->colour_id]['border_color'] ?? '#000000',
$this->isAllDayEvent()
);
}
diff --git a/resources/assets/stylesheets/scss/calendar.scss b/resources/assets/stylesheets/scss/calendar.scss
index 0effce1..e5bc90b 100644
--- a/resources/assets/stylesheets/scss/calendar.scss
+++ b/resources/assets/stylesheets/scss/calendar.scss
@@ -3,7 +3,7 @@
background-color: #fff;
color: #000;
- border-width: 2px;
+ border-width: 1px;
&:hover {
color: #000;
diff --git a/resources/assets/stylesheets/scss/my_courses.scss b/resources/assets/stylesheets/scss/my_courses.scss
index d47fb58..d288908 100644
--- a/resources/assets/stylesheets/scss/my_courses.scss
+++ b/resources/assets/stylesheets/scss/my_courses.scss
@@ -18,7 +18,8 @@ form.default table.mycourses-group-selector {
}
}
-form.default td.mycourses-group-selector {
+form.default td.mycourses-group-selector,
+form.default table.colour-selector td.colour {
position: relative;
background-clip: padding-box;
@@ -28,7 +29,8 @@ form.default td.mycourses-group-selector {
@extend .sr-only;
&:checked + label {
- .group-number {
+ .group-number,
+ .colour-id {
display: none;
}
.checked-icon {
diff --git a/resources/assets/stylesheets/scss/schedule.scss b/resources/assets/stylesheets/scss/schedule.scss
new file mode 100644
index 0000000..d12faf8
--- /dev/null
+++ b/resources/assets/stylesheets/scss/schedule.scss
@@ -0,0 +1,17 @@
+form.default.schedule-entry {
+
+ section.nowrap {
+ flex-wrap: nowrap;
+ }
+
+ table.colour-selector td.colour {
+ label {
+ width: 1.5em;
+ height: 1.5em;
+
+ .studip-icon {
+ height: 1.5em;
+ }
+ }
+ }
+}
diff --git a/resources/assets/stylesheets/studip.scss b/resources/assets/stylesheets/studip.scss
index eb4895b..4713c32 100644
--- a/resources/assets/stylesheets/studip.scss
+++ b/resources/assets/stylesheets/studip.scss
@@ -82,6 +82,7 @@
@import "scss/resources";
@import "scss/sidebar";
@import "scss/wizard";
+@import "scss/schedule";
@import "scss/select";
@import "scss/selects";
@import "scss/search";