diff --git a/application/views/helpers/FormDateTime.php b/application/views/helpers/FormDateTime.php index bb1f6012f..46398048d 100644 --- a/application/views/helpers/FormDateTime.php +++ b/application/views/helpers/FormDateTime.php @@ -51,7 +51,7 @@ class Zend_View_Helper_FormDateTime extends Zend_View_Helper_FormElement $type = $attribs['local'] === true ? 'datetime-local' : 'datetime'; unset($attribs['local']); // Unset local to not render it again in $this->_htmlAttribs($attribs) $html5 = sprintf( - 'view->escape($name), $this->view->escape($id), diff --git a/library/Icinga/Web/JavaScript.php b/library/Icinga/Web/JavaScript.php index 5861464aa..23fad5710 100644 --- a/library/Icinga/Web/JavaScript.php +++ b/library/Icinga/Web/JavaScript.php @@ -43,7 +43,6 @@ class JavaScript 'js/icinga/behavior/selectable.js', 'js/icinga/behavior/modal.js', 'js/icinga/behavior/input-enrichment.js', - 'js/icinga/behavior/datetime-picker.js', 'js/icinga/behavior/copy-to-clipboard.js' ]; diff --git a/public/css/icinga/controls.less b/public/css/icinga/controls.less index 9d9237541..0bac5a4b8 100644 --- a/public/css/icinga/controls.less +++ b/public/css/icinga/controls.less @@ -213,69 +213,3 @@ form:has(input.search:focus) > .search-icon { max-height: 2em; } } - -// Datetime picker colors - -// The less variables are essentially the official dark theme for the flatpickr -@fp-calendarBackground: #3f4458; -@fp-calendarBorderColor: darken(#3f4458, 50%); - -@fp-monthForeground: #fff; -@fp-monthBackground: #3f4458; - -@fp-weekdaysBackground: transparent; -@fp-weekdaysForeground: #fff; - -@fp-dayForeground: fadeout(white, 5%); -@fp-dayHoverBackground: lighten(@fp-calendarBackground, 25%); - -@fp-todayColor: #eee; -@fp-today_fg_color: #3f4458; - -@fp-selectedDayBackground: #80CBC4; - -.icinga-datetime-picker .flatpickr-day.today { - &:hover, - &:focus { - color: @fp-today_fg_color; - } -} - -@light-mode: { - :root { - // These are actually the default colors for the flatpickr - - @fp-dayForeground: #393939; - @fp-dayHoverBackground: #e6e6e6; - - --fp-calendarBackground: #ffffff; - --fp-calendarBorderColor: @fp-dayHoverBackground; - - --fp-arrowColor: fadeout(@fp-dayForeground, 40%); - --fp-arrow_hover_color: #f64747; - - --fp-monthForeground: fadeout(black, 10%); - --fp-monthBackground: transparent; - - --fp-weekdaysBackground: transparent; - --fp-weekdaysForeground: fadeout(black, 46%); - --fp-weekNumberForeground: fadeout(@fp-dayForeground, 70%); - - --fp-dayForeground: @fp-dayForeground; - --fp-dayHoverBackground: @fp-dayHoverBackground; - --fp-disabledDayForeground: fadeout(@fp-dayForeground, 90%); - --fp-outsideRangeDayForeground: fadeout(@fp-dayForeground, 70%); - --fp-selectedDayBackground: #569FF7; - --fp-todayColor: #959ea9; - - --fp-timeHoverBg: lighten(@fp-dayHoverBackground, 3); - - --fp-hoverInvertedBg: fadeout(black, 95%); - - --fp-numChooserSvgFillColor: fadeout(fadeout(black, 10%), 50%); - --fp-hoverNumChooserBg: fadeout(black, 90%); - --fp-numChooserBorderColor: fadeout(@fp-dayForeground, 85%); - } -}; - -// Datetime picker colors (end) diff --git a/public/js/icinga/behavior/datetime-picker.js b/public/js/icinga/behavior/datetime-picker.js deleted file mode 100644 index 4b8ea40c0..000000000 --- a/public/js/icinga/behavior/datetime-picker.js +++ /dev/null @@ -1,223 +0,0 @@ -// SPDX-FileCopyrightText: 2021 Icinga GmbH -// SPDX-License-Identifier: GPL-3.0-or-later - -/** - * DatetimePicker - Behavior for inputs that should show a date and time picker - */ -;(function(Icinga, $) { - - 'use strict'; - - try { - var Flatpickr = require('icinga/icinga-php-library/vendor/flatpickr'); - var notjQuery = require('icinga/icinga-php-library/notjQuery'); - } catch (e) { - console.warn('Unable to provide datetime picker. Libraries not available:', e); - return; - } - - Icinga.Behaviors = Icinga.Behaviors || {}; - - /** - * Behavior for datetime pickers. - * - * @param icinga {Icinga} The current Icinga Object - */ - var DatetimePicker = function(icinga) { - Icinga.EventListener.call(this, icinga); - this.icinga = icinga; - - /** - * The formats the server expects - * - * In a syntax flatpickr understands. Based on https://flatpickr.js.org/formatting/ - * - * @type {string} - */ - this.server_full_format = 'Y-m-d\\TH:i:S'; - this.server_date_format = 'Y-m-d'; - this.server_time_format = 'H:i:S'; - - /** - * The flatpickr instances created - * - * @type {Map} - * @private - */ - this._pickers = new Map(); - - this.on('rendered', '#main > .container, #modal-content', this.onRendered, this); - this.on('close-column', this.onCloseContainer, this); - this.on('close-modal', this.onCloseContainer, this); - }; - - DatetimePicker.prototype = new Icinga.EventListener(); - - /** - * Add flatpickr widget on selected inputs - * - * @param event {Event} - */ - DatetimePicker.prototype.onRendered = function(event) { - var _this = event.data.self; - var containerId = event.target.dataset.icingaContainerId; - var inputs = event.target.querySelectorAll('input[data-use-datetime-picker]'); - - // Cleanup left-over pickers from the previous content - _this.cleanupPickers(containerId); - - $.each(inputs, function () { - if (this.type !== 'text') { - // Ignore native inputs. Browser widgets are (mostly) superior. - // TODO: This makes the type distinction below useless. - // Refactor this once we decided how we continue here in the future. - return; - } - - var server_format = _this.server_full_format; - if (this.type === 'date') { - server_format = _this.server_date_format; - } else if (this.type === 'time') { - server_format = _this.server_time_format; - } - - // Inject calendar container into a new empty div, inside the column/modal but outside the form. - // See https://github.com/flatpickr/flatpickr/issues/2054 for details. - var appendTo = document.createElement('div'); - this.form.parentNode.insertBefore(appendTo, this.form.nextSibling); - - var enableTime = server_format !== _this.server_date_format; - var disableDate = server_format === _this.server_time_format; - var dateTimeFormatter = _this.createFormatter(! disableDate, enableTime); - var options = { - locale: _this.loadFlatpickrLocale(), - appendTo: appendTo, - altInput: true, - enableTime: enableTime, - noCalendar: disableDate, - dateFormat: server_format, - formatDate: function (date, format, locale) { - return format === this.dateFormat - ? Flatpickr.formatDate(date, format, locale) - : dateTimeFormatter.format(date); - } - }; - - for (name in this.dataset) { - if (name.length > 9 && name.substr(0, 9) === 'flatpickr') { - var value = this.dataset[name]; - if (value === '') { - value = true; - } - - options[name.charAt(9).toLowerCase() + name.substr(10)] = value; - } - } - - var element = this; - if (!! options.wrap) { - element = this.parentNode; - } - - var fp = Flatpickr(element, options); - fp.calendarContainer.classList.add('icinga-datetime-picker'); - - if (! !!options.wrap) { - this.parentNode.insertBefore(_this.renderIcon(), fp.altInput.nextSibling); - } - - _this._pickers.set(fp, containerId); - }); - }; - - /** - * Cleanup all flatpickr instances in the closed container - * - * @param event {Event} - */ - DatetimePicker.prototype.onCloseContainer = function (event) { - var _this = event.data.self; - var containerId = event.target.dataset.icingaContainerId; - - _this.cleanupPickers(containerId); - }; - - /** - * Destroy all flatpickr instances in the container with the given id - * - * @param containerId {String} - */ - DatetimePicker.prototype.cleanupPickers = function (containerId) { - this._pickers.forEach(function (cId, fp) { - if (cId === containerId) { - this._pickers.delete(fp); - fp.destroy(); - } - }, this); - }; - - /** - * Close all other flatpickr instances and keep the given one - * - * @param fp {Flatpickr} - */ - DatetimePicker.prototype.closePickers = function (fp) { - var containerId = this._pickers.get(fp); - this._pickers.forEach(function (cId, fp2) { - if (cId === containerId && fp2 !== fp) { - fp2.close(); - } - }, this); - }; - - DatetimePicker.prototype.createFormatter = function (withDate, withTime) { - var options = {}; - if (withDate) { - options.year = 'numeric'; - options.month = 'numeric'; - options.day = 'numeric'; - } - if (withTime) { - options.hour = 'numeric'; - options.minute = 'numeric'; - options.timeZoneName = 'short'; - options.timeZone = this.icinga.config.timezone; - } - - return new Intl.DateTimeFormat([this.icinga.config.locale, 'en'], options); - }; - - DatetimePicker.prototype.loadFlatpickrLocale = function () { - switch (this.icinga.config.locale) { - case 'ar': - return require('icinga/icinga-php-library/vendor/flatpickr/l10n/ar').Arabic; - case 'de': - return require('icinga/icinga-php-library/vendor/flatpickr/l10n/de').German; - case 'es': - return require('icinga/icinga-php-library/vendor/flatpickr/l10n/es').Spanish; - case 'fi': - return require('icinga/icinga-php-library/vendor/flatpickr/l10n/fi').Finnish; - case 'fr': - return require('icinga/icinga-php-library/vendor/flatpickr/l10n/fr').French; - case 'it': - return require('icinga/icinga-php-library/vendor/flatpickr/l10n/it').Italian; - case 'ja': - return require('icinga/icinga-php-library/vendor/flatpickr/l10n/ja').Japanese; - case 'pt': - return require('icinga/icinga-php-library/vendor/flatpickr/l10n/pt').Portuguese; - case 'ru': - return require('icinga/icinga-php-library/vendor/flatpickr/l10n/ru').Russian; - case 'uk': - return require('icinga/icinga-php-library/vendor/flatpickr/l10n/uk').Ukrainian; - default: - return 'default'; - } - }; - - DatetimePicker.prototype.renderIcon = function () { - return notjQuery.render(''); - }; - - Icinga.Behaviors.DatetimePicker = DatetimePicker; - -})(Icinga, jQuery);