diff --git a/juconnect-patterns-plugin/juconnect-patterns.zip b/juconnect-patterns-plugin/juconnect-patterns.zip index 0a790ba..403b050 100644 Binary files a/juconnect-patterns-plugin/juconnect-patterns.zip and b/juconnect-patterns-plugin/juconnect-patterns.zip differ diff --git a/juconnect-patterns-plugin/juconnect-patterns/juconnect-patterns.php b/juconnect-patterns-plugin/juconnect-patterns/juconnect-patterns.php index 719ef06..98c4ac0 100644 --- a/juconnect-patterns-plugin/juconnect-patterns/juconnect-patterns.php +++ b/juconnect-patterns-plugin/juconnect-patterns/juconnect-patterns.php @@ -2,7 +2,7 @@ /** * Plugin Name: JuConnect Patterns * Description: Gutenberg Block Patterns fuer JuConnect (Styleguide-Klassen). - * Version: 0.1 + * Version: 0.2 */ if (!defined('ABSPATH')) exit; @@ -294,6 +294,317 @@ HTML +HTML + ]); + + register_block_pattern('juconnect/single-card-with-graphic-right', [ + 'title' => __('Info Card + Grafik rechts', 'juconnect'), + 'categories' => ['juconnect'], + 'description' => __('Zweispaltig: links eine einzelne Inhaltskarte, rechts Bild/Grafik.', 'juconnect'), + 'content' => << +
+
+

Leistung im Ueberblick

+ + + +

Kerninformationen klar und ruhig dargestellt.

+
+ + + +
+
+

Wann ist dieses Angebot passend?

+ + + +

Fuer Traeger mit klaren Zielen, transparenten Ablaeufen und verbindlicher Kommunikation.

+ + + +
  • klare Zustaendigkeiten
  • regelmaessige Rueckmeldungen
  • dokumentierte Entwicklung
+ + + + +
+ + + +
+
+ + +

Rechts: Illustration oder Projektfoto.

+
+
+
+ +HTML + ]); + + register_block_pattern('juconnect/single-card-with-graphic-left', [ + 'title' => __('Grafik links + Info Card', 'juconnect'), + 'categories' => ['juconnect'], + 'description' => __('Zweispaltig: links Bild/Grafik, rechts eine einzelne Inhaltskarte.', 'juconnect'), + 'content' => << +
+
+

Leistung im Ueberblick

+ + + +

Kerninformationen klar und ruhig dargestellt.

+
+ + + +
+
+
+ + +

Links: Illustration oder Projektfoto.

+
+ + + +
+

Wann ist dieses Angebot passend?

+ + + +

Fuer Traeger mit klaren Zielen, transparenten Ablaeufen und verbindlicher Kommunikation.

+ + + +
  • klare Zustaendigkeiten
  • regelmaessige Rueckmeldungen
  • dokumentierte Entwicklung
+ + + + +
+
+
+ +HTML + ]); + + register_block_pattern('juconnect/section-grid-2', [ + 'title' => __('Section + 2 Cards', 'juconnect'), + 'categories' => ['juconnect'], + 'description' => __('Standard-Zweispalter fuer Inhalte oder Angebotskarten.', 'juconnect'), + 'content' => << +
+
+

Schwerpunkte

+ + + +

Zwei zentrale Themen kompakt nebeneinander.

+
+ + + +
+
+

Begleitung

+ + +

Verlaessliche Begleitung mit klarer Struktur fuer alle Beteiligten.

+ + +

Mehr erfahren

+
+ + + +
+

Koordination

+ + +

Abgestimmte Kommunikation zwischen Traegern, Familien und Fachkraeften.

+ + +

Mehr erfahren

+
+
+
+ +HTML + ]); + + register_block_pattern('juconnect/kpi-overview-3', [ + 'title' => __('KPI Ueberblick (3 Karten)', 'juconnect'), + 'categories' => ['juconnect'], + 'description' => __('Drei Kennzahlenkarten fuer Verlaesslichkeit, Bearbeitungszeit und Reichweite.', 'juconnect'), + 'content' => << +
+
+

Fakten im Ueberblick

+ + + +

Beispielwerte fuer eine transparente Darstellung.

+
+ + + +
+
+
+

Antwortzeit

+ + +

< 48h

+
+
+ + + +
+
+

Abgestimmte Plaene

+ + +

95%

+
+
+ + + +
+
+

Kooperationspartner

+ + +

24

+
+
+
+
+ +HTML + ]); + + register_block_pattern('juconnect/contact-cta-split', [ + 'title' => __('Kontakt CTA (Split)', 'juconnect'), + 'categories' => ['juconnect'], + 'description' => __('Linke Infokarte mit Aktionen, rechte Karte mit Kontaktfakten.', 'juconnect'), + 'content' => << +
+
+
+

Naechster Schritt

+ + + +

Unverbindlich Kontakt aufnehmen

+ + + +

Wir melden uns zeitnah und klaeren den passenden Rahmen fuer Ihr Anliegen.

+ + + + +
+ + + +
+

Kontaktzeiten

+ + + +
+

Mo - Fr

+ + +

08:00 - 17:00

+
+ + + +
+

E-Mail

+ + +

kontakt@juconnect.de

+
+ + + +
+

Hinweis

+ + +

Bitte Anlass und Rueckrufzeit kurz angeben.

+
+
+
+
+ +HTML + ]); + + register_block_pattern('juconnect/downloads-table', [ + 'title' => __('Downloads (Tabelle)', 'juconnect'), + 'categories' => ['juconnect'], + 'description' => __('Downloadbereich mit Tabelle im Styleguide-Look.', 'juconnect'), + 'content' => << +
+
+

Downloads

+ + + +

Dokumente, Vorlagen und Nachweise auf einen Blick.

+
+ + + +
+
+ + + + + + + + + +
DokumentStatusAktion
LeistungsbeschreibungEntwurfOeffnen
DatenschutzFinalOeffnen
AnsprechpartnerUpdateOeffnen
+
+
+
+ HTML ]); }); diff --git a/juconnect-strict-theme-v3/juconnect-strict.zip b/juconnect-strict-theme-v3/juconnect-strict.zip index 5097497..a219f97 100644 Binary files a/juconnect-strict-theme-v3/juconnect-strict.zip and b/juconnect-strict-theme-v3/juconnect-strict.zip differ diff --git a/juconnect-strict-theme-v3/juconnect-strict/assets/js/app.js b/juconnect-strict-theme-v3/juconnect-strict/assets/js/app.js index ba03cbb..ce3fddf 100644 --- a/juconnect-strict-theme-v3/juconnect-strict/assets/js/app.js +++ b/juconnect-strict-theme-v3/juconnect-strict/assets/js/app.js @@ -69,6 +69,48 @@ const Toast = (() => { return { show }; })(); +/* Equalize steps+image pattern column heights */ +(() => { + const collectColumns = (layout) => { + const inner = layout.querySelector(":scope > .wp-block-group__inner-container"); + if (inner) return Array.from(inner.children); + return Array.from(layout.children); + }; + + const hasTiles = (el) => !!el.querySelector(".grid.grid--4, .wp-block-group.grid.grid--4"); + const hasImage = (el) => !!el.querySelector(".wp-block-image img, img"); + + const equalize = () => { + const layouts = $$(".section .grid.grid--2, .wp-block-group.section .wp-block-group.grid.grid--2"); + layouts.forEach((layout) => { + const columns = collectColumns(layout).filter((el) => el.nodeType === 1); + if (columns.length < 2) return; + + const tilesCol = columns.find(hasTiles); + const imageCol = columns.find((el) => el !== tilesCol && hasImage(el)); + if (!tilesCol || !imageCol) return; + + tilesCol.style.minHeight = ""; + imageCol.style.minHeight = ""; + + const h = Math.max(tilesCol.offsetHeight, imageCol.offsetHeight); + if (!h) return; + tilesCol.style.minHeight = `${h}px`; + imageCol.style.minHeight = `${h}px`; + }); + }; + + let raf = 0; + const schedule = () => { + if (raf) cancelAnimationFrame(raf); + raf = requestAnimationFrame(equalize); + }; + + window.addEventListener("load", schedule); + window.addEventListener("resize", schedule); + schedule(); +})(); + /* Clipboard copy helper */ async function copyText(text, label="Kopiert.") { try { diff --git a/juconnect-strict-theme-v3/juconnect-strict/footer.php b/juconnect-strict-theme-v3/juconnect-strict/footer.php index 7b7b845..458c707 100644 --- a/juconnect-strict-theme-v3/juconnect-strict/footer.php +++ b/juconnect-strict-theme-v3/juconnect-strict/footer.php @@ -1,7 +1,23 @@ diff --git a/juconnect-strict-theme-v3/juconnect-strict/functions.php b/juconnect-strict-theme-v3/juconnect-strict/functions.php index 0827512..de9549f 100644 --- a/juconnect-strict-theme-v3/juconnect-strict/functions.php +++ b/juconnect-strict-theme-v3/juconnect-strict/functions.php @@ -19,9 +19,17 @@ function juconnect_setup() { add_action('after_setup_theme', 'juconnect_setup'); function juconnect_assets() { - $ver = wp_get_theme()->get('Version'); - wp_enqueue_style('juconnect-style', get_stylesheet_uri(), [], $ver); - wp_enqueue_script('juconnect-app', get_template_directory_uri().'/assets/js/app.js', [], $ver, true); + $theme_ver = wp_get_theme()->get('Version'); + $style_ver = filemtime(get_stylesheet_directory() . '/style.css'); + $script_ver = filemtime(get_template_directory() . '/assets/js/app.js'); + if (!$style_ver) { + $style_ver = $theme_ver; + } + if (!$script_ver) { + $script_ver = $theme_ver; + } + wp_enqueue_style('juconnect-style', get_stylesheet_uri(), [], $style_ver); + wp_enqueue_script('juconnect-app', get_template_directory_uri().'/assets/js/app.js', [], $script_ver, true); } add_action('wp_enqueue_scripts', 'juconnect_assets'); @@ -68,7 +76,7 @@ function juconnect_render_sidenav_nav() { // Add styleguide classes to WP menus function juconnect_nav_link_attributes($atts, $item, $args, $depth){ - if (!empty($args->theme_location) && $args->theme_location === 'primary'){ + if (!empty($args->theme_location) && in_array($args->theme_location, ['primary', 'footer'], true)){ $existing = isset($atts['class']) ? $atts['class'].' ' : ''; $atts['class'] = $existing . 'navlink'; } diff --git a/juconnect-strict-theme-v3/juconnect-strict/style.css b/juconnect-strict-theme-v3/juconnect-strict/style.css index 53538f1..3d156d1 100644 --- a/juconnect-strict-theme-v3/juconnect-strict/style.css +++ b/juconnect-strict-theme-v3/juconnect-strict/style.css @@ -339,7 +339,14 @@ a{ color: inherit; } } /* Sections */ -.section{ margin: 0 0 var(--s6) 0; } +.section{ + margin: 0 0 var(--s6) 0; + padding-bottom: var(--s4); +} +.wp-block-group.section{ + padding-bottom: var(--s4); + margin-bottom: var(--s4) !important; +} .section__head{ margin-bottom: var(--s4); } .main .wp-block-group.section{ width: 100%; @@ -355,6 +362,45 @@ a{ color: inherit; } padding-top: var(--s4); border-top: 1px solid var(--line); } +.footer__inner{ + display: flex; + align-items: flex-end; + justify-content: space-between; + gap: var(--s3); + flex-wrap: wrap; +} +.footer__nav{ + min-width: 0; +} +.footer__menu{ + list-style: none; + display: flex; + align-items: flex-start; + flex-wrap: wrap; + gap: 6px; + margin: 0; + padding: 0; +} +.footer__menu > li{ + margin: 0; +} +.footer__menu a.navlink{ + padding: 8px 10px; + border-radius: 10px; +} +.footer__menu .current-menu-item > a.navlink, +.footer__menu .current-page-ancestor > a.navlink{ + background: rgba(29,53,79,.10); + border-color: rgba(29,53,79,.18); + color: var(--text); +} + +@media (max-width: 760px){ + .footer__inner{ + flex-direction: column; + align-items: flex-start; + } +} /* Typography helpers */ .h1{ font-size: var(--fs-1); line-height: var(--lh-tight); margin: 0 0 var(--s2) 0; } @@ -381,6 +427,77 @@ a{ color: inherit; } .wp-block-group.grid.grid--2 > .wp-block-group__inner-container{ grid-template-columns: repeat(2, minmax(0, 1fr)) !important; } .wp-block-group.grid.grid--3 > .wp-block-group__inner-container{ grid-template-columns: repeat(3, minmax(0, 1fr)) !important; } .wp-block-group.grid.grid--4 > .wp-block-group__inner-container{ grid-template-columns: repeat(2, minmax(0, 1fr)) !important; } +.wp-block-group.grid.grid--2 > .wp-block-group__inner-container{ + align-items: stretch !important; +} +.grid.grid--2{ + align-items: stretch !important; +} +.grid.grid--2 > .wp-block-group, +.grid.grid--2 > .card{ + height: 100% !important; + align-self: stretch !important; +} +.grid.grid--2 > .wp-block-group{ + display: flex; + flex-direction: column; +} +.grid.grid--2 > .wp-block-group > .grid{ + flex: 1; +} +.grid.grid--4 > .card{ + height: 100%; + display: flex; + flex-direction: column; +} +.wp-block-group.grid.grid--2 > .wp-block-group__inner-container > .wp-block-group{ + display: flex; + flex-direction: column; + height: 100% !important; + align-self: stretch !important; +} +.wp-block-group.grid.grid--2 > .wp-block-group__inner-container > .wp-block-group > .wp-block-group__inner-container{ + display: flex; + flex-direction: column; + height: 100% !important; +} +.wp-block-group.grid.grid--2 > .wp-block-group__inner-container > .wp-block-group > .wp-block-group.grid{ + flex: 1; +} +.wp-block-group.grid.grid--2 > .wp-block-group__inner-container > .wp-block-group > .wp-block-group__inner-container > .wp-block-group.grid{ + flex: 1; +} +.wp-block-group.grid.grid--2 > .wp-block-group__inner-container > .wp-block-group > .wp-block-group__inner-container > .wp-block-group.grid > .wp-block-group__inner-container{ + height: 100%; +} +.wp-block-group.grid.grid--4 > .wp-block-group__inner-container > .card{ + height: 100%; + display: flex; + flex-direction: column; +} +.wp-block-group.grid.grid--2 > .wp-block-group__inner-container > .card{ + height: 100% !important; + align-self: stretch !important; +} +.main .wp-block-group.section + .wp-block-group.section{ + margin-top: var(--s4); +} +.main .wp-block-group.section + .section{ + margin-top: var(--s4); +} + +/* Fallback for pages built with core Columns instead of grid classes */ +.section .wp-block-columns{ + align-items: stretch !important; +} +.section .wp-block-column{ + display: flex; + flex-direction: column; +} +.section .wp-block-column > .wp-block-group, +.section .wp-block-column > .card{ + height: 100% !important; +} .section > .grid + .grid{ margin-top: var(--s4); } .section > .grid + .card, .section > .card + .grid{ margin-top: var(--s4); } @@ -919,7 +1036,7 @@ a{ color: inherit; } .topnav__submenu{ list-style:none; position:absolute; - top: calc(100% + 8px); + top: 100%; right: 0; min-width: 240px; margin: 0; @@ -930,7 +1047,8 @@ a{ color: inherit; } box-shadow: var(--shadow); display:none; } -.topnav__list li:hover > .topnav__submenu{ display:block; } +.topnav__list li:hover > .topnav__submenu, +.topnav__list li:focus-within > .topnav__submenu{ display:block; } .topnav__submenu a.navlink{ display:flex; width: 100%; @@ -938,6 +1056,24 @@ a{ color: inherit; } border-radius: 12px; } +/* Touch devices don't have hover; expose submenus inline for reliable access */ +@media (hover: none){ + .topnav__list > li{ width: 100%; } + .topnav__list a.navlink{ width: 100%; } + .topnav__submenu{ + position: static; + display: block; + min-width: 0; + margin-top: 4px; + padding: 4px 0 0 12px; + border: 0; + border-left: 1px solid var(--line); + border-radius: 0; + background: transparent; + box-shadow: none; + } +} + /* Hide original sidenav if any page still contains it */ .sidenav{ display:none !important; } @@ -989,7 +1125,7 @@ a{ color: inherit; } .wp-block-buttons .wp-block-button{ margin: 0; } /* Groups: don't add unexpected margins that break cards/grids */ -.wp-block-group{ margin: 0; } +.wp-block-group:not(.section){ margin: 0; } /* Images: prevent WP default inline styles from breaking rounded cards */ .wp-block-image img{ max-width: 100%; height: auto; }