diff --git a/Build/Sources/Sass/_minimal.scss b/Build/Sources/Sass/_minimal.scss index 26fc2eb13e93b0b2b3e6c4a13f622ce76109b46c..bde433fb9dd717ea94b61543ffe75e471f3e56a2 100644 --- a/Build/Sources/Sass/_minimal.scss +++ b/Build/Sources/Sass/_minimal.scss @@ -80,6 +80,8 @@ // Components // @import "component/root"; +@import "component/type"; +@import "component/spacer"; @import "component/alert"; @import "component/autocomplete"; @import "component/badges"; diff --git a/Build/Sources/Sass/backend.scss b/Build/Sources/Sass/backend.scss index 0afb22559ee42bc37a4d5bc977ef3ac3b693523f..400f5260603e4a40c62de3c89d8713f72ccfecce 100644 --- a/Build/Sources/Sass/backend.scss +++ b/Build/Sources/Sass/backend.scss @@ -59,6 +59,7 @@ @import "component/recordsearchbox"; @import "component/treelist"; @import "component/indent"; +@import "component/pagination"; // // Elements diff --git a/Build/Sources/Sass/component/_card.scss b/Build/Sources/Sass/component/_card.scss index df0b8022be85d36c319015791b8545ded9e285be..d9ddf78061cd82738a74be4531c9d216fe7d55b2 100644 --- a/Build/Sources/Sass/component/_card.scss +++ b/Build/Sources/Sass/component/_card.scss @@ -320,11 +320,11 @@ a.card { padding-bottom: var(--typo3-card-padding); } - *:first-child { + > *:first-child:not(.row) { margin-top: 0; } - *:last-child { + > *:last-child { margin-bottom: 0; } } diff --git a/Build/Sources/Sass/component/_checkbox.scss b/Build/Sources/Sass/component/_checkbox.scss index 36fc0f2369ed0c34d7eb03d2ddcaa145220c0808..1ec6b439f6d90ccba8cc987385f291b7d5375ff7 100644 --- a/Build/Sources/Sass/component/_checkbox.scss +++ b/Build/Sources/Sass/component/_checkbox.scss @@ -185,14 +185,12 @@ // // Styleguide component.checkbox.3 // -$form-toggle-color: rgba(0, 0, 0, .25) !default; $form-toggle-bg-image: url("data:image/svg+xml, <svg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'><g class='icon-color'><path d='M13 2c.6 0 1 .4 1 1v10c0 .6-.4 1-1 1H3c-.6 0-1-.4-1-1V3c0-.6.4-1 1-1h10m0-1H3c-1.1 0-2 .9-2 2v10c0 1.1.9 2 2 2h10c1.1 0 2-.9 2-2V3c0-1.1-.9-2-2-2z'/></g></svg>") !default; $form-toggle-checked-color: $component-active-color !default; $form-toggle-checked-bg-image: url("data:image/svg+xml, <svg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'><g class='icon-color'><path d='M12.1 5.3l-.4-.3c-.1-.1-.3-.1-.4 0L6.6 9.8l-2-2c-.1-.1-.3-.1-.4 0l-.3.4c-.1.1-.1.3 0 .4L6 10.7l.4.3c.1.1.3.1.4 0l.4-.4 4.9-4.9c.1-.1.1-.3 0-.4z'/><path d='M13 2c.6 0 1 .4 1 1v10c0 .6-.4 1-1 1H3c-.6 0-1-.4-1-1V3c0-.6.4-1 1-1h10m0-1H3c-1.1 0-2 .9-2 2v10c0 1.1.9 2 2 2h10c1.1 0 2-.9 2-2V3c0-1.1-.9-2-2-2z'/></g></svg>") !default; .form-check.form-check-type-toggle { display: inline-block; - color: $form-toggle-color; padding-left: 0; margin: 0; @@ -216,3 +214,13 @@ $form-toggle-checked-bg-image: url("data:image/svg+xml, <svg xmlns='http://www.w } } } + +// +// Utility +// +// Used in .form-groups to align checkboxes with inputs +// +.form-check.form-check-size-input { + margin-top: 7px; + margin-bottom: 7px; +} diff --git a/Build/Sources/Sass/component/_code.scss b/Build/Sources/Sass/component/_code.scss index 6c84365a081b04fbc6df3f643eba343c7480e03c..ea9bc284924280979fcec51e2244536d8476fcb5 100644 --- a/Build/Sources/Sass/component/_code.scss +++ b/Build/Sources/Sass/component/_code.scss @@ -1,6 +1,34 @@ // // Code // +pre, +code { + hyphens: none; +} + +pre[class*="language-"], +code[class*="language-"] { + color: inherit; + background: none; + font-size: 1em; + text-align: start; + white-space: pre; + word-spacing: normal; + word-break: normal; + word-wrap: normal; + line-height: 1.5; + tab-size: 4; + hyphens: none; +} + +pre[class*="language-"] { + border-radius: 4px; + padding: 1em; + overflow: auto; + margin-bottom: var(--typo3-spacing); +} + +:not(pre) > code[class*="language-"], pre[class*="language-"] { - margin-bottom: var(--typo3-component-spacing); + background-color: rgba(0, 0, 0, .05); } diff --git a/Build/Sources/Sass/component/_form.scss b/Build/Sources/Sass/component/_form.scss index 996c71e9316195d4b7163b617666beff814f2078..5d13f993f071b2cccf22d87da33515c7f82d5a4e 100644 --- a/Build/Sources/Sass/component/_form.scss +++ b/Build/Sources/Sass/component/_form.scss @@ -2,7 +2,35 @@ // Form // .form { - margin-bottom: var(--typo3-component-spacing); + margin-bottom: var(--typo3-spacing); +} + +// +// Row +// +@mixin make-form-row() { + display: flex; + flex-wrap: wrap; + gap: var(--typo3-spacing); + margin-bottom: var(--typo3-spacing); + + > .form-group { + margin-bottom: 0; + + > [class*="form-row"] { + margin-bottom: 0; + } + } +} + +@each $breakpoint in map-keys($grid-breakpoints) { + $infix: breakpoint-infix($breakpoint, $grid-breakpoints); + + @include media-breakpoint-up($breakpoint, $grid-breakpoints) { + .form-row#{$infix} { + @include make-form-row(); + } + } } // @@ -20,6 +48,10 @@ margin-bottom: $form-label-margin-bottom; } +.form-label + .form-description { + margin-top: calc($form-label-margin-bottom / 2 * -1); +} + // // Form group // diff --git a/Build/Sources/Sass/component/_module.scss b/Build/Sources/Sass/component/_module.scss index 241aeabff95404952a9570b402cb1e00b400f7c4..c7f4c6e3ba109e4a6a2b0b0787bb9ef6f13e9d74 100644 --- a/Build/Sources/Sass/component/_module.scss +++ b/Build/Sources/Sass/component/_module.scss @@ -116,10 +116,6 @@ .module-body { padding: var(--module-body-padding); - > .callout:first-child { - margin-top: 0; - } - > .container { padding-left: 0; padding-right: 0; diff --git a/Build/Sources/Sass/component/_note.scss b/Build/Sources/Sass/component/_note.scss index d55a279159ff3fe4f9a927caac63441d6caaf212..7e22350fd53062fc95d1cae75ae567726fc8ae8b 100644 --- a/Build/Sources/Sass/component/_note.scss +++ b/Build/Sources/Sass/component/_note.scss @@ -68,8 +68,8 @@ $note-padding: 1rem; // .note-list { display: grid; - gap: calc(var(--typo3-component-spacing) / 2); - margin-bottom: var(--typo3-component-spacing); + gap: var(--typo3-spacing); + margin-bottom: var(--typo3-spacing); .note { margin-bottom: 0; @@ -83,7 +83,7 @@ $note-padding: 1rem; color: var(--note-color); background-color: var(--note-bg); border-radius: var(--typo3-component-border-radius); - margin-bottom: var(--typo3-component-spacing); + margin-bottom: var(--typo3-spacing); box-shadow: var(--typo3-component-box-shadow); @include note-use-variant('default'); diff --git a/Build/Sources/Sass/component/_pagination.scss b/Build/Sources/Sass/component/_pagination.scss new file mode 100644 index 0000000000000000000000000000000000000000..b5d1b82394c6fbaf21603327761af1313d062570 --- /dev/null +++ b/Build/Sources/Sass/component/_pagination.scss @@ -0,0 +1,7 @@ +// +// Pagination +// +.pagination { + flex-wrap: wrap; + row-gap: 4px; +} diff --git a/Build/Sources/Sass/component/_panel.scss b/Build/Sources/Sass/component/_panel.scss index fb761c9e2136921c69253b71922c8a4406323b70..fb5acfc76014b7e101f38fe8e52f03ee8b583c08 100644 --- a/Build/Sources/Sass/component/_panel.scss +++ b/Build/Sources/Sass/component/_panel.scss @@ -87,7 +87,7 @@ $panel-heading-bg-scale: -85%; display: flex; flex-flow: column; overflow: hidden; - margin-bottom: var(--panel-spacing); + margin-bottom: var(--typo3-spacing); border-radius: var(--panel-border-radius); box-shadow: var(--panel-box-shadow); @@ -124,7 +124,7 @@ $panel-heading-bg-scale: -85%; border: var(--panel-border-width) solid var(--panel-border-color); border-radius: var(--panel-border-radius); box-shadow: var(--panel-box-shadow); - margin-bottom: var(--panel-spacing); + margin-bottom: var(--typo3-spacing); transition: all .2s ease-in-out; transition-property: box-shadow, border, transform; diff --git a/Build/Sources/Sass/component/_recordlist.scss b/Build/Sources/Sass/component/_recordlist.scss index 799a630f64c4a416e1884e7ccfd1c4bcd8cd79a6..c758abc1e677a563ecbe6d48bcbee2e6362faba8 100644 --- a/Build/Sources/Sass/component/_recordlist.scss +++ b/Build/Sources/Sass/component/_recordlist.scss @@ -7,7 +7,7 @@ box-shadow: var(--panel-box-shadow); border-radius: var(--panel-border-radius); border: var(--panel-border-width) solid var(--panel-default-border-color); - margin-bottom: var(--panel-spacing); + margin-bottom: var(--typo3-spacing); table tr { td.deletePlaceholder { @@ -27,6 +27,10 @@ .pagination { display: inline-flex; } + + + .recordlist { + margin-top: calc(var(--typo3-spacing) * 1.5); + } } .recordlist-heading { diff --git a/Build/Sources/Sass/component/_recordsearchbox.scss b/Build/Sources/Sass/component/_recordsearchbox.scss index 80613438accc181a5b0c882f49fc6bf497aee3a1..5daa24f3bbeb7877cb961a3728f9c631d602b4ad 100644 --- a/Build/Sources/Sass/component/_recordsearchbox.scss +++ b/Build/Sources/Sass/component/_recordsearchbox.scss @@ -2,7 +2,7 @@ // Record Search Box // .recordsearchbox-container { - margin-bottom: var(--typo3-component-spacing); + margin-bottom: var(--typo3-spacing); [data-recordsearchbox-levels] { max-width: 140px; diff --git a/Build/Sources/Sass/component/_resources.scss b/Build/Sources/Sass/component/_resources.scss index c41df1eb0ab351cc76a127b8a8ffebbd6c01c3a8..e4aebc2abc659898a58ecabd916993f7a67068db 100644 --- a/Build/Sources/Sass/component/_resources.scss +++ b/Build/Sources/Sass/component/_resources.scss @@ -45,7 +45,7 @@ /* clean-css ignore:start */ .resource-tiles-container { container-type: inline-size; - margin-bottom: var(--typo3-component-spacing); + margin-bottom: var(--typo3-spacing); } @container (min-width: 480px) { @@ -200,6 +200,7 @@ padding: var(--resource-tile-spacing); text-align: center; font-size: var(--resource-tile-nameplate-size); + width: 100%; } .resource-tile-nameplate-label { diff --git a/Build/Sources/Sass/component/_root.scss b/Build/Sources/Sass/component/_root.scss index 69cb52d3399ca4992d83210d8467fdcf4511e649..d6d112b71a16cfd140e9f55e4971f984c710a65d 100644 --- a/Build/Sources/Sass/component/_root.scss +++ b/Build/Sources/Sass/component/_root.scss @@ -78,7 +78,7 @@ --typo3-component-disabled-color: var(--typo3-light-disabled-color); --typo3-component-disabled-bg: var(--typo3-light-disabled-bg); --typo3-component-disabled-border-color: var(--typo3-light-disabled-border-color); - --typo3-component-spacing: 1.5rem; + --typo3-component-spacing: 2rem; // List --typo3-list-item-padding-y: .5rem; diff --git a/Build/Sources/Sass/component/_spacer.scss b/Build/Sources/Sass/component/_spacer.scss new file mode 100644 index 0000000000000000000000000000000000000000..4b63e2d1f5da2cc50fbd1714958260affa59d1d0 --- /dev/null +++ b/Build/Sources/Sass/component/_spacer.scss @@ -0,0 +1,13 @@ +// +// Spacer +// +// Usage +// ----- +// +// <hr class="spacer"> +// +hr.spacer { + border-top: none; + margin-top: var(--typo3-spacing); + margin-bottom: var(--typo3-spacing); +} diff --git a/Build/Sources/Sass/component/_statusreport.scss b/Build/Sources/Sass/component/_statusreport.scss index f557e16823f7eb130c5593a80be834493f2546ac..d0ba5b692a21a9dffa3f50f60b14064f6585daae 100644 --- a/Build/Sources/Sass/component/_statusreport.scss +++ b/Build/Sources/Sass/component/_statusreport.scss @@ -104,7 +104,7 @@ .statusreport-wrapper { border-radius: var(--statusreport-border-radius); box-shadow: var(--statusreport-box-shadow); - margin-bottom: var(--typo3-component-spacing); + margin-bottom: var(--typo3-spacing); .statusreport { &:first-child { diff --git a/Build/Sources/Sass/component/_table.scss b/Build/Sources/Sass/component/_table.scss index 52775a95e2ca38df3686e7ae5c543799db26c7fc..919f74a1c351672d36968e0cf375df67745c015f 100644 --- a/Build/Sources/Sass/component/_table.scss +++ b/Build/Sources/Sass/component/_table.scss @@ -193,7 +193,7 @@ td.selected { width: 100%; border-radius: var(--typo3-component-border-radius); box-shadow: var(--typo3-component-box-shadow); - margin-bottom: var(--typo3-component-spacing); + margin-bottom: var(--typo3-spacing); overflow-x: auto; overflow-y: hidden; -webkit-overflow-scrolling: touch; diff --git a/Build/Sources/Sass/component/_type.scss b/Build/Sources/Sass/component/_type.scss new file mode 100644 index 0000000000000000000000000000000000000000..f5d3efe070e55efcbeecd22ff20beb36766bac3a --- /dev/null +++ b/Build/Sources/Sass/component/_type.scss @@ -0,0 +1,26 @@ +// +// Type Adjustments +// +h1 { + font-family: var(--typo3-header-font-family); + font-variant: normal; + font-weight: 400; +} + +h1, +h2, +h3 { + &.headline-spaced, + &:not(:first-child):not([class]) { + margin-top: calc(var(--typo3-spacing) * 2); + } +} + +.h1, +.h2, +.h3, +.h4, +.h5, +.h6 { + font-family: inherit; +} diff --git a/Build/Sources/Sass/module/_install.scss b/Build/Sources/Sass/module/_install.scss index 389dc607a639a589f595d2224ee4f834054faee4..81ffeb6c5b67bfeed58d8e1b89221a91481ee38c 100644 --- a/Build/Sources/Sass/module/_install.scss +++ b/Build/Sources/Sass/module/_install.scss @@ -92,7 +92,9 @@ // Styles for specific modals: image processing .t3-install-displaytwinimageimages { border: 1px solid #ccc; + border-radius: 4px; padding: 10px; + margin-bottom: var(--typo3-spacing); } .t3-install-displaytwinimagetextarea { diff --git a/Build/Sources/Sass/module/_page.scss b/Build/Sources/Sass/module/_page.scss index ce51b698549331ecf04d0a633e857d61653617ba..f4ce1ffe31c235d07153401cfe4f0aeb99090b10 100644 --- a/Build/Sources/Sass/module/_page.scss +++ b/Build/Sources/Sass/module/_page.scss @@ -46,7 +46,7 @@ html { .t3-grid-container { overflow: hidden; - margin-bottom: var(--typo3-component-spacing); + margin-bottom: var(--typo3-spacing); } .t3-grid-container-inner { diff --git a/Build/Sources/Sass/module/_scheduler.scss b/Build/Sources/Sass/module/_scheduler.scss index b2f1fa56045cf4c744e76d8bb8ec8d68bca94a6a..1c7ec3400e63e7d428953c23fe70caa590e30640 100644 --- a/Build/Sources/Sass/module/_scheduler.scss +++ b/Build/Sources/Sass/module/_scheduler.scss @@ -11,10 +11,6 @@ } } -.scheduler-group-panel { - overflow: unset; -} - .task-form .form-wizards-wrap { margin-bottom: .5rem !important; } diff --git a/Build/Sources/Sass/typo3/_main_content.scss b/Build/Sources/Sass/typo3/_main_content.scss index 1812a873227f6534bbe0afaa0f59e60ababfdcef..fb7384c80c070ad8e5ef2ff2622a9fa65983bd69 100644 --- a/Build/Sources/Sass/typo3/_main_content.scss +++ b/Build/Sources/Sass/typo3/_main_content.scss @@ -1,12 +1,6 @@ // // TYPO3 styles for basic elements // -h1 { - font-family: var(--typo3-header-font-family); - font-variant: normal; - font-weight: 400; -} - video { background-color: #000; } @@ -22,13 +16,6 @@ video { white-space: normal !important; } -// -// TYPO3 styles for basic elements -// -em { - font-style: italic; -} - // // Various classes // diff --git a/Build/Sources/Sass/typo3/_main_form.scss b/Build/Sources/Sass/typo3/_main_form.scss index c99b4d5cbc7a5acc9ca75235d96c412fd433eafa..cc63b511c8e73e702c05e9b908c84e3aea6f1cfa 100644 --- a/Build/Sources/Sass/typo3/_main_form.scss +++ b/Build/Sources/Sass/typo3/_main_form.scss @@ -119,23 +119,6 @@ fieldset[disabled] .form-control { color: $input-color-disabled; } -// -// Form control icon -// -.form-control-icon { - position: absolute; - top: 50%; - left: 15px; - transform: translate(0, -50%); - z-index: 1; - pointer-events: none; - - + .form-control, - + .form-control-clearable .form-control { - padding-left: 3.25em; - } -} - // // Form group validation states // @@ -192,9 +175,17 @@ select { } // -// Styles for the "clearable" jquery plugin. +// Styles for the "clearable" plugin. +// +// <div class="form-control-clearable-wrapper"> +// <input type="text" class="form-control form-control-clearable" /> +// </div> // .form-control-clearable { + padding-right: 2.3em; +} + +.form-control-clearable-wrapper { position: relative; border: 0; padding: 0; @@ -445,13 +436,13 @@ textarea { // with a clearable div. If the field is unlocked for explanation view, the // wrap should grow to 100%, else it should shrink to 0%. // -.input-group > .form-control-clearable { +.input-group > .form-control-clearable-wrapper { flex: 1 1 auto; width: 1%; min-width: 0; } -.form-control:not(.hidden) + .form-control-clearable { +.form-control:not(.hidden) + .form-control-clearable-wrapper { flex-grow: 0; width: auto; } diff --git a/Build/Sources/Sass/variables/_main.scss b/Build/Sources/Sass/variables/_main.scss index 0423c1bc82e65bef9508ca2df27aab20a02df9a0..3a3fdc285a618d5e17f61bf567211493f001306a 100644 --- a/Build/Sources/Sass/variables/_main.scss +++ b/Build/Sources/Sass/variables/_main.scss @@ -76,16 +76,16 @@ $font-family-sans-serif: Verdana, Arial, Helvetica, sans-serif; $font-family-monospace: SFMono-Regular, Menlo, Monaco, Consolas, "Liberation Mono", "Courier New", monospace; $font-size-root: 16px; $font-size-base: 12px; -$font-size-large: ceil(($font-size-base * 1.25)); // ~15px -$font-size-small: 11px; // ~11px -$h1-font-size: $font-size-base * 2.25; -$h2-font-size: $font-size-base * 1.6; -$h3-font-size: $font-size-base * 1.4; -$h4-font-size: $font-size-base * 1.25; -$headings-line-height: 1.1; - -// Paragraphs -$paragraph-margin-bottom: .5rem; +$font-size-large: 16px; +$font-size-small: 11px; +$h1-font-size: 28px; +$h2-font-size: 20px; +$h3-font-size: 16px; +$h4-font-size: 14px; + +// Spacings +$headings-margin-bottom: calc(var(--typo3-spacing) / 2); +$paragraph-margin-bottom: var(--typo3-spacing); // Components $padding-base-vertical: 6px; diff --git a/Build/Sources/TypeScript/backend/form-engine.ts b/Build/Sources/TypeScript/backend/form-engine.ts index ac5382619f8ceae6be5255ee5ba68bd98c533b5d..1b6a1009d613354f5353c7e220c58018c410436a 100644 --- a/Build/Sources/TypeScript/backend/form-engine.ts +++ b/Build/Sources/TypeScript/backend/form-engine.ts @@ -720,10 +720,10 @@ export default (function() { */ FormEngine.reinitialize = function(): void { // Apply "close" button to all input / datetime fields - const clearables = Array.from(document.querySelectorAll('.t3js-clearable')); + const clearables = document.querySelectorAll('.t3js-clearable') as NodeListOf<HTMLInputElement>; if (clearables.length > 0) { import('@typo3/backend/input/clearable').then(function() { - clearables.forEach(clearableField => (clearableField as any).clearable()); + clearables.forEach(clearableField => clearableField.clearable()); }); } diff --git a/Build/Sources/TypeScript/backend/form-engine/field-control/password-generator.ts b/Build/Sources/TypeScript/backend/form-engine/field-control/password-generator.ts index 6f87495e1703d609d07a6993b77879a66095b16c..5cf040b83238d8858154ef19d545064f179ef981 100644 --- a/Build/Sources/TypeScript/backend/form-engine/field-control/password-generator.ts +++ b/Build/Sources/TypeScript/backend/form-engine/field-control/password-generator.ts @@ -57,7 +57,7 @@ class PasswordGenerator { // Also remove clearable possibility if (this.humanReadableField.isClearable || this.humanReadableField.classList.contains('t3js-clearable')) { this.humanReadableField.classList.remove('t3js-clearable'); - const clearableContainer = <HTMLDivElement>this.humanReadableField.closest('div.form-control-clearable'); + const clearableContainer = <HTMLDivElement>this.humanReadableField.closest('div.form-control-clearable-wrapper'); if (clearableContainer) { clearableContainer.classList.remove('form-control-clearable'); const closeButton = <HTMLButtonElement>clearableContainer.querySelector('button.close'); diff --git a/Build/Sources/TypeScript/backend/input/clearable.ts b/Build/Sources/TypeScript/backend/input/clearable.ts index 42bd3b174bf7e90daadbdcaf2e9cba35ec342818..f33c4ea858a35169791c3e7f9dcdd02d2aa4e656 100644 --- a/Build/Sources/TypeScript/backend/input/clearable.ts +++ b/Build/Sources/TypeScript/backend/input/clearable.ts @@ -68,8 +68,10 @@ class Clearable { throw new Error('Passed options must be an object, ' + typeof options + ' given'); } + this.classList.add('form-control-clearable'); + const wrap = document.createElement('div'); - wrap.classList.add('form-control-clearable'); + wrap.classList.add('form-control-clearable-wrapper'); this.parentNode.insertBefore(wrap, this); wrap.appendChild(this); diff --git a/Build/Sources/TypeScript/backend/login.ts b/Build/Sources/TypeScript/backend/login.ts index 13374cdd86496cf371eda4bf00c0f2c408c18367..ff5d8484b371899d70908e234be825996e759490 100644 --- a/Build/Sources/TypeScript/backend/login.ts +++ b/Build/Sources/TypeScript/backend/login.ts @@ -176,7 +176,7 @@ class BackendLogin { private initializeEvents(): void { new RegularEvent('submit', this.handleSubmit.bind(this)).bindTo(document.querySelector(this.options.loginForm)); - (<NodeListOf<HTMLInputElement>>document.querySelectorAll('.t3js-clearable')).forEach( + (document.querySelectorAll('.t3js-clearable') as NodeListOf<HTMLInputElement>).forEach( (clearableField: HTMLInputElement) => clearableField.clearable(), ); } diff --git a/Build/Sources/TypeScript/belog/backend-log.ts b/Build/Sources/TypeScript/belog/backend-log.ts index 60102c20f3951c5c7b412632e6fbfd0e10df68b6..8b785dfca51a3dac52a9b92cd25e3a04a4b62635 100644 --- a/Build/Sources/TypeScript/belog/backend-log.ts +++ b/Build/Sources/TypeScript/belog/backend-log.ts @@ -29,7 +29,7 @@ class BackendLog { constructor() { DocumentService.ready().then((): void => { - this.clearableElements = document.querySelectorAll('.t3js-clearable'); + this.clearableElements = document.querySelectorAll('.t3js-clearable') as NodeListOf<HTMLInputElement>; this.dateTimePickerElements = document.querySelectorAll('.t3js-datetimepicker'); this.elementBrowserElements = document.querySelectorAll('.t3js-element-browser'); this.initializeClearableElements(); @@ -41,7 +41,7 @@ class BackendLog { private initializeClearableElements(): void { this.clearableElements.forEach( - (clearableField: HTMLInputElement) => clearableField.clearable() + (clearableField) => clearableField.clearable() ); } diff --git a/Build/Sources/TypeScript/install/renderable/clearable.ts b/Build/Sources/TypeScript/install/renderable/clearable.ts index d5b69a839481bf7f5dc9d50966514ed536140841..5c523ae3d410cc19e9af82ee1f53d878ec5084f0 100644 --- a/Build/Sources/TypeScript/install/renderable/clearable.ts +++ b/Build/Sources/TypeScript/install/renderable/clearable.ts @@ -68,8 +68,10 @@ class Clearable { throw new Error('Passed options must be an object, ' + typeof options + ' given'); } + this.classList.add('form-control-clearable'); + const wrap = document.createElement('div'); - wrap.classList.add('form-control-clearable', 'form-control'); + wrap.classList.add('form-control-clearable-wrapper'); this.parentNode.insertBefore(wrap, this); wrap.appendChild(this); diff --git a/Build/Sources/TypeScript/lowlevel/query-generator.ts b/Build/Sources/TypeScript/lowlevel/query-generator.ts index 77a971d6de5b748c7f98e837162bd778c1f75f20..5d77b0c1069a9e1c6e53c8ebc925e86edcdc1f51 100644 --- a/Build/Sources/TypeScript/lowlevel/query-generator.ts +++ b/Build/Sources/TypeScript/lowlevel/query-generator.ts @@ -11,55 +11,52 @@ * The TYPO3 project - inspiring people to share! */ -import $ from 'jquery'; import '@typo3/backend/input/clearable'; import DateTimePicker from '@typo3/backend/date-time-picker'; +import RegularEvent from '@typo3/core/event/regular-event'; /** * Module: @typo3/lowlevel/query-generator * This module handle the QueryGenerator forms. */ class QueryGenerator { - private form: JQuery = null; - private limitField: JQuery = null; + private form: HTMLFormElement = null; + private limitField: HTMLInputElement = null; constructor() { - this.initialize(); - } + this.form = document.querySelector('form[name="queryform"]'); + this.limitField = document.querySelector('input#queryLimit'); - /** - * Initialize the QueryGenerator object - */ - private initialize(): void { - this.form = $('form[name="queryform"]'); - this.limitField = $('#queryLimit'); - this.form.on('click', '.t3js-submit-click', (e: JQueryEventObject): void => { - e.preventDefault(); + new RegularEvent('click', (event: Event) => { + event.preventDefault(); this.doSubmit(); - }); - this.form.on('change', '.t3js-submit-change', (e: JQueryEventObject): void => { - e.preventDefault(); + }).delegateTo(this.form, '.t3js-submit-click'); + + new RegularEvent('change', (event: Event) => { + event.preventDefault(); this.doSubmit(); - }); - this.form.on('click', '.t3js-limit-submit input[type="button"]', (e: JQueryEventObject): void => { - e.preventDefault(); - this.setLimit($(e.currentTarget).data('value')); + }).delegateTo(this.form, '.t3js-submit-change'); + + new RegularEvent('click', (event: Event, element: HTMLButtonElement) => { + event.preventDefault(); + this.setLimit(element.value); this.doSubmit(); - }); - this.form.on('click', '.t3js-addfield', (e: JQueryEventObject): void => { - e.preventDefault(); - const $field = $(e.currentTarget); - this.addValueToField($field.data('field'), $field.val()); - }); - this.form.on('change', '[data-assign-store-control-title]', (evt: JQueryEventObject): void => { - const $currentTarget = $(evt.currentTarget); - const $titleField = this.form.find('[name="storeControl[title]"]'); - if ($currentTarget.val() !== '0') { - $titleField.val($currentTarget.find('option:selected').text()); + }).delegateTo(this.form, '.t3js-limit-submit input[type="button"]'); + + new RegularEvent('click', (event: Event, element: HTMLButtonElement) => { + event.preventDefault(); + this.addValueToField(element.dataset.field, element.value); + }).delegateTo(this.form, '.t3js-addfield'); + + new RegularEvent('change', (event: Event, element: HTMLSelectElement) => { + const titleField = <HTMLInputElement>this.form.querySelector('input[name="storeControl[title]"]'); + if (element.value !== '0') { + titleField.value = element.querySelector('option:selected').textContent; } else { - $titleField.val(''); + titleField.value = ''; } - }); + }).delegateTo(this.form, 'select.t3js-addfield'); + (<NodeListOf<HTMLInputElement>>document.querySelectorAll('form[name="queryform"] .t3js-clearable')).forEach( (clearableField: HTMLInputElement) => clearableField.clearable({ onClear: (): void => { @@ -76,7 +73,7 @@ class QueryGenerator { * Submit the form */ private doSubmit(): void { - this.form.trigger('submit'); + this.form.submit(); } /** @@ -85,7 +82,7 @@ class QueryGenerator { * @param {String} value */ private setLimit(value: string): void { - this.limitField.val(value); + this.limitField.value = value; } /** @@ -95,9 +92,15 @@ class QueryGenerator { * @param {String} value the value to add */ private addValueToField(field: string, value: string): void { - const $target = this.form.find('[name="' + field + '"]'); - const currentValue = $target.val(); - $target.val(currentValue + ',' + value); + const target = <HTMLInputElement>this.form.querySelector('[name="' + field + '"]'); + value = target.value + ',' + value; + target.value = value + .split(',') + // Remove whitespace from fields + .map(fieldName => fieldName.trim()) + // Ensure fields only exist once + .filter((value, index, array) => array.indexOf(value) === index) + .join(','); } } diff --git a/typo3/sysext/backend/Classes/Controller/RecordListController.php b/typo3/sysext/backend/Classes/Controller/RecordListController.php index c76b467c89d0c9c1479c65f0c80116d117dea26a..d87d5e642021f287c074987798135dfb29d26190 100644 --- a/typo3/sysext/backend/Classes/Controller/RecordListController.php +++ b/typo3/sysext/backend/Classes/Controller/RecordListController.php @@ -195,7 +195,7 @@ class RecordListController } $clipboardHtml = ''; if ($this->allowClipboard && $this->moduleData->get('clipBoard') && ($tableListHtml || $clipboard->hasElements())) { - $clipboardHtml = '<typo3-backend-clipboard-panel return-url="' . htmlspecialchars($dbList->listURL()) . '"></typo3-backend-clipboard-panel>'; + $clipboardHtml = '<hr class="spacer"><typo3-backend-clipboard-panel return-url="' . htmlspecialchars($dbList->listURL()) . '"></typo3-backend-clipboard-panel>'; } $view->setTitle($languageService->sL('LLL:EXT:core/Resources/Private/Language/locallang_mod_web_list.xlf:mlang_tabs_tab'), $title); @@ -519,10 +519,14 @@ class RecordListController $output .= '<option value="' . htmlspecialchars($targetUrl) . '">' . htmlspecialchars($languageTitle) . '</option>'; } - return '<div class="row row-cols-auto align-items-end g-3 mb-4"><div class="col"><div class="form-group">' - . '<select class="form-select" name="createNewLanguage" data-global-event="change" data-action-navigate="$value">' - . $output - . '</select></div></div></div>'; + return '' + . '<div class="form-row">' + . '<div class="form-group">' + . '<select class="form-select" name="createNewLanguage" data-global-event="change" data-action-navigate="$value">' + . $output + . '</select>' + . '</div>' + . '</div>'; } return ''; } diff --git a/typo3/sysext/backend/Classes/Form/Element/DatetimeElement.php b/typo3/sysext/backend/Classes/Form/Element/DatetimeElement.php index df58837a3c0453db11228bcc3707813f44cffff9..3b027d080c74f8bc6716014a90968fa0fe5e6fd4 100644 --- a/typo3/sysext/backend/Classes/Form/Element/DatetimeElement.php +++ b/typo3/sysext/backend/Classes/Form/Element/DatetimeElement.php @@ -139,6 +139,7 @@ class DatetimeElement extends AbstractFormElement 'class' => implode(' ', [ 't3js-datetimepicker', 'form-control', + 'form-control-clearable', 't3js-clearable', 'hasDefaultValue', ]), diff --git a/typo3/sysext/backend/Classes/Form/Element/EmailElement.php b/typo3/sysext/backend/Classes/Form/Element/EmailElement.php index fceaff013992976b559c32121613ccb13cc2b23d..45784856ed16eb844814fc47b1f004dec234ff89 100644 --- a/typo3/sysext/backend/Classes/Form/Element/EmailElement.php +++ b/typo3/sysext/backend/Classes/Form/Element/EmailElement.php @@ -118,6 +118,7 @@ class EmailElement extends AbstractFormElement 'maxlength' => '254', 'class' => implode(' ', [ 'form-control', + 'form-control-clearable', 't3js-clearable', 'hasDefaultValue', ]), diff --git a/typo3/sysext/backend/Classes/Form/Element/InputTextElement.php b/typo3/sysext/backend/Classes/Form/Element/InputTextElement.php index c395bc8c65ada44018bc9505f9510b641b0a2f4d..98e47ad5b41bd716852db4d994b24c3bca554715 100644 --- a/typo3/sysext/backend/Classes/Form/Element/InputTextElement.php +++ b/typo3/sysext/backend/Classes/Form/Element/InputTextElement.php @@ -134,6 +134,7 @@ class InputTextElement extends AbstractFormElement 'id' => $fieldId, 'class' => implode(' ', [ 'form-control', + 'form-control-clearable', 't3js-clearable', 'hasDefaultValue', ]), diff --git a/typo3/sysext/backend/Classes/Form/Element/LinkElement.php b/typo3/sysext/backend/Classes/Form/Element/LinkElement.php index ed724b621975680f3840c6b4f38f4fe847219318..08b4db308cb212769622384af644af0ffcb2e745 100644 --- a/typo3/sysext/backend/Classes/Form/Element/LinkElement.php +++ b/typo3/sysext/backend/Classes/Form/Element/LinkElement.php @@ -136,6 +136,7 @@ class LinkElement extends AbstractFormElement 'id' => $fieldId, 'class' => implode(' ', [ 'form-control', + 'form-control-clearable', 't3js-clearable', 't3js-form-field-link-input', 'hidden', diff --git a/typo3/sysext/backend/Classes/Form/Element/NumberElement.php b/typo3/sysext/backend/Classes/Form/Element/NumberElement.php index fe67c21a5ccb15a50728816ec823b01f94124f96..254e558e143bd2a544320df7fd9d08313d4416ae 100644 --- a/typo3/sysext/backend/Classes/Form/Element/NumberElement.php +++ b/typo3/sysext/backend/Classes/Form/Element/NumberElement.php @@ -128,6 +128,7 @@ class NumberElement extends AbstractFormElement 'id' => $fieldId, 'class' => implode(' ', [ 'form-control', + 'form-control-clearable', 't3js-clearable', 'hasDefaultValue', ]), diff --git a/typo3/sysext/backend/Classes/Form/Element/PasswordElement.php b/typo3/sysext/backend/Classes/Form/Element/PasswordElement.php index 512f8ea54f217d9186534ba568b27fa195aa66fc..df030d4b3ba24bb5b2ae0b85551cf9942ebb2bef 100644 --- a/typo3/sysext/backend/Classes/Form/Element/PasswordElement.php +++ b/typo3/sysext/backend/Classes/Form/Element/PasswordElement.php @@ -114,6 +114,7 @@ class PasswordElement extends AbstractFormElement 'spellcheck' => 'false', 'class' => implode(' ', [ 'form-control', + 'form-control-clearable', 't3js-clearable', 'hasDefaultValue', ]), diff --git a/typo3/sysext/backend/Resources/Private/Layouts/Module.html b/typo3/sysext/backend/Resources/Private/Layouts/Module.html index 9bec2bfa254e07afd73fa933904ce8ae8a913134..f39e93aac4e51bfff651190bd5e9501bd6625d03 100644 --- a/typo3/sysext/backend/Resources/Private/Layouts/Module.html +++ b/typo3/sysext/backend/Resources/Private/Layouts/Module.html @@ -3,6 +3,8 @@ data-namespace-typo3-fluid="true" > +<f:render section="Before" arguments="{_all}" optional="true" /> + <div class="module {moduleClass}" data-module-id="{moduleId}" data-module-name="{moduleName}"> <f:if condition="{formTag}"> <f:then> @@ -30,4 +32,6 @@ </f:if> </div> +<f:render section="After" arguments="{_all}" optional="true" /> + </html> diff --git a/typo3/sysext/backend/Resources/Private/Partials/About/Logo.html b/typo3/sysext/backend/Resources/Private/Partials/About/Logo.html index 9b94daa3150522299abcbfeb769c81d4aa2d7f98..f454b031309e7c04e9d3aa98836f4014e42fae89 100644 --- a/typo3/sysext/backend/Resources/Private/Partials/About/Logo.html +++ b/typo3/sysext/backend/Resources/Private/Partials/About/Logo.html @@ -1,7 +1,8 @@ -<img src="{f:uri.resource(path: 'EXT:core/Resources/Public/Images/typo3_orange.svg')}" width="150" - alt="{f:translate(key:'LLL:EXT:backend/Resources/Private/Language/Modules/about.xlf:typo3_logo')}" /> -<br> -<br> +<img + src="{f:uri.resource(path: 'EXT:core/Resources/Public/Images/typo3_orange.svg')}" + width="150" + alt="{f:translate(key:'LLL:EXT:backend/Resources/Private/Language/Modules/about.xlf:typo3_logo')}" +/> <h1> TYPO3 CMS {typo3Version.version}<br> <f:translate key="LLL:EXT:backend/Resources/Private/Language/Modules/about.xlf:introtext" /> diff --git a/typo3/sysext/backend/Resources/Private/Partials/PageLayout/LanguageColumns.html b/typo3/sysext/backend/Resources/Private/Partials/PageLayout/LanguageColumns.html index 633dd70624cc015015905d5d7fb85b0fd41dbe9f..e1ebf51f6f526fb3141eb16179c71458ccace578 100644 --- a/typo3/sysext/backend/Resources/Private/Partials/PageLayout/LanguageColumns.html +++ b/typo3/sysext/backend/Resources/Private/Partials/PageLayout/LanguageColumns.html @@ -1,6 +1,6 @@ <f:if condition="{context.newLanguageOptions}"> - <div class="row row-cols-auto align-items-end g-3 mb-4"> - <div class="col"> + <div class="form-row"> + <div class="form-group"> <select class="form-select" name="createNewLanguage" data-global-event="change" data-action-navigate="$value"> <f:for each="{context.newLanguageOptions}" as="languageName" key="url"> <option value="{url}">{languageName}</option> diff --git a/typo3/sysext/backend/Resources/Private/Templates/Login/ForgetPasswordForm.html b/typo3/sysext/backend/Resources/Private/Templates/Login/ForgetPasswordForm.html index 5571b9b1e874b590c0986e0b46d61a23128eaff1..59a40414e582eaa9b67307f9ad96e9204f51fe16 100644 --- a/typo3/sysext/backend/Resources/Private/Templates/Login/ForgetPasswordForm.html +++ b/typo3/sysext/backend/Resources/Private/Templates/Login/ForgetPasswordForm.html @@ -28,7 +28,7 @@ <div class="form-control-wrap"> <div class="form-control-holder"> <label for="typo3-forget-password-email"><f:translate key="LLL:EXT:backend/Resources/Private/Language/locallang_reset_password.xlf:input.email" /></label> - <input type="email" name="email" value="{email}" placeholder="you@example.com" id="typo3-forget-password-email" class="form-control input-login t3js-clearable" autofocus="autofocus" autocomplete="email" required="required" /> + <input type="email" name="email" value="{email}" placeholder="you@example.com" id="typo3-forget-password-email" class="form-control form-control-clearable input-login t3js-clearable" autofocus="autofocus" autocomplete="email" required="required" /> </div> </div> </div> diff --git a/typo3/sysext/backend/Resources/Private/Templates/Login/ResetPasswordForm.html b/typo3/sysext/backend/Resources/Private/Templates/Login/ResetPasswordForm.html index 3406600515f9f80f6978e1a1dc4815cfd89764ef..ae4bede0bf46a96fc31fbb74574d226de0b564d3 100644 --- a/typo3/sysext/backend/Resources/Private/Templates/Login/ResetPasswordForm.html +++ b/typo3/sysext/backend/Resources/Private/Templates/Login/ResetPasswordForm.html @@ -44,7 +44,7 @@ name="password" placeholder="{f:translate(key: 'LLL:EXT:backend/Resources/Private/Language/locallang_reset_password.xlf:input.password')}" value="" - class="form-control input-login t3js-clearable t3js-login-password-field" + class="form-control form-control-clearable input-login t3js-clearable t3js-login-password-field" autocomplete="new-password" autofocus="autofocus" required="required" @@ -73,7 +73,7 @@ placeholder="{f:translate(key: 'LLL:EXT:backend/Resources/Private/Language/locallang_reset_password.xlf:input.passwordrepeat')}" value="" autocomplete="off" - class="form-control input-login t3js-clearable t3js-login-password-field" + class="form-control form-control-clearable input-login t3js-clearable t3js-login-password-field" required="required" spellcheck="false" /> diff --git a/typo3/sysext/backend/Resources/Private/Templates/Login/UserPassLoginForm.html b/typo3/sysext/backend/Resources/Private/Templates/Login/UserPassLoginForm.html index 686bd447fbc2ae8babef0e494f3bb7c277780840..00738c8a9683a18dd411343f40d319d669531e0e 100644 --- a/typo3/sysext/backend/Resources/Private/Templates/Login/UserPassLoginForm.html +++ b/typo3/sysext/backend/Resources/Private/Templates/Login/UserPassLoginForm.html @@ -23,7 +23,7 @@ value="{presetUsername}" aria-label="{f:translate(key: 'LLL:EXT:backend/Resources/Private/Language/locallang.xlf:login.username')}" placeholder="{f:translate(key: 'LLL:EXT:backend/Resources/Private/Language/locallang.xlf:login.username')}" - class="form-control input-login t3js-clearable t3js-login-username-field" + class="form-control form-control-clearable input-login t3js-clearable t3js-login-username-field" autofocus="autofocus" autocomplete="username" required="required" diff --git a/typo3/sysext/backend/Resources/Private/Templates/Page/NewPages.html b/typo3/sysext/backend/Resources/Private/Templates/Page/NewPages.html index 77ab579f02f3aaee34309f066ec568c597906e43..8051d120b0d7ecf9c597f0190e21f9ee981b659c 100644 --- a/typo3/sysext/backend/Resources/Private/Templates/Page/NewPages.html +++ b/typo3/sysext/backend/Resources/Private/Templates/Page/NewPages.html @@ -198,17 +198,13 @@ <div class="formengine-field-item t3js-formengine-field-item"> <div class="form-control-wrap"> <div class="form-wizards-wrap"> - <div class="form-wizards-element"> - <div class="form-control-clearable"> - <input - class="form-control t3js-newmultiplepages-page-title" - type="text" - id="page_new_{line.index}" - name="pages[NEW{line.index}][title]" - placeholder="{f:translate(key: 'LLL:EXT:core/Resources/Private/Language/locallang_general.xlf:LGL.title')}" - /> - </div> - </div> + <input + class="form-control t3js-newmultiplepages-page-title" + type="text" + id="page_new_{line.index}" + name="pages[NEW{line.index}][title]" + placeholder="{f:translate(key: 'LLL:EXT:core/Resources/Private/Language/locallang_general.xlf:LGL.title')}" + /> </div> </div> </div> diff --git a/typo3/sysext/backend/Resources/Private/Templates/PageLayout/PageModule.html b/typo3/sysext/backend/Resources/Private/Templates/PageLayout/PageModule.html index 1cc365fa5873af1089e9dff344dbd420729902a2..2175923f05034e8e2a74b19d9a0f5feac50526c4 100644 --- a/typo3/sysext/backend/Resources/Private/Templates/PageLayout/PageModule.html +++ b/typo3/sysext/backend/Resources/Private/Templates/PageLayout/PageModule.html @@ -5,8 +5,7 @@ <f:layout name="Module" /> -<f:section name="Content"> - +<f:section name="Before"> <f:be.pageRenderer includeJavaScriptModules="{ 0: '@typo3/backend/clear-cache.js', @@ -18,9 +17,14 @@ 6: '@typo3/backend/element/editable-page-title.js' }" /> - <f:variable name="immediateActionArgs" value="{0: 'web', 1: pageId, 2: 1}" /> - <typo3-immediate-action action="TYPO3.Backend.Storage.ModuleStateStorage.updateWithCurrentMount" args="{immediateActionArgs -> f:format.json() -> f:format.htmlspecialchars()}"></typo3-immediate-action> + <typo3-immediate-action + action="TYPO3.Backend.Storage.ModuleStateStorage.updateWithCurrentMount" + args="{immediateActionArgs -> f:format.json() -> f:format.htmlspecialchars()}" + ></typo3-immediate-action> +</f:section> + +<f:section name="Content"> <f:for each="{infoBoxes}" as="infoBox"> <f:be.infobox state="{infoBox.state}"> diff --git a/typo3/sysext/backend/Resources/Private/Templates/PageLayout/PageModuleNoAccess.html b/typo3/sysext/backend/Resources/Private/Templates/PageLayout/PageModuleNoAccess.html index e9e3e402a358ea639fae03c10b1ce0d69792f730..0ca68f9b69279ed084a23803f012c1bca6e65e5a 100644 --- a/typo3/sysext/backend/Resources/Private/Templates/PageLayout/PageModuleNoAccess.html +++ b/typo3/sysext/backend/Resources/Private/Templates/PageLayout/PageModuleNoAccess.html @@ -5,13 +5,17 @@ <f:layout name="Module" /> -<f:section name="Content"> - +<f:section name="Before"> <f:variable name="immediateActionArgs" value="{0: 'web', 1: pageId}" /> - <typo3-immediate-action action="TYPO3.Backend.Storage.ModuleStateStorage.update" args="{immediateActionArgs -> f:format.json() -> f:format.htmlspecialchars()}"></typo3-immediate-action> + <typo3-immediate-action + action="TYPO3.Backend.Storage.ModuleStateStorage.update" + args="{immediateActionArgs -> f:format.json() -> f:format.htmlspecialchars()}" + ></typo3-immediate-action> +</f:section> - <h1>{siteName}</h1> +<f:section name="Content"> + <h1>{siteName}</h1> <f:be.infobox message="{f:translate(key: 'LLL:EXT:backend/Resources/Private/Language/locallang_layout.xlf:clickAPage_content')}" state="-1" /> </f:section> diff --git a/typo3/sysext/backend/Resources/Private/Templates/PageTsConfig/Active.html b/typo3/sysext/backend/Resources/Private/Templates/PageTsConfig/Active.html index 995385365370173f985f15c81b4e0741f52f6175..1d6f1ecb5a45a5cb053c5286e9c7d780a0234683 100644 --- a/typo3/sysext/backend/Resources/Private/Templates/PageTsConfig/Active.html +++ b/typo3/sysext/backend/Resources/Private/Templates/PageTsConfig/Active.html @@ -7,7 +7,7 @@ <f:layout name="Module"/> -<f:section name="Content"> +<f:section name="Before"> <f:be.pageRenderer includeJavaScriptModules="{ 0: '@typo3/backend/context-menu.js', @@ -20,10 +20,14 @@ 'collapse-state-search.numberOfSearchMatches': 'LLL:EXT:backend/Resources/Private/Language/locallang_pagetsconfig.xlf:module.pagetsconfig_active.panel.header.numberOfSearchMatches' }" /> - <f:variable name="args" value="{0: 'web', 1: pageUid}" /> - <typo3-immediate-action action="TYPO3.Backend.Storage.ModuleStateStorage.update" args="{args -> f:format.json() -> f:format.htmlspecialchars()}"></typo3-immediate-action> + <typo3-immediate-action + action="TYPO3.Backend.Storage.ModuleStateStorage.update" + args="{args -> f:format.json() -> f:format.htmlspecialchars()}" + ></typo3-immediate-action> +</f:section> +<f:section name="Content"> <h1> <f:translate key="LLL:EXT:backend/Resources/Private/Language/locallang_pagetsconfig.xlf:module.pagetsconfig_active.headline" @@ -89,13 +93,13 @@ </f:section> <f:section name="Options"> - <div class="row row-cols-auto align-items-end g-3 mb-4 pt-2"> - <div class="col col-12 col-sm-6 col-md-5 col-lg-4 col-xl-3"> + <div class="form-row-md"> + <div class="form-group"> <form action="#"> <div class="input-group"> <input type="text" - class="form-control t3js-collapse-search-term" + class="form-control form-control-clearable t3js-collapse-search-term" name="searchValue" data-persist-collapse-search-key="collapse-search-term-pagets" value="" @@ -106,13 +110,13 @@ </div> </form> </div> - <div class="col"> - <div class="row row-cols-md-auto pb-1"> + <div class="form-group"> + <div class="form-row-sm"> <f:if condition="{siteSettingsAst}"> - <div class="col col-12 col-sm-12"> + <div class="form-group"> <form action="{f:be.uri(route: 'pagetsconfig_active', parameters: '{id: pageUid}')}" method="post"> <input type="hidden" name="displayConstantSubstitutions" value="0" /> - <div class="form-check form-switch"> + <div class="form-check form-switch form-check-size-input"> <input type="checkbox" class="form-check-input" @@ -131,10 +135,10 @@ </form> </div> </f:if> - <div class="col col-12 col-sm-12"> + <div class="form-group"> <form action="{f:be.uri(route: 'pagetsconfig_active', parameters: '{id: pageUid}')}" method="post"> <input type="hidden" name="displayComments" value="0" /> - <div class="form-check form-switch"> + <div class="form-check form-switch form-check-size-input"> <input type="checkbox" class="form-check-input" @@ -152,10 +156,10 @@ </div> </form> </div> - <div class="col col-12 col-sm-12"> + <div class="form-group"> <form action="{f:be.uri(route: 'pagetsconfig_active', parameters: '{id: pageUid}')}" method="post"> <input type="hidden" name="sortAlphabetically" value="0" /> - <div class="form-check form-switch"> + <div class="form-check form-switch form-check-size-input"> <input type="checkbox" class="form-check-input" @@ -236,46 +240,42 @@ > <div class="panel-body"> <form action="{f:be.uri(route: 'pagetsconfig_active', parameters: '{id: pageUid}')}" method="post"> - <div class="row"> - <div class="col-12"> - <f:for each="{conditions}" as="condition"> - <input type="hidden" name="pageTsConfigConditions[{condition.hash}]" value="0" /> - <div class="form-check form-switch"> - <input - type="checkbox" - class="form-check-input" - id="condition{condition.hash}" - name="pageTsConfigConditions[{condition.hash}]" - value="1" - data-global-event="change" - data-action-submit="$form" - data-value-selector="input[name='pageTsConfigConditions[{condition.hash}]']" - {f:if(condition: condition.active, then: 'checked="checked"')} - /> - <label class="form-check-label" for="condition{condition.hash}"> - <f:if condition="{displayConstantSubstitutions} && {condition.originalValue}"> - <f:then> - <span class="font-monospace">[{condition.value}]</span> - <span class="diff-item-result diff-item-result-inline font-monospace p-0"> - <f:format.raw> - <f:translate - key="LLL:EXT:backend/Resources/Private/Language/locallang_pagetsconfig.xlf:module.pagetsconfig_active.panel.info.conditionWithConstant" - arguments="{ - 0: '{backend:typoScript.fineDiff(from: condition.originalValue, to: condition.value)}' - }" - /> - </f:format.raw> - </span> - </f:then> - <f:else> - <span class="font-monospace">[{condition.value}]</span> - </f:else> - </f:if> - </label> - </div> - </f:for> + <f:for each="{conditions}" as="condition"> + <input type="hidden" name="pageTsConfigConditions[{condition.hash}]" value="0" /> + <div class="form-check form-switch"> + <input + type="checkbox" + class="form-check-input" + id="condition{condition.hash}" + name="pageTsConfigConditions[{condition.hash}]" + value="1" + data-global-event="change" + data-action-submit="$form" + data-value-selector="input[name='pageTsConfigConditions[{condition.hash}]']" + {f:if(condition: condition.active, then: 'checked="checked"')} + /> + <label class="form-check-label" for="condition{condition.hash}"> + <f:if condition="{displayConstantSubstitutions} && {condition.originalValue}"> + <f:then> + <span class="font-monospace">[{condition.value}]</span> + <span class="diff-item-result diff-item-result-inline font-monospace p-0"> + <f:format.raw> + <f:translate + key="LLL:EXT:backend/Resources/Private/Language/locallang_pagetsconfig.xlf:module.pagetsconfig_active.panel.info.conditionWithConstant" + arguments="{ + 0: '{backend:typoScript.fineDiff(from: condition.originalValue, to: condition.value)}' + }" + /> + </f:format.raw> + </span> + </f:then> + <f:else> + <span class="font-monospace">[{condition.value}]</span> + </f:else> + </f:if> + </label> </div> - </div> + </f:for> </form> </div> </div> diff --git a/typo3/sysext/backend/Resources/Private/Templates/PageTsConfig/Includes.html b/typo3/sysext/backend/Resources/Private/Templates/PageTsConfig/Includes.html index 1d53cf8714cbb1fdd64a0ae66cbd87b31f7721a9..70823655f610e752b3c3a6dc3e2ea4e8dcba5b76 100644 --- a/typo3/sysext/backend/Resources/Private/Templates/PageTsConfig/Includes.html +++ b/typo3/sysext/backend/Resources/Private/Templates/PageTsConfig/Includes.html @@ -7,7 +7,7 @@ <f:layout name="Module"/> -<f:section name="Content"> +<f:section name="Before"> <f:be.pageRenderer includeJavaScriptModules="{ 0: '@typo3/backend/context-menu.js', @@ -17,10 +17,14 @@ 4: '@typo3/backend/pagetsconfig/pagetsconfig-includes.js' }" /> - <f:variable name="args" value="{0: 'web', 1: pageUid}" /> - <typo3-immediate-action action="TYPO3.Backend.Storage.ModuleStateStorage.update" args="{args -> f:format.json() -> f:format.htmlspecialchars()}"></typo3-immediate-action> + <typo3-immediate-action + action="TYPO3.Backend.Storage.ModuleStateStorage.update" + args="{args -> f:format.json() -> f:format.htmlspecialchars()}" + ></typo3-immediate-action> +</f:section> +<f:section name="Content"> <h1> <f:translate key="LLL:EXT:backend/Resources/Private/Language/locallang_pagetsconfig.xlf:module.pagetsconfig_includes.headline" @@ -330,46 +334,42 @@ > <div class="panel-body"> <form action="{f:be.uri(route: 'pagetsconfig_includes', parameters: '{id: pageUid}')}" method="post"> - <div class="row"> - <div class="col-12"> - <f:for each="{conditions}" as="condition"> - <input type="hidden" name="pageTsConfigConditions[{condition.hash}]" value="0" /> - <div class="form-check form-switch"> - <input - type="checkbox" - class="form-check-input" - name="pageTsConfigConditions[{condition.hash}]" - id="pageTsConfigCondition{condition.hash}" - value="1" - data-global-event="change" - data-action-submit="$form" - data-value-selector="input[name='pageTsConfigConditions[{condition.hash}]']" - {f:if(condition: condition.active, then:'checked="checked"')} - /> - <label class="form-check-label" for="pageTsConfigCondition{condition.hash}"> - <f:if condition="{condition.originalValue}"> - <f:then> - <span class="font-monospace">[{condition.value}]</span> - <span class="diff-item-result diff-item-result-inline font-monospace p-0"> - <f:format.raw> - <f:translate - key="LLL:EXT:backend/Resources/Private/Language/locallang_pagetsconfig.xlf:module.pagetsconfig_includes.panel.info.conditionWithConstant" - arguments="{ - 0: '{backend:typoScript.fineDiff(from: condition.originalValue, to: condition.value)}' - }" - /> - </f:format.raw> - </span> - </f:then> - <f:else> - <span class="font-monospace">[{condition.value}]</span> - </f:else> - </f:if> - </label> - </div> - </f:for> + <f:for each="{conditions}" as="condition"> + <input type="hidden" name="pageTsConfigConditions[{condition.hash}]" value="0" /> + <div class="form-check form-switch"> + <input + type="checkbox" + class="form-check-input" + name="pageTsConfigConditions[{condition.hash}]" + id="pageTsConfigCondition{condition.hash}" + value="1" + data-global-event="change" + data-action-submit="$form" + data-value-selector="input[name='pageTsConfigConditions[{condition.hash}]']" + {f:if(condition: condition.active, then:'checked="checked"')} + /> + <label class="form-check-label" for="pageTsConfigCondition{condition.hash}"> + <f:if condition="{condition.originalValue}"> + <f:then> + <span class="font-monospace">[{condition.value}]</span> + <span class="diff-item-result diff-item-result-inline font-monospace p-0"> + <f:format.raw> + <f:translate + key="LLL:EXT:backend/Resources/Private/Language/locallang_pagetsconfig.xlf:module.pagetsconfig_includes.panel.info.conditionWithConstant" + arguments="{ + 0: '{backend:typoScript.fineDiff(from: condition.originalValue, to: condition.value)}' + }" + /> + </f:format.raw> + </span> + </f:then> + <f:else> + <span class="font-monospace">[{condition.value}]</span> + </f:else> + </f:if> + </label> </div> - </div> + </f:for> </form> </div> </div> diff --git a/typo3/sysext/backend/Resources/Private/Templates/PageTsConfig/RecordsOverview.html b/typo3/sysext/backend/Resources/Private/Templates/PageTsConfig/RecordsOverview.html index a239fcf2b8576f05688d287cdc409ea549012427..4e9bff9a2142e7823fd6db07f298dc64db1d3862 100644 --- a/typo3/sysext/backend/Resources/Private/Templates/PageTsConfig/RecordsOverview.html +++ b/typo3/sysext/backend/Resources/Private/Templates/PageTsConfig/RecordsOverview.html @@ -5,17 +5,21 @@ <f:layout name="Module"/> -<f:section name="Content"> - +<f:section name="Before"> <f:be.pageRenderer includeJavaScriptModules="{ 0: '@typo3/backend/context-menu.js', 1: '@typo3/backend/element/immediate-action-element.js' }" /> - <f:variable name="args" value="{0: 'web', 1: id}" /> - <typo3-immediate-action action="TYPO3.Backend.Storage.ModuleStateStorage.update" args="{args -> f:format.json() -> f:format.htmlspecialchars()}"></typo3-immediate-action> + <typo3-immediate-action + action="TYPO3.Backend.Storage.ModuleStateStorage.update" + args="{args -> f:format.json() -> f:format.htmlspecialchars()}" + ></typo3-immediate-action> +</f:section> + +<f:section name="Content"> <h1> <f:translate key="LLL:EXT:backend/Resources/Private/Language/locallang_pagetsconfig.xlf:module.pagetsconfig_pages.headline" /> diff --git a/typo3/sysext/backend/Resources/Private/Templates/RecordDownloadSettings.html b/typo3/sysext/backend/Resources/Private/Templates/RecordDownloadSettings.html index 43a4810d0c1d1b0b95cf0469ebfc21d42f968a3b..89276e7498e4eb0a3195fe509c58f1f7f0d1e9bf 100644 --- a/typo3/sysext/backend/Resources/Private/Templates/RecordDownloadSettings.html +++ b/typo3/sysext/backend/Resources/Private/Templates/RecordDownloadSettings.html @@ -9,18 +9,16 @@ id="downloadSettingsForm" > - <div class="row row-cols-auto"> - <div class="col-12"> - <h5><f:translate key="LLL:EXT:backend/Resources/Private/Language/locallang_download.xlf:downloadSettings.generalSettings"/></h5> - </div> - <div class="col"> - <p> - <strong><f:translate key="LLL:EXT:backend/Resources/Private/Language/locallang_download.xlf:downloadSettings.columnsToDownload"/></strong><br/> - <span class="text-body-secondary"> - <f:translate key="LLL:EXT:backend/Resources/Private/Language/locallang_download.xlf:downloadSettings.default" - arguments="{0: '{f:translate(key: \'LLL:EXT:backend/Resources/Private/Language/locallang_download.xlf:downloadSettings.selectedColumns\')}'}"/> - </span> - </p> + <h1 class="h3"><f:translate key="LLL:EXT:backend/Resources/Private/Language/locallang_download.xlf:downloadSettings.generalSettings"/></h1> + <div class="form-row"> + <div class="form-group"> + <label class="form-label"> + <f:translate key="LLL:EXT:backend/Resources/Private/Language/locallang_download.xlf:downloadSettings.columnsToDownload"/> + </label> + <div class="form-description"> + <f:translate key="LLL:EXT:backend/Resources/Private/Language/locallang_download.xlf:downloadSettings.default" + arguments="{0: '{f:translate(key: \'LLL:EXT:backend/Resources/Private/Language/locallang_download.xlf:downloadSettings.selectedColumns\')}'}"/> + </div> <div class="form-check form-switch"> <input type="checkbox" class="form-check-input" name="allColumns" value="1" data-empty-value="0" id="allColumns"> <label class="form-check-label" for="allColumns"> @@ -28,14 +26,14 @@ </label> </div> </div> - <div class="col"> - <p> - <strong><f:translate key="LLL:EXT:backend/Resources/Private/Language/locallang_download.xlf:downloadSettings.valueFormat"/></strong><br/> - <span class="text-body-secondary"> - <f:translate key="LLL:EXT:backend/Resources/Private/Language/locallang_download.xlf:downloadSettings.default" - arguments="{0: '{f:translate(key: \'LLL:EXT:backend/Resources/Private/Language/locallang_download.xlf:downloadSettings.processedValues\')}'}"/> - </span> - </p> + <div class="form-group"> + <label class="form-label"> + <f:translate key="LLL:EXT:backend/Resources/Private/Language/locallang_download.xlf:downloadSettings.valueFormat"/> + </label> + <div class="form-description"> + <f:translate key="LLL:EXT:backend/Resources/Private/Language/locallang_download.xlf:downloadSettings.default" + arguments="{0: '{f:translate(key: \'LLL:EXT:backend/Resources/Private/Language/locallang_download.xlf:downloadSettings.processedValues\')}'}"/> + </div> <div class="form-check form-switch"> <input type="checkbox" class="form-check-input" name="rawValues" value="1" data-empty-value="0" id="rawValues"/> <label class="form-check-label" for="rawValues"> @@ -43,17 +41,14 @@ </label> </div> </div> - </div> - - <div class="row row-cols-auto mt-2"> - <div class="col"> - <label for="filename"> + <div class="form-group"> + <label class="form-label" for="filename"> <strong><f:translate key="LLL:EXT:backend/Resources/Private/Language/locallang_download.xlf:downloadSettings.filename"/></strong> </label> <input type="text" id="filename" placeholder="{f:translate(key: 'LLL:EXT:backend/Resources/Private/Language/locallang_download.xlf:downloadSettings.filename.placeholder', arguments: '{0: table}')}" class="form-control" name="filename" size="30"> </div> - <div class="col"> - <label for="format"> + <div class="form-group"> + <label class="form-label" for="format"> <strong><f:translate key="LLL:EXT:backend/Resources/Private/Language/locallang_download.xlf:downloadSettings.format"/></strong> </label> <select class="form-select t3js-record-download-format-selector" id="format" name="format"> @@ -66,22 +61,22 @@ <f:if condition="{formatOptions}"> <f:for each="{formatOptions}" key="formatName" as="format" iteration="i"> - <div class="row row-cols-auto mt-4 {f:if(condition: '!{i.isFirst}', then: 'hide')} t3js-record-download-format-option" data-formatName="{formatName}"> - <div class="col-12"> - <h5><f:translate key="LLL:EXT:backend/Resources/Private/Language/locallang_download.xlf:downloadSettings.formatOptions.{formatName}"/></h5> + <div class="{f:if(condition: '!{i.isFirst}', then: 'hide')} t3js-record-download-format-option" data-formatName="{formatName}"> + <h2 class="h3 headline-spaced"><f:translate key="LLL:EXT:backend/Resources/Private/Language/locallang_download.xlf:downloadSettings.formatOptions.{formatName}"/></h2> + <div class="form-row mb-0"> + <f:for each="{format.options}" key="formatOptionName" as="formatOption"> + <div class="form-group"> + <label class="form-label" for="{formatName}-{formatOptionName}"> + <f:translate key="LLL:EXT:backend/Resources/Private/Language/locallang_download.xlf:downloadSettings.formatOptions.{formatName}.{formatOptionName}"/> + </label> + <select class="form-select" id="{formatName}-{formatOptionName}" name="{formatName}[{formatOptionName}]"> + <f:for each="{formatOption}" key="optionName" as="option"> + <option value="{option}" {f:if(condition: '{format.defaults.{formatOptionName}} == {option}', then: 'selected')}>{option} ({f:translate(key: 'LLL:EXT:backend/Resources/Private/Language/locallang_download.xlf:downloadSettings.formatOptions.{formatName}.{formatOptionName}.{optionName}')})</option> + </f:for> + </select> + </div> + </f:for> </div> - <f:for each="{format.options}" key="formatOptionName" as="formatOption"> - <div class="col"> - <label for="{formatName}-{formatOptionName}"> - <strong><f:translate key="LLL:EXT:backend/Resources/Private/Language/locallang_download.xlf:downloadSettings.formatOptions.{formatName}.{formatOptionName}"/></strong> - </label> - <select class="form-select" id="{formatName}-{formatOptionName}" name="{formatName}[{formatOptionName}]"> - <f:for each="{formatOption}" key="optionName" as="option"> - <option value="{option}" {f:if(condition: '{format.defaults.{formatOptionName}} == {option}', then: 'selected')}>{option} ({f:translate(key: 'LLL:EXT:backend/Resources/Private/Language/locallang_download.xlf:downloadSettings.formatOptions.{formatName}.{formatOptionName}.{optionName}')})</option> - </f:for> - </select> - </div> - </f:for> </div> </f:for> </f:if> diff --git a/typo3/sysext/backend/Resources/Private/Templates/RecordList.html b/typo3/sysext/backend/Resources/Private/Templates/RecordList.html index 3c02a8ee51a1d5e468b5372ec42edc8d4c8ff061..09f3cedb277deeec3fa06889bf556221c4a9ae59 100644 --- a/typo3/sysext/backend/Resources/Private/Templates/RecordList.html +++ b/typo3/sysext/backend/Resources/Private/Templates/RecordList.html @@ -5,8 +5,7 @@ <f:layout name="Module" /> -<f:section name="Content"> - +<f:section name="Before"> <f:be.pageRenderer includeJavaScriptModules="{ 0: '@typo3/backend/recordlist.js', @@ -23,10 +22,14 @@ 11: '@typo3/backend/element/editable-page-title.js' }" /> - <f:variable name="immediateActionArgs" value="{0: 'web', 1: pageId}" /> - <typo3-immediate-action action="TYPO3.Backend.Storage.ModuleStateStorage.update" args="{immediateActionArgs -> f:format.json() -> f:format.htmlspecialchars()}"></typo3-immediate-action> + <typo3-immediate-action + action="TYPO3.Backend.Storage.ModuleStateStorage.update" + args="{immediateActionArgs -> f:format.json() -> f:format.htmlspecialchars()}" + ></typo3-immediate-action> +</f:section> +<f:section name="Content"> <typo3-backend-editable-page-title pageTitle="{pageTitle}" pageId="{pageId}" @@ -34,7 +37,6 @@ > {pageTitle} </typo3-backend-editable-page-title> - <f:format.raw>{additionalContentTop}</f:format.raw> <f:format.raw>{languageSelectorHtml}</f:format.raw> <f:format.raw>{searchBoxHtml}</f:format.raw> diff --git a/typo3/sysext/backend/Resources/Private/Templates/SiteConfiguration/Overview.html b/typo3/sysext/backend/Resources/Private/Templates/SiteConfiguration/Overview.html index 973584ff844a7aafe3bff2a1d4d468ea0f3ccee5..78e2c76bd976a375d04d21b583715e0f36372f35 100644 --- a/typo3/sysext/backend/Resources/Private/Templates/SiteConfiguration/Overview.html +++ b/typo3/sysext/backend/Resources/Private/Templates/SiteConfiguration/Overview.html @@ -172,7 +172,7 @@ <f:if condition="{unassignedSites}"> <h2>{f:translate(key: 'LLL:EXT:backend/Resources/Private/Language/locallang_siteconfiguration.xlf:overview.unassignedSites.title')}</h2> - <p class="mb-3">{f:translate(key: 'LLL:EXT:backend/Resources/Private/Language/locallang_siteconfiguration.xlf:overview.unassignedSites.description')}</p> + <p>{f:translate(key: 'LLL:EXT:backend/Resources/Private/Language/locallang_siteconfiguration.xlf:overview.unassignedSites.description')}</p> <div class="table-fit"> <table class="table table-striped table-hover"> diff --git a/typo3/sysext/backend/Resources/Public/Css/backend.css b/typo3/sysext/backend/Resources/Public/Css/backend.css index 2a34482058320cdbccc351faff1b4a567dfa10bb..b0a74adb30fb9b995867b05c1b97d9badac804e8 100644 --- a/typo3/sysext/backend/Resources/Public/Css/backend.css +++ b/typo3/sysext/backend/Resources/Public/Css/backend.css @@ -20,17 +20,17 @@ } body{margin:0;font-family:var(--bs-body-font-family);font-size:var(--bs-body-font-size);font-weight:var(--bs-body-font-weight);line-height:var(--bs-body-line-height);color:var(--bs-body-color);text-align:var(--bs-body-text-align);background-color:var(--bs-body-bg);-webkit-text-size-adjust:100%;-webkit-tap-highlight-color:transparent} hr{margin:1rem 0;color:inherit;border:0;border-top:var(--bs-border-width) solid;opacity:1} -.h1,.h2,.h3,.h4,.h5,.h6,h1,h2,h3,h4,h5,h6,typo3-backend-editable-page-title{margin-top:0;margin-bottom:.5rem;font-weight:500;line-height:1.1;color:var(--bs-heading-color,inherit)} -.h1,h1,typo3-backend-editable-page-title{font-size:calc(1.29375rem + .525vw)} +.h1,.h2,.h3,.h4,.h5,.h6,h1,h2,h3,h4,h5,h6,typo3-backend-editable-page-title{margin-top:0;margin-bottom:calc(var(--typo3-spacing)/ 2);font-weight:500;line-height:1.2;color:var(--bs-heading-color,inherit)} +.h1,h1,typo3-backend-editable-page-title{font-size:calc(1.3rem + .6vw)} @media (min-width:1200px){ -.h1,h1,typo3-backend-editable-page-title{font-size:1.6875rem} +.h1,h1,typo3-backend-editable-page-title{font-size:1.75rem} } -.h2,h2{font-size:1.2rem} -.h3,h3{font-size:1.05rem} -.h4,h4{font-size:.9375rem} +.h2,h2{font-size:1.25rem} +.h3,h3{font-size:1rem} +.h4,h4{font-size:.875rem} .h5,h5{font-size:.9375rem} .h6,h6{font-size:.75rem} -p{margin-top:0;margin-bottom:.5rem} +p{margin-top:0;margin-bottom:var(--typo3-spacing)} abbr[title]{-webkit-text-decoration:underline dotted;text-decoration:underline dotted;cursor:help;-webkit-text-decoration-skip-ink:none;text-decoration-skip-ink:none} address{margin-bottom:1rem;font-style:normal;line-height:inherit} ol,ul{padding-left:2rem} @@ -92,27 +92,27 @@ summary{display:list-item;cursor:pointer} progress{vertical-align:baseline} [hidden]{display:none!important} .lead{font-size:.9375rem;font-weight:300} -.display-1{font-size:calc(1.625rem + 4.5vw);font-weight:300;line-height:1.1} +.display-1{font-size:calc(1.625rem + 4.5vw);font-weight:300;line-height:1.2} @media (min-width:1200px){ .display-1{font-size:5rem} } -.display-2{font-size:calc(1.575rem + 3.9vw);font-weight:300;line-height:1.1} +.display-2{font-size:calc(1.575rem + 3.9vw);font-weight:300;line-height:1.2} @media (min-width:1200px){ .display-2{font-size:4.5rem} } -.display-3{font-size:calc(1.525rem + 3.3vw);font-weight:300;line-height:1.1} +.display-3{font-size:calc(1.525rem + 3.3vw);font-weight:300;line-height:1.2} @media (min-width:1200px){ .display-3{font-size:4rem} } -.display-4{font-size:calc(1.475rem + 2.7vw);font-weight:300;line-height:1.1} +.display-4{font-size:calc(1.475rem + 2.7vw);font-weight:300;line-height:1.2} @media (min-width:1200px){ .display-4{font-size:3.5rem} } -.display-5{font-size:calc(1.425rem + 2.1vw);font-weight:300;line-height:1.1} +.display-5{font-size:calc(1.425rem + 2.1vw);font-weight:300;line-height:1.2} @media (min-width:1200px){ .display-5{font-size:3rem} } -.display-6{font-size:calc(1.375rem + 1.5vw);font-weight:300;line-height:1.1} +.display-6{font-size:calc(1.375rem + 1.5vw);font-weight:300;line-height:1.2} @media (min-width:1200px){ .display-6{font-size:2.5rem} } @@ -1574,10 +1574,10 @@ to{transform:rotate(360deg)} .column-gap-4{-moz-column-gap:1.5rem!important;column-gap:1.5rem!important} .column-gap-5{-moz-column-gap:3rem!important;column-gap:3rem!important} .font-monospace{font-family:var(--bs-font-monospace)!important} -.fs-1{font-size:calc(1.29375rem + .525vw)!important} -.fs-2{font-size:1.2rem!important} -.fs-3{font-size:1.05rem!important} -.fs-4{font-size:.9375rem!important} +.fs-1{font-size:calc(1.3rem + .6vw)!important} +.fs-2{font-size:1.25rem!important} +.fs-3{font-size:1rem!important} +.fs-4{font-size:.875rem!important} .fs-5{font-size:.9375rem!important} .fs-6{font-size:.75rem!important} .fst-italic{font-style:italic!important} @@ -2644,7 +2644,7 @@ to{transform:rotate(360deg)} .text-xxl-center{text-align:center!important} } @media (min-width:1200px){ -.fs-1{font-size:1.6875rem!important} +.fs-1{font-size:1.75rem!important} } @media print{ .d-print-inline{display:inline!important} @@ -2819,11 +2819,15 @@ button[aria-expanded=true]:not(:disabled) .modulemenu-indicator:after{transform: .scaffold-modulemenu-expanded .modulemenu-action{margin-left:0;width:100%} .scaffold-modulemenu-expanded .modulemenu-indicator{display:block!important} .scaffold-modulemenu-expanded .modulemenu-name{position:static;margin:0 0 0 1em;width:auto;height:auto} -:root{--typo3-font-family-sans-serif:Verdana,Arial,Helvetica,sans-serif;--typo3-font-family-monospace:SFMono-Regular,Menlo,Monaco,Consolas,Liberation Mono,Courier New,monospace;--typo3-font-family:var(--typo3-font-family-sans-serif);--typo3-font-family-code:var(--typo3-font-family-monospace);--typo3-spacing:1rem;--typo3-header-font-family:"Source Sans 3",sans-serif;--typo3-light-color:#000;--typo3-light-secondary-color:#666666;--typo3-light-bg:#fff;--typo3-light-border-color:rgb(215, 215, 215);--typo3-light-link-color:#0078e6;--typo3-light-link-hover-color:#1a86e9;--typo3-light-hover-color:var(--typo3-light-color);--typo3-light-hover-bg:#f2f8fe;--typo3-light-hover-border-color:#d9ebfb;--typo3-light-focus-color:var(--typo3-light-color);--typo3-light-focus-bg:#f2f8fe;--typo3-light-focus-border-color:#3393eb;--typo3-light-active-color:#fff;--typo3-light-active-bg:#3393eb;--typo3-light-active-border-color:#3393eb;--typo3-light-disabled-color:rgb(115, 115, 115);--typo3-light-disabled-bg:transparent;--typo3-light-disabled-border-color:transparent;--typo3-dark-color:#fff;--typo3-dark-secondary-color:#999999;--typo3-dark-bg:rgb(30, 30, 30);--typo3-dark-border-color:rgb(51, 51, 51);--typo3-dark-link-color:#66aef0;--typo3-dark-link-hover-color:#80bcf3;--typo3-dark-hover-color:var(--typo3-dark-color);--typo3-dark-hover-bg:rgb(51, 51, 51);--typo3-dark-hover-border-color:rgb(90, 90, 90);--typo3-dark-focus-color:var(--typo3-dark-color);--typo3-dark-focus-bg:#003c73;--typo3-dark-focus-border-color:#00488a;--typo3-dark-active-color:#fff;--typo3-dark-active-bg:#0066c4;--typo3-dark-active-border-color:#0060b8;--typo3-dark-disabled-color:rgb(115, 115, 115);--typo3-dark-disabled-bg:transparent;--typo3-dark-disabled-border-color:transparent;--typo3-component-color:var(--typo3-light-color);--typo3-component-secondary-color:var(--typo3-light-secondary-color);--typo3-component-bg:var(--typo3-light-bg);--typo3-component-link-color:var(--typo3-light-link-color);--typo3-component-link-hover-color:var(--typo3-light-link-hover-color);--typo3-component-font-size:12px;--typo3-component-line-height:1.5;--typo3-component-border-radius:4px;--typo3-component-border-width:1px;--typo3-component-border-color:var(--typo3-light-border-color);--typo3-component-padding-y:.75rem;--typo3-component-padding-x:1rem;--typo3-component-box-shadow:0 1px 2px rgba(0, 0, 0, .25);--typo3-component-hover-color:var(--typo3-light-hover-color);--typo3-component-hover-bg:var(--typo3-light-hover-bg);--typo3-component-hover-border-color:var(--typo3-light-hover-border-color);--typo3-component-focus-color:var(--typo3-light-focus-color);--typo3-component-focus-bg:var(--typo3-light-focus-bg);--typo3-component-focus-border-color:var(--typo3-light-focus-border-color);--typo3-component-active-color:var(--typo3-light-active-color);--typo3-component-active-bg:var(--typo3-light-active-bg);--typo3-component-active-border-color:var(--typo3-light-active-border-color);--typo3-component-disabled-color:var(--typo3-light-disabled-color);--typo3-component-disabled-bg:var(--typo3-light-disabled-bg);--typo3-component-disabled-border-color:var(--typo3-light-disabled-border-color);--typo3-component-spacing:1.5rem;--typo3-list-item-padding-y:.5rem;--typo3-list-item-padding-x:.75rem;--typo3-list-item-hover-color:var(--typo3-component-hover-color);--typo3-list-item-hover-bg:var(--typo3-component-hover-bg);--typo3-list-item-hover-border-color:var(--typo3-component-hover-border-color);--typo3-list-item-focus-color:var(--typo3-component-focus-color);--typo3-list-item-focus-bg:var(--typo3-component-focus-bg);--typo3-list-item-focus-border-color:var(--typo3-component-focus-border-color);--typo3-list-item-active-color:var(--typo3-list-item-focus-color);--typo3-list-item-active-bg:var(--typo3-list-item-focus-bg);--typo3-list-item-active-border-color:var(--typo3-list-item-focus-border-color);--typo3-list-item-disabled-color:var(--typo3-component-disabled-color);--typo3-list-item-disabled-bg:var(--typo3-component-disabled-bg);--typo3-list-item-disabled-border-color:var(--typo3-component-disabled-border-color);--typo3-input-color:#333;--typo3-input-bg:#fefefe;--typo3-input-border-width:var(--bs-border-width);--typo3-input-border-color:rgb(187, 187, 187);--typo3-input-border-radius:0.125rem;--typo3-input-box-shadow:inset 0 1px 2px rgba(0, 0, 0, 0.075);--typo3-input-focus-color:#333;--typo3-input-focus-bg:#fefefe;--typo3-input-focus-border-color:#80bcf3;--typo3-input-focus-box-shadow:0 0 0 0.25rem rgba(0, 120, 230, 0.25);--typo3-input-disabled-bg:var(--bs-secondary-bg)} +:root{--typo3-font-family-sans-serif:Verdana,Arial,Helvetica,sans-serif;--typo3-font-family-monospace:SFMono-Regular,Menlo,Monaco,Consolas,Liberation Mono,Courier New,monospace;--typo3-font-family:var(--typo3-font-family-sans-serif);--typo3-font-family-code:var(--typo3-font-family-monospace);--typo3-spacing:1rem;--typo3-header-font-family:"Source Sans 3",sans-serif;--typo3-light-color:#000;--typo3-light-secondary-color:#666666;--typo3-light-bg:#fff;--typo3-light-border-color:rgb(215, 215, 215);--typo3-light-link-color:#0078e6;--typo3-light-link-hover-color:#1a86e9;--typo3-light-hover-color:var(--typo3-light-color);--typo3-light-hover-bg:#f2f8fe;--typo3-light-hover-border-color:#d9ebfb;--typo3-light-focus-color:var(--typo3-light-color);--typo3-light-focus-bg:#f2f8fe;--typo3-light-focus-border-color:#3393eb;--typo3-light-active-color:#fff;--typo3-light-active-bg:#3393eb;--typo3-light-active-border-color:#3393eb;--typo3-light-disabled-color:rgb(115, 115, 115);--typo3-light-disabled-bg:transparent;--typo3-light-disabled-border-color:transparent;--typo3-dark-color:#fff;--typo3-dark-secondary-color:#999999;--typo3-dark-bg:rgb(30, 30, 30);--typo3-dark-border-color:rgb(51, 51, 51);--typo3-dark-link-color:#66aef0;--typo3-dark-link-hover-color:#80bcf3;--typo3-dark-hover-color:var(--typo3-dark-color);--typo3-dark-hover-bg:rgb(51, 51, 51);--typo3-dark-hover-border-color:rgb(90, 90, 90);--typo3-dark-focus-color:var(--typo3-dark-color);--typo3-dark-focus-bg:#003c73;--typo3-dark-focus-border-color:#00488a;--typo3-dark-active-color:#fff;--typo3-dark-active-bg:#0066c4;--typo3-dark-active-border-color:#0060b8;--typo3-dark-disabled-color:rgb(115, 115, 115);--typo3-dark-disabled-bg:transparent;--typo3-dark-disabled-border-color:transparent;--typo3-component-color:var(--typo3-light-color);--typo3-component-secondary-color:var(--typo3-light-secondary-color);--typo3-component-bg:var(--typo3-light-bg);--typo3-component-link-color:var(--typo3-light-link-color);--typo3-component-link-hover-color:var(--typo3-light-link-hover-color);--typo3-component-font-size:12px;--typo3-component-line-height:1.5;--typo3-component-border-radius:4px;--typo3-component-border-width:1px;--typo3-component-border-color:var(--typo3-light-border-color);--typo3-component-padding-y:.75rem;--typo3-component-padding-x:1rem;--typo3-component-box-shadow:0 1px 2px rgba(0, 0, 0, .25);--typo3-component-hover-color:var(--typo3-light-hover-color);--typo3-component-hover-bg:var(--typo3-light-hover-bg);--typo3-component-hover-border-color:var(--typo3-light-hover-border-color);--typo3-component-focus-color:var(--typo3-light-focus-color);--typo3-component-focus-bg:var(--typo3-light-focus-bg);--typo3-component-focus-border-color:var(--typo3-light-focus-border-color);--typo3-component-active-color:var(--typo3-light-active-color);--typo3-component-active-bg:var(--typo3-light-active-bg);--typo3-component-active-border-color:var(--typo3-light-active-border-color);--typo3-component-disabled-color:var(--typo3-light-disabled-color);--typo3-component-disabled-bg:var(--typo3-light-disabled-bg);--typo3-component-disabled-border-color:var(--typo3-light-disabled-border-color);--typo3-component-spacing:2rem;--typo3-list-item-padding-y:.5rem;--typo3-list-item-padding-x:.75rem;--typo3-list-item-hover-color:var(--typo3-component-hover-color);--typo3-list-item-hover-bg:var(--typo3-component-hover-bg);--typo3-list-item-hover-border-color:var(--typo3-component-hover-border-color);--typo3-list-item-focus-color:var(--typo3-component-focus-color);--typo3-list-item-focus-bg:var(--typo3-component-focus-bg);--typo3-list-item-focus-border-color:var(--typo3-component-focus-border-color);--typo3-list-item-active-color:var(--typo3-list-item-focus-color);--typo3-list-item-active-bg:var(--typo3-list-item-focus-bg);--typo3-list-item-active-border-color:var(--typo3-list-item-focus-border-color);--typo3-list-item-disabled-color:var(--typo3-component-disabled-color);--typo3-list-item-disabled-bg:var(--typo3-component-disabled-bg);--typo3-list-item-disabled-border-color:var(--typo3-component-disabled-border-color);--typo3-input-color:#333;--typo3-input-bg:#fefefe;--typo3-input-border-width:var(--bs-border-width);--typo3-input-border-color:rgb(187, 187, 187);--typo3-input-border-radius:0.125rem;--typo3-input-box-shadow:inset 0 1px 2px rgba(0, 0, 0, 0.075);--typo3-input-focus-color:#333;--typo3-input-focus-bg:#fefefe;--typo3-input-focus-border-color:#80bcf3;--typo3-input-focus-box-shadow:0 0 0 0.25rem rgba(0, 120, 230, 0.25);--typo3-input-disabled-bg:var(--bs-secondary-bg)} @media (prefers-color-scheme:dark){ :root{--typo3-component-color:var(--typo3-dark-color);--typo3-component-secondary-color:var(--typo3-dark-secondary-color);--typo3-component-bg:var(--typo3-dark-bg);--typo3-component-border-color:var(--typo3-dark-border-color);--typo3-component-link-color:var(--typo3-dark-link-color);--typo3-component-link-hover-color:var(--typo3-dark-link-hover-color);--typo3-component-hover-color:var(--typo3-dark-hover-color);--typo3-component-hover-bg:var(--typo3-dark-hover-bg);--typo3-component-hover-border-color:var(--typo3-dark-hover-border-color);--typo3-component-focus-color:var(--typo3-dark-focus-color);--typo3-component-focus-bg:var(--typo3-dark-focus-bg);--typo3-component-focus-border-color:var(--typo3-dark-focus-border-color);--typo3-component-active-color:var(--typo3-dark-active-color);--typo3-component-active-bg:var(--typo3-dark-active-bg);--typo3-component-active-border-color:var(--typo3-dark-active-border-color);--typo3-component-disabled-color:var(--typo3-dark-disabled-color);--typo3-component-disabled-bg:var(--typo3-dark-disabled-bg);--typo3-component-disabled-border-color:var(--typo3-dark-disabled-border-color)} } .dropdown-menu{--bs-secondary-color:var(--typo3-component-secondary-color)} +.h1,h1,typo3-backend-editable-page-title{font-family:var(--typo3-header-font-family);font-variant:normal;font-weight:400} +.h1:not(:first-child):not([class]),.h2:not(:first-child):not([class]),.h3:not(:first-child):not([class]),.headline-spaced.h1,.headline-spaced.h2,.headline-spaced.h3,h1.headline-spaced,h1:not(:first-child):not([class]),h2.headline-spaced,h2:not(:first-child):not([class]),h3.headline-spaced,h3:not(:first-child):not([class]),typo3-backend-editable-page-title.headline-spaced,typo3-backend-editable-page-title:not(:first-child):not([class]){margin-top:calc(var(--typo3-spacing) * 2)} +.h1,.h2,.h3,.h4,.h5,.h6{font-family:inherit} +hr.spacer{border-top:none;margin-top:var(--typo3-spacing);margin-bottom:var(--typo3-spacing)} .alert a{color:inherit;text-decoration:underline} .alert-title{font-size:1.12em;font-weight:700;margin:0 0 .25em} .alert-body,.alert-message{margin:0;font-size:.9em} @@ -2893,7 +2897,10 @@ typo3-backend-formengine-suggest-result-item .formengine-suggest-result-item-lab .btn-borderless{--bs-btn-bg:transparent;--bs-btn-border-color:transparent;--bs-btn-box-shadow:none;--bs-btn-padding-x:var(--bs-btn-padding-y)} .btn-permission{--bs-btn-bg:transparent;--bs-btn-border-color:transparent;--bs-btn-box-shadow:none;--bs-btn-padding-x:0;--bs-btn-padding-y:0} .table .btn:not(.btn-sm){--bs-btn-padding-x:var(--bs-btn-padding-y)} -pre[class*=language-]{margin-bottom:var(--typo3-component-spacing)} +code,pre{-webkit-hyphens:none;hyphens:none} +code[class*=language-],pre[class*=language-]{color:inherit;background:0 0;font-size:1em;text-align:start;white-space:pre;word-spacing:normal;word-break:normal;word-wrap:normal;line-height:1.5;-moz-tab-size:4;-o-tab-size:4;tab-size:4;-webkit-hyphens:none;hyphens:none} +pre[class*=language-]{border-radius:4px;padding:1em;overflow:auto;margin-bottom:var(--typo3-spacing)} +:not(pre)>code[class*=language-],pre[class*=language-]{background-color:rgba(0,0,0,.05)} .dropdown-menu{font-size:var(--typo3-component-font-size);line-height:var(--typo3-component-line-height);max-width:calc(100vw - 20px)} .dropdown-menu a:not([class]){color:var(--typo3-component-link-color)} .dropdown-menu a:not([class]):hover{color:var(--typo3-component-link-hover-color)} @@ -3005,7 +3012,7 @@ a.dropdown-toggle{text-decoration:none} .statusreport a:not([class]):hover{color:#0060b8;text-decoration:underline} .statusreport .statusreport-indicator-icon{position:relative;display:inline-flex;justify-content:center;align-items:center;color:var(--statusreport-icon-color);font-size:var(--statusreport-icon-size);height:var(--statusreport-icon-size);width:var(--statusreport-icon-size)} .statusreport .statusreport-indicator-icon:before{position:absolute;content:" ";top:50%;left:50%;height:calc(var(--statusreport-icon-size) * 1.5);width:calc(var(--statusreport-icon-size) * 1.5);background-color:var(--statusreport-icon-bg);transform:translate(-50%,-50%);border-radius:50%} -.statusreport-wrapper{border-radius:var(--statusreport-border-radius);box-shadow:var(--statusreport-box-shadow);margin-bottom:var(--typo3-component-spacing)} +.statusreport-wrapper{border-radius:var(--statusreport-border-radius);box-shadow:var(--statusreport-box-shadow);margin-bottom:var(--typo3-spacing)} .statusreport-wrapper .statusreport:first-child{border-top-left-radius:var(--statusreport-border-radius);border-top-right-radius:var(--statusreport-border-radius)} .statusreport-wrapper .statusreport:last-child{border-bottom-left-radius:var(--statusreport-border-radius);border-bottom-right-radius:var(--statusreport-border-radius)} .statusreport-wrapper .statusreport+.statusreport{margin-top:-1px} @@ -3053,16 +3060,15 @@ a.dropdown-toggle{text-decoration:none} .module-docheader .module-docheader-bar .form-group{margin:0} .module-docheader .module-docheader-bar-container{display:flex;gap:var(--module-docheader-spacing);flex-wrap:wrap} .module-body{padding:var(--module-body-padding)} -.module-body>.callout:first-child{margin-top:0} .module-body>.container{padding-left:0;padding-right:0} .module-body .container-small{max-width:768px;margin:0 auto} .module-body>:last-child{margin-bottom:0} :root{--panel-bg:#fff;--panel-border-color:#ccc;--panel-border-radius:var(--typo3-component-border-radius);--panel-border-width:var(--typo3-component-border-width);--panel-padding:var(--typo3-component-padding-x);--panel-header-padding-x:var(--typo3-component-padding-x);--panel-header-padding-y:var(--typo3-component-padding-y);--panel-spacing:var(--typo3-component-spacing);--panel-box-shadow:var(--typo3-component-box-shadow);--panel-primary-border-color:#99c9f5;--panel-primary-progress-bg:#0078e6;--panel-primary-heading-color:#000;--panel-primary-heading-bg:#d9ebfb;--panel-secondary-border-color:#c7c7c7;--panel-secondary-progress-bg:rgb(115, 115, 115);--panel-secondary-heading-color:#000;--panel-secondary-heading-bg:#eaeaea;--panel-success-border-color:#9fcb9f;--panel-success-progress-bg:#107c10;--panel-success-heading-color:#000;--panel-success-heading-bg:#dbebdb;--panel-info-border-color:#c5ddf3;--panel-info-progress-bg:#6daae0;--panel-info-heading-color:#000;--panel-info-heading-bg:#e9f2fa;--panel-warning-border-color:#f6dab1;--panel-warning-progress-bg:#e8a33d;--panel-warning-heading-color:#000;--panel-warning-heading-bg:#fcf1e2;--panel-danger-border-color:#e9b1b1;--panel-danger-progress-bg:#c83c3c;--panel-danger-heading-color:#000;--panel-danger-heading-bg:#f7e2e2;--panel-light-border-color:#c4c4c4;--panel-light-progress-bg:gainsboro;--panel-light-heading-color:#000;--panel-light-heading-bg:whitesmoke;--panel-default-border-color:#c4c4c4;--panel-default-progress-bg:gainsboro;--panel-default-heading-color:#000;--panel-default-heading-bg:whitesmoke;--panel-notice-border-color:#adadad;--panel-notice-progress-bg:rgb(51, 51, 51);--panel-notice-heading-color:#000;--panel-notice-heading-bg:#e0e0e0;--panel-dark-border-color:#a5a5a5;--panel-dark-progress-bg:rgb(30, 30, 30);--panel-dark-heading-color:#000;--panel-dark-heading-bg:#dddddd} -.panel-group{display:flex;flex-flow:column;overflow:hidden;margin-bottom:var(--panel-spacing);border-radius:var(--panel-border-radius);box-shadow:var(--panel-box-shadow)} +.panel-group{display:flex;flex-flow:column;overflow:hidden;margin-bottom:var(--typo3-spacing);border-radius:var(--panel-border-radius);box-shadow:var(--panel-box-shadow)} .panel-group>.panel{border-radius:0;margin-bottom:0;box-shadow:none;margin-top:calc(var(--panel-border-width) * -1)} .panel-group>.panel:first-child{margin-top:0;border-top-left-radius:var(--panel-border-radius);border-top-right-radius:var(--panel-border-radius)} .panel-group>.panel:last-child{border-bottom-left-radius:var(--panel-border-radius);border-bottom-right-radius:var(--panel-border-radius)} -.panel{display:flex;flex-direction:column;overflow:hidden;min-width:0;word-wrap:break-word;background-clip:border-box;background-color:var(--panel-bg);border:var(--panel-border-width) solid var(--panel-border-color);border-radius:var(--panel-border-radius);box-shadow:var(--panel-box-shadow);margin-bottom:var(--panel-spacing);transition:all .2s ease-in-out;transition-property:box-shadow,border,transform} +.panel{display:flex;flex-direction:column;overflow:hidden;min-width:0;word-wrap:break-word;background-clip:border-box;background-color:var(--panel-bg);border:var(--panel-border-width) solid var(--panel-border-color);border-radius:var(--panel-border-radius);box-shadow:var(--panel-box-shadow);margin-bottom:var(--typo3-spacing);transition:all .2s ease-in-out;transition-property:box-shadow,border,transform} .panel .table-fit{box-shadow:none;border-radius:0;border-left:0;border-right:0;border-bottom:0;margin-bottom:0} .panel-loader{padding:var(--panel-padding)} .panel-progress{display:none;position:absolute;top:0;left:0;height:3px;width:100%;z-index:1;background-color:transparent} @@ -3126,10 +3132,11 @@ a.dropdown-toggle{text-decoration:none} .form-check.form-check-type-icon-toggle .form-check-input:checked~.form-check-label .form-check-label-icon-checked{display:block} .form-check.form-check-type-icon-toggle .form-check-input:checked~.form-check-label .form-check-label-icon-unchecked{display:none} .form-check.form-check-type-icon-toggle .form-check-label{margin-top:.35em} -.form-check.form-check-type-toggle{display:inline-block;color:rgba(0,0,0,.25);padding-left:0;margin:0} +.form-check.form-check-type-toggle{display:inline-block;padding-left:0;margin:0} .form-check.form-check-type-toggle .form-check-input[type=checkbox]{margin:0;margin-top:1px;float:none;border:0;width:1.3333333333em;height:1.3333333333em;background-size:contain;background-image:url("data:image/svg+xml, %3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3e%3cg class='icon-color'%3e%3cpath d='M13 2c.6 0 1 .4 1 1v10c0 .6-.4 1-1 1H3c-.6 0-1-.4-1-1V3c0-.6.4-1 1-1h10m0-1H3c-1.1 0-2 .9-2 2v10c0 1.1.9 2 2 2h10c1.1 0 2-.9 2-2V3c0-1.1-.9-2-2-2z'/%3e%3c/g%3e%3c/svg%3e")} .form-check.form-check-type-toggle .form-check-input[type=checkbox]:active{filter:brightness(100%)} .form-check.form-check-type-toggle .form-check-input[type=checkbox]:checked{background-image:url("data:image/svg+xml, %3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3e%3cg class='icon-color'%3e%3cpath d='M12.1 5.3l-.4-.3c-.1-.1-.3-.1-.4 0L6.6 9.8l-2-2c-.1-.1-.3-.1-.4 0l-.3.4c-.1.1-.1.3 0 .4L6 10.7l.4.3c.1.1.3.1.4 0l.4-.4 4.9-4.9c.1-.1.1-.3 0-.4z'/%3e%3cpath d='M13 2c.6 0 1 .4 1 1v10c0 .6-.4 1-1 1H3c-.6 0-1-.4-1-1V3c0-.6.4-1 1-1h10m0-1H3c-1.1 0-2 .9-2 2v10c0 1.1.9 2 2 2h10c1.1 0 2-.9 2-2V3c0-1.1-.9-2-2-2z'/%3e%3c/g%3e%3c/svg%3e");background-color:#fff} +.form-check.form-check-size-input{margin-top:7px;margin-bottom:7px} .simpletable{padding:0;margin-bottom:1.5em} .simpletable td,.simpletable th{padding:.25em 1em} .simpletable td:first-child,.simpletable th:first-child{padding-left:0} @@ -3534,7 +3541,7 @@ to{opacity:1;transform:translate3d(0,0,0)} .table-transparent{--bs-table-bg:transparent} .table-vertical-top td,.table-vertical-top th{vertical-align:top!important} .table-center td,.table-center th{text-align:center!important} -.table-fit{width:100%;border-radius:var(--typo3-component-border-radius);box-shadow:var(--typo3-component-box-shadow);margin-bottom:var(--typo3-component-spacing);overflow-x:auto;overflow-y:hidden;-webkit-overflow-scrolling:touch;-ms-overflow-style:-ms-autohiding-scrollbar;border:1px solid #ccc} +.table-fit{width:100%;border-radius:var(--typo3-component-border-radius);box-shadow:var(--typo3-component-box-shadow);margin-bottom:var(--typo3-spacing);overflow-x:auto;overflow-y:hidden;-webkit-overflow-scrolling:touch;-ms-overflow-style:-ms-autohiding-scrollbar;border:1px solid #ccc} .table-fit .table-bordered>:not(caption)>*{border-width:0} .table-fit .table-bordered>:not(caption)>*>*{border-top:0;border-width:var(--bs-border-width)} .table-fit caption{border-top:var(--bs-border-width) solid #ccc;padding-left:var(--typo3-component-padding-x);padding-right:var(--typo3-component-padding-x)} @@ -3614,9 +3621,9 @@ to{opacity:1;transform:translate3d(0,0,0)} .modal-multi-step-wizard .modal-footer .btn+.btn{margin-left:.5em} .modal-multi-step-wizard .modal-footer .progress-bar.inactive{background:0 0;color:#000} :root{--note-primary-color:#000;--note-primary-bg:#d9ebfb;--note-primary-header-color:#000;--note-primary-header-bg:#99c9f5;--note-secondary-color:#000;--note-secondary-bg:#eaeaea;--note-secondary-header-color:#000;--note-secondary-header-bg:#c7c7c7;--note-success-color:#000;--note-success-bg:#dbebdb;--note-success-header-color:#000;--note-success-header-bg:#9fcb9f;--note-info-color:#000;--note-info-bg:#e9f2fa;--note-info-header-color:#000;--note-info-header-bg:#c5ddf3;--note-warning-color:#000;--note-warning-bg:#fcf1e2;--note-warning-header-color:#000;--note-warning-header-bg:#f6dab1;--note-danger-color:#000;--note-danger-bg:#f7e2e2;--note-danger-header-color:#000;--note-danger-header-bg:#e9b1b1;--note-light-color:#000;--note-light-bg:#fefefe;--note-light-header-color:#000;--note-light-header-bg:#fbfbfb;--note-default-color:#000;--note-default-bg:#fefefe;--note-default-header-color:#000;--note-default-header-bg:#fbfbfb;--note-notice-color:#000;--note-notice-bg:#e0e0e0;--note-notice-header-color:#000;--note-notice-header-bg:#adadad;--note-dark-color:#000;--note-dark-bg:#dddddd;--note-dark-header-color:#000;--note-dark-header-bg:#a5a5a5;--note-light-bg:rgb(245, 245, 245);--note-light-header-bg:#dddddd;--note-default-bg:rgb(238, 238, 238);--note-default-header-bg:#d6d6d6} -.note-list{display:grid;gap:calc(var(--typo3-component-spacing)/ 2);margin-bottom:var(--typo3-component-spacing)} +.note-list{display:grid;gap:var(--typo3-spacing);margin-bottom:var(--typo3-spacing)} .note-list .note{margin-bottom:0} -.note{overflow:hidden;position:relative;z-index:1;color:var(--note-color);background-color:var(--note-bg);border-radius:var(--typo3-component-border-radius);margin-bottom:var(--typo3-component-spacing);box-shadow:var(--typo3-component-box-shadow);--note-color:var(--note-default-color);--note-bg:var(--note-default-bg);--note-header-color:var(--note-default-header-color);--note-header-bg:var(--note-default-header-bg)} +.note{overflow:hidden;position:relative;z-index:1;color:var(--note-color);background-color:var(--note-bg);border-radius:var(--typo3-component-border-radius);margin-bottom:var(--typo3-spacing);box-shadow:var(--typo3-component-box-shadow);--note-color:var(--note-default-color);--note-bg:var(--note-default-bg);--note-header-color:var(--note-default-header-color);--note-header-bg:var(--note-default-header-bg)} .note-header{color:var(--note-header-color);background-color:var(--note-header-bg);padding:.5rem 1rem} .note-header-bar{display:flex;align-items:center;flex-wrap:wrap;gap:.5rem} .note-actions{margin-left:auto} @@ -3663,8 +3670,8 @@ a.card:hover{--typo3-card-border-color:var(--typo3-card-hover-border-color);text } .card-body,.card-footer,.card-header,.card-image{padding:var(--typo3-card-padding) var(--typo3-card-padding) 0 var(--typo3-card-padding)} .card-body:last-child,.card-footer:last-child,.card-header:last-child,.card-image:last-child{padding-bottom:var(--typo3-card-padding)} -.card-body :first-child,.card-footer :first-child,.card-header :first-child,.card-image :first-child{margin-top:0} -.card-body :last-child,.card-footer :last-child,.card-header :last-child,.card-image :last-child{margin-bottom:0} +.card-body>:first-child:not(.row),.card-footer>:first-child:not(.row),.card-header>:first-child:not(.row),.card-image>:first-child:not(.row){margin-top:0} +.card-body>:last-child,.card-footer>:last-child,.card-header>:last-child,.card-image>:last-child{margin-bottom:0} .card-image{position:relative;padding-left:0;padding-right:0} .card-image:first-child{padding-top:0} .card-image:first-child .card-image-badge{top:calc(var(--typo3-card-padding) * .5)} @@ -3689,9 +3696,38 @@ a.card:hover{--typo3-card-border-color:var(--typo3-card-hover-border-color);text .card-dark{--typo3-card-color:#000;--typo3-card-bg:#f4f4f4;--typo3-card-border-color:#a5a5a5;--typo3-card-hover-border-color:#787878} .card-light{--typo3-card-color:#000;--typo3-card-bg:rgb(245, 245, 245);--typo3-card-border-color:#dddddd;--typo3-card-hover-border-color:#c4c4c4} .card-default{--typo3-card-color:#000;--typo3-card-bg:rgb(238, 238, 238);--typo3-card-border-color:#d6d6d6;--typo3-card-hover-border-color:#bebebe} -.form{margin-bottom:var(--typo3-component-spacing)} +.form{margin-bottom:var(--typo3-spacing)} +.form-row{display:flex;flex-wrap:wrap;gap:var(--typo3-spacing);margin-bottom:var(--typo3-spacing)} +.form-row>.form-group{margin-bottom:0} +.form-row>.form-group>[class*=form-row]{margin-bottom:0} +@media (min-width:576px){ +.form-row-sm{display:flex;flex-wrap:wrap;gap:var(--typo3-spacing);margin-bottom:var(--typo3-spacing)} +.form-row-sm>.form-group{margin-bottom:0} +.form-row-sm>.form-group>[class*=form-row]{margin-bottom:0} +} +@media (min-width:768px){ +.form-row-md{display:flex;flex-wrap:wrap;gap:var(--typo3-spacing);margin-bottom:var(--typo3-spacing)} +.form-row-md>.form-group{margin-bottom:0} +.form-row-md>.form-group>[class*=form-row]{margin-bottom:0} +} +@media (min-width:992px){ +.form-row-lg{display:flex;flex-wrap:wrap;gap:var(--typo3-spacing);margin-bottom:var(--typo3-spacing)} +.form-row-lg>.form-group{margin-bottom:0} +.form-row-lg>.form-group>[class*=form-row]{margin-bottom:0} +} +@media (min-width:1200px){ +.form-row-xl{display:flex;flex-wrap:wrap;gap:var(--typo3-spacing);margin-bottom:var(--typo3-spacing)} +.form-row-xl>.form-group{margin-bottom:0} +.form-row-xl>.form-group>[class*=form-row]{margin-bottom:0} +} +@media (min-width:1400px){ +.form-row-xxl{display:flex;flex-wrap:wrap;gap:var(--typo3-spacing);margin-bottom:var(--typo3-spacing)} +.form-row-xxl>.form-group{margin-bottom:0} +.form-row-xxl>.form-group>[class*=form-row]{margin-bottom:0} +} .form-label{word-break:break-all} .form-description{opacity:.75;margin-bottom:.5rem} +.form-label+.form-description{margin-top:-.25rem} .form-group{margin-bottom:var(--typo3-spacing)} .form-group-dashed+.form-group-dashed{padding-top:var(--typo3-spacing);border-top:1px dashed rgba(0,0,0,.15)} .form-wizard-icon-list{color:var(--typo3-component-color);background:var(--typo3-component-bg);border:var(--typo3-component-border-width) solid var(--typo3-component-border-color);border-radius:var(--bs-border-radius);margin-top:.25rem;padding:calc(var(--typo3-spacing)/ 4);display:flex;flex-wrap:wrap;gap:2px} @@ -3735,10 +3771,11 @@ typo3-backend-live-search-result-item-action>*,typo3-backend-live-search-result- typo3-backend-live-search-result-item-action>* .livesearch-result-item-icon,typo3-backend-live-search-result-item>* .livesearch-result-item-icon{display:flex;gap:.5em;flex-grow:0;flex-shrink:0;align-items:center} typo3-backend-live-search-result-item-action>* .livesearch-result-item-title,typo3-backend-live-search-result-item>* .livesearch-result-item-title{flex-grow:1;word-break:break-word} typo3-backend-live-search-result-item-action>* .livesearch-result-item-title .small,typo3-backend-live-search-result-item-action>* .livesearch-result-item-title small,typo3-backend-live-search-result-item>* .livesearch-result-item-title .small,typo3-backend-live-search-result-item>* .livesearch-result-item-title small{opacity:var(--livesearch-item-opacity)} -.recordlist{overflow:hidden;background:var(--panel-bg);box-shadow:var(--panel-box-shadow);border-radius:var(--panel-border-radius);border:var(--panel-border-width) solid var(--panel-default-border-color);margin-bottom:var(--panel-spacing)} +.recordlist{overflow:hidden;background:var(--panel-bg);box-shadow:var(--panel-box-shadow);border-radius:var(--panel-border-radius);border:var(--panel-border-width) solid var(--panel-default-border-color);margin-bottom:var(--typo3-spacing)} .recordlist table tr td.deletePlaceholder{text-decoration:line-through} .recordlist .table-fit{box-shadow:none;border-radius:0;border-left:0;border-right:0;border-bottom:0;margin-bottom:0} .recordlist .pagination{display:inline-flex} +.recordlist+.recordlist{margin-top:calc(var(--typo3-spacing) * 1.5)} .recordlist-heading{display:flex;align-items:center;flex-wrap:wrap;color:var(--panel-default-heading-color);background:var(--panel-default-heading-bg);padding:var(--panel-header-padding-y) var(--panel-header-padding-x);gap:var(--panel-header-padding-y) var(--panel-header-padding-x)} .recordlist-heading-row{flex-grow:1;display:flex;align-items:center;flex-wrap:wrap;max-width:100%;gap:var(--panel-header-padding-y) var(--panel-header-padding-x)} .recordlist-heading-title{font-weight:700;flex-grow:1;width:250px;max-width:100%} @@ -3751,7 +3788,7 @@ typo3-backend-live-search-result-item-action>* .livesearch-result-item-title .sm .resource-tiles-container { container-type: inline-size; - margin-bottom: var(--typo3-component-spacing); + margin-bottom: var(--typo3-spacing); } @container (min-width: 480px) { @@ -3781,7 +3818,7 @@ typo3-backend-live-search-result-item-action>* .livesearch-result-item-title .sm .resource-tile-image{display:flex;height:100%;width:100%;justify-content:center;align-items:center} .resource-tile-image img{max-height:100%;max-width:100%;outline:2px solid #fff;outline-offset:0;border-radius:2px;box-shadow:0 0 4px 4px rgba(0,0,0,.05)} .resource-tile-image-icon{position:absolute;top:calc(var(--resource-tile-spacing) * -.5);left:calc(var(--resource-tile-spacing) * -.5)} -.resource-tile-nameplate{display:flex;flex-direction:column;padding:var(--resource-tile-spacing);text-align:center;font-size:var(--resource-tile-nameplate-size)} +.resource-tile-nameplate{display:flex;flex-direction:column;padding:var(--resource-tile-spacing);text-align:center;font-size:var(--resource-tile-nameplate-size);width:100%} .resource-tile-nameplate-label{overflow:hidden;white-space:nowrap;text-overflow:ellipsis} .resource-tile-nameplate-activity{font-size:var(--resource-tile-nameplate-activity-size);opacity:.75} .resource-tile-checkbox{display:none;position:absolute;font-size:var(--resource-tile-checkbox-size);right:calc(var(--resource-tile-spacing)/ 2);top:calc(var(--resource-tile-spacing)/ 2)} @@ -3790,7 +3827,7 @@ typo3-backend-live-search-result-item-action>* .livesearch-result-item-title .sm .resource-dragpreview-counter{display:flex;justify-content:center;align-items:center;height:32px;min-width:32px} .resource-dragpreview-thumbnails{display:flex;gap:2px} .resource-dragpreview-thumbnails img{height:32px;width:32px;background-color:#fff} -.recordsearchbox-container{margin-bottom:var(--typo3-component-spacing)} +.recordsearchbox-container{margin-bottom:var(--typo3-spacing)} .recordsearchbox-container [data-recordsearchbox-levels]{max-width:140px} :root{--treelist-color:#333;--treelist-comment-color:#666;--treelist-bg:#fff;--treelist-border-width:1px;--treelist-border-color:#ddd;--treelist-indentation:1rem;--treelist-indentation-spacer:.5rem;--treelist-item-spacer:2px;--treelist-item-line-height:24px;--treelist-control-size:16px} .treelist,.treelist ul{color:var(--treelist-color);background:var(--treelist-bg);padding:0;padding-left:calc(var(--treelist-indentation)/ 2);list-style:none;position:relative} @@ -3826,6 +3863,7 @@ typo3-backend-live-search-result-item-action>* .livesearch-result-item-title .sm .form-section{--treelist-bg:#fafafa} .indent{--indent-base:16px;--indent-level:0;margin-left:calc(var(--indent-base) * var(--indent-level))} .indent-inline-block{display:inline-block} +.pagination{flex-wrap:wrap;row-gap:4px} typo3-backend-editable-page-title{display:block;white-space:nowrap;text-overflow:ellipsis} typo3-backend-new-content-element-wizard{--typo3-component-color:var(--typo3-light-color);--typo3-component-secondary-color:var(--typo3-light-secondary-color);--typo3-component-bg:var(--typo3-light-bg);--typo3-component-border-color:var(--typo3-light-border-color);--typo3-component-link-color:var(--typo3-light-link-color);--typo3-component-link-hover-color:var(--typo3-light-link-hover-color);--typo3-component-hover-color:var(--typo3-light-hover-color);--typo3-component-hover-bg:var(--typo3-light-hover-bg);--typo3-component-hover-border-color:var(--typo3-light-hover-border-color);--typo3-component-focus-color:var(--typo3-light-focus-color);--typo3-component-focus-bg:var(--typo3-light-focus-bg);--typo3-component-focus-border-color:var(--typo3-light-focus-border-color);--typo3-component-active-color:var(--typo3-light-active-color);--typo3-component-active-bg:var(--typo3-light-active-bg);--typo3-component-active-border-color:var(--typo3-light-active-border-color);--typo3-component-disabled-color:var(--typo3-light-disabled-color);--typo3-component-disabled-bg:var(--typo3-light-disabled-bg);--typo3-component-disabled-border-color:var(--typo3-light-disabled-border-color)} .collapse-horizontal{height:auto;width:0;vertical-align:middle;overflow:hidden} @@ -4063,8 +4101,8 @@ span.dragIcon{display:inline-block;height:16px} .card-login{margin-bottom:0} } .card-login.card-mfa .card-heading .h2,.card-login.card-mfa .card-heading h2{margin:.75rem 0} -.input-login{height:41.2px;padding:12px 12px;font-size:12px;line-height:1.3333333;border-radius:2px} -select.input-login{height:41.2px;line-height:41.2px} +.input-login{height:43.2px;padding:12px 12px;font-size:12px;line-height:1.3333333;border-radius:2px} +select.input-login{height:43.2px;line-height:43.2px} select[multiple].input-login,textarea.input-login{height:auto} .input-login{border-color:#949494} .input-login:active,.input-login:active:focus,.input-login:active:hover,.input-login:focus,.input-login:hover{outline:1px solid #000;outline-offset:-1px} @@ -4082,11 +4120,9 @@ select[multiple].input-login,textarea.input-login{height:auto} .typo3-login-copyright-text{font-size:.95em;padding-top:1em;color:#444} .typo3-login-copyright-text>:first-child{margin-top:0} .typo3-login-copyright-text>:last-child{margin-bottom:0} -.h1,h1,typo3-backend-editable-page-title{font-family:var(--typo3-header-font-family);font-variant:normal;font-weight:400} video{background-color:#000} .nowrap{white-space:nowrap} .nowrap-disabled{white-space:normal!important} -em{font-style:italic} .section{margin-bottom:15px} .diff-r{color:red} div.diff-r{background-color:red;color:#000} @@ -4139,8 +4175,6 @@ label .icon img{pointer-events:none} .formengine-field-item>.t3js-charcounter-wrapper .t3js-charcounter-min{margin:0 2px} .form-group .panel,.form-group .panel-group{overflow:visible} .form-control[disabled],.form-control[readonly],fieldset[disabled] .form-control{color:#737373} -.form-control-icon{position:absolute;top:50%;left:15px;transform:translate(0,-50%);z-index:1;pointer-events:none} -.form-control-icon+.form-control,.form-control-icon+.form-control-clearable .form-control{padding-left:3.25em} .form-group.has-error .form-label:before{content:"";vertical-align:middle;-webkit-mask:url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' xml:space='preserve' viewBox='0 0 16 16'%3e%3cg class='icon-color'%3e%3cpath d='M8 2c3.3 0 6 2.7 6 6s-2.7 6-6 6-6-2.7-6-6 2.7-6 6-6m0-1C4.1 1 1 4.1 1 8s3.1 7 7 7 7-3.1 7-7-3.1-7-7-7z'/%3e%3ccircle cx='8' cy='11' r='1'/%3e%3cpath d='M8.5 9h-1l-.445-4.45A.5.5 0 0 1 7.552 4h.896a.5.5 0 0 1 .497.55L8.5 9z'/%3e%3c/g%3e%3c/svg%3e");mask:url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' xml:space='preserve' viewBox='0 0 16 16'%3e%3cg class='icon-color'%3e%3cpath d='M8 2c3.3 0 6 2.7 6 6s-2.7 6-6 6-6-2.7-6-6 2.7-6 6-6m0-1C4.1 1 1 4.1 1 8s3.1 7 7 7 7-3.1 7-7-3.1-7-7-7z'/%3e%3ccircle cx='8' cy='11' r='1'/%3e%3cpath d='M8.5 9h-1l-.445-4.45A.5.5 0 0 1 7.552 4h.896a.5.5 0 0 1 .497.55L8.5 9z'/%3e%3c/g%3e%3c/svg%3e");background-color:#c83c3c;background-size:contain;display:inline-block;border-radius:50%;width:14px;height:14px} .form-group.has-error .btn-toolbar label:before{font-family:inherit;font-size:inherit;margin-right:inherit;text-align:inherit;content:"";color:inherit;display:block} select.form-select[multiple],select.form-select[size]:not([size="1"]){min-height:156px} @@ -4148,13 +4182,14 @@ select.form-select>optgroup{margin-top:9px} select.form-select>optgroup:first-child{margin-top:0} select.form-select option{padding-top:2px;padding-bottom:2px} select.icon-select option{padding-left:22px} -.form-control-clearable{position:relative;border:0;padding:0} -.form-control-clearable input[type=search]::-webkit-search-cancel-button{display:none} -.form-control-clearable .form-control{padding-right:2.3em} -.form-control-clearable .close{border:none;background-color:transparent;position:absolute;height:16px;z-index:3;top:50%;right:.5em;transform:translate(0,-50%);opacity:.2} -.form-control-clearable .close:hover{opacity:.5} -.form-control-clearable .close .icon{vertical-align:0} -.form-control-clearable:focus{box-shadow:none;border-color:inherit} +.form-control-clearable{padding-right:2.3em} +.form-control-clearable-wrapper{position:relative;border:0;padding:0} +.form-control-clearable-wrapper input[type=search]::-webkit-search-cancel-button{display:none} +.form-control-clearable-wrapper .form-control{padding-right:2.3em} +.form-control-clearable-wrapper .close{border:none;background-color:transparent;position:absolute;height:16px;z-index:3;top:50%;right:.5em;transform:translate(0,-50%);opacity:.2} +.form-control-clearable-wrapper .close:hover{opacity:.5} +.form-control-clearable-wrapper .close .icon{vertical-align:0} +.form-control-clearable-wrapper:focus{box-shadow:none;border-color:inherit} .form-notice-capslock{position:absolute;right:25px;top:50%;margin-top:-10px;height:20px;width:20px;padding:3px;z-index:10;background-color:#fff} .form-notice-capslock>img{display:block;opacity:.5} .form-section{border:1px solid #ccc;background-color:#fafafa;padding:15px 12px 3px} @@ -4189,8 +4224,8 @@ select.icon-select option{padding-left:22px} .form-multigroup-wrap .form-multigroup-item-wizard+select.form-select[multiple],.form-multigroup-wrap .form-multigroup-item-wizard+select.form-select[size]{min-height:125px} .form-multigroup-wrap .form-wizards-wrap{width:100%} textarea.formengine-textarea{resize:none} -.input-group>.form-control-clearable{flex:1 1 auto;width:1%;min-width:0} -.form-control:not(.hidden)+.form-control-clearable{flex-grow:0;width:auto} +.input-group>.form-control-clearable-wrapper{flex:1 1 auto;width:1%;min-width:0} +.form-control:not(.hidden)+.form-control-clearable-wrapper{flex-grow:0;width:auto} .form-control.hidden+.close{display:none} .sticky-form-actions{position:sticky;top:0;z-index:2;padding:calc(1rem / 2) 1rem;background:#fff} .modal-body .sticky-form-actions{margin-left:calc(var(--bs-modal-padding) * -1);margin-right:calc(var(--bs-modal-padding) * -1);margin-bottom:var(--bs-modal-padding);padding:calc(var(--bs-modal-padding)/ 2) var(--bs-modal-padding);border-bottom:var(--bs-modal-border-width) solid var(--bs-modal-border-color)} @@ -4283,7 +4318,7 @@ td.permission-column-group{padding-left:0;width:200px;white-space:nowrap} .install-tool-modal .list-group-item.active a{color:#fff} .install-tool-modal a[data-bs-toggle=collapse]{display:block} .install-tool-modal .table .t3-languagePacks-inactive,.install-tool-modal .table .t3-languagePacks-inactive td{color:#aaa} -.install-tool-modal .t3-install-displaytwinimageimages{border:1px solid #ccc;padding:10px} +.install-tool-modal .t3-install-displaytwinimageimages{border:1px solid #ccc;border-radius:4px;padding:10px;margin-bottom:var(--typo3-spacing)} .install-tool-modal .t3-install-displaytwinimagetextarea pre{border-top:0} .install-tool-modal .bg-transparent-emulation{padding:10px;text-align:center;background:url(../Images/bg_transparent_emulation.png)} .install-tool-modal .bg-transparent-emulation img{max-width:300px} @@ -4310,7 +4345,7 @@ html{scroll-behavior:smooth} :target:before{content:"";display:block;height:80px;margin:-80px 0 0} :root{--pagemodule-grid-spacing:1rem;--pagemodule-grid-inner-spacing:1rem;--pagemodule-grid-cell-header-size:1em;--pagemodule-grid-cell-border-radius:4px;--pagemodule-grid-cell-bg:#f2f2f2;--pagemodule-grid-cell-restricted-bg:#fcf1e2;--pagemodule-grid-column-unused-bg:#fcf1e2;--pagemodule-element-spacing:1rem;--pagemodule-element-bg:#fff;--pagemodule-element-border-radius:2px;--pagemodule-element-box-shadow:0 1px 2px 1px rgba(0, 0, 0, .15);--pagemodule-element-warning-bg:#fcf1e2;--pagemodule-element-warning-border-color:#f6dab1;--pagemodule-element-hidden-bg:#f2f2f2;--pagemodule-dropzone-bg:#fcf1e2;--pagemodule-dropzone-possible-bg:#dbebdb} .t3-grid-table{border-collapse:separate;border-spacing:var(--pagemodule-grid-spacing);min-width:100%;table-layout:fixed} -.t3-grid-container{overflow:hidden;margin-bottom:var(--typo3-component-spacing)} +.t3-grid-container{overflow:hidden;margin-bottom:var(--typo3-spacing)} .t3-grid-container-inner{margin:calc(var(--pagemodule-grid-spacing) * -1)} .t3-grid-cell{border-radius:var(--pagemodule-grid-cell-border-radius);background-color:var(--pagemodule-grid-cell-bg);padding:calc(var(--pagemodule-grid-inner-spacing) - var(--pagemodule-grid-spacing)) 0} .t3-grid-cell-restricted{background-color:var(--pagemodule-grid-cell-restricted-bg)} @@ -4370,7 +4405,6 @@ html{scroll-behavior:smooth} .tx_recycler_recycler tr.collapse.show{display:table-row} .scheduler-group-dragitem{cursor:move} .scheduler-group-dragitem [editable=true],.scheduler-group-dragitem a,.scheduler-group-dragitem button{cursor:initial} -.scheduler-group-panel{overflow:unset} .task-form .form-wizards-wrap{margin-bottom:.5rem!important} @media (min-width:992px){ .task-form .form-group{width:50%} diff --git a/typo3/sysext/backend/Resources/Public/JavaScript/form-engine.js b/typo3/sysext/backend/Resources/Public/JavaScript/form-engine.js index e852f3567cd27ab1c6d988a39ec579866affd9c7..d7c4b85c3b3360441c27aff5bf59f6db759574b6 100644 --- a/typo3/sysext/backend/Resources/Public/JavaScript/form-engine.js +++ b/typo3/sysext/backend/Resources/Public/JavaScript/form-engine.js @@ -10,4 +10,4 @@ * * The TYPO3 project - inspiring people to share! */ -import DocumentService from"@typo3/core/document-service.js";import $ from"jquery";import FormEngineValidation from"@typo3/backend/form-engine-validation.js";import Icons from"@typo3/backend/icons.js";import{default as Modal}from"@typo3/backend/modal.js";import*as MessageUtility from"@typo3/backend/utility/message-utility.js";import Severity from"@typo3/backend/severity.js";import*as BackendExceptionModule from"@typo3/backend/backend-exception.js";import InteractionRequestMap from"@typo3/backend/event/interaction-request-map.js";import Utility from"@typo3/backend/utility.js";export default(function(){function e(e,t){t?n.interactionRequestMap.resolveFor(e):n.interactionRequestMap.rejectFor(e)}const t=new Map;t.set("typo3-backend-form-update-value",(e=>{const t=document.querySelector('[name="'+CSS.escape(e.elementName)+'"]'),n=document.querySelector('[data-formengine-input-name="'+CSS.escape(e.elementName)+'"]');FormEngineValidation.updateInputField(e.elementName),null!==t&&(FormEngineValidation.markFieldAsChanged(t),FormEngineValidation.validateField(t)),null!==n&&n!==t&&FormEngineValidation.validateField(n)})),t.set("typo3-backend-form-reload",(e=>{if(!e.confirmation)return void n.saveDocument();const t=Modal.advanced({title:TYPO3.lang["FormEngine.refreshRequiredTitle"],content:TYPO3.lang["FormEngine.refreshRequiredContent"],severity:Severity.warning,staticBackdrop:!0,buttons:[{text:TYPO3.lang["button.cancel"]||"Cancel",active:!0,btnClass:"btn-default",name:"cancel"},{text:TYPO3.lang["button.ok"]||"OK",btnClass:"btn-"+Severity.getCssClass(Severity.warning),name:"ok",trigger:()=>{n.saveDocument()}}]});t.addEventListener("button.clicked",(()=>t.hideModal()))})),t.set("typo3-backend-form-update-bitmask",((e,t)=>{const n=t.target,a=document.editform[e.elementName],o=n.checked!==e.invert,i=Math.pow(2,e.position),r=Math.pow(2,e.total)-i-1;a.value=o?a.value|i:a.value&r,a.dispatchEvent(new Event("change",{bubbles:!0,cancelable:!0}))}));const n={consumeTypes:["typo3.setUrl","typo3.beforeSetUrl","typo3.refresh"],Validation:FormEngineValidation,interactionRequestMap:InteractionRequestMap,formName:TYPO3.settings.FormEngine.formName,openedPopupWindow:null,legacyFieldChangedCb:function(){!$.isFunction(TYPO3.settings.FormEngine.legacyFieldChangedCb)||TYPO3.settings.FormEngine.legacyFieldChangedCb()},browserUrl:"",openPopupWindow:function(e,t,a){return Modal.advanced({type:Modal.types.iframe,content:n.browserUrl+"&mode="+e+"&bparams="+t+(a?"&"+("db"===e?"expandPage":"expandFolder")+"="+a:""),size:Modal.sizes.large})},setSelectOptionFromExternalSource:function(e,t,a,o,i,r){i=String(i);let c,l,s=!1,d=!1;l=n.getFieldElement(e),c=l.get(0);const u=l.get(0);if(null===u||"--div--"===t||u instanceof HTMLOptGroupElement)return;const m=n.getFieldElement(e,"_list",!0);if(m.length>0&&(l=m,c=l.get(0),s=l.prop("multiple")&&"1"!=l.prop("size"),d=!0),s||d){const d=n.getFieldElement(e,"_avail");if(!s){for(const e of c.querySelectorAll("option")){const t=d.find('option[value="'+$.escapeSelector($(e).attr("value"))+'"]');t.length&&(t.removeClass("hidden").prop("disabled",!1),n.enableOptGroup(t.get(0)))}l.empty()}if(i){let e=!1,a=new RegExp("(^|,)"+t+"($|,)");i.match(a)?(l.empty(),e=!0):1==l.find("option").length&&(a=new RegExp("(^|,)"+l.find("option").prop("value")+"($|,)"),i.match(a)&&(l.empty(),e=!0)),e&&void 0!==r&&r.closest("select").querySelectorAll("[disabled]").forEach((function(e){e.classList.remove("hidden"),e.disabled=!1,n.enableOptGroup(e)}))}let m=!0;const f=n.getFieldElement(e,"_mul",!0);if(0==f.length||0==f.val()){for(const e of c.querySelectorAll("option"))if(e.value==t){m=!1;break}if(m&&void 0!==r){r.classList.add("hidden"),r.disabled=!0;const e=r.parentElement;e instanceof HTMLOptGroupElement&&0===e.querySelectorAll("option:not([disabled]):not([hidden]):not(.hidden)").length&&(e.disabled=!0,e.classList.add("hidden"))}}if(m){const e=$("<option></option>");e.attr({value:t,title:o}).text(a),e.appendTo(l),n.updateHiddenFieldValueFromSelect(c,u),n.legacyFieldChangedCb(),FormEngineValidation.markFieldAsChanged(u),n.Validation.validateField(l),n.Validation.validateField(d)}}else{const e=/_(\d+)$/,a=t.toString().match(e);null!=a&&(t=a[1]),l.val(t),n.Validation.validateField(l)}},updateHiddenFieldValueFromSelect:function(e,t){const n=Array.from(e.options).map((e=>e.value));t.value=n.join(","),t.dispatchEvent(new Event("change",{bubbles:!0,cancelable:!0}))},getFormElement:function(e){const t=$('form[name="'+n.formName+'"]:first');if(!e)return t;{const a=n.getFieldElement(e),o=n.getFieldElement(e,"_list");if(a.length>0&&("select-one"===a.prop("type")||o.length>0&&o.prop("type").match(/select-(one|multiple)/)))return t;console.error("Form fields missing: form: "+n.formName+", field name: "+e),alert("Form field is invalid")}},getFieldElement:function(e,t,a){const o=$('form[name="'+n.formName+'"]:first');if(t){let n;switch(t){case"_list":n=$(':input[data-formengine-input-name="'+e+'"]:not([type=hidden])',o);break;case"_avail":n=$(':input[data-relatedfieldname="'+e+'"]',o);break;case"_mul":case"_hr":n=$(':input[type=hidden][data-formengine-input-name="'+e+'"]',o);break;default:n=null}if(n&&n.length>0||!0===a)return n}return $(':input[name="'+e+'"]',o)},initializeEvents:function(){top.TYPO3&&void 0!==top.TYPO3.Backend&&(top.TYPO3.Backend.consumerScope.attach(n),$(window).on("unload",(function(){top.TYPO3.Backend.consumerScope.detach(n)}))),$(document).on("click",".t3js-editform-close",(e=>{e.preventDefault(),n.preventExitIfNotSaved(n.preventExitIfNotSavedCallback)})).on("click",".t3js-editform-view",(e=>{e.preventDefault(),n.previewAction(e,n.previewActionCallback)})).on("click",".t3js-editform-new",(e=>{e.preventDefault(),n.newAction(e,n.newActionCallback)})).on("click",".t3js-editform-duplicate",(e=>{e.preventDefault(),n.duplicateAction(e,n.duplicateActionCallback)})).on("click",".t3js-editform-delete-record",(e=>{e.preventDefault(),n.deleteAction(e,n.deleteActionCallback)})).on("click",".t3js-editform-submitButton",(e=>{const t=$(e.currentTarget),n=t.data("name")||e.currentTarget.name,a=$("<input />").attr("type","hidden").attr("name",n).attr("value","1");t.parents("form").append(a)})).on("change",'.t3-form-field-eval-null-checkbox input[type="checkbox"]',(e=>{$(e.currentTarget).closest(".t3js-formengine-field-item").toggleClass("disabled")})).on("change",'.t3js-form-field-eval-null-placeholder-checkbox input[type="checkbox"]',(e=>{n.toggleCheckboxField($(e.currentTarget)),FormEngineValidation.markFieldAsChanged($(e.currentTarget))})).on("change",(()=>{$(".module-docheader-bar .btn").removeClass("disabled").prop("disabled",!1)})).on("click",".t3js-element-browser",(function(e){e.preventDefault(),e.stopPropagation();const t=$(e.currentTarget),a=t.data("mode"),o=t.data("params"),i=t.data("entryPoint");n.openPopupWindow(a,o,i)})).on("click",'[data-formengine-field-change-event="click"]',(e=>{const t=JSON.parse(e.currentTarget.dataset.formengineFieldChangeItems);n.processOnFieldChange(t,e)})).on("change",'[data-formengine-field-change-event="change"]',(e=>{const t=JSON.parse(e.currentTarget.dataset.formengineFieldChangeItems);n.processOnFieldChange(t,e)})),document.editform.addEventListener("submit",(function(){if(document.editform.closeDoc.value)return;const e=["button[form]",'button[name^="_save"]','a[data-name^="_save"]','button[name="CMD"][value^="save"]','a[data-name="CMD"][data-value^="save"]'].join(","),t=document.querySelector(e);null!==t&&(t.disabled=!0,Icons.getIcon("spinner-circle-dark",Icons.sizes.small).then((function(e){t.querySelector(".t3js-icon").outerHTML=e})))})),window.addEventListener("message",n.handlePostMessage)},consume:function(t){if(!t)throw new BackendExceptionModule.BackendException("No interaction request given",1496589980);const a=$.Deferred();if(t.concernsTypes(n.consumeTypes)){const o=t.outerMostRequest;n.interactionRequestMap.attachFor(o,a),o.isProcessed()?e(o,o.getProcessedData().response):n.hasChange()?n.preventExitIfNotSaved((function(t){o.setProcessedData({response:t}),e(o,t)})):n.interactionRequestMap.resolveFor(o)}return a},handlePostMessage:function(e){if(!MessageUtility.MessageUtility.verifyOrigin(e.origin))throw"Denied message sent by "+e.origin;if("typo3:elementBrowser:elementAdded"===e.data.actionName){if(void 0===e.data.fieldName)throw"fieldName not defined in message";if(void 0===e.data.value)throw"value not defined in message";const t=e.data.label||e.data.value,a=e.data.title||t,o=e.data.exclusiveValues||"";n.setSelectOptionFromExternalSource(e.data.fieldName,e.data.value,t,a,o)}},initializeRemainingCharacterViews:function(){const e=$("[maxlength]").not(".t3js-datetimepicker").not(".t3js-color-picker").not(".t3js-charcounter-initialized");e.on("focus",(e=>{const t=$(e.currentTarget),a=t.parents(".t3js-formengine-field-item:first"),o=n.getCharacterCounterProperties(t);let i=a.find(".t3js-charcounter-wrapper");i.length||(i=$("<div>"),i.addClass("t3js-charcounter-wrapper"),a.append(i)),i.append($("<div />",{class:"t3js-charcounter"}).append($("<span />",{class:o.labelClass}).text(TYPO3.lang["FormEngine.remainingCharacters"].replace("{0}",o.remainingCharacters))))})).on("blur",(e=>{$(e.currentTarget).parents(".t3js-formengine-field-item:first").find(".t3js-charcounter").remove()})).on("keyup",(e=>{const t=$(e.currentTarget),a=t.parents(".t3js-formengine-field-item:first"),o=n.getCharacterCounterProperties(t);a.find(".t3js-charcounter span").removeClass().addClass(o.labelClass).text(TYPO3.lang["FormEngine.remainingCharacters"].replace("{0}",o.remainingCharacters))})),e.addClass("t3js-charcounter-initialized")},getCharacterCounterProperties:function(e){const t=e.val(),n=parseInt(e.attr("maxlength"),10)-t.length-(t.match(/\n/g)||[]).length;let a="";return a=n<15?"badge-danger":n<30?"badge-warning":"badge-info",{remainingCharacters:n,labelClass:"badge "+a}},initializeMinimumCharactersLeftViews:function(){const e=(e,t)=>{const n=t.currentTarget.closest(".t3js-formengine-field-item"),a=n.querySelector(".t3js-charcounter-min"),o=TYPO3.lang["FormEngine.minCharactersLeft"].replace("{0}",e);if(a)a.querySelector("span").innerHTML=o;else{const e=document.createElement("div");e.classList.add("t3js-charcounter-min");const t=document.createElement("span");t.classList.add("badge","badge-danger"),t.innerHTML=o,e.append(t);let a=n.querySelector(".t3js-charcounter-wrapper");a||(a=document.createElement("div"),a.classList.add("t3js-charcounter-wrapper"),n.append(a)),a.prepend(e)}},t=e=>{const t=e.currentTarget.closest(".t3js-formengine-field-item").querySelector(".t3js-charcounter-min");t&&t.remove()};document.querySelectorAll("[minlength]:not(.t3js-datetimepicker):not(.t3js-charcounter-min-initialized)").forEach((a=>{a.addEventListener("focus",(t=>{const o=n.getMinCharacterLeftCount(a);o>0&&e(o,t)})),a.addEventListener("blur",t),a.addEventListener("keyup",(o=>{const i=n.getMinCharacterLeftCount(a);i>0?e(i,o):t(o)}))}))},getMinCharacterLeftCount:function(e){const t=e.value,n=e.minLength,a=t.length;if(0===a)return 0;return n-a-(t.match(/\n/g)||[]).length},initializeNullNoPlaceholderCheckboxes:function(){document.querySelectorAll(".t3-form-field-eval-null-checkbox").forEach((e=>{const t=e.querySelector('input[type="checkbox"]'),n=e.closest(".t3js-formengine-field-item");t.checked||n.classList.add("disabled")}))},initializeNullWithPlaceholderCheckboxes:function(){document.querySelectorAll(".t3js-form-field-eval-null-placeholder-checkbox").forEach((e=>{n.toggleCheckboxField($(e).find('input[type="checkbox"]'),!1)}))},toggleCheckboxField:function(e,t=!0){const n=e.closest(".t3js-formengine-field-item");e.prop("checked")?(n.find(".t3js-formengine-placeholder-placeholder").hide(),n.find(".t3js-formengine-placeholder-formfield").show(),t&&n.find(".t3js-formengine-placeholder-formfield").find(":input").trigger("focus")):(n.find(".t3js-formengine-placeholder-placeholder").show(),n.find(".t3js-formengine-placeholder-formfield").hide())},reinitialize:function(){const e=Array.from(document.querySelectorAll(".t3js-clearable"));e.length>0&&import("@typo3/backend/input/clearable.js").then((function(){e.forEach((e=>e.clearable()))})),n.initializeNullNoPlaceholderCheckboxes(),n.initializeNullWithPlaceholderCheckboxes(),n.initializeLocalizationStateSelector(),n.initializeMinimumCharactersLeftViews(),n.initializeRemainingCharacterViews()},initializeLocalizationStateSelector:function(){document.querySelectorAll(".t3js-l10n-state-container").forEach((e=>{const t=e.closest(".t3js-formengine-field-item")?.querySelector("[data-formengine-input-name]");if(void 0===t)return;const n=e.querySelector('input[type="radio"]:checked').value;"parent"!==n&&"source"!==n||(t.disabled=!0)}))},hasChange:function(){const e=$('form[name="'+n.formName+'"] .has-change').length>0,t=$('[name^="data["].has-change').length>0;return e||t},preventExitIfNotSavedCallback:()=>{n.closeDocument()},preventFollowLinkIfNotSaved:function(e){return n.preventExitIfNotSaved((function(){window.location.href=e})),!1},preventExitIfNotSaved:function(e){if(e=e||n.preventExitIfNotSavedCallback,n.hasChange()){const t=TYPO3.lang["label.confirm.close_without_save.title"]||"Do you want to close without saving?",a=TYPO3.lang["label.confirm.close_without_save.content"]||"You currently have unsaved changes. Are you sure you want to discard these changes?",o=$("<input />").attr("type","hidden").attr("name","_saveandclosedok").attr("value","1"),i=[{text:TYPO3.lang["buttons.confirm.close_without_save.no"]||"No, I will continue editing",btnClass:"btn-default",name:"no"},{text:TYPO3.lang["buttons.confirm.close_without_save.yes"]||"Yes, discard my changes",btnClass:"btn-default",name:"yes"}];0===$(".has-error").length&&i.push({text:TYPO3.lang["buttons.confirm.save_and_close"]||"Save and close",btnClass:"btn-primary",name:"save",active:!0});const r=Modal.confirm(t,a,Severity.warning,i);r.addEventListener("button.clicked",(function(t){"no"===t.target.name?r.hideModal():"yes"===t.target.name?(r.hideModal(),e.call(null,!0)):"save"===t.target.name&&($("form[name="+n.formName+"]").append(o),r.hideModal(),n.saveDocument())}))}else e.call(null,!0)},preventSaveIfHasErrors:function(){if($(".has-error").length>0){const e=TYPO3.lang["label.alert.save_with_error.title"]||"You have errors in your form!",t=TYPO3.lang["label.alert.save_with_error.content"]||"Please check the form, there is at least one error in your form.",n=Modal.confirm(e,t,Severity.error,[{text:TYPO3.lang["buttons.alert.save_with_error.ok"]||"OK",btnClass:"btn-danger",name:"ok"}]);return n.addEventListener("button.clicked",(function(e){"ok"===e.target.name&&n.hideModal()})),!1}return!0},requestFormEngineUpdate:function(e){if(e){const e=Modal.advanced({title:TYPO3.lang["FormEngine.refreshRequiredTitle"],content:TYPO3.lang["FormEngine.refreshRequiredContent"],severity:Severity.warning,staticBackdrop:!0,buttons:[{text:TYPO3.lang["button.cancel"]||"Cancel",active:!0,btnClass:"btn-default",name:"cancel",trigger:()=>{e.hideModal()}},{text:TYPO3.lang["button.ok"]||"OK",btnClass:"btn-"+Severity.getCssClass(Severity.warning),name:"ok",trigger:()=>{n.closeModalsRecursive(),n.saveDocument()}}]})}else n.saveDocument()},processOnFieldChange:function(e,n){e.forEach((e=>{const a=t.get(e.name);a instanceof Function&&a.call(null,e.data||null,n)}))},registerOnFieldChangeHandler:function(e,n){t.has(e)&&console.warn("Handler for onFieldChange name `"+e+"` has been overridden."),t.set(e,n)},closeModalsRecursive:function(){void 0!==Modal.currentModal&&null!==Modal.currentModal&&(Modal.currentModal.addEventListener("typo3-modal-hidden",(function(){n.closeModalsRecursive()})),Modal.currentModal.hideModal())},previewAction:function(e,t){t=t||n.previewActionCallback;const a=e.currentTarget.href,o="isNew"in e.target.dataset,i=$("<input />").attr("type","hidden").attr("name","_savedokview").attr("value","1");n.hasChange()?n.showPreviewModal(a,o,i,t):($("form[name="+n.formName+"]").append(i),window.open("","newTYPO3frontendWindow"),document.editform.submit())},previewActionCallback:function(e,t,a){switch(Modal.dismiss(),e){case"discard":const e=window.open(t,"newTYPO3frontendWindow");e.focus(),Utility.urlsPointToSameServerSideResource(e.location.href,t)&&e.location.reload();break;case"save":$("form[name="+n.formName+"]").append($(a)),window.open("","newTYPO3frontendWindow"),n.saveDocument()}},showPreviewModal:function(e,t,n,a){const o=TYPO3.lang["label.confirm.view_record_changed.title"]||"Do you want to save before viewing?",i={text:TYPO3.lang["buttons.confirm.view_record_changed.cancel"]||"Cancel",btnClass:"btn-default",name:"cancel"},r={text:TYPO3.lang["buttons.confirm.view_record_changed.no-save"]||"View without changes",btnClass:"btn-default",name:"discard"},c={text:TYPO3.lang["buttons.confirm.view_record_changed.save"]||"Save changes and view",btnClass:"btn-primary",name:"save",active:!0};let l=[],s="";t?(l=[i,c],s=TYPO3.lang["label.confirm.view_record_changed.content.is-new-page"]||"You need to save your changes before viewing the page. Do you want to save and view them now?"):(l=[i,r,c],s=TYPO3.lang["label.confirm.view_record_changed.content"]||"You currently have unsaved changes. You can either discard these changes or save and view them.");const d=Modal.confirm(o,s,Severity.info,l);d.addEventListener("button.clicked",(function(t){a(t.target.name,e,n,d)}))},newAction:function(e,t){t=t||n.newActionCallback;const a=$("<input />").attr("type","hidden").attr("name","_savedoknew").attr("value","1"),o="isNew"in e.target.dataset;n.hasChange()?n.showNewModal(o,a,t):($("form[name="+n.formName+"]").append(a),document.editform.submit())},newActionCallback:function(e,t){const a=$("form[name="+n.formName+"]");switch(Modal.dismiss(),e){case"no":a.append(t),document.editform.submit();break;case"yes":a.append(t),n.saveDocument()}},showNewModal:function(e,t,n){const a=TYPO3.lang["label.confirm.new_record_changed.title"]||"Do you want to save before adding?",o=TYPO3.lang["label.confirm.new_record_changed.content"]||"You need to save your changes before creating a new record. Do you want to save and create now?";let i=[];const r={text:TYPO3.lang["buttons.confirm.new_record_changed.cancel"]||"Cancel",btnClass:"btn-default",name:"cancel"},c={text:TYPO3.lang["buttons.confirm.new_record_changed.no"]||"No, just add",btnClass:"btn-default",name:"no"},l={text:TYPO3.lang["buttons.confirm.new_record_changed.yes"]||"Yes, save and create now",btnClass:"btn-primary",name:"yes",active:!0};i=e?[r,l]:[r,c,l];Modal.confirm(a,o,Severity.info,i).addEventListener("button.clicked",(function(e){n(e.target.name,t)}))},duplicateAction:function(e,t){t=t||n.duplicateActionCallback;const a=$("<input />").attr("type","hidden").attr("name","_duplicatedoc").attr("value","1"),o="isNew"in e.target.dataset;n.hasChange()?n.showDuplicateModal(o,a,t):($("form[name="+n.formName+"]").append(a),document.editform.submit())},duplicateActionCallback:function(e,t){const a=$("form[name="+n.formName+"]");switch(Modal.dismiss(),e){case"no":a.append(t),document.editform.submit();break;case"yes":a.append(t),n.saveDocument()}},showDuplicateModal:function(e,t,n){const a=TYPO3.lang["label.confirm.duplicate_record_changed.title"]||"Do you want to save before duplicating this record?",o=TYPO3.lang["label.confirm.duplicate_record_changed.content"]||"You currently have unsaved changes. Do you want to save your changes before duplicating this record?";let i=[];const r={text:TYPO3.lang["buttons.confirm.duplicate_record_changed.cancel"]||"Cancel",btnClass:"btn-default",name:"cancel"},c={text:TYPO3.lang["buttons.confirm.duplicate_record_changed.no"]||"No, just duplicate the original",btnClass:"btn-default",name:"no"},l={text:TYPO3.lang["buttons.confirm.duplicate_record_changed.yes"]||"Yes, save and duplicate this record",btnClass:"btn-primary",name:"yes",active:!0};i=e?[r,l]:[r,c,l];Modal.confirm(a,o,Severity.info,i).addEventListener("button.clicked",(function(e){n(e.target.name,t)}))},deleteAction:function(e,t){t=t||n.deleteActionCallback;const a=$(e.target);n.showDeleteModal(a,t)},deleteActionCallback:function(e,t){Modal.dismiss(),"yes"===e&&n.invokeRecordDeletion(t)},showDeleteModal:function(e,t){const n=TYPO3.lang["label.confirm.delete_record.title"]||"Delete this record?";let a=(TYPO3.lang["label.confirm.delete_record.content"]||"Are you sure you want to delete the record '%s'?").replace("%s",e.data("record-info"));e.data("reference-count-message")&&(a+="\n"+e.data("reference-count-message")),e.data("translation-count-message")&&(a+="\n"+e.data("translation-count-message"));Modal.confirm(n,a,Severity.warning,[{text:TYPO3.lang["buttons.confirm.delete_record.no"]||"Cancel",btnClass:"btn-default",name:"no"},{text:TYPO3.lang["buttons.confirm.delete_record.yes"]||"Yes, delete this record",btnClass:"btn-warning",name:"yes",active:!0}]).addEventListener("button.clicked",(function(n){t(n.target.name,e)}))},enableOptGroup:function(e){const t=e.parentElement;t instanceof HTMLOptGroupElement&&t.querySelectorAll("option:not([hidden]):not([disabled]):not(.hidden)").length&&(t.hidden=!1,t.disabled=!1,t.classList.remove("hidden"))},closeDocument:function(){document.editform.closeDoc.value=1,n.dispatchSubmitEvent(),document.editform.submit()},saveDocument:function(){document.editform.doSave.value=1,n.dispatchSubmitEvent(),document.editform.submit()},dispatchSubmitEvent:function(){const e=document.createEvent("Event");e.initEvent("submit",!1,!0),document.editform.dispatchEvent(e)},initialize:function(e){n.browserUrl=e,DocumentService.ready().then((()=>{n.initializeEvents(),n.Validation.initialize(),n.reinitialize(),$("#t3js-ui-block").remove()}))},invokeRecordDeletion:function(e){window.location.href=e.attr("href")}};if(void 0!==TYPO3.settings.RequireJS&&void 0!==TYPO3.settings.RequireJS.PostInitializationModules["TYPO3/CMS/Backend/FormEngine"])for(const e of TYPO3.settings.RequireJS.PostInitializationModules["TYPO3/CMS/Backend/FormEngine"])window.require([e]);return TYPO3.FormEngine=n,n}()); \ No newline at end of file +import DocumentService from"@typo3/core/document-service.js";import $ from"jquery";import FormEngineValidation from"@typo3/backend/form-engine-validation.js";import Icons from"@typo3/backend/icons.js";import{default as Modal}from"@typo3/backend/modal.js";import*as MessageUtility from"@typo3/backend/utility/message-utility.js";import Severity from"@typo3/backend/severity.js";import*as BackendExceptionModule from"@typo3/backend/backend-exception.js";import InteractionRequestMap from"@typo3/backend/event/interaction-request-map.js";import Utility from"@typo3/backend/utility.js";export default(function(){function e(e,t){t?n.interactionRequestMap.resolveFor(e):n.interactionRequestMap.rejectFor(e)}const t=new Map;t.set("typo3-backend-form-update-value",(e=>{const t=document.querySelector('[name="'+CSS.escape(e.elementName)+'"]'),n=document.querySelector('[data-formengine-input-name="'+CSS.escape(e.elementName)+'"]');FormEngineValidation.updateInputField(e.elementName),null!==t&&(FormEngineValidation.markFieldAsChanged(t),FormEngineValidation.validateField(t)),null!==n&&n!==t&&FormEngineValidation.validateField(n)})),t.set("typo3-backend-form-reload",(e=>{if(!e.confirmation)return void n.saveDocument();const t=Modal.advanced({title:TYPO3.lang["FormEngine.refreshRequiredTitle"],content:TYPO3.lang["FormEngine.refreshRequiredContent"],severity:Severity.warning,staticBackdrop:!0,buttons:[{text:TYPO3.lang["button.cancel"]||"Cancel",active:!0,btnClass:"btn-default",name:"cancel"},{text:TYPO3.lang["button.ok"]||"OK",btnClass:"btn-"+Severity.getCssClass(Severity.warning),name:"ok",trigger:()=>{n.saveDocument()}}]});t.addEventListener("button.clicked",(()=>t.hideModal()))})),t.set("typo3-backend-form-update-bitmask",((e,t)=>{const n=t.target,a=document.editform[e.elementName],o=n.checked!==e.invert,i=Math.pow(2,e.position),r=Math.pow(2,e.total)-i-1;a.value=o?a.value|i:a.value&r,a.dispatchEvent(new Event("change",{bubbles:!0,cancelable:!0}))}));const n={consumeTypes:["typo3.setUrl","typo3.beforeSetUrl","typo3.refresh"],Validation:FormEngineValidation,interactionRequestMap:InteractionRequestMap,formName:TYPO3.settings.FormEngine.formName,openedPopupWindow:null,legacyFieldChangedCb:function(){!$.isFunction(TYPO3.settings.FormEngine.legacyFieldChangedCb)||TYPO3.settings.FormEngine.legacyFieldChangedCb()},browserUrl:"",openPopupWindow:function(e,t,a){return Modal.advanced({type:Modal.types.iframe,content:n.browserUrl+"&mode="+e+"&bparams="+t+(a?"&"+("db"===e?"expandPage":"expandFolder")+"="+a:""),size:Modal.sizes.large})},setSelectOptionFromExternalSource:function(e,t,a,o,i,r){i=String(i);let c,l,s=!1,d=!1;l=n.getFieldElement(e),c=l.get(0);const u=l.get(0);if(null===u||"--div--"===t||u instanceof HTMLOptGroupElement)return;const m=n.getFieldElement(e,"_list",!0);if(m.length>0&&(l=m,c=l.get(0),s=l.prop("multiple")&&"1"!=l.prop("size"),d=!0),s||d){const d=n.getFieldElement(e,"_avail");if(!s){for(const e of c.querySelectorAll("option")){const t=d.find('option[value="'+$.escapeSelector($(e).attr("value"))+'"]');t.length&&(t.removeClass("hidden").prop("disabled",!1),n.enableOptGroup(t.get(0)))}l.empty()}if(i){let e=!1,a=new RegExp("(^|,)"+t+"($|,)");i.match(a)?(l.empty(),e=!0):1==l.find("option").length&&(a=new RegExp("(^|,)"+l.find("option").prop("value")+"($|,)"),i.match(a)&&(l.empty(),e=!0)),e&&void 0!==r&&r.closest("select").querySelectorAll("[disabled]").forEach((function(e){e.classList.remove("hidden"),e.disabled=!1,n.enableOptGroup(e)}))}let m=!0;const f=n.getFieldElement(e,"_mul",!0);if(0==f.length||0==f.val()){for(const e of c.querySelectorAll("option"))if(e.value==t){m=!1;break}if(m&&void 0!==r){r.classList.add("hidden"),r.disabled=!0;const e=r.parentElement;e instanceof HTMLOptGroupElement&&0===e.querySelectorAll("option:not([disabled]):not([hidden]):not(.hidden)").length&&(e.disabled=!0,e.classList.add("hidden"))}}if(m){const e=$("<option></option>");e.attr({value:t,title:o}).text(a),e.appendTo(l),n.updateHiddenFieldValueFromSelect(c,u),n.legacyFieldChangedCb(),FormEngineValidation.markFieldAsChanged(u),n.Validation.validateField(l),n.Validation.validateField(d)}}else{const e=/_(\d+)$/,a=t.toString().match(e);null!=a&&(t=a[1]),l.val(t),n.Validation.validateField(l)}},updateHiddenFieldValueFromSelect:function(e,t){const n=Array.from(e.options).map((e=>e.value));t.value=n.join(","),t.dispatchEvent(new Event("change",{bubbles:!0,cancelable:!0}))},getFormElement:function(e){const t=$('form[name="'+n.formName+'"]:first');if(!e)return t;{const a=n.getFieldElement(e),o=n.getFieldElement(e,"_list");if(a.length>0&&("select-one"===a.prop("type")||o.length>0&&o.prop("type").match(/select-(one|multiple)/)))return t;console.error("Form fields missing: form: "+n.formName+", field name: "+e),alert("Form field is invalid")}},getFieldElement:function(e,t,a){const o=$('form[name="'+n.formName+'"]:first');if(t){let n;switch(t){case"_list":n=$(':input[data-formengine-input-name="'+e+'"]:not([type=hidden])',o);break;case"_avail":n=$(':input[data-relatedfieldname="'+e+'"]',o);break;case"_mul":case"_hr":n=$(':input[type=hidden][data-formengine-input-name="'+e+'"]',o);break;default:n=null}if(n&&n.length>0||!0===a)return n}return $(':input[name="'+e+'"]',o)},initializeEvents:function(){top.TYPO3&&void 0!==top.TYPO3.Backend&&(top.TYPO3.Backend.consumerScope.attach(n),$(window).on("unload",(function(){top.TYPO3.Backend.consumerScope.detach(n)}))),$(document).on("click",".t3js-editform-close",(e=>{e.preventDefault(),n.preventExitIfNotSaved(n.preventExitIfNotSavedCallback)})).on("click",".t3js-editform-view",(e=>{e.preventDefault(),n.previewAction(e,n.previewActionCallback)})).on("click",".t3js-editform-new",(e=>{e.preventDefault(),n.newAction(e,n.newActionCallback)})).on("click",".t3js-editform-duplicate",(e=>{e.preventDefault(),n.duplicateAction(e,n.duplicateActionCallback)})).on("click",".t3js-editform-delete-record",(e=>{e.preventDefault(),n.deleteAction(e,n.deleteActionCallback)})).on("click",".t3js-editform-submitButton",(e=>{const t=$(e.currentTarget),n=t.data("name")||e.currentTarget.name,a=$("<input />").attr("type","hidden").attr("name",n).attr("value","1");t.parents("form").append(a)})).on("change",'.t3-form-field-eval-null-checkbox input[type="checkbox"]',(e=>{$(e.currentTarget).closest(".t3js-formengine-field-item").toggleClass("disabled")})).on("change",'.t3js-form-field-eval-null-placeholder-checkbox input[type="checkbox"]',(e=>{n.toggleCheckboxField($(e.currentTarget)),FormEngineValidation.markFieldAsChanged($(e.currentTarget))})).on("change",(()=>{$(".module-docheader-bar .btn").removeClass("disabled").prop("disabled",!1)})).on("click",".t3js-element-browser",(function(e){e.preventDefault(),e.stopPropagation();const t=$(e.currentTarget),a=t.data("mode"),o=t.data("params"),i=t.data("entryPoint");n.openPopupWindow(a,o,i)})).on("click",'[data-formengine-field-change-event="click"]',(e=>{const t=JSON.parse(e.currentTarget.dataset.formengineFieldChangeItems);n.processOnFieldChange(t,e)})).on("change",'[data-formengine-field-change-event="change"]',(e=>{const t=JSON.parse(e.currentTarget.dataset.formengineFieldChangeItems);n.processOnFieldChange(t,e)})),document.editform.addEventListener("submit",(function(){if(document.editform.closeDoc.value)return;const e=["button[form]",'button[name^="_save"]','a[data-name^="_save"]','button[name="CMD"][value^="save"]','a[data-name="CMD"][data-value^="save"]'].join(","),t=document.querySelector(e);null!==t&&(t.disabled=!0,Icons.getIcon("spinner-circle-dark",Icons.sizes.small).then((function(e){t.querySelector(".t3js-icon").outerHTML=e})))})),window.addEventListener("message",n.handlePostMessage)},consume:function(t){if(!t)throw new BackendExceptionModule.BackendException("No interaction request given",1496589980);const a=$.Deferred();if(t.concernsTypes(n.consumeTypes)){const o=t.outerMostRequest;n.interactionRequestMap.attachFor(o,a),o.isProcessed()?e(o,o.getProcessedData().response):n.hasChange()?n.preventExitIfNotSaved((function(t){o.setProcessedData({response:t}),e(o,t)})):n.interactionRequestMap.resolveFor(o)}return a},handlePostMessage:function(e){if(!MessageUtility.MessageUtility.verifyOrigin(e.origin))throw"Denied message sent by "+e.origin;if("typo3:elementBrowser:elementAdded"===e.data.actionName){if(void 0===e.data.fieldName)throw"fieldName not defined in message";if(void 0===e.data.value)throw"value not defined in message";const t=e.data.label||e.data.value,a=e.data.title||t,o=e.data.exclusiveValues||"";n.setSelectOptionFromExternalSource(e.data.fieldName,e.data.value,t,a,o)}},initializeRemainingCharacterViews:function(){const e=$("[maxlength]").not(".t3js-datetimepicker").not(".t3js-color-picker").not(".t3js-charcounter-initialized");e.on("focus",(e=>{const t=$(e.currentTarget),a=t.parents(".t3js-formengine-field-item:first"),o=n.getCharacterCounterProperties(t);let i=a.find(".t3js-charcounter-wrapper");i.length||(i=$("<div>"),i.addClass("t3js-charcounter-wrapper"),a.append(i)),i.append($("<div />",{class:"t3js-charcounter"}).append($("<span />",{class:o.labelClass}).text(TYPO3.lang["FormEngine.remainingCharacters"].replace("{0}",o.remainingCharacters))))})).on("blur",(e=>{$(e.currentTarget).parents(".t3js-formengine-field-item:first").find(".t3js-charcounter").remove()})).on("keyup",(e=>{const t=$(e.currentTarget),a=t.parents(".t3js-formengine-field-item:first"),o=n.getCharacterCounterProperties(t);a.find(".t3js-charcounter span").removeClass().addClass(o.labelClass).text(TYPO3.lang["FormEngine.remainingCharacters"].replace("{0}",o.remainingCharacters))})),e.addClass("t3js-charcounter-initialized")},getCharacterCounterProperties:function(e){const t=e.val(),n=parseInt(e.attr("maxlength"),10)-t.length-(t.match(/\n/g)||[]).length;let a="";return a=n<15?"badge-danger":n<30?"badge-warning":"badge-info",{remainingCharacters:n,labelClass:"badge "+a}},initializeMinimumCharactersLeftViews:function(){const e=(e,t)=>{const n=t.currentTarget.closest(".t3js-formengine-field-item"),a=n.querySelector(".t3js-charcounter-min"),o=TYPO3.lang["FormEngine.minCharactersLeft"].replace("{0}",e);if(a)a.querySelector("span").innerHTML=o;else{const e=document.createElement("div");e.classList.add("t3js-charcounter-min");const t=document.createElement("span");t.classList.add("badge","badge-danger"),t.innerHTML=o,e.append(t);let a=n.querySelector(".t3js-charcounter-wrapper");a||(a=document.createElement("div"),a.classList.add("t3js-charcounter-wrapper"),n.append(a)),a.prepend(e)}},t=e=>{const t=e.currentTarget.closest(".t3js-formengine-field-item").querySelector(".t3js-charcounter-min");t&&t.remove()};document.querySelectorAll("[minlength]:not(.t3js-datetimepicker):not(.t3js-charcounter-min-initialized)").forEach((a=>{a.addEventListener("focus",(t=>{const o=n.getMinCharacterLeftCount(a);o>0&&e(o,t)})),a.addEventListener("blur",t),a.addEventListener("keyup",(o=>{const i=n.getMinCharacterLeftCount(a);i>0?e(i,o):t(o)}))}))},getMinCharacterLeftCount:function(e){const t=e.value,n=e.minLength,a=t.length;if(0===a)return 0;return n-a-(t.match(/\n/g)||[]).length},initializeNullNoPlaceholderCheckboxes:function(){document.querySelectorAll(".t3-form-field-eval-null-checkbox").forEach((e=>{const t=e.querySelector('input[type="checkbox"]'),n=e.closest(".t3js-formengine-field-item");t.checked||n.classList.add("disabled")}))},initializeNullWithPlaceholderCheckboxes:function(){document.querySelectorAll(".t3js-form-field-eval-null-placeholder-checkbox").forEach((e=>{n.toggleCheckboxField($(e).find('input[type="checkbox"]'),!1)}))},toggleCheckboxField:function(e,t=!0){const n=e.closest(".t3js-formengine-field-item");e.prop("checked")?(n.find(".t3js-formengine-placeholder-placeholder").hide(),n.find(".t3js-formengine-placeholder-formfield").show(),t&&n.find(".t3js-formengine-placeholder-formfield").find(":input").trigger("focus")):(n.find(".t3js-formengine-placeholder-placeholder").show(),n.find(".t3js-formengine-placeholder-formfield").hide())},reinitialize:function(){const e=document.querySelectorAll(".t3js-clearable");e.length>0&&import("@typo3/backend/input/clearable.js").then((function(){e.forEach((e=>e.clearable()))})),n.initializeNullNoPlaceholderCheckboxes(),n.initializeNullWithPlaceholderCheckboxes(),n.initializeLocalizationStateSelector(),n.initializeMinimumCharactersLeftViews(),n.initializeRemainingCharacterViews()},initializeLocalizationStateSelector:function(){document.querySelectorAll(".t3js-l10n-state-container").forEach((e=>{const t=e.closest(".t3js-formengine-field-item")?.querySelector("[data-formengine-input-name]");if(void 0===t)return;const n=e.querySelector('input[type="radio"]:checked').value;"parent"!==n&&"source"!==n||(t.disabled=!0)}))},hasChange:function(){const e=$('form[name="'+n.formName+'"] .has-change').length>0,t=$('[name^="data["].has-change').length>0;return e||t},preventExitIfNotSavedCallback:()=>{n.closeDocument()},preventFollowLinkIfNotSaved:function(e){return n.preventExitIfNotSaved((function(){window.location.href=e})),!1},preventExitIfNotSaved:function(e){if(e=e||n.preventExitIfNotSavedCallback,n.hasChange()){const t=TYPO3.lang["label.confirm.close_without_save.title"]||"Do you want to close without saving?",a=TYPO3.lang["label.confirm.close_without_save.content"]||"You currently have unsaved changes. Are you sure you want to discard these changes?",o=$("<input />").attr("type","hidden").attr("name","_saveandclosedok").attr("value","1"),i=[{text:TYPO3.lang["buttons.confirm.close_without_save.no"]||"No, I will continue editing",btnClass:"btn-default",name:"no"},{text:TYPO3.lang["buttons.confirm.close_without_save.yes"]||"Yes, discard my changes",btnClass:"btn-default",name:"yes"}];0===$(".has-error").length&&i.push({text:TYPO3.lang["buttons.confirm.save_and_close"]||"Save and close",btnClass:"btn-primary",name:"save",active:!0});const r=Modal.confirm(t,a,Severity.warning,i);r.addEventListener("button.clicked",(function(t){"no"===t.target.name?r.hideModal():"yes"===t.target.name?(r.hideModal(),e.call(null,!0)):"save"===t.target.name&&($("form[name="+n.formName+"]").append(o),r.hideModal(),n.saveDocument())}))}else e.call(null,!0)},preventSaveIfHasErrors:function(){if($(".has-error").length>0){const e=TYPO3.lang["label.alert.save_with_error.title"]||"You have errors in your form!",t=TYPO3.lang["label.alert.save_with_error.content"]||"Please check the form, there is at least one error in your form.",n=Modal.confirm(e,t,Severity.error,[{text:TYPO3.lang["buttons.alert.save_with_error.ok"]||"OK",btnClass:"btn-danger",name:"ok"}]);return n.addEventListener("button.clicked",(function(e){"ok"===e.target.name&&n.hideModal()})),!1}return!0},requestFormEngineUpdate:function(e){if(e){const e=Modal.advanced({title:TYPO3.lang["FormEngine.refreshRequiredTitle"],content:TYPO3.lang["FormEngine.refreshRequiredContent"],severity:Severity.warning,staticBackdrop:!0,buttons:[{text:TYPO3.lang["button.cancel"]||"Cancel",active:!0,btnClass:"btn-default",name:"cancel",trigger:()=>{e.hideModal()}},{text:TYPO3.lang["button.ok"]||"OK",btnClass:"btn-"+Severity.getCssClass(Severity.warning),name:"ok",trigger:()=>{n.closeModalsRecursive(),n.saveDocument()}}]})}else n.saveDocument()},processOnFieldChange:function(e,n){e.forEach((e=>{const a=t.get(e.name);a instanceof Function&&a.call(null,e.data||null,n)}))},registerOnFieldChangeHandler:function(e,n){t.has(e)&&console.warn("Handler for onFieldChange name `"+e+"` has been overridden."),t.set(e,n)},closeModalsRecursive:function(){void 0!==Modal.currentModal&&null!==Modal.currentModal&&(Modal.currentModal.addEventListener("typo3-modal-hidden",(function(){n.closeModalsRecursive()})),Modal.currentModal.hideModal())},previewAction:function(e,t){t=t||n.previewActionCallback;const a=e.currentTarget.href,o="isNew"in e.target.dataset,i=$("<input />").attr("type","hidden").attr("name","_savedokview").attr("value","1");n.hasChange()?n.showPreviewModal(a,o,i,t):($("form[name="+n.formName+"]").append(i),window.open("","newTYPO3frontendWindow"),document.editform.submit())},previewActionCallback:function(e,t,a){switch(Modal.dismiss(),e){case"discard":const e=window.open(t,"newTYPO3frontendWindow");e.focus(),Utility.urlsPointToSameServerSideResource(e.location.href,t)&&e.location.reload();break;case"save":$("form[name="+n.formName+"]").append($(a)),window.open("","newTYPO3frontendWindow"),n.saveDocument()}},showPreviewModal:function(e,t,n,a){const o=TYPO3.lang["label.confirm.view_record_changed.title"]||"Do you want to save before viewing?",i={text:TYPO3.lang["buttons.confirm.view_record_changed.cancel"]||"Cancel",btnClass:"btn-default",name:"cancel"},r={text:TYPO3.lang["buttons.confirm.view_record_changed.no-save"]||"View without changes",btnClass:"btn-default",name:"discard"},c={text:TYPO3.lang["buttons.confirm.view_record_changed.save"]||"Save changes and view",btnClass:"btn-primary",name:"save",active:!0};let l=[],s="";t?(l=[i,c],s=TYPO3.lang["label.confirm.view_record_changed.content.is-new-page"]||"You need to save your changes before viewing the page. Do you want to save and view them now?"):(l=[i,r,c],s=TYPO3.lang["label.confirm.view_record_changed.content"]||"You currently have unsaved changes. You can either discard these changes or save and view them.");const d=Modal.confirm(o,s,Severity.info,l);d.addEventListener("button.clicked",(function(t){a(t.target.name,e,n,d)}))},newAction:function(e,t){t=t||n.newActionCallback;const a=$("<input />").attr("type","hidden").attr("name","_savedoknew").attr("value","1"),o="isNew"in e.target.dataset;n.hasChange()?n.showNewModal(o,a,t):($("form[name="+n.formName+"]").append(a),document.editform.submit())},newActionCallback:function(e,t){const a=$("form[name="+n.formName+"]");switch(Modal.dismiss(),e){case"no":a.append(t),document.editform.submit();break;case"yes":a.append(t),n.saveDocument()}},showNewModal:function(e,t,n){const a=TYPO3.lang["label.confirm.new_record_changed.title"]||"Do you want to save before adding?",o=TYPO3.lang["label.confirm.new_record_changed.content"]||"You need to save your changes before creating a new record. Do you want to save and create now?";let i=[];const r={text:TYPO3.lang["buttons.confirm.new_record_changed.cancel"]||"Cancel",btnClass:"btn-default",name:"cancel"},c={text:TYPO3.lang["buttons.confirm.new_record_changed.no"]||"No, just add",btnClass:"btn-default",name:"no"},l={text:TYPO3.lang["buttons.confirm.new_record_changed.yes"]||"Yes, save and create now",btnClass:"btn-primary",name:"yes",active:!0};i=e?[r,l]:[r,c,l];Modal.confirm(a,o,Severity.info,i).addEventListener("button.clicked",(function(e){n(e.target.name,t)}))},duplicateAction:function(e,t){t=t||n.duplicateActionCallback;const a=$("<input />").attr("type","hidden").attr("name","_duplicatedoc").attr("value","1"),o="isNew"in e.target.dataset;n.hasChange()?n.showDuplicateModal(o,a,t):($("form[name="+n.formName+"]").append(a),document.editform.submit())},duplicateActionCallback:function(e,t){const a=$("form[name="+n.formName+"]");switch(Modal.dismiss(),e){case"no":a.append(t),document.editform.submit();break;case"yes":a.append(t),n.saveDocument()}},showDuplicateModal:function(e,t,n){const a=TYPO3.lang["label.confirm.duplicate_record_changed.title"]||"Do you want to save before duplicating this record?",o=TYPO3.lang["label.confirm.duplicate_record_changed.content"]||"You currently have unsaved changes. Do you want to save your changes before duplicating this record?";let i=[];const r={text:TYPO3.lang["buttons.confirm.duplicate_record_changed.cancel"]||"Cancel",btnClass:"btn-default",name:"cancel"},c={text:TYPO3.lang["buttons.confirm.duplicate_record_changed.no"]||"No, just duplicate the original",btnClass:"btn-default",name:"no"},l={text:TYPO3.lang["buttons.confirm.duplicate_record_changed.yes"]||"Yes, save and duplicate this record",btnClass:"btn-primary",name:"yes",active:!0};i=e?[r,l]:[r,c,l];Modal.confirm(a,o,Severity.info,i).addEventListener("button.clicked",(function(e){n(e.target.name,t)}))},deleteAction:function(e,t){t=t||n.deleteActionCallback;const a=$(e.target);n.showDeleteModal(a,t)},deleteActionCallback:function(e,t){Modal.dismiss(),"yes"===e&&n.invokeRecordDeletion(t)},showDeleteModal:function(e,t){const n=TYPO3.lang["label.confirm.delete_record.title"]||"Delete this record?";let a=(TYPO3.lang["label.confirm.delete_record.content"]||"Are you sure you want to delete the record '%s'?").replace("%s",e.data("record-info"));e.data("reference-count-message")&&(a+="\n"+e.data("reference-count-message")),e.data("translation-count-message")&&(a+="\n"+e.data("translation-count-message"));Modal.confirm(n,a,Severity.warning,[{text:TYPO3.lang["buttons.confirm.delete_record.no"]||"Cancel",btnClass:"btn-default",name:"no"},{text:TYPO3.lang["buttons.confirm.delete_record.yes"]||"Yes, delete this record",btnClass:"btn-warning",name:"yes",active:!0}]).addEventListener("button.clicked",(function(n){t(n.target.name,e)}))},enableOptGroup:function(e){const t=e.parentElement;t instanceof HTMLOptGroupElement&&t.querySelectorAll("option:not([hidden]):not([disabled]):not(.hidden)").length&&(t.hidden=!1,t.disabled=!1,t.classList.remove("hidden"))},closeDocument:function(){document.editform.closeDoc.value=1,n.dispatchSubmitEvent(),document.editform.submit()},saveDocument:function(){document.editform.doSave.value=1,n.dispatchSubmitEvent(),document.editform.submit()},dispatchSubmitEvent:function(){const e=document.createEvent("Event");e.initEvent("submit",!1,!0),document.editform.dispatchEvent(e)},initialize:function(e){n.browserUrl=e,DocumentService.ready().then((()=>{n.initializeEvents(),n.Validation.initialize(),n.reinitialize(),$("#t3js-ui-block").remove()}))},invokeRecordDeletion:function(e){window.location.href=e.attr("href")}};if(void 0!==TYPO3.settings.RequireJS&&void 0!==TYPO3.settings.RequireJS.PostInitializationModules["TYPO3/CMS/Backend/FormEngine"])for(const e of TYPO3.settings.RequireJS.PostInitializationModules["TYPO3/CMS/Backend/FormEngine"])window.require([e]);return TYPO3.FormEngine=n,n}()); \ No newline at end of file diff --git a/typo3/sysext/backend/Resources/Public/JavaScript/form-engine/field-control/password-generator.js b/typo3/sysext/backend/Resources/Public/JavaScript/form-engine/field-control/password-generator.js index 9ee0e030e8e590ca4b0f4d69a9fcb31d77f3befb..81c1568940189e6b6bfaf4f03aa8be3dcae106ce 100644 --- a/typo3/sysext/backend/Resources/Public/JavaScript/form-engine/field-control/password-generator.js +++ b/typo3/sysext/backend/Resources/Public/JavaScript/form-engine/field-control/password-generator.js @@ -10,4 +10,4 @@ * * The TYPO3 project - inspiring people to share! */ -import DocumentService from"@typo3/core/document-service.js";import SecurityUtility from"@typo3/core/security-utility.js";import FormEngineValidation from"@typo3/backend/form-engine-validation.js";import AjaxRequest from"@typo3/core/ajax/ajax-request.js";import Notification from"@typo3/backend/notification.js";class PasswordGenerator{constructor(e){this.securityUtility=null,this.controlElement=null,this.humanReadableField=null,this.hiddenField=null,this.passwordRules=null,this.securityUtility=new SecurityUtility,DocumentService.ready().then((()=>{if(this.controlElement=document.getElementById(e),this.humanReadableField=document.querySelector('input[data-formengine-input-name="'+this.controlElement.dataset.itemName+'"]'),this.hiddenField=document.querySelector('input[name="'+this.controlElement.dataset.itemName+'"]'),this.passwordRules=JSON.parse(this.controlElement.dataset.passwordRules||"{}"),!this.controlElement.dataset.allowEdit&&(this.humanReadableField.disabled=!0,this.humanReadableField.readOnly=!0,this.humanReadableField.isClearable||this.humanReadableField.classList.contains("t3js-clearable"))){this.humanReadableField.classList.remove("t3js-clearable");const e=this.humanReadableField.closest("div.form-control-clearable");if(e){e.classList.remove("form-control-clearable");const t=e.querySelector("button.close");t&&e.removeChild(t)}}this.controlElement.addEventListener("click",this.generatePassword.bind(this))}))}generatePassword(e){e.preventDefault(),new AjaxRequest(TYPO3.settings.ajaxUrls.password_generate).post({passwordRules:this.passwordRules}).then((async e=>{const t=await e.resolve();!0===t.success?(this.humanReadableField.type="text",this.humanReadableField.value=t.password,this.humanReadableField.dispatchEvent(new Event("change")),this.humanReadableField.value=this.hiddenField.value,FormEngineValidation.validateField(this.humanReadableField),FormEngineValidation.markFieldAsChanged(this.humanReadableField)):Notification.warning(t.message||"No password was generated")})).catch((()=>{Notification.error("Password could not be generated")}))}}export default PasswordGenerator; \ No newline at end of file +import DocumentService from"@typo3/core/document-service.js";import SecurityUtility from"@typo3/core/security-utility.js";import FormEngineValidation from"@typo3/backend/form-engine-validation.js";import AjaxRequest from"@typo3/core/ajax/ajax-request.js";import Notification from"@typo3/backend/notification.js";class PasswordGenerator{constructor(e){this.securityUtility=null,this.controlElement=null,this.humanReadableField=null,this.hiddenField=null,this.passwordRules=null,this.securityUtility=new SecurityUtility,DocumentService.ready().then((()=>{if(this.controlElement=document.getElementById(e),this.humanReadableField=document.querySelector('input[data-formengine-input-name="'+this.controlElement.dataset.itemName+'"]'),this.hiddenField=document.querySelector('input[name="'+this.controlElement.dataset.itemName+'"]'),this.passwordRules=JSON.parse(this.controlElement.dataset.passwordRules||"{}"),!this.controlElement.dataset.allowEdit&&(this.humanReadableField.disabled=!0,this.humanReadableField.readOnly=!0,this.humanReadableField.isClearable||this.humanReadableField.classList.contains("t3js-clearable"))){this.humanReadableField.classList.remove("t3js-clearable");const e=this.humanReadableField.closest("div.form-control-clearable-wrapper");if(e){e.classList.remove("form-control-clearable");const t=e.querySelector("button.close");t&&e.removeChild(t)}}this.controlElement.addEventListener("click",this.generatePassword.bind(this))}))}generatePassword(e){e.preventDefault(),new AjaxRequest(TYPO3.settings.ajaxUrls.password_generate).post({passwordRules:this.passwordRules}).then((async e=>{const t=await e.resolve();!0===t.success?(this.humanReadableField.type="text",this.humanReadableField.value=t.password,this.humanReadableField.dispatchEvent(new Event("change")),this.humanReadableField.value=this.hiddenField.value,FormEngineValidation.validateField(this.humanReadableField),FormEngineValidation.markFieldAsChanged(this.humanReadableField)):Notification.warning(t.message||"No password was generated")})).catch((()=>{Notification.error("Password could not be generated")}))}}export default PasswordGenerator; \ No newline at end of file diff --git a/typo3/sysext/backend/Resources/Public/JavaScript/input/clearable.js b/typo3/sysext/backend/Resources/Public/JavaScript/input/clearable.js index 44ff54b0714ba304b8fac3a30b7d9bcf1ae20e1a..5caddf26eb0a20d286be7caaa565e99fafba938b 100644 --- a/typo3/sysext/backend/Resources/Public/JavaScript/input/clearable.js +++ b/typo3/sysext/backend/Resources/Public/JavaScript/input/clearable.js @@ -10,4 +10,4 @@ * * The TYPO3 project - inspiring people to share! */ -class Clearable{constructor(){"function"!=typeof HTMLInputElement.prototype.clearable&&this.registerClearable()}static createCloseButton(){const e=document.createElement("button");return e.type="button",e.tabIndex=-1,e.innerHTML='<span class="t3js-icon icon icon-size-small icon-state-default icon-actions-close" data-identifier="actions-close">\n <span class="icon-markup">\n <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 16 16">\n <path\n d="M11.9 5.5L9.4 8l2.5 2.5c.2.2.2.5 0\n .7l-.7.7c-.2.2-.5.2-.7 0L8 9.4l-2.5 2.5c-.2.2-.5.2-.7\n 0l-.7-.7c-.2-.2-.2-.5 0-.7L6.6 8 4.1 5.5c-.2-.2-.2-.5\n 0-.7l.7-.7c.2-.2.5-.2.7 0L8 6.6l2.5-2.5c.2-.2.5-.2.7\n 0l.7.7c.2.2.2.5 0 .7z"\n class="icon-color"/>\n </svg>\n </span>\n </span>',e.style.visibility="hidden",e.classList.add("close"),e}registerClearable(){HTMLInputElement.prototype.clearable=function(e={}){if(this.isClearable)return;if("object"!=typeof e)throw new Error("Passed options must be an object, "+typeof e+" given");const t=document.createElement("div");t.classList.add("form-control-clearable"),this.parentNode.insertBefore(t,this),t.appendChild(this);const n=Clearable.createCloseButton(),s=()=>{n.style.visibility=0===this.value.length?"hidden":"visible"};n.addEventListener("click",(t=>{t.preventDefault(),this.value="","function"==typeof e.onClear&&e.onClear(this),this.dispatchEvent(new Event("change",{bubbles:!0,cancelable:!0})),s()})),t.appendChild(n),this.addEventListener("focus",s),this.addEventListener("keyup",s),s(),this.isClearable=!0}}}export default new Clearable; \ No newline at end of file +class Clearable{constructor(){"function"!=typeof HTMLInputElement.prototype.clearable&&this.registerClearable()}static createCloseButton(){const e=document.createElement("button");return e.type="button",e.tabIndex=-1,e.innerHTML='<span class="t3js-icon icon icon-size-small icon-state-default icon-actions-close" data-identifier="actions-close">\n <span class="icon-markup">\n <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 16 16">\n <path\n d="M11.9 5.5L9.4 8l2.5 2.5c.2.2.2.5 0\n .7l-.7.7c-.2.2-.5.2-.7 0L8 9.4l-2.5 2.5c-.2.2-.5.2-.7\n 0l-.7-.7c-.2-.2-.2-.5 0-.7L6.6 8 4.1 5.5c-.2-.2-.2-.5\n 0-.7l.7-.7c.2-.2.5-.2.7 0L8 6.6l2.5-2.5c.2-.2.5-.2.7\n 0l.7.7c.2.2.2.5 0 .7z"\n class="icon-color"/>\n </svg>\n </span>\n </span>',e.style.visibility="hidden",e.classList.add("close"),e}registerClearable(){HTMLInputElement.prototype.clearable=function(e={}){if(this.isClearable)return;if("object"!=typeof e)throw new Error("Passed options must be an object, "+typeof e+" given");this.classList.add("form-control-clearable");const t=document.createElement("div");t.classList.add("form-control-clearable-wrapper"),this.parentNode.insertBefore(t,this),t.appendChild(this);const n=Clearable.createCloseButton(),s=()=>{n.style.visibility=0===this.value.length?"hidden":"visible"};n.addEventListener("click",(t=>{t.preventDefault(),this.value="","function"==typeof e.onClear&&e.onClear(this),this.dispatchEvent(new Event("change",{bubbles:!0,cancelable:!0})),s()})),t.appendChild(n),this.addEventListener("focus",s),this.addEventListener("keyup",s),s(),this.isClearable=!0}}}export default new Clearable; \ No newline at end of file diff --git a/typo3/sysext/belog/Resources/Private/Partials/Content/Filter.html b/typo3/sysext/belog/Resources/Private/Partials/Content/Filter.html index 958079076e5b5d9ab0f18270ca9efa4fb2196366..3edf0b5c069c54cf8b9b9a48e6d9cae429d72f48 100644 --- a/typo3/sysext/belog/Resources/Private/Partials/Content/Filter.html +++ b/typo3/sysext/belog/Resources/Private/Partials/Content/Filter.html @@ -5,9 +5,9 @@ data-namespace-typo3-fluid="true"> <f:form object="{constraint}" action="list" name="constraint" class="belog-filter-form"> - <div class="row row-cols-auto align-items-end g-3 mb-4"> + <div class="form-row"> - <div class="col"> + <div class="form-group"> <label for="belog-users" class="form-label"><f:translate key="users" /></label> <f:form.select property="userOrGroup" @@ -17,7 +17,7 @@ /> </div> - <div class="col"> + <div class="form-group"> <label for="belog-max" class="form-label"><f:translate key="max" /></label> <f:form.select property="number" @@ -28,7 +28,7 @@ </div> <f:if condition="{showWorkspaceSelector}"> - <div class="col"> + <div class="form-group"> <label for="belog-workspaces" class="form-label"><f:translate key="workspace" /></label> <f:form.select property="workspaceUid" @@ -39,7 +39,7 @@ </div> </f:if> - <div class="col"> + <div class="form-group"> <label for="belog-pageId" class="form-label"><f:translate key="chLog_menuPageId" /></label> <div class="input-group"> <f:form.textfield @@ -62,7 +62,7 @@ </div> <f:if condition="{pageId}"> - <div class="col"> + <div class="form-group"> <label for="belog-depth" class="form-label"><f:translate key="chLog_menuDepth" /></label> <f:form.select property="depth" @@ -73,7 +73,7 @@ </div> </f:if> - <div class="col"> + <div class="form-group"> <label for="belog-channel" class="form-label"><f:translate key="channel" /></label> <f:form.select property="channel" @@ -86,7 +86,7 @@ /> </div> - <div class="col"> + <div class="form-group"> <label for="belog-level" class="form-label"><f:translate key="levels" /></label> <f:form.select property="level" @@ -99,7 +99,7 @@ /> </div> - <div class="col"> + <div class="form-group"> <label for="manualDateStart" class="form-label"><f:translate key="LLL:EXT:core/Resources/Private/Language/locallang_common.xlf:from" /></label> <div class="input-group"> <f:form.textfield @@ -107,7 +107,7 @@ value="{f:if(condition: constraint.manualDateStart, then: \"{f:format.date(format:'{settings.dateTimeFormat}', date: '{constraint.manualDateStart}')}\")}" id="manualDateStart" additionalAttributes="{'autocomplete': 'off'}" - class="form-control t3js-datetimepicker t3js-clearable" + class="form-control form-control-clearable t3js-datetimepicker t3js-clearable" data="{date-type: 'datetime'}" /> <f:form.hidden @@ -120,7 +120,7 @@ </div> </div> - <div class="col"> + <div class="form-group"> <label for="manualDateStop" class="form-label"><f:translate key="LLL:EXT:core/Resources/Private/Language/locallang_common.xlf:to" /></label> <div class="input-group"> <f:form.textfield @@ -128,7 +128,7 @@ value="{f:format.date(format:'{settings.dateTimeFormat}', date: '{constraint.manualDateStop}')}" additionalAttributes="{'autocomplete': 'off'}" id="manualDateStop" - class="form-control t3js-datetimepicker t3js-clearable" + class="form-control form-control-clearable t3js-datetimepicker t3js-clearable" data="{date-type: 'datetime'}" /> <f:form.hidden @@ -141,8 +141,8 @@ </div> </div> - <div class="col"> - <f:form.button type="submit" name="operation" value="filter" class="btn btn-light">{f:translate(key: 'set')}</f:form.button> + <div class="form-group align-self-end"> + <f:form.button type="submit" name="operation" value="filter" class="btn btn-default">{f:translate(key: 'set')}</f:form.button> <f:form.button type="submit" name="operation" value="reset-filters" class="btn btn-link">{f:translate(key: 'reset')}</f:form.button> </div> </div> diff --git a/typo3/sysext/beuser/Resources/Private/Partials/BackendUser/Filter.html b/typo3/sysext/beuser/Resources/Private/Partials/BackendUser/Filter.html index ca3c5fa0939a6f25390a602a238409acdc225c2b..a7d1fdc865ba21ab9a6d4afc517dc7b92acdeb2e 100644 --- a/typo3/sysext/beuser/Resources/Private/Partials/BackendUser/Filter.html +++ b/typo3/sysext/beuser/Resources/Private/Partials/BackendUser/Filter.html @@ -4,8 +4,8 @@ > <f:form action="index" objectName="demand" object="{demand}"> - <div class="row row-cols-auto align-items-end g-3 mb-4"> - <div class="col"> + <div class="form-row"> + <div class="form-group"> <label for="tx_Beuser_username" class="form-label"><f:translate key="userName">Username</f:translate></label> <f:form.textfield id="tx_Beuser_username" @@ -13,7 +13,7 @@ property="userName" /> </div> - <div class="col"> + <div class="form-group"> <label for="tx_Beuser_usertype" class="form-label"><f:translate key="admin">Admin</f:translate></label> <f:form.select id="tx_Beuser_usertype" @@ -22,7 +22,7 @@ options="{0: '{f:translate(key:\"both\")}', 1: '{f:translate(key:\"adminOnly\")}', 2: '{f:translate(key:\"normalUserOnly\")}'}" /> </div> - <div class="col"> + <div class="form-group"> <label for="tx_Beuser_status" class="form-label"><f:translate key="status">Status</f:translate></label> <f:form.select id="tx_Beuser_status" @@ -31,7 +31,7 @@ options="{0: '{f:translate(key:\"both\")}', 1: '{f:translate(key:\"activeOnly\")}', 2: '{f:translate(key:\"inactiveOnly\")}'}" /> </div> - <div class="col"> + <div class="form-group"> <label for="tx_Beuser_logins" class="form-label"><f:translate key="login">Login</f:translate></label> <f:form.select id="tx_Beuser_logins" @@ -40,7 +40,7 @@ options="{0: '{f:translate(key:\"both\")}', 1: '{f:translate(key:\"loginBefore\")}', 2: '{f:translate(key:\"neverLoggedIn\")}'}" /> </div> - <div class="col"> + <div class="form-group"> <label for="tx_beuser_backendUserGroup" class="form-label"><f:translate key="backendUserGroup">User Group</f:translate></label> <f:form.select id="tx_beuser_backendUserGroup" @@ -51,8 +51,8 @@ optionValueField="uid" /> </div> - <div class="col"> - <f:form.button type="submit" name="operation" value="filter" class="btn btn-light">{f:translate(key: 'filter')}</f:form.button> + <div class="form-group align-self-end"> + <f:form.button type="submit" name="operation" value="filter" class="btn btn-default">{f:translate(key: 'filter')}</f:form.button> <f:form.button type="submit" name="operation" value="reset-filters" class="btn btn-link">{f:translate(key: 'reset')}</f:form.button> </div> </div> diff --git a/typo3/sysext/beuser/Resources/Private/Partials/BackendUserGroup/Filter.html b/typo3/sysext/beuser/Resources/Private/Partials/BackendUserGroup/Filter.html index a5d6dc2c6fa357cc9d3fcf04101463961437f5a8..8c3669940d10000f00baf232dda610a864073df5 100644 --- a/typo3/sysext/beuser/Resources/Private/Partials/BackendUserGroup/Filter.html +++ b/typo3/sysext/beuser/Resources/Private/Partials/BackendUserGroup/Filter.html @@ -4,16 +4,16 @@ > <f:form action="groups" objectName="userGroupDto" object="{userGroupDto}"> - <div class="row row-cols-auto align-items-end g-3 mb-4"> - <div class="col"> + <div class="form-row"> + <div class="form-group"> <label for="tx_Beugroups_title" class="form-label"><f:translate key="userGroupTitle" /></label> <f:form.textfield id="tx_Beugroups_title" class="form-control" property="title"/> </div> - <div class="col"> - <f:form.button type="submit" name="operation" value="filter" class="btn btn-light">{f:translate(key: 'filter')}</f:form.button> + <div class="form-group align-self-end"> + <f:form.button type="submit" name="operation" value="filter" class="btn btn-default">{f:translate(key: 'filter')}</f:form.button> <f:form.button type="submit" name="operation" value="reset-filters" class="btn btn-link">{f:translate(key: 'reset')}</f:form.button> </div> </div> diff --git a/typo3/sysext/beuser/Resources/Private/Templates/BackendUser/List.html b/typo3/sysext/beuser/Resources/Private/Templates/BackendUser/List.html index 3f7a488c4d540d402df12edd3ba1d26c5fb50b86..1a4b083ae2c24bef952d01dc6d85d04fb1718bc7 100644 --- a/typo3/sysext/beuser/Resources/Private/Templates/BackendUser/List.html +++ b/typo3/sysext/beuser/Resources/Private/Templates/BackendUser/List.html @@ -55,16 +55,14 @@ </tbody> </table> </div> - <div class="mb-4"> - <f:link.action action="compare" title="{f:translate(key: 'compareUserList', default: 'Compare user list')}" class="btn btn-default t3js-acceptance-compare"> - <core:icon identifier="actions-code-compare" /> - {f:translate(key: 'compareUserList', default: 'Compare user list')} - </f:link.action> - <f:link.action action="removeAllFromCompareList" class="btn btn-default"> - <core:icon identifier="actions-selection-delete" /> - {f:translate(key: 'clearCompareList')} - </f:link.action> - </div> + <f:link.action action="compare" title="{f:translate(key: 'compareUserList', default: 'Compare user list')}" class="btn btn-default t3js-acceptance-compare"> + <core:icon identifier="actions-code-compare" /> + {f:translate(key: 'compareUserList', default: 'Compare user list')} + </f:link.action> + <f:link.action action="removeAllFromCompareList" class="btn btn-default"> + <core:icon identifier="actions-selection-delete" /> + {f:translate(key: 'clearCompareList')} + </f:link.action> <h2>{f:translate(key: 'section.allUsers', default: 'All backend users')}</h2> </f:if> diff --git a/typo3/sysext/beuser/Resources/Private/Templates/BackendUser/Show.html b/typo3/sysext/beuser/Resources/Private/Templates/BackendUser/Show.html index c7262185449ddb25b9de5747d50bf7c47291b902..a6bd288eb4745745d5fd2eb1942f3ae66c40431c 100644 --- a/typo3/sysext/beuser/Resources/Private/Templates/BackendUser/Show.html +++ b/typo3/sysext/beuser/Resources/Private/Templates/BackendUser/Show.html @@ -76,44 +76,44 @@ <div class="row"> <div class="col-lg-4"> - <h2><f:translate key="LLL:EXT:core/Resources/Private/Language/locallang_tca.xlf:be_groups.subgroup" /></h2> + <h2 class="headline-spaced"><f:translate key="LLL:EXT:core/Resources/Private/Language/locallang_tca.xlf:be_groups.subgroup" /></h2> <f:render partial="Compare/Information" section="groups" arguments="{groups:data.groups}"/> </div> <div class="col-lg-4"> - <h2><f:translate key="allowedLanguages" /></h2> + <h2 class="headline-spaced"><f:translate key="allowedLanguages" /></h2> <f:render partial="Compare/Information" section="languages" arguments="{languages:data.languages}"/> </div> <div class="col-lg-4"> - <h2><f:translate key="dbMountPoints" /></h2> + <h2 class="headline-spaced"><f:translate key="dbMountPoints" /></h2> <f:render partial="Compare/Information" section="dbMounts" arguments="{dbMounts:data.dbMounts}"/> - <h2><f:translate key="fileMounts" /></h2> + <h2 class="headline-spaced"><f:translate key="fileMounts" /></h2> <f:render partial="Compare/Information" section="fileMounts" arguments="{fileMounts:data.fileMounts}"/> </div> </div> <div class="row"> <div class="col-md-6"> - <h2>{f:translate(key:'LLL:EXT:core/Resources/Private/Language/locallang_tca.xlf:be_groups.pagetypes_select')}</h2> + <h2 class="headline-spaced">{f:translate(key:'LLL:EXT:core/Resources/Private/Language/locallang_tca.xlf:be_groups.pagetypes_select')}</h2> <f:render partial="Compare/Information" section="pageTypes" arguments="{pageTypes:data.pageTypes}" /> - <h2><f:translate key="permissions" /></h2> + <h2 class="headline-spaced"><f:translate key="permissions" /></h2> <f:render partial="Compare/Information" section="modules" arguments="{showTitle:1,modules:data.modules}"/> - <h2>{f:translate(key:'compare.tables')}</h2> + <h2 class="headline-spaced">{f:translate(key:'compare.tables')}</h2> <f:render partial="Compare/Information" section="tables" arguments="{showTitle:1,tables:data.tables}"/> - <h2>{f:translate(key:'LLL:EXT:core/Resources/Private/Language/locallang_tca.xlf:category_perms')}</h2> + <h2 class="headline-spaced">{f:translate(key:'LLL:EXT:core/Resources/Private/Language/locallang_tca.xlf:category_perms')}</h2> <f:render partial="Compare/Information" section="categories" arguments="{categories:data.categories}"/> - <h2>{f:translate(key:'LLL:EXT:core/Resources/Private/Language/locallang_tca.xlf:TSconfig')}</h2> + <h2 class="headline-spaced">{f:translate(key:'LLL:EXT:core/Resources/Private/Language/locallang_tca.xlf:TSconfig')}</h2> <f:render partial="Compare/Information" section="tsconfig" arguments="{tsconfig:data.tsconfig,id:data.user.uid}" /> </div> <div class="col-md-6"> - <h2>{f:translate(key:'LLL:EXT:core/Resources/Private/Language/locallang_tca.xlf:be_groups.non_exclude_fields')}</h2> + <h2 class="headline-spaced">{f:translate(key:'LLL:EXT:core/Resources/Private/Language/locallang_tca.xlf:be_groups.non_exclude_fields')}</h2> <f:render partial="Compare/Information" section="nonExcludeFields" arguments="{nonExcludeFields:data.non_exclude_fields, id:data.user.uid}"/> - <h2>{f:translate(key:'LLL:EXT:core/Resources/Private/Language/locallang_tca.xlf:be_groups.fileoper_perms')}</h2> + <h2 class="headline-spaced">{f:translate(key:'LLL:EXT:core/Resources/Private/Language/locallang_tca.xlf:be_groups.fileoper_perms')}</h2> <f:render partial="Compare/Information" section="fileFolderPermissions" arguments="{fileFolderPermissions:data.fileFolderPermissions}" /> </div> </div> diff --git a/typo3/sysext/beuser/Resources/Private/Templates/BackendUserGroup/List.html b/typo3/sysext/beuser/Resources/Private/Templates/BackendUserGroup/List.html index 30d31e70132c717db1a329779f4c73dd0232123d..0627a08c539c3150d91b39b38cc3d9ef07f91f73 100644 --- a/typo3/sysext/beuser/Resources/Private/Templates/BackendUserGroup/List.html +++ b/typo3/sysext/beuser/Resources/Private/Templates/BackendUserGroup/List.html @@ -44,16 +44,14 @@ </tbody> </table> </div> - <div class="mb-4"> - <f:link.action action="compareGroups" class="btn btn-default t3js-acceptance-compare"> - <core:icon identifier="actions-code-compare" /> - {f:translate(key: 'compareBackendUsersGroups')} - </f:link.action> - <f:link.action action="removeAllGroupsFromCompareList" class="btn btn-default"> - <core:icon identifier="actions-selection-delete" /> - {f:translate(key: 'clearCompareList')} - </f:link.action> - </div> + <f:link.action action="compareGroups" class="btn btn-default t3js-acceptance-compare"> + <core:icon identifier="actions-code-compare" /> + {f:translate(key: 'compareBackendUsersGroups')} + </f:link.action> + <f:link.action action="removeAllGroupsFromCompareList" class="btn btn-default"> + <core:icon identifier="actions-selection-delete" /> + {f:translate(key: 'clearCompareList')} + </f:link.action> <h2>{f:translate(key: 'section.allUserGroups', default: 'All backend user groups')}</h2> </f:if> diff --git a/typo3/sysext/beuser/Resources/Private/Templates/Permission/Edit.html b/typo3/sysext/beuser/Resources/Private/Templates/Permission/Edit.html index b6bd244b9b9ece83edc1f3fe9b1b128a1dc696f9..1ffac442f9092ffee3b71469f8e2df8b00f4eb3c 100644 --- a/typo3/sysext/beuser/Resources/Private/Templates/Permission/Edit.html +++ b/typo3/sysext/beuser/Resources/Private/Templates/Permission/Edit.html @@ -22,17 +22,17 @@ <form action="{formAction}" method="post" name="editform" id="PermissionControllerEdit"> - <div class="row row-cols-auto align-items-end g-3 mb-4"> - <div class="col"> - <label for="selectOwner"><f:translate key="LLL:EXT:beuser/Resources/Private/Language/locallang_mod_permission.xlf:Owner" /></label> + <div class="form-row"> + <div class="form-group"> + <label class="form-label" for="selectOwner"><f:translate key="LLL:EXT:beuser/Resources/Private/Language/locallang_mod_permission.xlf:Owner" /></label> <select class="form-select" name="data[pages][{id}][perms_userid]" id="selectOwner"> <f:for each="{beUserData}" key="userId" as="user"> <option value="{userId}" {f:if(condition: '{userId} == {currentBeUser}', then: 'selected')}>{user}</option> </f:for> </select> </div> - <div class="col"> - <label for="selectGroup"><f:translate key="LLL:EXT:beuser/Resources/Private/Language/locallang_mod_permission.xlf:Group" /></label> + <div class="form-group"> + <label class="form-label" for="selectGroup"><f:translate key="LLL:EXT:beuser/Resources/Private/Language/locallang_mod_permission.xlf:Group" /></label> <f:if condition="{f:count(subject:beGroupData)} > 1"> <f:then> <select class="form-select" name="data[pages][{id}][perms_groupid]" id="selectGroup"> @@ -46,8 +46,8 @@ </f:else> </f:if> </div> - <div class="col"> - <label for="recursionLevel"><f:translate key="LLL:EXT:beuser/Resources/Private/Language/locallang_mod_permission.xlf:Depth" /></label> + <div class="form-group"> + <label class="form-label" for="recursionLevel"><f:translate key="LLL:EXT:beuser/Resources/Private/Language/locallang_mod_permission.xlf:Depth" /></label> <select class="form-select" name="mirror[pages][{id}]" id="recursionLevel"> <f:for each="{recursiveSelectOptions}" key="depth" as="depthLabel"> <option value="{depth}" {f:if(condition: '{depth} == {currentBeUser}', then: 'selected')}>{depthLabel}</option> @@ -71,27 +71,87 @@ <tbody> <tr> <td><strong><f:translate key="LLL:EXT:beuser/Resources/Private/Language/locallang_mod_permission.xlf:Owner" /></strong></td> - <td><input type="checkbox" name="check[perms_user][]" value="{base ^ 0}" data-check-change-permissions="check[perms_user],data[pages][{id}][perms_user]" /></td> - <td><input type="checkbox" name="check[perms_user][]" value="{base ^ 4}" data-check-change-permissions="check[perms_user],data[pages][{id}][perms_user]" /></td> - <td><input type="checkbox" name="check[perms_user][]" value="{base ^ 1}" data-check-change-permissions="check[perms_user],data[pages][{id}][perms_user]" /></td> - <td><input type="checkbox" name="check[perms_user][]" value="{base ^ 2}" data-check-change-permissions="check[perms_user],data[pages][{id}][perms_user]" /></td> - <td><input type="checkbox" name="check[perms_user][]" value="{base ^ 3}" data-check-change-permissions="check[perms_user],data[pages][{id}][perms_user]" /></td> + <td> + <div class="form-check form-check-type-toggle"> + <input class="form-check-input" type="checkbox" name="check[perms_user][]" value="{base ^ 0}" data-check-change-permissions="check[perms_user],data[pages][{id}][perms_user]" /> + </div> + </td> + <td> + <div class="form-check form-check-type-toggle"> + <input class="form-check-input" type="checkbox" name="check[perms_user][]" value="{base ^ 4}" data-check-change-permissions="check[perms_user],data[pages][{id}][perms_user]" /> + </div> + </td> + <td> + <div class="form-check form-check-type-toggle"> + <input class="form-check-input" type="checkbox" name="check[perms_user][]" value="{base ^ 1}" data-check-change-permissions="check[perms_user],data[pages][{id}][perms_user]" /> + </div> + </td> + <td> + <div class="form-check form-check-type-toggle"> + <input class="form-check-input" type="checkbox" name="check[perms_user][]" value="{base ^ 2}" data-check-change-permissions="check[perms_user],data[pages][{id}][perms_user]" /> + </div> + </td> + <td> + <div class="form-check form-check-type-toggle"> + <input class="form-check-input" type="checkbox" name="check[perms_user][]" value="{base ^ 3}" data-check-change-permissions="check[perms_user],data[pages][{id}][perms_user]" /> + </div> + </td> </tr> <tr> <td><strong><f:translate key="LLL:EXT:beuser/Resources/Private/Language/locallang_mod_permission.xlf:Group" /></strong></td> - <td><input type="checkbox" name="check[perms_group][]" value="{base ^ 0}" data-check-change-permissions="check[perms_group],data[pages][{id}][perms_group]" /></td> - <td><input type="checkbox" name="check[perms_group][]" value="{base ^ 4}" data-check-change-permissions="check[perms_group],data[pages][{id}][perms_group]" /></td> - <td><input type="checkbox" name="check[perms_group][]" value="{base ^ 1}" data-check-change-permissions="check[perms_group],data[pages][{id}][perms_group]" /></td> - <td><input type="checkbox" name="check[perms_group][]" value="{base ^ 2}" data-check-change-permissions="check[perms_group],data[pages][{id}][perms_group]" /></td> - <td><input type="checkbox" name="check[perms_group][]" value="{base ^ 3}" data-check-change-permissions="check[perms_group],data[pages][{id}][perms_group]" /></td> + <td> + <div class="form-check form-check-type-toggle"> + <input class="form-check-input" type="checkbox" name="check[perms_group][]" value="{base ^ 0}" data-check-change-permissions="check[perms_group],data[pages][{id}][perms_group]" /> + </div> + </td> + <td> + <div class="form-check form-check-type-toggle"> + <input class="form-check-input" type="checkbox" name="check[perms_group][]" value="{base ^ 4}" data-check-change-permissions="check[perms_group],data[pages][{id}][perms_group]" /> + </div> + </td> + <td> + <div class="form-check form-check-type-toggle"> + <input class="form-check-input" type="checkbox" name="check[perms_group][]" value="{base ^ 1}" data-check-change-permissions="check[perms_group],data[pages][{id}][perms_group]" /> + </div> + </td> + <td> + <div class="form-check form-check-type-toggle"> + <input class="form-check-input" type="checkbox" name="check[perms_group][]" value="{base ^ 2}" data-check-change-permissions="check[perms_group],data[pages][{id}][perms_group]" /> + </div> + </td> + <td> + <div class="form-check form-check-type-toggle"> + <input class="form-check-input" type="checkbox" name="check[perms_group][]" value="{base ^ 3}" data-check-change-permissions="check[perms_group],data[pages][{id}][perms_group]" /> + </div> + </td> </tr> <tr> <td><strong><f:translate key="LLL:EXT:beuser/Resources/Private/Language/locallang_mod_permission.xlf:Everybody" /></strong></td> - <td><input type="checkbox" name="check[perms_everybody][]" value="{base ^ 0}" data-check-change-permissions="check[perms_everybody],data[pages][{id}][perms_everybody]" /></td> - <td><input type="checkbox" name="check[perms_everybody][]" value="{base ^ 4}" data-check-change-permissions="check[perms_everybody],data[pages][{id}][perms_everybody]" /></td> - <td><input type="checkbox" name="check[perms_everybody][]" value="{base ^ 1}" data-check-change-permissions="check[perms_everybody],data[pages][{id}][perms_everybody]" /></td> - <td><input type="checkbox" name="check[perms_everybody][]" value="{base ^ 2}" data-check-change-permissions="check[perms_everybody],data[pages][{id}][perms_everybody]" /></td> - <td><input type="checkbox" name="check[perms_everybody][]" value="{base ^ 3}" data-check-change-permissions="check[perms_everybody],data[pages][{id}][perms_everybody]" /></td> + <td> + <div class="form-check form-check-type-toggle"> + <input class="form-check-input" type="checkbox" name="check[perms_everybody][]" value="{base ^ 0}" data-check-change-permissions="check[perms_everybody],data[pages][{id}][perms_everybody]" /> + </div> + </td> + <td> + <div class="form-check form-check-type-toggle"> + <input class="form-check-input" type="checkbox" name="check[perms_everybody][]" value="{base ^ 4}" data-check-change-permissions="check[perms_everybody],data[pages][{id}][perms_everybody]" /> + </div> + </td> + <td> + <div class="form-check form-check-type-toggle"> + <input class="form-check-input" type="checkbox" name="check[perms_everybody][]" value="{base ^ 1}" data-check-change-permissions="check[perms_everybody],data[pages][{id}][perms_everybody]" /> + </div> + </td> + <td> + <div class="form-check form-check-type-toggle"> + <input class="form-check-input" type="checkbox" name="check[perms_everybody][]" value="{base ^ 2}" data-check-change-permissions="check[perms_everybody],data[pages][{id}][perms_everybody]" /> + </div> + </td> + <td> + <div class="form-check form-check-type-toggle"> + <input class="form-check-input" type="checkbox" name="check[perms_everybody][]" value="{base ^ 3}" data-check-change-permissions="check[perms_everybody],data[pages][{id}][perms_everybody]" /> + </div> + </td> </tr> </tbody> </table> diff --git a/typo3/sysext/core/Tests/Acceptance/Application/DbCheck/DbCheckModuleCest.php b/typo3/sysext/core/Tests/Acceptance/Application/DbCheck/DbCheckModuleCest.php index d5d98438e3806a65e864e60fd5a8dda0dd704f2b..fd0c5447d465f667ba22101eda39aba06a4e2e69 100644 --- a/typo3/sysext/core/Tests/Acceptance/Application/DbCheck/DbCheckModuleCest.php +++ b/typo3/sysext/core/Tests/Acceptance/Application/DbCheck/DbCheckModuleCest.php @@ -94,11 +94,11 @@ final class DbCheckModuleCest { $this->goToPageAndSeeHeadline($I, 'Full search', 'Search whole Database'); $I->see('Search options', 'h2'); - $I->see('Result', 'h2'); // Fill in search phrase and check results $I->fillField('input[name="SET[sword]"]', 'styleguide demo group 1'); $I->click('Search All Records'); + $I->see('Result', 'h2'); $I->see('styleguide demo group 1', 'td'); $I->dontSee('styleguide demo group 2', 'td'); diff --git a/typo3/sysext/core/Tests/Acceptance/Application/RecordList/RecordDownloadCest.php b/typo3/sysext/core/Tests/Acceptance/Application/RecordList/RecordDownloadCest.php index b09d115a0ae645c488f2bdbf98a4a4d0f090d2d3..676b42834a10c70e0ddc605440df905d2f60e7f8 100644 --- a/typo3/sysext/core/Tests/Acceptance/Application/RecordList/RecordDownloadCest.php +++ b/typo3/sysext/core/Tests/Acceptance/Application/RecordList/RecordDownloadCest.php @@ -46,10 +46,10 @@ final class RecordDownloadCest $modalDialog->canSeeDialog(); $I->canSee('Download Page:', ModalDialog::$openedModalSelector . ' .modal-title'); $I->fillField(ModalDialog::$openedModalSelector . ' input[name="filename"]', 'test-download'); - $I->canSee('CSV options', ModalDialog::$openedModalSelector . ' .modal-body h5'); + $I->canSee('CSV options', ModalDialog::$openedModalSelector . ' .modal-body h2'); $I->selectOption(ModalDialog::$openedModalSelector . ' select[name="format"]', 'json'); - $I->dontSee('CSV options', ModalDialog::$openedModalSelector . ' .modal-body h5'); - $I->see('JSON options', ModalDialog::$openedModalSelector . ' .modal-body h5'); + $I->dontSee('CSV options', ModalDialog::$openedModalSelector . ' .modal-body h2'); + $I->see('JSON options', ModalDialog::$openedModalSelector . ' .modal-body h2'); $I->selectOption(ModalDialog::$openedModalSelector . ' select[name="json[meta]"]', 'full'); $I->click('button[name="download"]', ModalDialog::$openedModalButtonContainerSelector); $I->waitForElementNotVisible(ModalDialog::$openedModalSelector, 30); diff --git a/typo3/sysext/extensionmanager/Resources/Private/Templates/List/Distributions.html b/typo3/sysext/extensionmanager/Resources/Private/Templates/List/Distributions.html index 9098df63aa05119b8b8673ebe64904124d401a16..c15bc90dd2f232fa64ae96f1822d1cba562ca255 100644 --- a/typo3/sysext/extensionmanager/Resources/Private/Templates/List/Distributions.html +++ b/typo3/sysext/extensionmanager/Resources/Private/Templates/List/Distributions.html @@ -21,12 +21,10 @@ <f:if condition="{enableDistributionsView}"> <f:then> <f:if condition="{showUnsuitableDistributions} == 0"> - <div class="row"> - <div class="col-sm-6"> - <f:form class="typo3-extensionmanager-unsuitable-dist" action="distributions" arguments="{showUnsuitableDistributions: 1}" > - <f:form.submit class="btn btn-default" value="{f:translate(key:'extensionList.showUnsuitableDistributions')}"/> - </f:form> - </div> + <div class="form-group"> + <f:form class="typo3-extensionmanager-unsuitable-dist" action="distributions" arguments="{showUnsuitableDistributions: 1}" > + <f:form.submit class="btn btn-default" value="{f:translate(key:'extensionList.showUnsuitableDistributions')}"/> + </f:form> </div> </f:if> <div class="card-container"> diff --git a/typo3/sysext/extensionmanager/Resources/Private/Templates/List/Index.html b/typo3/sysext/extensionmanager/Resources/Private/Templates/List/Index.html index 2bdd9c8b87bf9bea660247e60183977122748f16..d8e4f19f4628b3fbb52759f7a1c6f3704202bde7 100644 --- a/typo3/sysext/extensionmanager/Resources/Private/Templates/List/Index.html +++ b/typo3/sysext/extensionmanager/Resources/Private/Templates/List/Index.html @@ -20,14 +20,14 @@ <h1><f:translate key="installedExtensions" /></h1> <f:render partial="List/UploadForm" /> <form> - <div class="row row-cols-auto align-items-end justify-content-between g-3"> - <div class="col"> + <div class="form-row justify-content-between"> + <div class="form-group"> <div class="input-group"> <f:form.textfield name="Tx_Extensionmanager_extensionkey" placeholder="{f:translate(key:'extensionList.search')}" id="Tx_Extensionmanager_extensionkey" value="{search}" class="form-control extension-list-search" /> <button type="submit" class="btn btn-default"><core:icon identifier="actions-search" /></button> </div> </div> - <div class="col"> + <div class="form-group"> <div class="btn-group"> <f:link.action action="index" diff --git a/typo3/sysext/extensionmanager/Resources/Private/Templates/List/Ter.html b/typo3/sysext/extensionmanager/Resources/Private/Templates/List/Ter.html index c01999eb15ebd74aa7f8a3202a1259aba3ee3f2a..52071249dff40d8cc71d7fc0601894a94df39270 100644 --- a/typo3/sysext/extensionmanager/Resources/Private/Templates/List/Ter.html +++ b/typo3/sysext/extensionmanager/Resources/Private/Templates/List/Ter.html @@ -19,8 +19,8 @@ <h1><f:translate key="getExtensions">Get Extensions</f:translate></h1> <f:render partial="List/UploadForm" /> - <div class="row row-cols-auto align-items-end justify-content-between g-3"> - <div class="col"> + <div class="form-row justify-content-between"> + <div class="form-group"> <f:form class="typo3-extensionmanager-searchTerForm" action="ter"> <div class="input-group"> <f:form.textfield name="search" value="{search}" class="form-control" placeholder="{f:translate(key:'extensionList.search')}" /> @@ -30,7 +30,7 @@ </div> </f:form> </div> - <div class="col"> + <div class="form-group"> <f:render partial="List/UpdateFromTer" /> </div> </div> diff --git a/typo3/sysext/filelist/Resources/Private/Templates/File/List.html b/typo3/sysext/filelist/Resources/Private/Templates/File/List.html index a3f867f86ea6172ecc4f5fb114145f0cd643263c..832765b853ff249c1e1a094de8e20c3cc0ba17f4 100644 --- a/typo3/sysext/filelist/Resources/Private/Templates/File/List.html +++ b/typo3/sysext/filelist/Resources/Private/Templates/File/List.html @@ -43,8 +43,8 @@ <form method="post" name="fileListForm" action="{listUrl}"> <input type="hidden" name="cmd"/> <f:if condition="{searchTerm} || {totalItems}"> - <div class="row mb-3"> - <div class="col-6"> + <div class="form-row"> + <div class="form-group"> <div class="input-group"> <button class="btn btn-default" type="submit" name="search"> <core:icon identifier="actions-search" size="small" /> @@ -143,6 +143,7 @@ <f:if condition="{listHtml}"> <f:if condition="{showClipboardPanel}"> + <hr class="spacer"> <typo3-backend-clipboard-panel return-url="{listUrl}" table="_FILE"></typo3-backend-clipboard-panel> </f:if> </f:if> diff --git a/typo3/sysext/impexp/Resources/Private/Templates/Export.html b/typo3/sysext/impexp/Resources/Private/Templates/Export.html index 4b0c7255055228dffc0a6707fe356492fa4104d6..4f4f2ee1403dba803f6fdb932634e7cd95f6393d 100644 --- a/typo3/sysext/impexp/Resources/Private/Templates/Export.html +++ b/typo3/sysext/impexp/Resources/Private/Templates/Export.html @@ -5,8 +5,8 @@ > <f:layout name="Module" /> -<f:section name="Content"> +<f:section name="Before"> <f:be.pageRenderer includeJavaScriptModules="{ 0: '@typo3/backend/context-menu.js', @@ -14,15 +14,20 @@ 2: '@typo3/backend/element/immediate-action-element.js' }" /> - <form action="{f:be.uri(route:'tx_impexp_export')}" method="post" id="ImportExportController"> - <f:variable name="args" value="{0: 'web', 1: id}" /> - <typo3-immediate-action action="TYPO3.Backend.Storage.ModuleStateStorage.update" args="{args -> f:format.json() -> f:format.htmlspecialchars()}"></typo3-immediate-action> - <input type="hidden" name="id" value="{id}" /> + <f:variable name="args" value="{0: 'web', 1: id}" /> + <typo3-immediate-action + action="TYPO3.Backend.Storage.ModuleStateStorage.update" + args="{args -> f:format.json() -> f:format.htmlspecialchars()}" + ></typo3-immediate-action> +</f:section> - <h1> - <f:translate key="LLL:EXT:impexp/Resources/Private/Language/locallang.xlf:title_export" /> - </h1> +<f:section name="Content"> + <h1> + <f:translate key="LLL:EXT:impexp/Resources/Private/Language/locallang.xlf:title_export" /> + </h1> + <form action="{f:be.uri(route:'tx_impexp_export')}" method="post" id="ImportExportController"> + <input type="hidden" name="id" value="{id}" /> <ul class="nav nav-tabs" role="tablist"> <li role="presentation" class="nav-item"> <a class="nav-link text-capitalize active" href="#export-configuration" aria-controls="export-configuration" role="tab" data-bs-toggle="tab"> @@ -68,7 +73,6 @@ </div> </f:if> </div> - <f:render partial="Preview" arguments="{_all}" /> </form> diff --git a/typo3/sysext/impexp/Resources/Private/Templates/Import.html b/typo3/sysext/impexp/Resources/Private/Templates/Import.html index 7376e5a18d8a9c883fe1fa7eeca765ab818496da..b74b5684e463d5098695b4204e697e0d54fae5d0 100644 --- a/typo3/sysext/impexp/Resources/Private/Templates/Import.html +++ b/typo3/sysext/impexp/Resources/Private/Templates/Import.html @@ -5,8 +5,8 @@ > <f:layout name="Module" /> -<f:section name="Content"> +<f:section name="Before"> <f:be.pageRenderer includeJavaScriptModules="{ 0: '@typo3/backend/context-menu.js', @@ -14,15 +14,20 @@ 2: '@typo3/backend/element/immediate-action-element.js' }" /> - <form action="{f:be.uri(route:'tx_impexp_import')}" method="post" id="ImportExportController" enctype="multipart/form-data"> - <f:variable name="args" value="{0: 'web', 1: id}" /> - <typo3-immediate-action action="TYPO3.Backend.Storage.ModuleStateStorage.update" args="{args -> f:format.json() -> f:format.htmlspecialchars()}"></typo3-immediate-action> - <input type="hidden" name="id" value="{id}" /> + <f:variable name="args" value="{0: 'web', 1: id}" /> + <typo3-immediate-action + action="TYPO3.Backend.Storage.ModuleStateStorage.update" + args="{args -> f:format.json() -> f:format.htmlspecialchars()}" + ></typo3-immediate-action> +</f:section> - <h1> - <f:translate key="LLL:EXT:impexp/Resources/Private/Language/locallang.xlf:title_import" /> - </h1> +<f:section name="Content"> + <h1> + <f:translate key="LLL:EXT:impexp/Resources/Private/Language/locallang.xlf:title_import" /> + </h1> + <form action="{f:be.uri(route:'tx_impexp_import')}" method="post" id="ImportExportController" enctype="multipart/form-data"> + <input type="hidden" name="id" value="{id}" /> <ul class="nav nav-tabs" role="tablist"> <li role="presentation" class="nav-item"> <a class="nav-link text-capitalize active" href="#import-import" aria-controls="import-import" role="tab" data-bs-toggle="tab"> diff --git a/typo3/sysext/indexed_search/Resources/Private/Templates/Administration/Index.html b/typo3/sysext/indexed_search/Resources/Private/Templates/Administration/Index.html index fbf057a5b686a03216c649b0c48995eecae235f8..326d5b6e174495af753a0f4e88b81735e15799a5 100644 --- a/typo3/sysext/indexed_search/Resources/Private/Templates/Administration/Index.html +++ b/typo3/sysext/indexed_search/Resources/Private/Templates/Administration/Index.html @@ -11,7 +11,7 @@ <h2><f:translate key="administration.index.description" /></h2> <div class="row"> <div class="col-md-6"> - <h4><f:translate key="administration.statistics.header" /></h4> + <h3><f:translate key="administration.statistics.header" /></h3> <div class="table-fit"> <table class="table table-striped table-hover"> <thead> @@ -32,7 +32,7 @@ </div> </div> <div class="col-md-6"> - <h4><f:translate key="administration.statistics.headerTypes" /></h4> + <h3><f:translate key="administration.statistics.headerTypes" /></h3> <div class="table-fit"> <table class="table table-striped table-hover"> <thead> @@ -91,9 +91,9 @@ </f:section> <f:section name="statistic"> - <h4> + <h3> <f:translate key="administration.statistics.mostSearched.{title}" /> - </h4> + </h3> <f:if condition="{statistic}"> <f:then> <div class="table-fit"> diff --git a/typo3/sysext/indexed_search/Resources/Private/Templates/Administration/Statistic.html b/typo3/sysext/indexed_search/Resources/Private/Templates/Administration/Statistic.html index d113dfabdd27103eb4b4c655188f09ada190d8be..3e9cf331617ba748d9815fc1c525026c0bb9e163 100644 --- a/typo3/sysext/indexed_search/Resources/Private/Templates/Administration/Statistic.html +++ b/typo3/sysext/indexed_search/Resources/Private/Templates/Administration/Statistic.html @@ -12,8 +12,8 @@ <f:if condition="{tree}"> <f:then> <f:form name="statistic" action="statistic" arguments="{id:pageUid}"> - <div class="row row-cols-auto align-items-center g-3 mb-3"> - <div class="col"> + <div class="form-row"> + <div class="form-group"> <label for="mode" class="form-label"> <f:translate key="LLL:EXT:indexed_search/Resources/Private/Language/locallang.xlf:administration.moduleFunctions.mode" /> </label> @@ -22,7 +22,7 @@ content:'{f:translate(key:\'administration.statistics.view.content\')}' }" value="{mode}" additionalAttributes="{data-global-event='change', data-action-submit: '$form'}" /> </div> - <div class="col"> + <div class="form-group"> <label for="depth" class="form-label"> <f:translate key="LLL:EXT:indexed_search/Resources/Private/Language/locallang.xlf:administration.moduleFunctions.depth" /> </label> diff --git a/typo3/sysext/indexed_search/Resources/Private/Templates/Administration/StatisticDetails.html b/typo3/sysext/indexed_search/Resources/Private/Templates/Administration/StatisticDetails.html index a03d5ad5baa440a821ccc7b8d9c70f5437d8fde7..81149d8915693ad1c36b5f86a8b5936bc7ab5aa8 100644 --- a/typo3/sysext/indexed_search/Resources/Private/Templates/Administration/StatisticDetails.html +++ b/typo3/sysext/indexed_search/Resources/Private/Templates/Administration/StatisticDetails.html @@ -31,22 +31,22 @@ <f:render section="wordlisting" arguments="{words:topFrequency,phash:phash,title:'topFrequency'}" /> <f:if condition="{debug}"> - <h4> + <h3> <f:translate key="administration.statistics.debug" /> - </h4> + </h3> <f:debug inline="1" title="">{debug}</f:debug> </f:if> <f:if condition="{lexer}"> - <h4> + <h3> <f:translate key="administration.statistics.lexer" /> - </h4> + </h3> <f:format.raw>{lexer}</f:format.raw> </f:if> <f:if condition="{metaphone}"> - <h4> + <h3> <f:translate key="administration.statistics.metaphone" /> - </h4> + </h3> <div class="table-fit"> <table class="table table-striped table-hover"> <thead> @@ -81,7 +81,7 @@ </div> </f:if> <f:if condition="{sections}"> - <h4><f:translate key="administration.statistics.sectionRecords" /></h4> + <h3><f:translate key="administration.statistics.sectionRecords" /></h3> <div class="table-fit"> <table class="table table-striped table-hover"> <thead> @@ -117,12 +117,12 @@ </f:section> <f:section name="wordlisting"> - <h4> + <h3> <f:translate key="administration.document.{title}" /> <f:if condition="{title}=='words'"> ({f:count(subject:words)}) </f:if> - </h4> + </h3> <f:if condition="{words}"> <f:form class="form" method="post" action="saveStopwordsKeywords" name="stopwordskeywords" arguments="{pageHash:phash}"> <f:form.hidden name="pageHash" value="{phash}" /> diff --git a/typo3/sysext/info/Resources/Private/Templates/PageInformation.html b/typo3/sysext/info/Resources/Private/Templates/PageInformation.html index 06bbd3332543133f853e9d789f75a0e11e9a0830..db24f00a9761a71dd5645320d587695dc50aeb0a 100644 --- a/typo3/sysext/info/Resources/Private/Templates/PageInformation.html +++ b/typo3/sysext/info/Resources/Private/Templates/PageInformation.html @@ -5,35 +5,40 @@ <f:layout name="Module"/> -<f:section name="Content"> - +<f:section name="Before"> <f:be.pageRenderer includeJavaScriptModules="{ 0: '@typo3/backend/context-menu.js', 1: '@typo3/backend/element/immediate-action-element.js' }" /> + <f:if condition="{accessContent}"> + <f:variable name="args" value="{0: 'web', 1: id}"/> + <typo3-immediate-action + action="TYPO3.Backend.Storage.ModuleStateStorage.update" + args="{args -> f:format.json() -> f:format.htmlspecialchars()}" + ></typo3-immediate-action> + </f:if> +</f:section> + +<f:section name="Content"> <f:if condition="{accessContent}"> <f:then> - - <f:variable name="args" value="{0: 'web', 1: id}"/> - <typo3-immediate-action action="TYPO3.Backend.Storage.ModuleStateStorage.update" - args="{args -> f:format.json() -> f:format.htmlspecialchars()}"></typo3-immediate-action> <h1> <f:translate key="LLL:EXT:info/Resources/Private/Language/locallang_webinfo.xlf:page_title"/> </h1> <f:if condition="{content}"> <form action="{f:be.uri(route: 'web_info_overview', parameters: '{id: pageUid}')}" method="post"> - <div class="row row-cols-auto mb-3 g-3 align-items-center"> - <div class="col"> + <div class="form-row"> + <div class="form-group"> <label class="form-label" for="depth"> <f:translate key="LLL:EXT:info/Resources/Private/Language/locallang_webinfo.xlf:moduleFunctions.depth"/> </label> <f:render partial="DropdownMenu" arguments="{name: 'depth', id: 'depth', options: depthDropdownOptions, currentValue: depthDropdownCurrentValue}"/> </div> - <div class="col"> + <div class="form-group"> <label class="form-label" for="pages"> <f:translate key="LLL:EXT:info/Resources/Private/Language/locallang_webinfo.xlf:moduleFunctions.type"/> </label> diff --git a/typo3/sysext/info/Resources/Private/Templates/TranslationStatus.html b/typo3/sysext/info/Resources/Private/Templates/TranslationStatus.html index 49203018cf59e11390d87ce208d40ef53cc8ced8..c172fc743f3a16e3e32ada0be5b3d207002a24c0 100644 --- a/typo3/sysext/info/Resources/Private/Templates/TranslationStatus.html +++ b/typo3/sysext/info/Resources/Private/Templates/TranslationStatus.html @@ -5,8 +5,7 @@ <f:layout name="Module"/> -<f:section name="Content"> - +<f:section name="Before"> <f:be.pageRenderer includeJavaScriptModules="{ 0: '@typo3/backend/context-menu.js', @@ -14,29 +13,39 @@ 2: '@typo3/info/translation-status.js' }" /> + <f:if condition="{accessContent}"> + <f:variable name="args" value="{0: 'web', 1: id}" /> + <typo3-immediate-action + action="TYPO3.Backend.Storage.ModuleStateStorage.update" + args="{args -> f:format.json() -> f:format.htmlspecialchars()}" + ></typo3-immediate-action> + </f:if> +</f:section> + +<f:section name="Content"> <f:if condition="{accessContent}"> <f:then> - <f:variable name="args" value="{0: 'web', 1: id}" /> - <typo3-immediate-action action="TYPO3.Backend.Storage.ModuleStateStorage.update" args="{args -> f:format.json() -> f:format.htmlspecialchars()}"></typo3-immediate-action> <h1><f:translate key="LLL:EXT:info/Resources/Private/Language/locallang_webinfo.xlf:lang_title" /></h1> <f:if condition="{content}"> - <form action="{f:be.uri(route: 'web_info_translations', parameters: '{id: pageUid}')}" method="post" id="InfoModuleController" name="webinfoForm"><div class="row row-cols-auto mb-3 g-3 align-items-center"> - <div class="col"> - <label class="form-label" for="depth"> - <f:translate key="LLL:EXT:info/Resources/Private/Language/locallang_webinfo.xlf:moduleFunctions.depth" /> - </label> - <f:render partial="DropdownMenu" arguments="{name: 'depth', id: 'depth', options: depthDropdownOptions, currentValue: depthDropdownCurrentValue}"/> - </div> - <f:if condition="{displayLangDropdown}"> - <div class="col"> - <label class="form-label" for="lang"> - <f:translate key="LLL:EXT:info/Resources/Private/Language/locallang_webinfo.xlf:moduleFunctions.lang" /> + <form action="{f:be.uri(route: 'web_info_translations', parameters: '{id: pageUid}')}" method="post" id="InfoModuleController" name="webinfoForm"> + <div class="form-row"> + <div class="form-group"> + <label class="form-label" for="depth"> + <f:translate key="LLL:EXT:info/Resources/Private/Language/locallang_webinfo.xlf:moduleFunctions.depth" /> </label> - <f:render partial="DropdownMenu" arguments="{name: 'lang', id: 'lang', options: langDropdownOptions, currentValue: langDropdownCurrentValue}"/> + <f:render partial="DropdownMenu" arguments="{name: 'depth', id: 'depth', options: depthDropdownOptions, currentValue: depthDropdownCurrentValue}"/> </div> - </f:if> - </div><f:format.raw>{content}</f:format.raw> + <f:if condition="{displayLangDropdown}"> + <div class="form-group"> + <label class="form-label" for="lang"> + <f:translate key="LLL:EXT:info/Resources/Private/Language/locallang_webinfo.xlf:moduleFunctions.lang" /> + </label> + <f:render partial="DropdownMenu" arguments="{name: 'lang', id: 'lang', options: langDropdownOptions, currentValue: langDropdownCurrentValue}"/> + </div> + </f:if> + </div> + <f:format.raw>{content}</f:format.raw> </form> </f:if> </f:then> diff --git a/typo3/sysext/install/Resources/Private/Templates/Environment/ImageProcessing.html b/typo3/sysext/install/Resources/Private/Templates/Environment/ImageProcessing.html index ac20d87517e11ce48372adafa8a83fbf6ebbbaa0..e2b96e4295d050e5a98274826a394cb3407ba7cd 100644 --- a/typo3/sysext/install/Resources/Private/Templates/Environment/ImageProcessing.html +++ b/typo3/sysext/install/Resources/Private/Templates/Environment/ImageProcessing.html @@ -1,36 +1,12 @@ <html xmlns:f="http://typo3.org/ns/TYPO3/CMS/Fluid/ViewHelpers" data-namespace-typo3-fluid="true"> -<div style="display:none;"> - <div class="t3js-imageProcessing-twinImage-template"> - <div class="t3-install-displaytwinimageimages t3js-imageProcessing-images" style="display:none;"> - <div class="row"> - <div class="col-12 col-md-6"> - <h4>Reference</h4> - <div class="bg-transparent-emulation"> - <img class="reference"/> - </div> - </div> - <div class="col-12 col-md-6"> - <h4>Your system</h4> - <div class="bg-transparent-emulation"> - <img class="result"/> - </div> - </div> - </div> - </div> - <div class="t3-install-displaytwinimagetextarea t3js-imageProcessing-command" style="display:none;"> - <pre class="mt-2"><code class="language-bash t3js-imageProcessing-command-text"></code></pre> - </div> - </div> -</div> - -<h3>True type font tests</h3> +<h2>True type font tests</h2> <f:be.infobox title="FreeType2 hint" state="-1"> <p>If the two images below do not look the same, please check your FreeType 2 module.</p> </f:be.infobox> <div class="t3js-imageProcessing-twinContainer" data-test="imageProcessingTrueType"></div> -<h3 class="mt-4">Convert image formats to jpg</h3> +<h2>Convert image formats to jpg</h2> <p> This verifies that your ImageMagick installation is able to read the default formats <code>jpg</code>, <code>gif</code>, <code>png</code>, <code>tif</code>, <code>pdf</code> and @@ -45,84 +21,84 @@ </p> </f:be.infobox> -<h4 class="mt-4">Read jpg</h4> +<h3>Read jpg</h3> <div class="t3js-imageProcessing-twinContainer" data-test="imageProcessingReadJpg"></div> -<h4 class="mt-4">Read gif</h4> +<h3>Read gif</h3> <div class="t3js-imageProcessing-twinContainer" data-test="imageProcessingReadGif"></div> -<h4 class="mt-4">Read png</h4> +<h3>Read png</h3> <div class="t3js-imageProcessing-twinContainer" data-test="imageProcessingReadPng"></div> -<h4 class="mt-4">Read tif</h4> +<h3>Read tif</h3> <div class="t3js-imageProcessing-twinContainer" data-test="imageProcessingReadTif"></div> -<h4 class="mt-4">Read pdf</h4> +<h3>Read pdf</h3> <div class="t3js-imageProcessing-twinContainer" data-test="imageProcessingReadPdf"></div> -<h4 class="mt-4">Read ai</h4> +<h3>Read ai</h3> <div class="t3js-imageProcessing-twinContainer" data-test="imageProcessingReadAi"></div> -<h3 class="mt-4">Writing gif, png, webp</h3> +<h2>Writing gif, png, webp</h2> <p> This verifies that ImageMagick is able to write GIF and PNG and WEBP files. The GIF-file is attempted compressed by the <code>\TYPO3\CMS\Core\Imaging\GraphicalFunctions::gifCompress()</code> function. </p> -<h4 class="mt-4">Write gif</h4> +<h3>Write gif</h3> <div class="t3js-imageProcessing-twinContainer" data-test="imageProcessingWriteGif"></div> -<h4 class="mt-4">Write png</h4> +<h3>Write png</h3> <div class="t3js-imageProcessing-twinContainer" data-test="imageProcessingWritePng"></div> -<h4 class="mt-4">Write webp</h4> +<h3>Write webp</h3> <div class="t3js-imageProcessing-twinContainer" data-test="imageProcessingWriteWebp"></div> -<h3 class="mt-4">Scaling images</h3> +<h2>Scaling images</h2> <p> This shows how ImageMagick reacts when scaling transparent GIF and PNG files. </p> -<h4 class="mt-4">gif to gif</h4> +<h3>gif to gif</h3> <div class="t3js-imageProcessing-twinContainer" data-test="imageProcessingGifToGif"></div> -<h4 class="mt-4">png to png</h4> +<h3>png to png</h3> <div class="t3js-imageProcessing-twinContainer" data-test="imageProcessingPngToPng"></div> -<h4 class="mt-4">gif to jpg</h4> +<h3>gif to jpg</h3> <div class="t3js-imageProcessing-twinContainer" data-test="imageProcessingGifToJpg"></div> -<h4 class="mt-4">jpg to webp</h4> +<h3>jpg to webp</h3> <div class="t3js-imageProcessing-twinContainer" data-test="imageProcessingJpgToWebp"></div> -<h3 class="mt-4">Combining images</h3> +<h2>Combining images</h2> <p> This verifies that the ImageMagick tools, <code>combine</code>, <code>composite</code>, are able to combine two images through a grayscale mask. </p> -<h4 class="mt-4">Combine using a GIF mask with only black and white</h4> +<h3>Combine using a GIF mask with only black and white</h3> <div class="t3js-imageProcessing-twinContainer" data-test="imageProcessingCombineGifMask"></div> -<h4 class="mt-4">Combine using a JPG mask with graylevels</h4> +<h3>Combine using a JPG mask with graylevels</h3> <div class="t3js-imageProcessing-twinContainer" data-test="imageProcessingCombineJpgMask"></div> -<h3 class="mt-4">GDlib</h3> +<h2>GDlib</h2> <p> This verifies that the GDLib installation works properly. </p> -<h4 class="mt-4">Create simple image</h4> +<h3>Create simple image</h3> <div class="t3js-imageProcessing-twinContainer" data-test="imageProcessingGdlibSimple"></div> -<h4 class="mt-4">Create image from file</h4> +<h3>Create image from file</h3> <div class="t3js-imageProcessing-twinContainer" data-test="imageProcessingGdlibFromFile"></div> -<h4 class="mt-4">Render text with TrueType font</h4> +<h3>Render text with TrueType font</h3> <div class="t3js-imageProcessing-twinContainer" data-test="imageProcessingGdlibRenderText"></div> -<h4 class="mt-4">Render text with TrueType font using 'niceText' option</h4> +<h3>Render text with TrueType font using 'niceText' option</h3> <f:be.infobox title="Note on 'niceText'" state="-1"> <p> 'niceText' is a concept that tries to improve the antialiasing of the rendered type by actually @@ -132,7 +108,7 @@ </f:be.infobox> <div class="t3js-imageProcessing-twinContainer" data-test="imageProcessingGdlibNiceText"></div> -<h4 class="mt-4">Render 'niceText' with a shadow under</h4> +<h3>Render 'niceText' with a shadow under</h3> <f:be.infobox title="Note on 'shadow'" state="-1"> <p> This test makes sense only if the above test had a correct output. But if so, you may not see @@ -142,7 +118,7 @@ </f:be.infobox> <div class="t3js-imageProcessing-twinContainer" data-test="imageProcessingGdlibNiceTextShadow"></div> -<div class="panel-group mt-4" id="accordion" role="tablist" aria-multiselectable="true"> +<div class="panel-group mb-0" id="accordion" role="tablist" aria-multiselectable="true"> <div class="panel panel-default"> <div class="panel-heading" role="tab" id="headingConfiguration"> <h4 class="panel-title"> @@ -150,11 +126,10 @@ <span class="caret"></span> Current configuration </a> - </h4> + </h3> </div> <div id="collapseConfiguration" class="panel-collapse collapse" role="tabpanel" aria-labelledby="headingConfiguration"> - <div class="panel-body"> - + <div class="table-fit"> <table class="table table-striped"> <tr> <td>{imageProcessingProcessor} enabled:</td> @@ -200,11 +175,11 @@ <span class="caret"></span> Verify test results </a> - </h4> + </h3> </div> <div id="collapseVerify" class="panel-collapse collapse" role="tabpanel" aria-labelledby="headingVerify"> <div class="panel-body"> - <h4>Verify test results</h4> + <h3>Verify test results</h3> <p> This page performs image processing and displays the result. It's a thorough check that everything you've configured is working correctly. @@ -229,7 +204,7 @@ <span class="caret"></span> About image handling </a> - </h4> + </h3> </div> <div id="collapseAbout" class="panel-collapse collapse" role="tabpanel" aria-labelledby="headingAbout"> <div class="panel-body"> @@ -288,7 +263,7 @@ <span class="caret"></span> About test images </a> - </h4> + </h3> </div> <div id="collapseTestImages" class="panel-collapse collapse" role="tabpanel" aria-labelledby="headingTestImages"> <div class="panel-body"> @@ -302,4 +277,28 @@ </div> </div> +<div style="display:none;"> + <div class="t3js-imageProcessing-twinImage-template"> + <div class="t3-install-displaytwinimageimages t3js-imageProcessing-images" style="display:none;"> + <div class="row"> + <div class="col-12 col-md-6"> + <h3>Reference</h3> + <div class="bg-transparent-emulation"> + <img class="reference"/> + </div> + </div> + <div class="col-12 col-md-6"> + <h3>Your system</h3> + <div class="bg-transparent-emulation"> + <img class="result"/> + </div> + </div> + </div> + </div> + <div class="t3-install-displaytwinimagetextarea t3js-imageProcessing-command" style="display:none;"> + <pre class="language-bash"><code class="language-bash t3js-imageProcessing-command-text"></code></pre> + </div> + </div> +</div> + </html> diff --git a/typo3/sysext/install/Resources/Public/JavaScript/renderable/clearable.js b/typo3/sysext/install/Resources/Public/JavaScript/renderable/clearable.js index b15486ad91bbf4796b0623cc733c3ea4e14629cf..e90caeef460f1bcfe15ca16461989a28c2717c2e 100644 --- a/typo3/sysext/install/Resources/Public/JavaScript/renderable/clearable.js +++ b/typo3/sysext/install/Resources/Public/JavaScript/renderable/clearable.js @@ -10,4 +10,4 @@ * * The TYPO3 project - inspiring people to share! */ -class Clearable{constructor(){"function"!=typeof HTMLInputElement.prototype.clearable&&this.registerClearable()}static createCloseButton(){const e=document.createElement("button");return e.type="button",e.tabIndex=-1,e.innerHTML='<span class="t3js-icon icon icon-size-small icon-state-default icon-actions-close" data-identifier="actions-close">\n <span class="icon-markup">\n <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 16 16">\n <path\n d="M11.9 5.5L9.4 8l2.5 2.5c.2.2.2.5 0\n .7l-.7.7c-.2.2-.5.2-.7 0L8 9.4l-2.5 2.5c-.2.2-.5.2-.7\n 0l-.7-.7c-.2-.2-.2-.5 0-.7L6.6 8 4.1 5.5c-.2-.2-.2-.5\n 0-.7l.7-.7c.2-.2.5-.2.7 0L8 6.6l2.5-2.5c.2-.2.5-.2.7\n 0l.7.7c.2.2.2.5 0 .7z"\n class="icon-color"/>\n </svg>\n </span>\n </span>',e.style.visibility="hidden",e.classList.add("close"),e}registerClearable(){HTMLInputElement.prototype.clearable=function(e={}){if(this.dataset.clearable)return;if("object"!=typeof e)throw new Error("Passed options must be an object, "+typeof e+" given");const t=document.createElement("div");t.classList.add("form-control-clearable","form-control"),this.parentNode.insertBefore(t,this),t.appendChild(this);const n=Clearable.createCloseButton(),s=()=>{n.style.visibility=0===this.value.length?"hidden":"visible"};n.addEventListener("click",(t=>{t.preventDefault(),this.value="","function"==typeof e.onClear&&e.onClear(this),this.dispatchEvent(new Event("change",{bubbles:!0,cancelable:!0})),s()})),t.appendChild(n),this.addEventListener("focus",s),this.addEventListener("keyup",s),s(),this.dataset.clearable="true"}}}export default new Clearable; \ No newline at end of file +class Clearable{constructor(){"function"!=typeof HTMLInputElement.prototype.clearable&&this.registerClearable()}static createCloseButton(){const e=document.createElement("button");return e.type="button",e.tabIndex=-1,e.innerHTML='<span class="t3js-icon icon icon-size-small icon-state-default icon-actions-close" data-identifier="actions-close">\n <span class="icon-markup">\n <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 16 16">\n <path\n d="M11.9 5.5L9.4 8l2.5 2.5c.2.2.2.5 0\n .7l-.7.7c-.2.2-.5.2-.7 0L8 9.4l-2.5 2.5c-.2.2-.5.2-.7\n 0l-.7-.7c-.2-.2-.2-.5 0-.7L6.6 8 4.1 5.5c-.2-.2-.2-.5\n 0-.7l.7-.7c.2-.2.5-.2.7 0L8 6.6l2.5-2.5c.2-.2.5-.2.7\n 0l.7.7c.2.2.2.5 0 .7z"\n class="icon-color"/>\n </svg>\n </span>\n </span>',e.style.visibility="hidden",e.classList.add("close"),e}registerClearable(){HTMLInputElement.prototype.clearable=function(e={}){if(this.dataset.clearable)return;if("object"!=typeof e)throw new Error("Passed options must be an object, "+typeof e+" given");this.classList.add("form-control-clearable");const t=document.createElement("div");t.classList.add("form-control-clearable-wrapper"),this.parentNode.insertBefore(t,this),t.appendChild(this);const n=Clearable.createCloseButton(),a=()=>{n.style.visibility=0===this.value.length?"hidden":"visible"};n.addEventListener("click",(t=>{t.preventDefault(),this.value="","function"==typeof e.onClear&&e.onClear(this),this.dispatchEvent(new Event("change",{bubbles:!0,cancelable:!0})),a()})),t.appendChild(n),this.addEventListener("focus",a),this.addEventListener("keyup",a),a(),this.dataset.clearable="true"}}}export default new Clearable; \ No newline at end of file diff --git a/typo3/sysext/linkvalidator/Resources/Private/Partials/LevelSelector.html b/typo3/sysext/linkvalidator/Resources/Private/Partials/LevelSelector.html index c9b1a95167977d94585b030382b2bfeed0477dbc..4f38a44004b361835c42a508b65dc45d0277ccf2 100644 --- a/typo3/sysext/linkvalidator/Resources/Private/Partials/LevelSelector.html +++ b/typo3/sysext/linkvalidator/Resources/Private/Partials/LevelSelector.html @@ -3,15 +3,13 @@ data-namespace-typo3-fluid="true" > -<div> - <select name="{prefix}_search_levels" class="form-select"> - <option value="0"{f:if(condition: '{selectedLevel} == 0', then: 'selected')}><f:translate key="LLL:EXT:core/Resources/Private/Language/locallang_core.xlf:labels.depth_0" /></option> - <option value="1"{f:if(condition: '{selectedLevel} == 1', then: 'selected')}><f:translate key="LLL:EXT:core/Resources/Private/Language/locallang_core.xlf:labels.depth_1" /></option> - <option value="2"{f:if(condition: '{selectedLevel} == 2', then: 'selected')}><f:translate key="LLL:EXT:core/Resources/Private/Language/locallang_core.xlf:labels.depth_2" /></option> - <option value="3"{f:if(condition: '{selectedLevel} == 3', then: 'selected')}><f:translate key="LLL:EXT:core/Resources/Private/Language/locallang_core.xlf:labels.depth_3" /></option> - <option value="4"{f:if(condition: '{selectedLevel} == 4', then: 'selected')}><f:translate key="LLL:EXT:core/Resources/Private/Language/locallang_core.xlf:labels.depth_4" /></option> - <option value="999"{f:if(condition: '{selectedLevel} == 999', then: 'selected')}><f:translate key="LLL:EXT:core/Resources/Private/Language/locallang_core.xlf:labels.depth_infi" /></option> - </select> -</div> +<select name="{prefix}_search_levels" class="form-select"> + <option value="0"{f:if(condition: '{selectedLevel} == 0', then: 'selected')}><f:translate key="LLL:EXT:core/Resources/Private/Language/locallang_core.xlf:labels.depth_0" /></option> + <option value="1"{f:if(condition: '{selectedLevel} == 1', then: 'selected')}><f:translate key="LLL:EXT:core/Resources/Private/Language/locallang_core.xlf:labels.depth_1" /></option> + <option value="2"{f:if(condition: '{selectedLevel} == 2', then: 'selected')}><f:translate key="LLL:EXT:core/Resources/Private/Language/locallang_core.xlf:labels.depth_2" /></option> + <option value="3"{f:if(condition: '{selectedLevel} == 3', then: 'selected')}><f:translate key="LLL:EXT:core/Resources/Private/Language/locallang_core.xlf:labels.depth_3" /></option> + <option value="4"{f:if(condition: '{selectedLevel} == 4', then: 'selected')}><f:translate key="LLL:EXT:core/Resources/Private/Language/locallang_core.xlf:labels.depth_4" /></option> + <option value="999"{f:if(condition: '{selectedLevel} == 999', then: 'selected')}><f:translate key="LLL:EXT:core/Resources/Private/Language/locallang_core.xlf:labels.depth_infi" /></option> +</select> </html> diff --git a/typo3/sysext/linkvalidator/Resources/Private/Templates/Backend/CheckLinks.html b/typo3/sysext/linkvalidator/Resources/Private/Templates/Backend/CheckLinks.html index 4674a77e1de74fed268ec3b3dec5fd673ca2ec0b..d7f8eff2c167d959c08d54f469dac147f1b7eda7 100644 --- a/typo3/sysext/linkvalidator/Resources/Private/Templates/Backend/CheckLinks.html +++ b/typo3/sysext/linkvalidator/Resources/Private/Templates/Backend/CheckLinks.html @@ -16,12 +16,16 @@ </f:if> <div class="row row-cols-auto align-items-start t3js-linkvalidator-settings"> <div class="col"> - <h4><f:translate key="LLL:EXT:linkvalidator/Resources/Private/Language/Module/locallang.xlf:checklinks.statistics.header" /></h4> - <f:render partial="CheckOptions" arguments="{_all}" /> + <div class="form-group"> + <label class="form-label"><f:translate key="LLL:EXT:linkvalidator/Resources/Private/Language/Module/locallang.xlf:checklinks.statistics.header" /></label> + <f:render partial="CheckOptions" arguments="{_all}" /> + </div> </div> - <div class="col mb-3"> - <h4><f:translate key="LLL:EXT:linkvalidator/Resources/Private/Language/Module/locallang.xlf:checklinks.func.title" /></h4> - <f:render partial="LevelSelector" arguments="{_all}" /> + <div class="col"> + <div class="form-group"> + <label class="form-label"><f:translate key="LLL:EXT:linkvalidator/Resources/Private/Language/Module/locallang.xlf:checklinks.func.title" /></label> + <f:render partial="LevelSelector" arguments="{_all}" /> + </div> </div> <div class="col-12"> <input diff --git a/typo3/sysext/linkvalidator/Resources/Private/Templates/Backend/Report.html b/typo3/sysext/linkvalidator/Resources/Private/Templates/Backend/Report.html index d796509c7bf3ff9459bc28f543122ba3da6d5ead..fc1f7d767fc3d9220076b8337d53401ca6c27361 100644 --- a/typo3/sysext/linkvalidator/Resources/Private/Templates/Backend/Report.html +++ b/typo3/sysext/linkvalidator/Resources/Private/Templates/Backend/Report.html @@ -14,14 +14,18 @@ <f:if condition="{title}"> <h1>{title}</h1> </f:if> - <div class="row row-cols-auto align-items-start t3js-linkvalidator-settings mb-4"> + <div class="row row-cols-auto align-items-start t3js-linkvalidator-settings"> <div class="col"> - <h4><f:translate key="LLL:EXT:linkvalidator/Resources/Private/Language/Module/locallang.xlf:report.statistics.header" /></h4> - <f:render partial="CheckOptions" arguments="{_all}" /> + <div class="form-group"> + <label class="form-label"><f:translate key="LLL:EXT:linkvalidator/Resources/Private/Language/Module/locallang.xlf:report.statistics.header" /></label> + <f:render partial="CheckOptions" arguments="{_all}" /> + </div> </div> - <div class="col mb-3"> - <h4><f:translate key="LLL:EXT:linkvalidator/Resources/Private/Language/Module/locallang.xlf:report.func.title" /></h4> - <f:render partial="LevelSelector" arguments="{_all}" /> + <div class="col"> + <div class="form-group"> + <label class="form-label"><f:translate key="LLL:EXT:linkvalidator/Resources/Private/Language/Module/locallang.xlf:report.func.title" /></label> + <f:render partial="LevelSelector" arguments="{_all}" /> + </div> </div> <div class="col-12"> <input @@ -35,7 +39,7 @@ </div> </div> - <h3><f:translate key="LLL:EXT:linkvalidator/Resources/Private/Language/Module/locallang.xlf:list.header" /></h3> + <h2><f:translate key="LLL:EXT:linkvalidator/Resources/Private/Language/Module/locallang.xlf:list.header" /></h2> <f:if condition="{brokenLinks -> f:count()}"> <f:then> <div class="table-fit"> diff --git a/typo3/sysext/lowlevel/Classes/Controller/DatabaseIntegrityController.php b/typo3/sysext/lowlevel/Classes/Controller/DatabaseIntegrityController.php index 83ae6604854b050ffba4202ad9ada7d88b560487..505e684b2e72b0f598bda9f72d364f825d826b5a 100644 --- a/typo3/sysext/lowlevel/Classes/Controller/DatabaseIntegrityController.php +++ b/typo3/sysext/lowlevel/Classes/Controller/DatabaseIntegrityController.php @@ -409,6 +409,7 @@ class DatabaseIntegrityController 'binaryPath' => ExtensionManagementUtility::extPath('core', 'bin/typo3'), 'referenceIndexResult' => $referenceIndexResult, ]); + return $view->renderResponse('ReferenceIndex'); } @@ -421,18 +422,21 @@ class DatabaseIntegrityController $this->showFieldAndTableNames = $this->getBackendUserAuthentication()->shallDisplayDebugInformation(); $searchMode = $this->MOD_SETTINGS['search']; $this->setFormName('queryform'); - $submenu = '<div class="row row-cols-auto align-items-end g-3 mb-4">'; - $submenu .= '<div class="col">' . self::getDropdownMenu(0, 'SET[search]', $searchMode, $this->MOD_MENU['search'], $request) . '</div>'; + $submenu = ''; + $submenu .= '<div class="form-row">'; + $submenu .= '<div class="form-group">' . self::getDropdownMenu(0, 'SET[search]', $searchMode, $this->MOD_MENU['search'], $request) . '</div>'; if ($this->MOD_SETTINGS['search'] === 'query') { - $submenu .= '<div class="col">' . self::getDropdownMenu(0, 'SET[search_query_makeQuery]', $this->MOD_SETTINGS['search_query_makeQuery'], $this->MOD_MENU['search_query_makeQuery'], $request) . '</div>'; + $submenu .= '<div class="form-group">' . self::getDropdownMenu(0, 'SET[search_query_makeQuery]', $this->MOD_SETTINGS['search_query_makeQuery'], $this->MOD_MENU['search_query_makeQuery'], $request) . '</div>'; } $submenu .= '</div>'; if ($this->MOD_SETTINGS['search'] === 'query') { + $submenu .= '<div class="form-group">'; $submenu .= '<div class="form-check">' . self::getFuncCheck(0, 'SET[search_query_smallparts]', $this->MOD_SETTINGS['search_query_smallparts'] ?? '', $request, '', '', 'id="checkSearch_query_smallparts"') . '<label class="form-check-label" for="checkSearch_query_smallparts">' . $lang->sL('LLL:EXT:lowlevel/Resources/Private/Language/locallang.xlf:showSQL') . '</label></div>'; $submenu .= '<div class="form-check">' . self::getFuncCheck(0, 'SET[search_result_labels]', $this->MOD_SETTINGS['search_result_labels'] ?? '', $request, '', '', 'id="checkSearch_result_labels"') . '<label class="form-check-label" for="checkSearch_result_labels">' . $lang->sL('LLL:EXT:lowlevel/Resources/Private/Language/locallang.xlf:useFormattedStrings') . '</label></div>'; $submenu .= '<div class="form-check">' . self::getFuncCheck(0, 'SET[labels_noprefix]', $this->MOD_SETTINGS['labels_noprefix'] ?? '', $request, '', '', 'id="checkLabels_noprefix"') . '<label class="form-check-label" for="checkLabels_noprefix">' . $lang->sL('LLL:EXT:lowlevel/Resources/Private/Language/locallang.xlf:dontUseOrigValues') . '</label></div>'; $submenu .= '<div class="form-check">' . self::getFuncCheck(0, 'SET[options_sortlabel]', $this->MOD_SETTINGS['options_sortlabel'] ?? '', $request, '', '', 'id="checkOptions_sortlabel"') . '<label class="form-check-label" for="checkOptions_sortlabel">' . $lang->sL('LLL:EXT:lowlevel/Resources/Private/Language/locallang.xlf:sortOptions') . '</label></div>'; $submenu .= '<div class="form-check">' . self::getFuncCheck(0, 'SET[show_deleted]', $this->MOD_SETTINGS['show_deleted'] ?? 0, $request, '', '', 'id="checkShow_deleted"') . '<label class="form-check-label" for="checkShow_deleted">' . $lang->sL('LLL:EXT:lowlevel/Resources/Private/Language/locallang.xlf:showDeleted') . '</label></div>'; + $submenu .= '</div>'; } $view->assign('submenu', $submenu); $view->assign('searchMode', $searchMode); @@ -445,6 +449,7 @@ class DatabaseIntegrityController $view->assign('searchOptions', $this->form()); $view->assign('results', $this->search($request)); } + return $view->renderResponse('CustomSearch'); } @@ -460,8 +465,8 @@ class DatabaseIntegrityController $msg = $this->procesStoreControl($request); $userTsConfig = $this->getBackendUserAuthentication()->getTSConfig(); if (!($userTsConfig['mod.']['dbint.']['disableStoreControl'] ?? false)) { - $output .= '<h2>Load/Save Query</h2>'; - $output .= '<div>' . $this->makeStoreControl() . '</div>'; + $output .= '<h2 class="headline-spaced">Load/Save Query</h2>'; + $output .= $this->makeStoreControl(); $output .= $msg; } // Query Maker: @@ -469,8 +474,8 @@ class DatabaseIntegrityController if ($this->formName) { $this->setFormName($this->formName); } - $tmpCode = $this->makeSelectorTable($this->MOD_SETTINGS, $request); - $output .= '<div id="query"></div><h2>Make query</h2><div>' . $tmpCode . '</div>'; + $output .= '<h2>Make query</h2>'; + $output .= $this->makeSelectorTable($this->MOD_SETTINGS, $request); $mQ = $this->MOD_SETTINGS['search_query_makeQuery'] ?? ''; // Make form elements: if ($this->table && is_array($GLOBALS['TCA'][$this->table])) { @@ -505,22 +510,38 @@ class DatabaseIntegrityController $dataRows = $connection->executeQuery($selectQueryString)->fetchAllAssociative(); } if (!($userTsConfig['mod.']['dbint.']['disableShowSQLQuery'] ?? false)) { - $output .= '<h2>SQL query</h2><div><code>' . htmlspecialchars($fullQueryString) . '</code></div>'; + $output .= '<h2>SQL query</h2>'; + $output .= '<pre class="language-sql">'; + $output .= '<code class="language-sql">'; + $output .= htmlspecialchars($fullQueryString); + $output .= '</code>'; + $output .= '</pre>'; } $cPR = $this->getQueryResultCode($mQ, $dataRows, $this->table, $request); - $output .= '<h2>' . ($cPR['header'] ?? '') . '</h2><div>' . $cPR['content'] . '</div>'; + if ($cPR['header'] ?? null) { + $output .= '<h2>' . $cPR['header'] . '</h2>'; + } + if ($cPR['content'] ?? null) { + $output .= $cPR['content']; + } } catch (DBALException $e) { if (!($userTsConfig['mod.']['dbint.']['disableShowSQLQuery'] ?? false)) { - $output .= '<h2>SQL query</h2><div><code>' . htmlspecialchars($fullQueryString) . '</code></div>'; + $output .= '<h2>SQL query</h2>'; + $output .= '<pre class="language-sql">'; + $output .= '<code class="language-sql">'; + $output .= htmlspecialchars($fullQueryString); + $output .= '</code>'; + $output .= '</pre>'; } - $out = '<p><strong>Error: <span class="text-danger">' - . htmlspecialchars($e->getMessage()) - . '</span></strong></p>'; - $output .= '<h2>SQL error</h2><div>' . $out . '</div>'; + $output .= '<h2>SQL error</h2>'; + $output .= '<div class="alert alert-danger">'; + $output .= '<p class="alert-message"><strong>Error:</strong> ' . htmlspecialchars($e->getMessage()) . '</p>'; + $output .= '</div>'; } } } - return '<div class="database-query-builder">' . $output . '</div>'; + + return $output; } protected function getSelectQuery(string $qString = ''): string @@ -646,6 +667,7 @@ class DatabaseIntegrityController } } } + return $theList; } @@ -660,7 +682,7 @@ class DatabaseIntegrityController switch ($type) { case 'count': $cPR['header'] = 'Count'; - $cPR['content'] = '<br><strong>' . (int)$dataRows[0] . '</strong> records selected.'; + $cPR['content'] = '<p><strong>' . (int)$dataRows[0] . '</strong> records selected.</p>'; break; case 'all': $rowArr = []; @@ -675,9 +697,11 @@ class DatabaseIntegrityController } if (!empty($rowArr)) { $cPR['header'] = 'Result'; - $out .= '<div class="table-fit"><table class="table table-striped table-hover">' - . $this->resultRowTitles((array)$dataRow, $GLOBALS['TCA'][$table]) . implode(LF, $rowArr) - . '</table></div>'; + $out .= '<div class="table-fit">'; + $out .= '<table class="table table-striped table-hover">'; + $out .= $this->resultRowTitles((array)$dataRow, $GLOBALS['TCA'][$table]) . implode(LF, $rowArr); + $out .= '</table>'; + $out .= '</div>'; } else { $this->renderNoResultsFoundMessage(); } @@ -696,12 +720,16 @@ class DatabaseIntegrityController } if (!empty($rowArr)) { $cPR['header'] = 'Result'; - $out .= '<textarea name="whatever" rows="20" class="font-monospace" style="width:100%">' - . htmlspecialchars(implode(LF, $rowArr)) - . '</textarea>'; + $out .= '<div class="form-group">'; + $out .= '<textarea class="form-control" name="whatever" rows="20" class="font-monospace" style="width:100%">'; + $out .= htmlspecialchars(implode(LF, $rowArr)); + $out .= '</textarea>'; + $out .= '</div>'; if (!$this->noDownloadB) { - $out .= '<br><input class="btn btn-default" type="submit" name="download_file" ' - . 'value="Click to download file">'; + $out .= '<button class="btn btn-default" type="submit" name="download_file" value="Click to download file">'; + $out .= $this->iconFactory->getIcon('actions-file-csv-download', Icon::SIZE_SMALL)->render(); + $out .= ' Click to download file'; + $out .= '</button>'; } // Downloads file: // @todo: args. routing anyone? @@ -721,11 +749,12 @@ class DatabaseIntegrityController case 'explain': default: foreach ($dataRows as $dataRow) { - $out .= '<br />' . DebugUtility::viewArray($dataRow); + $out .= DebugUtility::viewArray($dataRow); } $cPR['header'] = 'Explain SQL query'; $cPR['content'] = $out; } + return $cPR; } @@ -737,6 +766,7 @@ class DatabaseIntegrityController $valueArray[$key] = $this->getProcessedValueExtra($table, $key, (string)$val, $conf, ';'); } } + return CsvUtility::csvValues($valueArray, $delim, $quote); } @@ -768,6 +798,7 @@ class DatabaseIntegrityController $tableHeader[] = '<th></th>'; // Close header row $tableHeader[] = '</tr></thead>'; + return implode(LF, $tableHeader); } @@ -789,7 +820,7 @@ class DatabaseIntegrityController $out .= '<td>' . $fVnew . '</td>'; } } - $out .= '<td>'; + $out .= '<td class="col-control">'; $uriBuilder = GeneralUtility::makeInstance(UriBuilder::class); if (!($row['deleted'] ?? false)) { @@ -804,7 +835,8 @@ class DatabaseIntegrityController . HttpUtility::buildQueryString(['SET' => $request->getParsedBody()['SET'] ?? []], '&'), ]); $out .= '<a class="btn btn-default" href="' . htmlspecialchars($url) . '">' - . $this->iconFactory->getIcon('actions-open', Icon::SIZE_SMALL)->render() . '</a>'; + . $this->iconFactory->getIcon('actions-open', Icon::SIZE_SMALL)->render() + . '</a>'; $out .= '</div><div class="btn-group" role="group">'; $out .= sprintf( '<a class="btn btn-default" href="#" data-dispatch-action="%s" data-dispatch-args-list="%s">%s</a>', @@ -835,6 +867,7 @@ class DatabaseIntegrityController } } $out .= '</td></tr>'; + return $out; } @@ -957,6 +990,7 @@ class DatabaseIntegrityController default: $out = htmlspecialchars($fieldValue); } + return $out; } @@ -1144,6 +1178,7 @@ class DatabaseIntegrityController } } } + return $out; } @@ -1179,6 +1214,7 @@ class DatabaseIntegrityController } $first = false; } + return $qs; } @@ -1228,6 +1264,7 @@ class DatabaseIntegrityController $qsTmp = str_replace('#VALUE1#', trim($queryBuilder->quote((string)$inputVal), '\''), $qsTmp); } $qs .= trim((string)$qsTmp); + return $qs; } @@ -1261,6 +1298,7 @@ class DatabaseIntegrityController // fallback to float casting, the whole class smells like it needs a refactoring. $inputVal = (float)($var ?? 0.0); } + return $inputVal; } @@ -1286,6 +1324,7 @@ class DatabaseIntegrityController } $format = 'Y-m-d\\TH:i:s\\Z'; $formattedDate = \DateTime::createFromFormat($format, (string)$date); + return $formattedDate && $formattedDate->format($format) === $date; } @@ -1298,12 +1337,8 @@ class DatabaseIntegrityController // Make output if (in_array('table', $enableArr) && !($userTsConfig['mod.']['dbint.']['disableSelectATable'] ?? false)) { $out[] = '<div class="form-group">'; - $out[] = '<label for="SET[queryTable]">Select a table:</label>'; - $out[] = '<div class="row row-cols-auto">'; - $out[] = '<div class="col">'; - $out[] = $this->mkTableSelect('SET[queryTable]', $this->table); - $out[] = '</div>'; - $out[] = '</div>'; + $out[] = '<label class="form-label" for="SET[queryTable]">Select a table:</label>'; + $out[] = $this->mkTableSelect('SET[queryTable]', $this->table); $out[] = '</div>'; } if ($this->table) { @@ -1341,67 +1376,61 @@ class DatabaseIntegrityController $codeArr = $this->getFormElements(); $queryCode = $this->printCodeArray($codeArr); if (in_array('fields', $enableArr) && !($userTsConfig['mod.']['dbint.']['disableSelectFields'] ?? false)) { - $out[] = '<div class="form-group form-group-with-button-addon">'; - $out[] = ' <label for="SET[queryFields]">Select fields:</label>'; + $out[] = '<div class="form-group">'; + $out[] = '<label class="form-label" for="SET[queryFields]">Select fields:</label>'; $out[] = $this->mkFieldToInputSelect('SET[queryFields]', $this->extFieldLists['queryFields']); $out[] = '</div>'; } if (in_array('query', $enableArr) && !($userTsConfig['mod.']['dbint.']['disableMakeQuery'] ?? false)) { $out[] = '<div class="form-group">'; - $out[] = ' <label>Make Query:</label>'; + $out[] = '<label class="form-label">Make Query:</label>'; $out[] = $queryCode; $out[] = '</div>'; } if (in_array('group', $enableArr) && !($userTsConfig['mod.']['dbint.']['disableGroupBy'] ?? false)) { $out[] = '<div class="form-group">'; - $out[] = '<label for="SET[queryGroup]">Group By:</label>'; - $out[] = '<div class="row row-cols-auto">'; - $out[] = '<div class="col">'; - $out[] = $this->mkTypeSelect('SET[queryGroup]', $this->extFieldLists['queryGroup'], ''); - $out[] = '</div>'; - $out[] = '</div>'; + $out[] = '<label class="form-label" for="SET[queryGroup]">Group By:</label>'; + $out[] = $this->mkTypeSelect('SET[queryGroup]', $this->extFieldLists['queryGroup'], ''); $out[] = '</div>'; } if (in_array('order', $enableArr) && !($userTsConfig['mod.']['dbint.']['disableOrderBy'] ?? false)) { $orderByArr = explode(',', $this->extFieldLists['queryOrder']); $orderBy = []; - $orderBy[] = '<div class="row row-cols-auto align-items-center">'; - $orderBy[] = '<div class="col">'; - $orderBy[] = $this->mkTypeSelect('SET[queryOrder]', $orderByArr[0], ''); - $orderBy[] = '</div>'; - $orderBy[] = '<div class="col mt-2">'; - $orderBy[] = '<div class="form-check">'; - $orderBy[] = self::getFuncCheck(0, 'SET[queryOrderDesc]', $modSettings['queryOrderDesc'] ?? '', $request, '', '', 'id="checkQueryOrderDesc"'); - $orderBy[] = '<label class="form-check-label" for="checkQueryOrderDesc">Descending</label>'; - $orderBy[] = '</div>'; + $orderBy[] = '<div class="form-group">'; + $orderBy[] = '<div class="input-group">'; + $orderBy[] = $this->mkTypeSelect('SET[queryOrder]', $orderByArr[0], ''); + $orderBy[] = '<div class="input-group-text">'; + $orderBy[] = '<div class="form-check form-check-type-toggle">'; + $orderBy[] = self::getFuncCheck(0, 'SET[queryOrderDesc]', $modSettings['queryOrderDesc'] ?? '', $request, '', '', 'id="checkQueryOrderDesc"'); + $orderBy[] = '<label class="form-check-label" for="checkQueryOrderDesc">Descending</label>'; + $orderBy[] = '</div>'; $orderBy[] = '</div>'; + $orderBy[] = '</div>'; $orderBy[] = '</div>'; if ($orderByArr[0]) { - $orderBy[] = '<div class="row row-cols-auto align-items-center mt-2">'; - $orderBy[] = '<div class="col">'; - $orderBy[] = '<div class="input-group">'; - $orderBy[] = $this->mkTypeSelect('SET[queryOrder2]', $orderByArr[1] ?? '', ''); - $orderBy[] = '</div>'; - $orderBy[] = '</div>'; - $orderBy[] = '<div class="col mt-2">'; - $orderBy[] = '<div class="form-check">'; - $orderBy[] = self::getFuncCheck(0, 'SET[queryOrder2Desc]', $modSettings['queryOrder2Desc'] ?? false, $request, '', '', 'id="checkQueryOrder2Desc"'); - $orderBy[] = '<label class="form-check-label" for="checkQueryOrder2Desc">Descending</label>'; - $orderBy[] = '</div>'; + $orderBy[] = '<div class="form-group">'; + $orderBy[] = '<div class="input-group">'; + $orderBy[] = $this->mkTypeSelect('SET[queryOrder2]', $orderByArr[1] ?? '', ''); + $orderBy[] = '<div class="input-group-text">'; + $orderBy[] = '<div class="form-check form-check-type-toggle">'; + $orderBy[] = self::getFuncCheck(0, 'SET[queryOrder2Desc]', $modSettings['queryOrder2Desc'] ?? false, $request, '', '', 'id="checkQueryOrder2Desc"'); + $orderBy[] = '<label class="form-check-label" for="checkQueryOrder2Desc">Descending</label>'; + $orderBy[] = '</div>'; $orderBy[] = '</div>'; + $orderBy[] = '</div>'; $orderBy[] = '</div>'; } $out[] = '<div class="form-group">'; - $out[] = ' <label>Order By:</label>'; - $out[] = implode(LF, $orderBy); + $out[] = ' <label class="form-label">Order By:</label>'; + $out[] = implode(LF, $orderBy); $out[] = '</div>'; } if (in_array('limit', $enableArr) && !($userTsConfig['mod.']['dbint.']['disableLimit'] ?? false)) { $limit = []; $limit[] = '<div class="input-group">'; - $limit[] = $this->updateIcon(); - $limit[] = '<input type="text" class="form-control" value="' . htmlspecialchars($this->extFieldLists['queryLimit']) . '" name="SET[queryLimit]" id="queryLimit">'; + $limit[] = $this->updateIcon(); + $limit[] = '<input type="text" class="form-control" value="' . htmlspecialchars($this->extFieldLists['queryLimit']) . '" name="SET[queryLimit]" id="queryLimit">'; $limit[] = '</div>'; $prevLimit = $limitBegin - $limitLength < 0 ? 0 : $limitBegin - $limitLength; @@ -1424,29 +1453,30 @@ class DatabaseIntegrityController } $out[] = '<div class="form-group">'; - $out[] = ' <label>Limit:</label>'; - $out[] = ' <div class="row row-cols-auto">'; - $out[] = ' <div class="col">'; + $out[] = ' <label class="form-label">Limit:</label>'; + $out[] = ' <div class="form-row">'; + $out[] = ' <div class="form-group">'; $out[] = implode(LF, $limit); - $out[] = ' </div>'; - $out[] = ' <div class="col">'; - $out[] = ' <div class="btn-group t3js-limit-submit">'; - $out[] = $prevButton; - $out[] = $nextButton; - $out[] = ' </div>'; - $out[] = ' </div>'; - $out[] = ' <div class="col">'; - $out[] = ' <div class="btn-group t3js-limit-submit">'; - $out[] = ' <input type="button" class="btn btn-default" data-value="10" value="10">'; - $out[] = ' <input type="button" class="btn btn-default" data-value="20" value="20">'; - $out[] = ' <input type="button" class="btn btn-default" data-value="50" value="50">'; - $out[] = ' <input type="button" class="btn btn-default" data-value="100" value="100">'; - $out[] = ' </div>'; - $out[] = ' </div>'; - $out[] = ' </div>'; + $out[] = ' </div>'; + $out[] = ' <div class="form-group">'; + $out[] = ' <div class="btn-group t3js-limit-submit">'; + $out[] = $prevButton; + $out[] = $nextButton; + $out[] = ' </div>'; + $out[] = ' </div>'; + $out[] = ' <div class="form-group">'; + $out[] = ' <div class="btn-group t3js-limit-submit">'; + $out[] = ' <input type="button" class="btn btn-default" data-value="10" value="10">'; + $out[] = ' <input type="button" class="btn btn-default" data-value="20" value="20">'; + $out[] = ' <input type="button" class="btn btn-default" data-value="50" value="50">'; + $out[] = ' <input type="button" class="btn btn-default" data-value="100" value="100">'; + $out[] = ' </div>'; + $out[] = ' </div>'; + $out[] = ' </div>'; $out[] = '</div>'; } } + return implode(LF, $out); } @@ -1492,6 +1522,7 @@ class DatabaseIntegrityController $queryConfig[$key]['inputValue1'] = $this->cleanInputVal($queryConfig[$key], '1'); } } + return $queryConfig; } @@ -1506,6 +1537,7 @@ class DatabaseIntegrityController return $key; } } + return $first; } @@ -1524,6 +1556,7 @@ class DatabaseIntegrityController return $i; } } + return $first; } @@ -1575,7 +1608,7 @@ class DatabaseIntegrityController $lineHTML[] = ''; break; case 'date': - $lineHTML[] = '<div class="row row-cols-auto mb-2 mb-sm-0">'; + $lineHTML[] = '<div class="form-row">'; $lineHTML[] = $this->makeComparisonSelector($subscript, $fieldName, $conf); if ($conf['comparison'] === 100 || $conf['comparison'] === 101) { // between @@ -1587,7 +1620,7 @@ class DatabaseIntegrityController $lineHTML[] = '</div>'; break; case 'time': - $lineHTML[] = '<div class="row row-cols-auto mb-2 mb-sm-0">'; + $lineHTML[] = '<div class="form-row">'; $lineHTML[] = $this->makeComparisonSelector($subscript, $fieldName, $conf); if ($conf['comparison'] === 100 || $conf['comparison'] === 101) { // between: @@ -1601,16 +1634,16 @@ class DatabaseIntegrityController case 'multiple': case 'binary': case 'relation': - $lineHTML[] = '<div class="row row-cols-auto mb-2 mb-sm-0">'; + $lineHTML[] = '<div class="form-row">'; $lineHTML[] = $this->makeComparisonSelector($subscript, $fieldName, $conf); - $lineHTML[] = '<div class="col mb-sm-2">'; + $lineHTML[] = '<div class="form-group">'; if ($conf['comparison'] === 68 || $conf['comparison'] === 69 || $conf['comparison'] === 162 || $conf['comparison'] === 163) { $lineHTML[] = '<select class="form-select" name="' . $fieldPrefix . '[inputValue][]" multiple="multiple">'; } elseif ($conf['comparison'] === 66 || $conf['comparison'] === 67) { if (is_array($conf['inputValue'])) { $conf['inputValue'] = implode(',', $conf['inputValue']); } - $lineHTML[] = '<input class="form-control t3js-clearable" type="text" value="' . htmlspecialchars($conf['inputValue'] ?? '') . '" name="' . $fieldPrefix . '[inputValue]">'; + $lineHTML[] = '<input class="form-control form-control-clearable t3js-clearable" type="text" value="' . htmlspecialchars($conf['inputValue'] ?? '') . '" name="' . $fieldPrefix . '[inputValue]">'; } elseif ($conf['comparison'] === 64) { if (is_array($conf['inputValue'])) { $conf['inputValue'] = $conf['inputValue'][0]; @@ -1627,41 +1660,60 @@ class DatabaseIntegrityController $lineHTML[] = '</div>'; break; case 'boolean': - $lineHTML[] = '<div class="row row-cols-auto mb-2 mb-sm-0">'; + $lineHTML[] = '<div class="form-row">'; $lineHTML[] = $this->makeComparisonSelector($subscript, $fieldName, $conf); $lineHTML[] = '<input type="hidden" value="1" name="' . $fieldPrefix . '[inputValue]">'; $lineHTML[] = '</div>'; break; default: - $lineHTML[] = '<div class="row row-cols-auto mb-2 mb-sm-0">'; + $lineHTML[] = '<div class="form-row">'; $lineHTML[] = $this->makeComparisonSelector($subscript, $fieldName, $conf); - $lineHTML[] = '<div class="col mb-sm-2">'; if ($conf['comparison'] === 37 || $conf['comparison'] === 36) { // between: - $lineHTML[] = '<input class="form-control t3js-clearable" type="text" value="' . htmlspecialchars($conf['inputValue'] ?? '') . '" name="' . $fieldPrefix . '[inputValue]">'; - $lineHTML[] = '<input class="form-control t3js-clearable" type="text" value="' . htmlspecialchars($conf['inputValue1'] ?? '') . '" name="' . $fieldPrefix . '[inputValue1]">'; + $lineHTML[] = '<div class="form-group">'; + $lineHTML[] = ' <input class="form-control form-control-clearable t3js-clearable" type="text" value="' . htmlspecialchars($conf['inputValue'] ?? '') . '" name="' . $fieldPrefix . '[inputValue]">'; + $lineHTML[] = '</div>'; + $lineHTML[] = '<div class="form-group">'; + $lineHTML[] = ' <input class="form-control form-control-clearable t3js-clearable" type="text" value="' . htmlspecialchars($conf['inputValue1'] ?? '') . '" name="' . $fieldPrefix . '[inputValue1]">'; + $lineHTML[] = '</div>'; } else { - $lineHTML[] = '<input class="form-control t3js-clearable" type="text" value="' . htmlspecialchars($conf['inputValue'] ?? '') . '" name="' . $fieldPrefix . '[inputValue]">'; + $lineHTML[] = '<div class="form-group">'; + $lineHTML[] = ' <input class="form-control form-control-clearable t3js-clearable" type="text" value="' . htmlspecialchars($conf['inputValue'] ?? '') . '" name="' . $fieldPrefix . '[inputValue]">'; + $lineHTML[] = '</div>'; } $lineHTML[] = '</div>'; - $lineHTML[] = '</div>'; } if ($fieldType !== 'ignore') { - $lineHTML[] = '<div class="row row-cols-auto mb-2">'; + $lineHTML[] = '<div class="form-row">'; $lineHTML[] = '<div class="btn-group">'; $lineHTML[] = $this->updateIcon(); if ($loopCount) { - $lineHTML[] = '<button class="btn btn-default" title="Remove condition" name="qG_del' . htmlspecialchars($subscript) . '">' . $this->iconFactory->getIcon('actions-delete', Icon::SIZE_SMALL)->render() . '</button>'; + $lineHTML[] = '' + . '<button class="btn btn-default" title="Remove condition" name="qG_del' . htmlspecialchars($subscript) . '">' + . $this->iconFactory->getIcon('actions-delete', Icon::SIZE_SMALL)->render() + . '</button>'; } - $lineHTML[] = '<button class="btn btn-default" title="Add condition" name="qG_ins' . htmlspecialchars($subscript) . '">' . $this->iconFactory->getIcon('actions-plus', Icon::SIZE_SMALL)->render() . '</button>'; + $lineHTML[] = '' + . '<button class="btn btn-default" title="Add condition" name="qG_ins' . htmlspecialchars($subscript) . '">' + . $this->iconFactory->getIcon('actions-plus', Icon::SIZE_SMALL)->render() + . '</button>'; if ($c != 0) { - $lineHTML[] = '<button class="btn btn-default" title="Move up" name="qG_up' . htmlspecialchars($subscript) . '">' . $this->iconFactory->getIcon('actions-chevron-up', Icon::SIZE_SMALL)->render() . '</button>'; + $lineHTML[] = '' + . '<button class="btn btn-default" title="Move up" name="qG_up' . htmlspecialchars($subscript) . '">' + . $this->iconFactory->getIcon('actions-chevron-up', Icon::SIZE_SMALL)->render() + . '</button>'; } if ($c != 0 && $fieldType !== 'newlevel') { - $lineHTML[] = '<button class="btn btn-default" title="New level" name="qG_nl' . htmlspecialchars($subscript) . '">' . $this->iconFactory->getIcon('actions-chevron-right', Icon::SIZE_SMALL)->render() . '</button>'; + $lineHTML[] = '' + . '<button class="btn btn-default" title="New level" name="qG_nl' . htmlspecialchars($subscript) . '">' + . $this->iconFactory->getIcon('actions-chevron-right', Icon::SIZE_SMALL)->render() + . '</button>'; } if ($fieldType === 'newlevel') { - $lineHTML[] = '<button class="btn btn-default" title="Collapse new level" name="qG_remnl' . htmlspecialchars($subscript) . '">' . $this->iconFactory->getIcon('actions-chevron-left', Icon::SIZE_SMALL)->render() . '</button>'; + $lineHTML[] = '' + . '<button class="btn btn-default" title="Collapse new level" name="qG_remnl' . htmlspecialchars($subscript) . '">' + . $this->iconFactory->getIcon('actions-chevron-left', Icon::SIZE_SMALL)->render() + . '</button>'; } $lineHTML[] = '</div>'; $lineHTML[] = '</div>'; @@ -1673,6 +1725,7 @@ class DatabaseIntegrityController $loopCount = 1; } $this->queryConfig = $queryConfig; + return $codeArr; } @@ -1681,15 +1734,16 @@ class DatabaseIntegrityController $value = strtotime($timestamp) ? date($GLOBALS['TYPO3_CONF_VARS']['SYS']['hhmm'] . ' ' . $GLOBALS['TYPO3_CONF_VARS']['SYS']['ddmmyy'], (int)strtotime($timestamp)) : ''; $id = StringUtility::getUniqueId('dt_'); $html = []; - $html[] = '<div class="col mb-sm-2">'; + $html[] = '<div class="form-group">'; $html[] = ' <div class="input-group" id="' . $id . '-wrapper">'; - $html[] = ' <input data-formengine-input-name="' . htmlspecialchars($name) . '" value="' . $value . '" class="form-control t3js-datetimepicker t3js-clearable" data-date-type="' . htmlspecialchars($type) . '" type="text" id="' . $id . '">'; + $html[] = ' <input data-formengine-input-name="' . htmlspecialchars($name) . '" value="' . $value . '" class="form-control form-control-clearable t3js-datetimepicker t3js-clearable" data-date-type="' . htmlspecialchars($type) . '" type="text" id="' . $id . '">'; $html[] = ' <input name="' . htmlspecialchars($name) . '" value="' . htmlspecialchars($timestamp) . '" type="hidden">'; $html[] = ' <button class="btn btn-default" type="button" data-global-event="click" data-action-focus="#' . $id . '">'; $html[] = $this->iconFactory->getIcon('actions-calendar-alternative', Icon::SIZE_SMALL)->render(); $html[] = ' </button>'; $html[] = ' </div>'; $html[] = '</div>'; + return implode(LF, $html); } @@ -1882,6 +1936,7 @@ class DatabaseIntegrityController } } } + return implode(LF, $out); } @@ -1889,17 +1944,16 @@ class DatabaseIntegrityController { $out = []; if ($draw) { - $out[] = '<div class="row row-cols-auto mb-2">'; - $out[] = ' <div class="col">'; - $out[] = ' <select class="form-select' . ($submit ? ' t3js-submit-change' : '') . '" name="' . htmlspecialchars($name) . '[operator]">'; - $out[] = ' <option value="AND"' . (!$op || $op === 'AND' ? ' selected' : '') . '>' . htmlspecialchars($this->lang['AND']) . '</option>'; - $out[] = ' <option value="OR"' . ($op === 'OR' ? ' selected' : '') . '>' . htmlspecialchars($this->lang['OR']) . '</option>'; - $out[] = ' </select>'; - $out[] = ' </div>'; + $out[] = '<div class="form-group">'; + $out[] = ' <select class="form-select' . ($submit ? ' t3js-submit-change' : '') . '" name="' . htmlspecialchars($name) . '[operator]">'; + $out[] = ' <option value="AND"' . (!$op || $op === 'AND' ? ' selected' : '') . '>' . htmlspecialchars($this->lang['AND']) . '</option>'; + $out[] = ' <option value="OR"' . ($op === 'OR' ? ' selected' : '') . '>' . htmlspecialchars($this->lang['OR']) . '</option>'; + $out[] = ' </select>'; $out[] = '</div>'; } else { $out[] = '<input type="hidden" value="' . htmlspecialchars($op) . '" name="' . htmlspecialchars($name) . '[operator]">'; } + return implode(LF, $out); } @@ -1907,17 +1961,20 @@ class DatabaseIntegrityController { $fieldPrefix = $this->name . $subscript; $lineHTML = []; - $lineHTML[] = '<div class="col mb-sm-2">'; - $lineHTML[] = $this->mkTypeSelect($fieldPrefix . '[type]', $fieldName); + $lineHTML[] = '<div class="form-group">'; + $lineHTML[] = $this->mkTypeSelect($fieldPrefix . '[type]', $fieldName); $lineHTML[] = '</div>'; - $lineHTML[] = '<div class="col mb-sm-2">'; - $lineHTML[] = ' <div class="input-group">'; - $lineHTML[] = $this->mkCompSelect($fieldPrefix . '[comparison]', (string)$conf['comparison'], ($conf['negate'] ?? null) ? 1 : 0); - $lineHTML[] = ' <span class="input-group-addon">'; - $lineHTML[] = ' <input type="checkbox" class="checkbox t3js-submit-click"' . (($conf['negate'] ?? null) ? ' checked' : '') . ' name="' . htmlspecialchars($fieldPrefix) . '[negate]">'; - $lineHTML[] = ' </span>'; - $lineHTML[] = ' </div>'; + $lineHTML[] = '<div class="form-group">'; + $lineHTML[] = ' <div class="input-group">'; + $lineHTML[] = $this->mkCompSelect($fieldPrefix . '[comparison]', (string)$conf['comparison'], ($conf['negate'] ?? null) ? 1 : 0); + $lineHTML[] = ' <span class="input-group-addon">'; + $lineHTML[] = ' <div class="form-check form-check-type-toggle">'; + $lineHTML[] = ' <input type="checkbox" class="form-check-input t3js-submit-click"' . (($conf['negate'] ?? null) ? ' checked' : '') . ' name="' . htmlspecialchars($fieldPrefix) . '[negate]">'; + $lineHTML[] = ' </div>'; + $lineHTML[] = ' </span>'; + $lineHTML[] = ' </div>'; $lineHTML[] = '</div>'; + return implode(LF, $lineHTML); } @@ -1932,6 +1989,7 @@ class DatabaseIntegrityController } } $out[] = '</select>'; + return implode(LF, $out); } @@ -1940,37 +1998,33 @@ class DatabaseIntegrityController $out = []; foreach (array_values($codeArr) as $queryComponent) { $out[] = '<div class="card">'; - $out[] = '<div class="card-body pb-2">'; + $out[] = '<div class="card-body">'; $out[] = $queryComponent['html']; if ($this->enableQueryParts) { - $out[] = '<div class="row row-cols-auto mb-2">'; - $out[] = '<div class="col">'; - $out[] = '<code class="m-0">'; - $out[] = htmlspecialchars($queryComponent['query']); - $out[] = '</code>'; - $out[] = '</div>'; - $out[] = '</div>'; + $out[] = '<pre class="language-sql">'; + $out[] = '<code class="language-sql">'; + $out[] = htmlspecialchars($queryComponent['query']); + $out[] = '</code>'; + $out[] = '</pre>'; } if (is_array($queryComponent['sub'] ?? null)) { - $out[] = '<div class="mb-2">'; - $out[] = $this->printCodeArray($queryComponent['sub'], $recursionLevel + 1); - $out[] = '</div>'; + $out[] = $this->printCodeArray($queryComponent['sub'], $recursionLevel + 1); } $out[] = '</div>'; $out[] = '</div>'; } + return implode(LF, $out); } protected function mkFieldToInputSelect(string $name, string $fieldName): string { $out = []; - $out[] = '<div class="input-group mb-2">'; - $out[] = $this->updateIcon(); - $out[] = '<input type="text" class="form-control t3js-clearable" value="' . htmlspecialchars($fieldName) . '" name="' . htmlspecialchars($name) . '">'; + $out[] = '<div class="input-group mb-1">'; + $out[] = $this->updateIcon(); + $out[] = '<input type="text" class="form-control form-control-clearable t3js-clearable" value="' . htmlspecialchars($fieldName) . '" name="' . htmlspecialchars($name) . '">'; $out[] = '</div>'; - $out[] = '<select class="form-select t3js-addfield" name="_fieldListDummy" size="5" data-field="' . htmlspecialchars($name) . '">'; foreach ($this->fields as $key => $value) { if (!$value['exclude'] || $this->getBackendUserAuthentication()->check('non_exclude_fields', $this->table . ':' . $key)) { @@ -1982,6 +2036,7 @@ class DatabaseIntegrityController } } $out[] = '</select>'; + return implode(LF, $out); } @@ -2101,6 +2156,7 @@ class DatabaseIntegrityController break; } } + return $retArr; } @@ -2124,6 +2180,7 @@ class DatabaseIntegrityController } } $out[] = '</select>'; + return implode(LF, $out); } @@ -2159,6 +2216,7 @@ class DatabaseIntegrityController } } $out[] = '</select>'; + return implode(LF, $out); } @@ -2321,6 +2379,7 @@ class DatabaseIntegrityController $fieldListArr[] = $GLOBALS['TCA'][$this->table]['ctrl']['sortby']; } } + return implode(',', $fieldListArr); } @@ -2335,23 +2394,26 @@ class DatabaseIntegrityController } $markup = []; - $markup[] = '<div class="load-queries">'; - $markup[] = ' <div class="row row-cols-auto">'; - $markup[] = ' <div class="col">'; - $markup[] = ' <select class="form-select" name="storeControl[STORE]" data-assign-store-control-title>' . implode(LF, $opt) . '</select>'; - $markup[] = ' </div>'; - $markup[] = ' <div class="col">'; - $markup[] = ' <input class="form-control" name="storeControl[title]" value="" type="text" max="80">'; - $markup[] = ' </div>'; - $markup[] = ' <div class="col">'; - $markup[] = ' <input class="btn btn-default" type="submit" name="storeControl[LOAD]" value="Load">'; - $markup[] = ' </div>'; - $markup[] = ' <div class="col">'; - $markup[] = ' <input class="btn btn-default" type="submit" name="storeControl[SAVE]" value="Save">'; - $markup[] = ' </div>'; - $markup[] = ' <div class="col">'; - $markup[] = ' <input class="btn btn-default" type="submit" name="storeControl[REMOVE]" value="Remove">'; - $markup[] = ' </div>'; + $markup[] = '<div class="form-row">'; + $markup[] = ' <div class="form-group">'; + $markup[] = ' <select class="form-select" name="storeControl[STORE]" data-assign-store-control-title>' . implode(LF, $opt) . '</select>'; + $markup[] = ' </div>'; + $markup[] = ' <div class="form-group">'; + $markup[] = ' <input class="form-control" name="storeControl[title]" value="" type="text" max="80">'; + $markup[] = ' </div>'; + $markup[] = ' <div class="form-group">'; + $markup[] = ' <button class="btn btn-default" type="submit" name="storeControl[LOAD]" value="Load">'; + $markup[] = $this->iconFactory->getIcon('actions-upload', Icon::SIZE_SMALL)->render(); + $markup[] = ' Load'; + $markup[] = ' </button>'; + $markup[] = ' <button class="btn btn-default" type="submit" name="storeControl[SAVE]" value="Save">'; + $markup[] = $this->iconFactory->getIcon('actions-save', Icon::SIZE_SMALL)->render(); + $markup[] = ' Save'; + $markup[] = ' </button>'; + $markup[] = ' <button class="btn btn-default" type="submit" name="storeControl[REMOVE]" value="Remove">'; + $markup[] = $this->iconFactory->getIcon('actions-delete', Icon::SIZE_SMALL)->render(); + $markup[] = ' Remove'; + $markup[] = ' </button>'; $markup[] = ' </div>'; $markup[] = '</div>'; @@ -2425,6 +2487,7 @@ class DatabaseIntegrityController 'ses' ); } + return $msg; } @@ -2437,6 +2500,7 @@ class DatabaseIntegrityController } } } + return $storeQueryConfigs; } @@ -2447,6 +2511,7 @@ class DatabaseIntegrityController foreach ($keyArr as $k) { $storeQueryConfigs[$index][$k] = $this->MOD_SETTINGS[$k] ?? null; } + return $storeQueryConfigs; } @@ -2458,6 +2523,7 @@ class DatabaseIntegrityController $writeArray[$k] = $storeQueryConfigs[$storeIndex][$k]; } } + return $writeArray; } @@ -2470,6 +2536,7 @@ class DatabaseIntegrityController if (is_array($savedStoreArray)) { $storeArray = array_merge($storeArray, $savedStoreArray); } + return $storeArray; } @@ -2477,12 +2544,12 @@ class DatabaseIntegrityController { $markup = []; $markup[] = '<div class="form-group">'; - $markup[] = '<input placeholder="Search Word" class="form-control" type="search" name="SET[sword]" value="' - . htmlspecialchars($this->MOD_SETTINGS['sword'] ?? '') . '">'; + $markup[] = '<input placeholder="Search Word" class="form-control" type="search" name="SET[sword]" value="' . htmlspecialchars($this->MOD_SETTINGS['sword'] ?? '') . '">'; $markup[] = '</div>'; $markup[] = '<div class="form-group">'; - $markup[] = '<input class="btn btn-default" type="submit" name="submit" value="Search All Records">'; + $markup[] = '<input class="btn btn-default" type="submit" name="submit" value="Search All Records">'; $markup[] = '</div>'; + return implode(LF, $markup); } @@ -2587,6 +2654,7 @@ class DatabaseIntegrityController } } } + return $out; } @@ -2704,6 +2772,7 @@ class DatabaseIntegrityController 'doktypes' => $doktypes, 'tables' => $tableStatistic, ]); + return $view->renderResponse('RecordStatistics'); } @@ -2718,6 +2787,7 @@ class DatabaseIntegrityController 'select_db' => $databaseIntegrityCheck->testDBRefs($databaseIntegrityCheck->getCheckSelectDBRefs()), 'group_db' => $databaseIntegrityCheck->testDBRefs($databaseIntegrityCheck->getCheckGroupDBRefs()), ]); + return $view->renderResponse('Relations'); } @@ -2782,13 +2852,11 @@ class DatabaseIntegrityController 'data-action-navigate' => '$data=~s/$value/', 'data-navigate-value' => $scriptUrl . '&' . $elementName . '=${value}', ], $additionalAttributes), true); + return ' - <div class="input-group"> - <!-- Function Menu of module --> <select class="form-select" ' . $attributes . '> ' . implode(LF, $options) . ' - </select> - </div>'; + </select>'; } /** @@ -2825,6 +2893,7 @@ class DatabaseIntegrityController 'data-navigate-value' => sprintf('%s&%s=${value}', $scriptUrl, $elementName), 'data-empty-value' => '0', ], true); + return '<input ' . $attributes . ($currentValue ? ' checked="checked"' : '') . diff --git a/typo3/sysext/lowlevel/Resources/Private/Templates/Configuration.html b/typo3/sysext/lowlevel/Resources/Private/Templates/Configuration.html index 8e06404debbee93eefc3fb2d589b29f615199756..dac60a5038bce58d872e4e3f55d763cddfec37e3 100644 --- a/typo3/sysext/lowlevel/Resources/Private/Templates/Configuration.html +++ b/typo3/sysext/lowlevel/Resources/Private/Templates/Configuration.html @@ -24,13 +24,13 @@ <h2>{treeName}</h2> - <div id="lowlevel-config" class="row row-cols-auto mb-3"> - <div class="col"> + <div id="lowlevel-config" class="form-row"> + <div class="form-group"> <form action="#"> <div class="input-group"> <input type="text" - class="form-control t3js-collapse-search-term" + class="form-control form-control-clearable t3js-collapse-search-term" name="searchValue" id="searchValue" data-persist-collapse-search-key="collapse-search-term-lowlevel-configuration-{treeLabelHash}" @@ -42,12 +42,12 @@ </div> </form> </div> - <div class="col d-flex align-items-center"> + <div class="d-flex align-items-center"> <span class="badge badge-success hidden t3js-collapse-states-search-numberOfSearchMatches"></span> </div> </div> - <div class="nowrap t3js-collapse-states-search-tree"> + <div class="t3js-collapse-states-search-tree"> <f:format.raw>{tree}</f:format.raw> </div> </form> diff --git a/typo3/sysext/lowlevel/Resources/Private/Templates/CustomSearch.html b/typo3/sysext/lowlevel/Resources/Private/Templates/CustomSearch.html index c19b0ae09c000b2cbac95a385edd0ba01edeba24..3e87b128c636c80da3e9f1dff1cfbd25127cefc9 100644 --- a/typo3/sysext/lowlevel/Resources/Private/Templates/CustomSearch.html +++ b/typo3/sysext/lowlevel/Resources/Private/Templates/CustomSearch.html @@ -5,8 +5,7 @@ <f:layout name="Module" /> -<f:section name="Content"> - +<f:section name="Before"> <f:if condition="{searchMode} == 'query'"> <f:be.pageRenderer includeJavaScriptModules="{ @@ -14,25 +13,33 @@ }" /> </f:if> +</f:section> - <h1>{f:translate(key:'LLL:EXT:lowlevel/Resources/Private/Language/locallang.xlf:search_whole_database')}</h1> +<f:section name="Content"> + <h1>{f:translate(key:'LLL:EXT:lowlevel/Resources/Private/Language/locallang.xlf:search_whole_database')}</h1> <f:format.raw>{submenu}</f:format.raw> + + <f:if condition="{searchMode} != 'query'"> + <h2>{f:translate(key:'LLL:EXT:lowlevel/Resources/Private/Language/locallang.xlf:searchOptions')}</h2> + </f:if> + <form action="" method="post" id="DatabaseIntegrityView" name="queryform"> <f:if condition="{searchMode} == 'query'"> <f:then> <f:format.raw>{queryMaker}</f:format.raw> </f:then> <f:else> - <h2>{f:translate(key:'LLL:EXT:lowlevel/Resources/Private/Language/locallang.xlf:searchOptions')}</h2> <f:format.raw>{searchOptions}</f:format.raw> - - <h2>{f:translate(key:'LLL:EXT:lowlevel/Resources/Private/Language/locallang.xlf:result')}</h2> - <f:format.raw>{results}</f:format.raw> </f:else> </f:if> </form> + <f:if condition="{results}"> + <h2>{f:translate(key:'LLL:EXT:lowlevel/Resources/Private/Language/locallang.xlf:result')}</h2> + <f:format.raw>{results}</f:format.raw> + </f:if> + </f:section> </html> diff --git a/typo3/sysext/lowlevel/Resources/Public/JavaScript/query-generator.js b/typo3/sysext/lowlevel/Resources/Public/JavaScript/query-generator.js index 2a6ea5ccd1e73806107331db637923574f6ae4c5..bb00a4ce3057ff2dd0c4e116a4a1a29b15ea4118 100644 --- a/typo3/sysext/lowlevel/Resources/Public/JavaScript/query-generator.js +++ b/typo3/sysext/lowlevel/Resources/Public/JavaScript/query-generator.js @@ -10,4 +10,4 @@ * * The TYPO3 project - inspiring people to share! */ -import $ from"jquery";import"@typo3/backend/input/clearable.js";import DateTimePicker from"@typo3/backend/date-time-picker.js";class QueryGenerator{constructor(){this.form=null,this.limitField=null,this.initialize()}initialize(){this.form=$('form[name="queryform"]'),this.limitField=$("#queryLimit"),this.form.on("click",".t3js-submit-click",(t=>{t.preventDefault(),this.doSubmit()})),this.form.on("change",".t3js-submit-change",(t=>{t.preventDefault(),this.doSubmit()})),this.form.on("click",'.t3js-limit-submit input[type="button"]',(t=>{t.preventDefault(),this.setLimit($(t.currentTarget).data("value")),this.doSubmit()})),this.form.on("click",".t3js-addfield",(t=>{t.preventDefault();const e=$(t.currentTarget);this.addValueToField(e.data("field"),e.val())})),this.form.on("change","[data-assign-store-control-title]",(t=>{const e=$(t.currentTarget),i=this.form.find('[name="storeControl[title]"]');"0"!==e.val()?i.val(e.find("option:selected").text()):i.val("")})),document.querySelectorAll('form[name="queryform"] .t3js-clearable').forEach((t=>t.clearable({onClear:()=>{this.doSubmit()}}))),document.querySelectorAll('form[name="queryform"] .t3js-datetimepicker').forEach((t=>DateTimePicker.initialize(t)))}doSubmit(){this.form.trigger("submit")}setLimit(t){this.limitField.val(t)}addValueToField(t,e){const i=this.form.find('[name="'+t+'"]'),r=i.val();i.val(r+","+e)}}export default new QueryGenerator; \ No newline at end of file +import"@typo3/backend/input/clearable.js";import DateTimePicker from"@typo3/backend/date-time-picker.js";import RegularEvent from"@typo3/core/event/regular-event.js";class QueryGenerator{constructor(){this.form=null,this.limitField=null,this.form=document.querySelector('form[name="queryform"]'),this.limitField=document.querySelector("input#queryLimit"),new RegularEvent("click",(e=>{e.preventDefault(),this.doSubmit()})).delegateTo(this.form,".t3js-submit-click"),new RegularEvent("change",(e=>{e.preventDefault(),this.doSubmit()})).delegateTo(this.form,".t3js-submit-change"),new RegularEvent("click",((e,t)=>{e.preventDefault(),this.setLimit(t.value),this.doSubmit()})).delegateTo(this.form,'.t3js-limit-submit input[type="button"]'),new RegularEvent("click",((e,t)=>{e.preventDefault(),this.addValueToField(t.dataset.field,t.value)})).delegateTo(this.form,".t3js-addfield"),new RegularEvent("change",((e,t)=>{const i=this.form.querySelector('input[name="storeControl[title]"]');"0"!==t.value?i.value=t.querySelector("option:selected").textContent:i.value=""})).delegateTo(this.form,"select.t3js-addfield"),document.querySelectorAll('form[name="queryform"] .t3js-clearable').forEach((e=>e.clearable({onClear:()=>{this.doSubmit()}}))),document.querySelectorAll('form[name="queryform"] .t3js-datetimepicker').forEach((e=>DateTimePicker.initialize(e)))}doSubmit(){this.form.submit()}setLimit(e){this.limitField.value=e}addValueToField(e,t){const i=this.form.querySelector('[name="'+e+'"]');t=i.value+","+t,i.value=t.split(",").map((e=>e.trim())).filter(((e,t,i)=>i.indexOf(e)===t)).join(",")}}export default new QueryGenerator; \ No newline at end of file diff --git a/typo3/sysext/reactions/Resources/Private/Templates/Management/Overview.html b/typo3/sysext/reactions/Resources/Private/Templates/Management/Overview.html index a1c695fe15d72d1cd914fa5aebefda945c93006b..7e1c4b6c4fd70121112dd65cfd9bdf2296a7433b 100644 --- a/typo3/sysext/reactions/Resources/Private/Templates/Management/Overview.html +++ b/typo3/sysext/reactions/Resources/Private/Templates/Management/Overview.html @@ -202,12 +202,12 @@ <form action="{f:be.uri(route:'system_reactions')}" method="post" enctype="multipart/form-data" name="demand"> <input type="hidden" name="orderField" value="{demand.orderField}"> <input type="hidden" name="orderDirection" value="{demand.orderDirection}"> - <div class="row row-cols-auto align-items-end g-3 mb-4"> - <div class="col"> + <div class="form-row"> + <div class="form-group"> <label for="demand-name" class="form-label"><f:translate key="LLL:EXT:reactions/Resources/Private/Language/locallang_module_reactions.xlf:filter.name"/></label> <input type="text" id="demand-name" class="form-control" name="demand[name]" value="{demand.name}"/> </div> - <div class="col"> + <div class="form-group"> <label for="demand-reaction-type" class="form-label"><f:translate key="LLL:EXT:reactions/Resources/Private/Language/locallang_module_reactions.xlf:filter.reaction_type"/></label> <select id="demand-reaction-type" class="form-select" name="demand[reaction_type]" data-on-change="submit"> <option value=""><f:translate key="LLL:EXT:reactions/Resources/Private/Language/locallang_module_reactions.xlf:filter.reaction_type.showAll"/></option> @@ -218,7 +218,7 @@ </f:for> </select> </div> - <div class="col"> + <div class="form-group align-self-end"> <input type="submit" value="{f:translate(key: 'LLL:EXT:reactions/Resources/Private/Language/locallang_module_reactions.xlf:filter.sendButton')}" class="btn btn-default" /> <a href="{f:be.uri(route:'system_reactions')}" class="btn btn-link"><f:translate key="LLL:EXT:reactions/Resources/Private/Language/locallang_module_reactions.xlf:filter.resetButton"/></a> </div> diff --git a/typo3/sysext/recycler/Resources/Private/Templates/RecyclerModule.html b/typo3/sysext/recycler/Resources/Private/Templates/RecyclerModule.html index edafc05e207a2add1d23580415efb6395e8057a2..11f32feb5cf32b4e78a56ffd0dc2c2e4d2e7d3ef 100644 --- a/typo3/sysext/recycler/Resources/Private/Templates/RecyclerModule.html +++ b/typo3/sysext/recycler/Resources/Private/Templates/RecyclerModule.html @@ -12,14 +12,14 @@ <div id="recycler-index" class="tx_recycler_recycler"> <form id="recycler-form"> - <div class="row row-cols-auto align-items-end g-3 mb-4"> - <div class="col"> + <div class="form-row"> + <div class="form-group align-self-end"> <div class="input-group"> - <input type="text" name="search-text" class="form-control" placeholder="{f:translate(key: 'LLL:EXT:core/Resources/Private/Language/locallang_core.xlf:labels.enterSearchString')}"> + <input type="text" name="search-text" class="form-control form-control-clearable" placeholder="{f:translate(key: 'LLL:EXT:core/Resources/Private/Language/locallang_core.xlf:labels.enterSearchString')}"> <button type="submit" class="btn btn-default disabled"><core:icon identifier="actions-search" /></button> </div> </div> - <div class="col"> + <div class="form-group"> <label for="depth" class="form-label"><f:translate key="LLL:EXT:recycler/Resources/Private/Language/locallang.xlf:filter.depth" /></label> <select name="depth" id="depth" class="form-select"> <option value="0"><f:translate key="LLL:EXT:core/Resources/Private/Language/locallang_core.xlf:labels.depth_0" /></option> @@ -30,7 +30,7 @@ <option value="999"><f:translate key="LLL:EXT:core/Resources/Private/Language/locallang_core.xlf:labels.depth_infi" /></option> </select> </div> - <div class="col"> + <div class="form-group"> <label for="pages" class="form-label"><f:translate key="LLL:EXT:recycler/Resources/Private/Language/locallang.xlf:filter.type" /></label> <select name="pages" id="pages" class="form-select"></select> </div> diff --git a/typo3/sysext/redirects/Resources/Private/Templates/Management/Overview.html b/typo3/sysext/redirects/Resources/Private/Templates/Management/Overview.html index ea085d8e9f35553554016aa12b7134078197d832..3474e1d2306e75d05a4d95aaf6992ed99fe1c4e1 100644 --- a/typo3/sysext/redirects/Resources/Private/Templates/Management/Overview.html +++ b/typo3/sysext/redirects/Resources/Private/Templates/Management/Overview.html @@ -228,8 +228,8 @@ <form action="{f:be.uri(route:'site_redirects', parameters: '{action: \'overview\'}')}" method="post" enctype="multipart/form-data" name="demand"> <input type="hidden" name="orderField" value="{demand.orderField}"> <input type="hidden" name="orderDirection" value="{demand.orderDirection}"> - <div class="row row-cols-auto align-items-end g-3 mb-4"> - <div class="col"> + <div class="form-row"> + <div class="form-group"> <label for="demand-source-host" class="form-label"><f:translate key="LLL:EXT:redirects/Resources/Private/Language/locallang_db.xlf:sys_redirect.source_host"/></label> <select id="demand-source-host" class="form-select" name="demand[source_host]" data-on-change="submit"> <option value=""><f:translate key="LLL:EXT:redirects/Resources/Private/Language/locallang_module_redirect.xlf:filter.source_host.showAll"/></option> @@ -238,15 +238,15 @@ </f:for> </select> </div> - <div class="col"> + <div class="form-group"> <label for="demand-source-path" class="form-label"><f:translate key="LLL:EXT:redirects/Resources/Private/Language/locallang_db.xlf:sys_redirect.source_path"/></label> <input type="text" id="demand-source-path" class="form-control" name="demand[source_path]" value="{demand.sourcePath}"/> </div> - <div class="col"> + <div class="form-group"> <label for="demand-target" class="form-label"><f:translate key="LLL:EXT:redirects/Resources/Private/Language/locallang_db.xlf:sys_redirect.target"/></label> <input type="text" id="demand-target" class="form-control" name="demand[target]" value="{demand.target}"/> </div> - <div class="col"> + <div class="form-group"> <label for="demand-target-status-code" class="form-label"><f:translate key="LLL:EXT:redirects/Resources/Private/Language/locallang_module_redirect.xlf:filter.targetStatusCode"/></label> <select id="demand-target-status-code" class="form-select" name="demand[target_statuscode]" data-on-change="submit"> <option value=""><f:translate key="LLL:EXT:redirects/Resources/Private/Language/locallang_module_redirect.xlf:filter.source_host.showAll"/></option> @@ -255,7 +255,7 @@ </f:for> </select> </div> - <div class="col"> + <div class="form-group"> <label for="demand-target-automatically-created" class="form-label"><f:translate key="LLL:EXT:redirects/Resources/Private/Language/locallang_module_redirect.xlf:filter.creationType"/></label> <select id="demand-target-automatically-created" class="form-select" name="demand[creation_type]" data-on-change="submit"> <option value="-1"><f:translate key="LLL:EXT:redirects/Resources/Private/Language/locallang_module_redirect.xlf:filter.creationType.showAll"/></option> @@ -265,14 +265,16 @@ </select> </div> <f:if condition="{showHitCounter}"> - <div class="form-check form-switch"> - <input type="checkbox" class="form-check-input" name="demand[max_hits]" id="demand-never-hit" value="1" data-on-change="submit" {f:if(condition: demand.maxHits, then: 'checked="checked"')}> - <label class="form-check-label" for="demand-never-hit"> - <f:translate key="LLL:EXT:redirects/Resources/Private/Language/locallang_module_redirect.xlf:filter.neverHit"/> - </label> + <div class="form-group align-self-end"> + <div class="form-check form-switch form-check-size-input"> + <input type="checkbox" class="form-check-input" name="demand[max_hits]" id="demand-never-hit" value="1" data-on-change="submit" {f:if(condition: demand.maxHits, then: 'checked="checked"')}> + <label class="form-check-label" for="demand-never-hit"> + <f:translate key="LLL:EXT:redirects/Resources/Private/Language/locallang_module_redirect.xlf:filter.neverHit"/> + </label> + </div> </div> </f:if> - <div class="col"> + <div class="form-group align-self-end"> <input type="submit" value="{f:translate(key: 'LLL:EXT:redirects/Resources/Private/Language/locallang_module_redirect.xlf:filter.sendButton')}" class="btn btn-default" /> <a href="{f:be.uri(route:'site_redirects')}" class="btn btn-link"><f:translate key="LLL:EXT:redirects/Resources/Private/Language/locallang_module_redirect.xlf:filter.resetButton"/></a> </div> diff --git a/typo3/sysext/scheduler/Resources/Private/Partials/AddEditStartEndFields.html b/typo3/sysext/scheduler/Resources/Private/Partials/AddEditStartEndFields.html index 97506ec2c0d656d0337b76705ce399c832f57588..d44fa7282dffd9932ebfc8f40fcd8fb382f7168b 100644 --- a/typo3/sysext/scheduler/Resources/Private/Partials/AddEditStartEndFields.html +++ b/typo3/sysext/scheduler/Resources/Private/Partials/AddEditStartEndFields.html @@ -6,7 +6,7 @@ <input name="tx_scheduler[start]_hr" value="{f:format.date(format:'H:i d-m-Y', date:currentData.start)}" - class="form-control t3js-datetimepicker t3js-clearable" + class="form-control form-control-clearable t3js-datetimepicker t3js-clearable" data-date-type="datetime" data-date-offset="0" type="text" @@ -27,7 +27,7 @@ <input name="tx_scheduler[end]_hr" value="{formattedEnd}" - class="form-control t3js-datetimepicker t3js-clearable" + class="form-control form-control-clearable t3js-datetimepicker t3js-clearable" data-date-type="datetime" data-date-offset="0" type="text" diff --git a/typo3/sysext/setup/Resources/Private/Templates/Main.html b/typo3/sysext/setup/Resources/Private/Templates/Main.html index 3b478f27d58f316cc75471e5468106f20ef8825f..3500e480e8f9179da86075ba76945de764a69473 100644 --- a/typo3/sysext/setup/Resources/Private/Templates/Main.html +++ b/typo3/sysext/setup/Resources/Private/Templates/Main.html @@ -5,19 +5,23 @@ <f:layout name="Module" /> -<f:section name="Content"> - +<f:section name="Before"> <f:be.pageRenderer includeJavaScriptModules="{ 0: '@typo3/backend/tabs.js' }" /> - <f:if condition="{isLanguageUpdate}"> <typo3-immediate-action action="TYPO3.ModuleMenu.App.refreshMenu"></typo3-immediate-action> <typo3-immediate-action action="TYPO3.Backend.Topbar.refresh"></typo3-immediate-action> </f:if> +</f:section> +<f:section name="Content"> + + <h1> + <f:translate key="LLL:EXT:setup/Resources/Private/Language/locallang.xlf:UserSettings" /> + </h1> <form action="{f:be.uri(route: 'user_setup')}" method="post" @@ -27,10 +31,6 @@ spellcheck="false" > <div id="user-setup-wrapper"> - <h1> - <f:translate key="LLL:EXT:setup/Resources/Private/Language/locallang.xlf:UserSettings" /> - </h1> - <div role="tabpanel"> <ul class="nav nav-tabs t3js-tabs" role="tablist" id="tabs-{menuId}" data-store-last-tab="1"> <f:for each="{menuItems}" as="item" iteration="iteration"> diff --git a/typo3/sysext/tstemplate/Resources/Private/Partials/ActiveConditions.html b/typo3/sysext/tstemplate/Resources/Private/Partials/ActiveConditions.html index b5810c4c1dc23e5eb55c6ae720921db64432ab75..58350abd498551799d8e3a869cd9aa90f0f2b04c 100644 --- a/typo3/sysext/tstemplate/Resources/Private/Partials/ActiveConditions.html +++ b/typo3/sysext/tstemplate/Resources/Private/Partials/ActiveConditions.html @@ -61,46 +61,42 @@ > <div class="panel-body"> <form action="{f:be.uri(route: 'typoscript_active', parameters: '{id: pageUid}')}" method="post"> - <div class="row"> - <div class="col-12"> - <f:for each="{conditions}" as="condition"> - <input type="hidden" name="{type}Conditions[{condition.hash}]" value="0" /> - <div class="form-check form-switch"> - <input - type="checkbox" - class="form-check-input" - name="{type}Conditions[{condition.hash}]" - id="{type}Condition{condition.hash}" - value="1" - {f:if(condition: condition.active, then:'checked="checked"')} - data-global-event="change" - data-action-submit="$form" - data-value-selector="input[name='{type}Conditions[{condition.hash}]']" - /> - <label class="form-check-label" for="{type}Condition{condition.hash}"> - <f:if condition="{displayConstantSubstitutions} && {condition.originalValue}"> - <f:then> - <span class="font-monospace">[{condition.value}]</span> - <span class="diff-item-result diff-item-result-inline font-monospace p-0"> - <f:format.raw> - <f:translate - key="LLL:EXT:tstemplate/Resources/Private/Language/locallang_active.xlf:panel.info.conditionWithConstant" - arguments="{ - 0: '{backend:typoScript.fineDiff(from: condition.originalValue, to: condition.value)}' - }" - /> - </f:format.raw> - </span> - </f:then> - <f:else> - <span class="font-monospace">[{condition.value}]</span> - </f:else> - </f:if> - </label> - </div> - </f:for> + <f:for each="{conditions}" as="condition"> + <input type="hidden" name="{type}Conditions[{condition.hash}]" value="0" /> + <div class="form-check form-switch"> + <input + type="checkbox" + class="form-check-input" + name="{type}Conditions[{condition.hash}]" + id="{type}Condition{condition.hash}" + value="1" + {f:if(condition: condition.active, then:'checked="checked"')} + data-global-event="change" + data-action-submit="$form" + data-value-selector="input[name='{type}Conditions[{condition.hash}]']" + /> + <label class="form-check-label" for="{type}Condition{condition.hash}"> + <f:if condition="{displayConstantSubstitutions} && {condition.originalValue}"> + <f:then> + <span class="font-monospace">[{condition.value}]</span> + <span class="diff-item-result diff-item-result-inline font-monospace p-0"> + <f:format.raw> + <f:translate + key="LLL:EXT:tstemplate/Resources/Private/Language/locallang_active.xlf:panel.info.conditionWithConstant" + arguments="{ + 0: '{backend:typoScript.fineDiff(from: condition.originalValue, to: condition.value)}' + }" + /> + </f:format.raw> + </span> + </f:then> + <f:else> + <span class="font-monospace">[{condition.value}]</span> + </f:else> + </f:if> + </label> </div> - </div> + </f:for> </form> </div> </div> diff --git a/typo3/sysext/tstemplate/Resources/Private/Partials/ActiveOptions.html b/typo3/sysext/tstemplate/Resources/Private/Partials/ActiveOptions.html index 17880c69cc0251d7d2c54977b91d4a4c9b685eec..804544dd0f0368cf952bf8947ab55c693d44d8f3 100644 --- a/typo3/sysext/tstemplate/Resources/Private/Partials/ActiveOptions.html +++ b/typo3/sysext/tstemplate/Resources/Private/Partials/ActiveOptions.html @@ -4,9 +4,9 @@ data-namespace-typo3-fluid="true" > -<div class="row row-cols-auto align-items-end g-3 mb-4{f:if(condition: '{f:count(subject: allTemplatesOnPage)} < 2', then: ' pt-2')}"> +<div class="form-row-md"> <f:if condition="{f:count(subject: allTemplatesOnPage)} > 1"> - <div class="col col-12 col-sm-6 col-md-4 col-lg-3 col-xl-2"> + <div class="form-group"> <form action="{f:be.uri(route: 'typoscript_active', parameters: '{id: pageUid}')}" method="post"> <label class="form-label" for="selectedTemplate"> <f:translate key="LLL:EXT:tstemplate/Resources/Private/Language/locallang_active.xlf:options.selectedRecord" /> @@ -31,12 +31,12 @@ </form> </div> </f:if> - <div class="col col-12 col-sm-6 col-md-5 col-lg-4 col-xl-3"> + <div class="form-group"> <form action="#"> <div class="input-group"> <input type="text" - class="form-control t3js-collapse-search-term" + class="form-control form-control-clearable t3js-collapse-search-term" name="searchValue" id="searchValue" data-persist-collapse-search-key="collapse-search-term-typoscript-active" @@ -48,12 +48,12 @@ </div> </form> </div> - <div class="col"> - <div class="row row-cols-md-auto pb-1"> - <div class="col col-12 col-sm-12"> + <div class="form-group"> + <div class="form-row-md"> + <div class="form-group"> <form action="{f:be.uri(route: 'typoscript_active', parameters: '{id: pageUid}')}" method="post"> <input type="hidden" name="displayConstantSubstitutions" value="0" /> - <div class="form-check form-switch"> + <div class="form-check form-switch form-check-size-input"> <input type="checkbox" class="form-check-input" @@ -71,10 +71,10 @@ </div> </form> </div> - <div class="col col-12 col-sm-12"> + <div class="form-group"> <form action="{f:be.uri(route: 'typoscript_active', parameters: '{id: pageUid}')}" method="post"> <input type="hidden" name="displayComments" value="0" /> - <div class="form-check form-switch"> + <div class="form-check form-switch form-check-size-input"> <input type="checkbox" class="form-check-input" @@ -92,10 +92,10 @@ </div> </form> </div> - <div class="col col-12 col-sm-12"> + <div class="form-group"> <form action="{f:be.uri(route: 'typoscript_active', parameters: '{id: pageUid}')}" method="post"> <input type="hidden" name="sortAlphabetically" value="0" /> - <div class="form-check form-switch"> + <div class="form-check form-switch form-check-size-input"> <input type="checkbox" class="form-check-input" diff --git a/typo3/sysext/tstemplate/Resources/Private/Partials/ActiveTreePanel.html b/typo3/sysext/tstemplate/Resources/Private/Partials/ActiveTreePanel.html index f3bc63760aa4ba709b63b9771633304b371a713e..9bf7ad5191895ffadca15e79980f2532d5899192 100644 --- a/typo3/sysext/tstemplate/Resources/Private/Partials/ActiveTreePanel.html +++ b/typo3/sysext/tstemplate/Resources/Private/Partials/ActiveTreePanel.html @@ -35,7 +35,7 @@ aria-labelledby="typoscript-active-{type}-ast-heading" role="tabpanel" > - <div class="panel-body t3js-collapse-states-search-tree"> + <div class="panel-body t3js-collapse-states-search-tree"> <form action="{f:be.uri(route: 'typoscript_active', parameters: '{id: pageUid}')}" method="post"> <ul class="treelist"> <f:comment> diff --git a/typo3/sysext/tstemplate/Resources/Private/Partials/AnalyzerConditions.html b/typo3/sysext/tstemplate/Resources/Private/Partials/AnalyzerConditions.html index 6b127e558990d1350d3e4090d59c2a8ac6aa4332..d08969dbdfbf9563ddcbfb5afe46c4e2194a2fec 100644 --- a/typo3/sysext/tstemplate/Resources/Private/Partials/AnalyzerConditions.html +++ b/typo3/sysext/tstemplate/Resources/Private/Partials/AnalyzerConditions.html @@ -61,46 +61,42 @@ > <div class="panel-body"> <form action="{f:be.uri(route: 'web_typoscript_analyzer', parameters: '{id: pageUid}')}" method="post"> - <div class="row"> - <div class="col-12"> - <f:for each="{conditions}" as="condition"> - <input type="hidden" name="{type}Conditions[{condition.hash}]" value="0" /> - <div class="form-check form-switch"> - <input - type="checkbox" - class="form-check-input" - name="{type}Conditions[{condition.hash}]" - id="{type}Condition{condition.hash}" - value="1" - {f:if(condition: condition.active, then:'checked="checked"')} - data-global-event="change" - data-action-submit="$form" - data-value-selector="input[name='{type}Conditions[{condition.hash}]']" - /> - <label class="form-check-label" for="{type}Condition{condition.hash}"> - <f:if condition="{condition.originalValue}"> - <f:then> - <span class="font-monospace">[{condition.value}]</span> - <span class="diff-item-result diff-item-result-inline font-monospace p-0"> - <f:format.raw> - <f:translate - key="LLL:EXT:tstemplate/Resources/Private/Language/locallang_analyzer.xlf:panel.info.conditionWithConstant" - arguments="{ - 0: '{backend:typoScript.fineDiff(from: condition.originalValue, to: condition.value)}' - }" - /> - </f:format.raw> - </span> - </f:then> - <f:else> - <span class="font-monospace">[{condition.value}]</span> - </f:else> - </f:if> - </label> - </div> - </f:for> + <f:for each="{conditions}" as="condition"> + <input type="hidden" name="{type}Conditions[{condition.hash}]" value="0" /> + <div class="form-check form-switch"> + <input + type="checkbox" + class="form-check-input" + name="{type}Conditions[{condition.hash}]" + id="{type}Condition{condition.hash}" + value="1" + {f:if(condition: condition.active, then:'checked="checked"')} + data-global-event="change" + data-action-submit="$form" + data-value-selector="input[name='{type}Conditions[{condition.hash}]']" + /> + <label class="form-check-label" for="{type}Condition{condition.hash}"> + <f:if condition="{condition.originalValue}"> + <f:then> + <span class="font-monospace">[{condition.value}]</span> + <span class="diff-item-result diff-item-result-inline font-monospace p-0"> + <f:format.raw> + <f:translate + key="LLL:EXT:tstemplate/Resources/Private/Language/locallang_analyzer.xlf:panel.info.conditionWithConstant" + arguments="{ + 0: '{backend:typoScript.fineDiff(from: condition.originalValue, to: condition.value)}' + }" + /> + </f:format.raw> + </span> + </f:then> + <f:else> + <span class="font-monospace">[{condition.value}]</span> + </f:else> + </f:if> + </label> </div> - </div> + </f:for> </form> </div> </div> diff --git a/typo3/sysext/tstemplate/Resources/Private/Partials/AnalyzerOptions.html b/typo3/sysext/tstemplate/Resources/Private/Partials/AnalyzerOptions.html index 8fcab05bcba10287106168890051790646edfb8a..1f549fb3232c286edce8e69f3cbe9dc26cec634e 100644 --- a/typo3/sysext/tstemplate/Resources/Private/Partials/AnalyzerOptions.html +++ b/typo3/sysext/tstemplate/Resources/Private/Partials/AnalyzerOptions.html @@ -5,8 +5,8 @@ > <f:if condition="{f:count(subject: allTemplatesOnPage)} > 1"> - <div class="row g-3 mb-4"> - <div class="col col-12 col-sm-6 col-md-4 col-lg-3 col-xl-2"> + <div class="form-row"> + <div class="form-group"> <form action="{f:be.uri(route: 'web_typoscript_analyzer', parameters: '{id: pageUid}')}" method="post"> <label class="form-label" for="selectedTemplate"> <f:translate key="LLL:EXT:tstemplate/Resources/Private/Language/locallang_analyzer.xlf:options.selectedRecord" /> diff --git a/typo3/sysext/tstemplate/Resources/Private/Partials/ConstantEditorOptions.html b/typo3/sysext/tstemplate/Resources/Private/Partials/ConstantEditorOptions.html index c0f5c7e85e12872f634682f13dfb8c5d3ce1d1d7..73010d76fd38a8e488a3e05e1427c4d978610180 100644 --- a/typo3/sysext/tstemplate/Resources/Private/Partials/ConstantEditorOptions.html +++ b/typo3/sysext/tstemplate/Resources/Private/Partials/ConstantEditorOptions.html @@ -5,9 +5,9 @@ > <f:if condition="({f:count(subject: allTemplatesOnPage)} > 1) || ({f:count(subject: relevantCategories)} > 1)"> - <div class="row g-3 mb-4"> + <div class="form-row"> <f:if condition="{f:count(subject: allTemplatesOnPage)} > 1"> - <div class="col col-12 col-sm-6 col-md-4 col-lg-3 col-xl-2"> + <div class="form-group"> <form action="{f:be.uri(route: 'web_typoscript_constanteditor', parameters: '{id: pageUid}')}" method="post"> <label class="form-label" for="selectedTemplate"> <f:translate key="LLL:EXT:tstemplate/Resources/Private/Language/locallang_ceditor.xlf:options.selectedRecord" /> @@ -33,7 +33,7 @@ </div> </f:if> <f:if condition="{f:count(subject: relevantCategories)} > 1"> - <div class="col col-12 col-sm-6 col-md-4 col-lg-3 col-xl-2"> + <div class="form-group"> <form action="{f:be.uri(route: 'web_typoscript_constanteditor', parameters: '{id: pageUid}')}" method="post"> <label class="form-label" for="selectedCategory"> <f:translate key="LLL:EXT:tstemplate/Resources/Private/Language/locallang_ceditor.xlf:options.selectedCategory" /> diff --git a/typo3/sysext/tstemplate/Resources/Private/Templates/ActiveMain.html b/typo3/sysext/tstemplate/Resources/Private/Templates/ActiveMain.html index 5c35829dee9dfa052e9bdd280f8684d57db0e544..92ad7746e8842a0c8b3952c44a7ed73c79297ede 100644 --- a/typo3/sysext/tstemplate/Resources/Private/Templates/ActiveMain.html +++ b/typo3/sysext/tstemplate/Resources/Private/Templates/ActiveMain.html @@ -5,8 +5,7 @@ <f:layout name="Module"/> -<f:section name="Content"> - +<f:section name="Before"> <f:be.pageRenderer includeJavaScriptModules="{ 0: '@typo3/backend/context-menu.js', @@ -19,11 +18,15 @@ 'collapse-state-search.numberOfSearchMatches': 'LLL:EXT:tstemplate/Resources/Private/Language/locallang_active.xlf:panel.header.numberOfSearchMatches' }" /> - <f:variable name="args" value="{0: 'web', 1: pageUid}" /> - <typo3-immediate-action action="TYPO3.Backend.Storage.ModuleStateStorage.update" args="{args -> f:format.json() -> f:format.htmlspecialchars()}"></typo3-immediate-action> + <typo3-immediate-action + action="TYPO3.Backend.Storage.ModuleStateStorage.update" + args="{args -> f:format.json() -> f:format.htmlspecialchars()}" + ></typo3-immediate-action> +</f:section> + +<f:section name="Content"> - <f:comment><!-- Heading --></f:comment> <h1> <f:if condition="{templateTitle}"> <f:then> diff --git a/typo3/sysext/tstemplate/Resources/Private/Templates/Analyzer.html b/typo3/sysext/tstemplate/Resources/Private/Templates/Analyzer.html index 7aa026d548199d79143f56fa70084891d9fef02d..be6510561e2bd9e8fd7c281efffab39047e90f76 100644 --- a/typo3/sysext/tstemplate/Resources/Private/Templates/Analyzer.html +++ b/typo3/sysext/tstemplate/Resources/Private/Templates/Analyzer.html @@ -5,8 +5,7 @@ <f:layout name="Module"/> -<f:section name="Content"> - +<f:section name="Before"> <f:be.pageRenderer includeJavaScriptModules="{ 0: '@typo3/backend/context-menu.js', @@ -14,11 +13,15 @@ 2: '@typo3/tstemplate/template-analyzer.js' }" /> - <f:variable name="args" value="{0: 'web', 1: pageUid}" /> - <typo3-immediate-action action="TYPO3.Backend.Storage.ModuleStateStorage.update" args="{args -> f:format.json() -> f:format.htmlspecialchars()}"></typo3-immediate-action> + <typo3-immediate-action + action="TYPO3.Backend.Storage.ModuleStateStorage.update" + args="{args -> f:format.json() -> f:format.htmlspecialchars()}" + ></typo3-immediate-action> +</f:section> + +<f:section name="Content"> - <f:comment><!-- Heading --></f:comment> <h1> <f:if condition="{templateTitle}"> <f:then> diff --git a/typo3/sysext/tstemplate/Resources/Private/Templates/ConstantEditorMain.html b/typo3/sysext/tstemplate/Resources/Private/Templates/ConstantEditorMain.html index 11e3b6b0d31104d09d2b8bedb6988f63e3b65659..c42435a528687b1e280385f044796f2eb89a8506 100644 --- a/typo3/sysext/tstemplate/Resources/Private/Templates/ConstantEditorMain.html +++ b/typo3/sysext/tstemplate/Resources/Private/Templates/ConstantEditorMain.html @@ -5,8 +5,7 @@ <f:layout name="Module"/> -<f:section name="Content"> - +<f:section name="Before"> <f:be.pageRenderer includeJavaScriptModules="{ 0: '@typo3/backend/context-menu.js', @@ -15,11 +14,14 @@ 4: '@typo3/tstemplate/constant-editor.js' }" /> - <f:variable name="args" value="{0: 'web', 1: pageUid}" /> - <typo3-immediate-action action="TYPO3.Backend.Storage.ModuleStateStorage.update" args="{args -> f:format.json() -> f:format.htmlspecialchars()}"></typo3-immediate-action> + <typo3-immediate-action + action="TYPO3.Backend.Storage.ModuleStateStorage.update" + args="{args -> f:format.json() -> f:format.htmlspecialchars()}" + ></typo3-immediate-action> +</f:section> - <f:comment><!-- Heading --></f:comment> +<f:section name="Content"> <h1> <f:if condition="{templateTitle}"> <f:then> diff --git a/typo3/sysext/tstemplate/Resources/Private/Templates/InfoModifyMain.html b/typo3/sysext/tstemplate/Resources/Private/Templates/InfoModifyMain.html index b3f8788775a9773e38fa34f563d86e6438e5b550..c83c6dd02254bd773cc7e48a066954483a736b4c 100644 --- a/typo3/sysext/tstemplate/Resources/Private/Templates/InfoModifyMain.html +++ b/typo3/sysext/tstemplate/Resources/Private/Templates/InfoModifyMain.html @@ -7,8 +7,7 @@ <f:layout name="Module"/> -<f:section name="Content"> - +<f:section name="Before"> <f:be.pageRenderer includeJavaScriptModules="{ 0: '@typo3/backend/context-menu.js', @@ -16,9 +15,14 @@ 2: '@typo3/tstemplate/information-module.js' }" /> - <f:variable name="args" value="{0: 'web', 1: pageUid}" /> - <typo3-immediate-action action="TYPO3.Backend.Storage.ModuleStateStorage.update" args="{args -> f:format.json() -> f:format.htmlspecialchars()}"></typo3-immediate-action> + <typo3-immediate-action + action="TYPO3.Backend.Storage.ModuleStateStorage.update" + args="{args -> f:format.json() -> f:format.htmlspecialchars()}" + ></typo3-immediate-action> +</f:section> + +<f:section name="Content"> <h1> <f:if condition="{templateRecord.title}"> @@ -38,8 +42,8 @@ <p><f:translate key="LLL:EXT:tstemplate/Resources/Private/Language/locallang_info.xlf:submodule.description" /></p> <f:if condition="{f:count(subject: allTemplatesOnPage)} > 1"> - <div class="row g-3 mb-4"> - <div class="col col-12 col-sm-6 col-md-4 col-lg-3 col-xl-2"> + <div class="form-row"> + <div class="form-group"> <form action="{f:be.uri(route: 'web_typoscript_infomodify', parameters: '{id: pageUid}')}" method="post"> <label class="form-label" for="selectedTemplate"> <f:translate key="LLL:EXT:tstemplate/Resources/Private/Language/locallang_info.xlf:options.selectedRecord" /> diff --git a/typo3/sysext/webhooks/Resources/Private/Templates/Management/Overview.html b/typo3/sysext/webhooks/Resources/Private/Templates/Management/Overview.html index f908debd4e9f57299ac947b471449d9ba32212b6..25f53d7f6f68f51797cb3d5144979dfa2efd70a8 100644 --- a/typo3/sysext/webhooks/Resources/Private/Templates/Management/Overview.html +++ b/typo3/sysext/webhooks/Resources/Private/Templates/Management/Overview.html @@ -158,12 +158,12 @@ <form action="{f:be.uri(route:'webhooks_management')}" method="post" enctype="multipart/form-data" name="demand"> <input type="hidden" name="orderField" value="{demand.orderField}"> <input type="hidden" name="orderDirection" value="{demand.orderDirection}"> - <div class="row row-cols-auto align-items-end g-3 mb-4"> - <div class="col"> + <div class="form-row"> + <div class="form-group"> <label for="demand-name" class="form-label"><f:translate key="LLL:EXT:webhooks/Resources/Private/Language/locallang_module_webhooks.xlf:filter.name"/></label> <input type="text" id="demand-name" class="form-control" name="demand[name]" value="{demand.name}"/> </div> - <div class="col"> + <div class="form-group"> <label for="demand-webhook-type" class="form-label"><f:translate key="LLL:EXT:webhooks/Resources/Private/Language/locallang_module_webhooks.xlf:filter.webhook_type"/></label> <select id="demand-webhook-type" class="form-select" name="demand[webhook_type]" data-on-change="submit"> <option value=""><f:translate key="LLL:EXT:webhooks/Resources/Private/Language/locallang_module_webhooks.xlf:filter.webhook_type.showAll"/></option> @@ -174,7 +174,7 @@ </f:for> </select> </div> - <div class="col"> + <div class="form-group align-self-end"> <input type="submit" value="{f:translate(key: 'LLL:EXT:webhooks/Resources/Private/Language/locallang_module_webhooks.xlf:filter.sendButton')}" class="btn btn-default" /> <a href="{f:be.uri(route:'webhooks_management')}" class="btn btn-link"><f:translate key="LLL:EXT:webhooks/Resources/Private/Language/locallang_module_webhooks.xlf:filter.resetButton"/></a> </div> diff --git a/typo3/sysext/workspaces/Resources/Private/Partials/WorkingTable.html b/typo3/sysext/workspaces/Resources/Private/Partials/WorkingTable.html index 5ff4b114b8800d74e8ea296de86dbd30660dc967..96658496a3d867d804b497b64dd3cdfe61e51b2a 100644 --- a/typo3/sysext/workspaces/Resources/Private/Partials/WorkingTable.html +++ b/typo3/sysext/workspaces/Resources/Private/Partials/WorkingTable.html @@ -5,8 +5,8 @@ > <div class="workspace-panel" id="workspace-panel"> <form id="workspace-settings-form"> - <div class="row row-cols-auto align-items-end g-3 mb-4"> - <div class="col"> + <div class="form-row"> + <div class="form-group"> <label for="depth" class="form-label"><f:translate key="LLL:EXT:workspaces/Resources/Private/Language/locallang.xlf:workingTable.depth" /></label> <select name="depth" id="depth" class="form-select"> <option value="0" {f:if(condition: '{selectedDepth} == 0', then: 'selected')}><f:translate key="LLL:EXT:core/Resources/Private/Language/locallang_core.xlf:labels.depth_0" /></option> @@ -17,7 +17,7 @@ <option value="999" {f:if(condition: '{selectedDepth} == 999', then: 'selected')}><f:translate key="LLL:EXT:core/Resources/Private/Language/locallang_core.xlf:labels.depth_infi" /></option> </select> </div> - <div class="col"> + <div class="form-group"> <label for="languages" class="form-label"><f:translate key="LLL:EXT:workspaces/Resources/Private/Language/locallang.xlf:workingTable.languages" /></label> <div class="input-group"> <span class="input-group-addon input-group-icon"> @@ -30,7 +30,7 @@ </select> </div> </div> - <div class="col"> + <div class="form-group"> <label for="stageFilter" class="form-label"><f:translate key="LLL:EXT:workspaces/Resources/Private/Language/locallang.xlf:workingTable.stages" /></label> <select name="stages" id="stageFilter" class="form-select"> <f:for each="{availableSelectStages}" as="availableSelectStage"> @@ -38,9 +38,9 @@ </f:for> </select> </div> - <div class="col"> + <div class="form-group align-self-end"> <div class="input-group"> - <input class="form-control t3js-clearable" type="text" name="search-text" placeholder="{f:translate(key: 'LLL:EXT:core/Resources/Private/Language/locallang_core.xlf:labels.enterSearchString')}"> + <input class="form-control form-control-clearable t3js-clearable" type="text" name="search-text" placeholder="{f:translate(key: 'LLL:EXT:core/Resources/Private/Language/locallang_core.xlf:labels.enterSearchString')}"> <button type="submit" class="btn btn-default disabled"><core:icon identifier="actions-search" /></button> </div> </div>