Last modified by Veronika Kocher on Friday, 04 Sep 2026 14:45

From version 5.12
edited by Veronika Kocher
on Thursday, 03 Sep 2026 14:15
Change comment: There is no comment for this version
To version 5.8
edited by Veronika Kocher
on Thursday, 03 Sep 2026 9:18
Change comment: There is no comment for this version

Summary

Details

Page properties
Content
... ... @@ -262,132 +262,21 @@
262 262  {{/html}}
263 263  
264 264  {{html clean="false"}}
265 -<!-- SN_SERVICE_NAVIGATOR_MASTER_STYLE_START -->
266 -
267 -<style data-sn-service-navigator-master="1">
268 -/* =========================================================
269 - MASTER TYPOGRAPHY
270 - ========================================================= */
271 -#xwikicontent h1,
272 -#xwikicontent h2,
273 -#xwikicontent h3,
274 -#xwikicontent h4,
275 -#xwikicontent h5,
276 -#xwikicontent h6,
277 -#xwikicontent .box-title,
278 -#xwikicontent [role="heading"],
279 -#xwikicontent h1 a,
280 -#xwikicontent h2 a,
281 -#xwikicontent h3 a,
282 -#xwikicontent h4 a,
283 -#xwikicontent h5 a,
284 -#xwikicontent h6 a,
285 -#xwikicontent .box-title a,
286 -#xwikicontent [role="heading"] a{
287 - text-align:left!important;
288 - text-justify:auto!important;
289 - word-spacing:normal!important;
265 +<!-- SN_HORIZONTAL_BOX_HARMONIZER_START -->
266 +<style data-sn-horizontal-box-harmonizer="1">
267 +[data-sn-equal-height-managed="1"]{box-sizing:border-box}
268 +@media(max-width:767px){
269 + [data-sn-equal-height-managed="1"]{min-height:0!important}
290 290  }
291 -
292 -/* =========================================================
293 - COMING SOON / IN VORBEREITUNG
294 - ========================================================= */
295 -.sn-coming-soon-badge{
296 - display:inline-block;
297 - vertical-align:middle;
298 - margin-left:10px;
299 - padding:4px 8px;
300 - border-radius:14px;
301 - border:1px solid #efd9cc;
302 - background:#fff4ee;
303 - color:#8a4d36;
304 - font-size:11px;
305 - font-weight:700;
306 - letter-spacing:.055em;
307 - line-height:1.2;
308 - white-space:nowrap;
309 -}
310 -
311 -/* =========================================================
312 - NATIVE / DETAIL CALLOUT GEOMETRY
313 - Preserve existing backgrounds.
314 - ========================================================= */
315 -#xwikicontent .arsn-info,
316 -#xwikicontent .dmp-info,
317 -#xwikicontent .ido-info,
318 -#xwikicontent .pp-info,
319 -#xwikicontent .infomessage{
320 - box-sizing:border-box!important;
321 - border-left:4px solid #21b6d7!important;
322 - border-radius:8px;
323 - text-align:left!important;
324 - word-spacing:normal!important;
325 -}
326 -
327 -#xwikicontent .arsn-warn,
328 -#xwikicontent .dmp-warn,
329 -#xwikicontent .ido-warn,
330 -#xwikicontent .pp-warn,
331 -#xwikicontent .warn,
332 -#xwikicontent .warning,
333 -#xwikicontent .warningmessage,
334 -#xwikicontent .errormessage{
335 - box-sizing:border-box!important;
336 - border-left:4px solid #e94b13!important;
337 - border-radius:8px;
338 - text-align:left!important;
339 - word-spacing:normal!important;
340 -}
341 -
342 -[data-sn-master-equal-height],
343 -[data-sn-master-first-row]{
344 - box-sizing:border-box;
345 -}
346 -
347 -/* =========================================================
348 - FULL-WIDTH THREE-LINE NUMBER / TITLE / SUBTITLE BLOCKS
349 - ========================================================= */
350 -#xwikicontent .arsn-area-label[data-sn-three-line="1"]{
351 - display:grid!important;
352 - grid-template-columns:minmax(0,1fr)!important;
353 - grid-auto-rows:auto!important;
354 - width:100%!important;
355 - max-width:none!important;
356 - box-sizing:border-box!important;
357 - justify-items:start!important;
358 - align-items:start!important;
359 - gap:2px!important;
360 - text-align:left!important;
361 - text-align-last:left!important;
362 - text-justify:auto!important;
363 - word-spacing:normal!important;
364 - white-space:normal!important;
365 -}
366 -#xwikicontent .arsn-area-label[data-sn-three-line="1"] > .arsn-area-number,
367 -#xwikicontent .arsn-area-label[data-sn-three-line="1"] > .sn-area-label-title,
368 -#xwikicontent .arsn-area-label[data-sn-three-line="1"] > .arsn-area-action{
369 - display:block!important;
370 - width:100%!important;
371 - margin:0!important;
372 - text-align:left!important;
373 - text-align-last:left!important;
374 - text-justify:auto!important;
375 - word-spacing:normal!important;
376 - white-space:normal!important;
377 -}
378 378  </style>
379 -
380 -<script data-sn-service-navigator-master="1">
272 +<script data-sn-horizontal-box-harmonizer="1">
381 381  (function(){
382 382   "use strict";
383 383  
384 - var PAGE_KIND="detail";
385 - var PLACEHOLDER=false;
386 - var PLACEHOLDER_LABEL="COMING SOON";
387 -
388 388   var MOBILE_MAX=767;
389 - var ROW_TOLERANCE=6;
390 - var RESIZE_DEBOUNCE=220;
277 + var ROW_TOLERANCE=4;
278 + var MIN_W=150;
279 + var MIN_H=36;
391 391  
392 392   var root=
393 393   document.getElementById("xwikicontent")||
... ... @@ -397,1268 +397,212 @@
397 397  
398 398   if(!root)return;
399 399  
400 - var managedHeight=new Set();
401 - var managedMargin=new Set();
402 - var originalHeight=new WeakMap();
403 - var originalMargin=new WeakMap();
289 + var managed=new Set();
290 + var raf=0;
404 404  
405 - var resizeTimer=0;
406 - var running=false;
407 -
408 - var THEMES=[
409 - {
410 - name:"BLUE",
411 - accent:"#21b6d7",
412 - bg:"#eaf7fb",
413 - text:"#315d68",
414 - labels:[
415 - "HIER STARTEN",
416 - "ENTSCHEIDEN",
417 - "ÜBERPRÜFEN & ANPASSEN",
418 - "START HERE",
419 - "DECIDE",
420 - "REVIEW & ADAPT"
421 - ]
422 - },
423 - {
424 - name:"RED",
425 - accent:"#e94b13",
426 - bg:"#fff1ec",
427 - text:"#8a4d36",
428 - labels:[
429 - "PLANEN & ORGANISIEREN",
430 - "ORGANISIEREN & DOKUMENTIEREN",
431 - "PUBLIZIEREN & PRÄSENTIEREN",
432 - "PLAN & ORGANISE",
433 - "PLAN & ORGANIZE",
434 - "ORGANISE & DOCUMENT",
435 - "ORGANIZE & DOCUMENT",
436 - "PUBLISH & PRESENT"
437 - ]
438 - },
439 - {
440 - name:"YELLOW",
441 - accent:"#f0aa00",
442 - bg:"#fff8e7",
443 - text:"#785b17",
444 - labels:[
445 - "SCHÜTZEN & KLÄREN",
446 - "STANDARDISIEREN & IDENTIFIZIEREN",
447 - "ÖFFNEN, NACHNUTZEN & AUFFINDBAR MACHEN",
448 - "PROTECT & CLARIFY",
449 - "STANDARDISE & IDENTIFY",
450 - "STANDARDIZE & IDENTIFY",
451 - "OPEN, REUSE & MAKE FINDABLE"
452 - ]
453 - },
454 - {
455 - name:"GREEN",
456 - accent:"#38b76a",
457 - bg:"#edf9f1",
458 - text:"#3f7451",
459 - labels:[
460 - "INFRASTRUKTUR EINRICHTEN",
461 - "INFRASTRUKTUR & ZUSAMMENARBEIT EINRICHTEN",
462 - "SPEICHERN & ZUGRIFF STEUERN",
463 - "REPOSITORIUM, ERHALTEN & ÜBERGEBEN",
464 - "SET UP INFRASTRUCTURE",
465 - "SET UP INFRASTRUCTURE & COLLABORATION",
466 - "STORE & CONTROL ACCESS",
467 - "REPOSITORY, PRESERVE & HAND OVER"
468 - ]
469 - }
470 - ];
471 -
472 - function num(value){
473 - var n=parseFloat(value);
292 + function num(v){
293 + var n=parseFloat(v);
474 474   return Number.isFinite(n)?n:0;
475 475   }
476 476  
477 - function norm(value){
478 - return String(value||"")
479 - .replace(/\s+/g," ")
480 - .trim()
481 - .toUpperCase();
482 - }
483 -
484 484   function visible(el){
485 485   if(!el||el.nodeType!==1)return false;
486 -
487 - var style=getComputedStyle(el);
488 - var rect=el.getBoundingClientRect();
489 -
490 - return (
491 - style.display!=="none"&&
492 - style.visibility!=="hidden"&&
493 - rect.width>20&&
494 - rect.height>4
495 - );
299 + var s=getComputedStyle(el);
300 + if(s.display==="none"||s.visibility==="hidden"||Number(s.opacity)===0)return false;
301 + var r=el.getBoundingClientRect();
302 + return r.width>=MIN_W&&r.height>=MIN_H;
496 496   }
497 497  
498 - function saveStyle(el,map,property){
499 - if(map.has(el))return;
500 -
501 - map.set(el,{
502 - value:el.style.getPropertyValue(property),
503 - priority:el.style.getPropertyPriority(property)
504 - });
505 - }
506 -
507 - function restoreStyle(el,map,property){
508 - var original=map.get(el);
509 -
510 - if(original&&original.value){
511 - el.style.setProperty(
512 - property,
513 - original.value,
514 - original.priority||""
515 - );
516 - }else{
517 - el.style.removeProperty(property);
518 - }
519 - }
520 -
521 - function resetRuntime(){
522 - managedHeight.forEach(function(el){
523 - restoreStyle(
524 - el,
525 - originalHeight,
526 - "min-height"
527 - );
528 - el.removeAttribute(
529 - "data-sn-master-equal-height"
530 - );
531 - });
532 -
533 - managedMargin.forEach(function(el){
534 - restoreStyle(
535 - el,
536 - originalMargin,
537 - "margin-top"
538 - );
539 - el.removeAttribute(
540 - "data-sn-master-first-row"
541 - );
542 - });
543 -
544 - managedHeight.clear();
545 - managedMargin.clear();
546 - }
547 -
548 - function themeFor(text){
549 - var value=norm(text);
550 -
551 - for(var i=0;i<THEMES.length;i++){
552 - for(var j=0;j<THEMES[i].labels.length;j++){
553 - var label=THEMES[i].labels[j];
554 -
555 - if(
556 - value===label||
557 - value.indexOf(label+" ")===0||
558 - value.indexOf(label+" -")===0||
559 - value.indexOf(label+" ·")===0
560 - ){
561 - return THEMES[i];
562 - }
563 - }
564 - }
565 -
566 - return null;
567 - }
568 -
569 - /* =======================================================
570 - BORDERLESS FILLED RED/ORANGE CTA BUTTONS
571 - ======================================================= */
572 -
573 - function colourDistance(a,b){
574 - return Math.sqrt(
575 - Math.pow(a[0]-b[0],2)+
576 - Math.pow(a[1]-b[1],2)+
577 - Math.pow(a[2]-b[2],2)
305 + function excluded(el){
306 + return !el.matches||el.matches(
307 + "button,input,select,textarea,option,label,img,svg,canvas,table,thead,tbody,tfoot,tr,td,th,summary,script,style,noscript,template,.btn,.chip,[role=button]"
578 578   );
579 579   }
580 580  
581 - function makeFilledRedOrangeCTAsBorderless(){
582 - var RED_ORANGE=[233,75,19];
583 -
584 - Array.from(
585 - root.querySelectorAll(
586 - 'a,button,[role="button"],input[type="submit"],input[type="button"]'
587 - )
588 - ).forEach(function(el){
589 - if(!visible(el))return;
590 -
591 - var style=getComputedStyle(el);
592 - var rgb=parseRGB(style.backgroundColor);
593 -
594 - if(!rgb)return;
595 -
596 - if(
597 - colourDistance(
598 - rgb,
599 - RED_ORANGE
600 - )>55
601 - ){
602 - return;
603 - }
604 -
605 - var rect=el.getBoundingClientRect();
606 -
607 - if(
608 - rect.width<80||
609 - rect.height<24
610 - ){
611 - return;
612 - }
613 -
614 - el.style.setProperty(
615 - "border",
616 - "none",
617 - "important"
618 - );
619 -
620 - el.style.setProperty(
621 - "border-left",
622 - "none",
623 - "important"
624 - );
625 -
626 - el.style.setProperty(
627 - "border-top",
628 - "none",
629 - "important"
630 - );
631 -
632 - el.style.setProperty(
633 - "border-right",
634 - "none",
635 - "important"
636 - );
637 -
638 - el.style.setProperty(
639 - "border-bottom",
640 - "none",
641 - "important"
642 - );
643 -
644 - el.style.setProperty(
645 - "box-shadow",
646 - "none",
647 - "important"
648 - );
649 - });
311 + function namedLikeBox(el){
312 + var c=typeof el.className==="string"?el.className:"";
313 + return /(^|[\s_-])(box|card|tile|panel|role|check|service|source|call|area|detail|resource|topic|warn|info)([\s_-]|$)/i.test(c);
650 650   }
651 651  
652 - /* =======================================================
653 - FULL-WIDTH THREE-LINE AREA LABELS
654 - ======================================================= */
655 -
656 - function compactText(value){
657 - return String(value||"")
658 - .replace(/\s+/g," ")
659 - .trim();
660 - }
661 -
662 - function makeThreeLineAreaLabels(){
663 - Array.from(
664 - root.querySelectorAll(
665 - ".arsn-area-label"
666 - )
667 - ).forEach(function(label){
668 - if(
669 - label.getAttribute(
670 - "data-sn-three-line"
671 - )==="1"
672 - ){
673 - return;
674 - }
675 -
676 - var number=
677 - label.querySelector(
678 - ":scope > .arsn-area-number"
679 - );
680 -
681 - var action=
682 - label.querySelector(
683 - ":scope > .arsn-area-action"
684 - );
685 -
686 - if(
687 - !number||
688 - !action
689 - ){
690 - return;
691 - }
692 -
693 - var clone=
694 - label.cloneNode(true);
695 -
696 - var cloneNumber=
697 - clone.querySelector(
698 - ":scope > .arsn-area-number"
699 - );
700 -
701 - var cloneAction=
702 - clone.querySelector(
703 - ":scope > .arsn-area-action"
704 - );
705 -
706 - if(cloneNumber){
707 - cloneNumber.remove();
708 - }
709 -
710 - if(cloneAction){
711 - cloneAction.remove();
712 - }
713 -
714 - var titleText=
715 - compactText(
716 - clone.textContent
717 - );
718 -
719 - if(!titleText){
720 - return;
721 - }
722 -
723 - var numberNode=
724 - number.cloneNode(true);
725 -
726 - var actionNode=
727 - action.cloneNode(true);
728 -
729 - var titleNode=
730 - document.createElement(
731 - "span"
732 - );
733 -
734 - titleNode.className=
735 - "sn-area-label-title";
736 -
737 - titleNode.textContent=
738 - titleText;
739 -
740 - while(label.firstChild){
741 - label.removeChild(
742 - label.firstChild
743 - );
744 - }
745 -
746 - label.appendChild(
747 - numberNode
748 - );
749 -
750 - label.appendChild(
751 - titleNode
752 - );
753 -
754 - label.appendChild(
755 - actionNode
756 - );
757 -
758 - label.setAttribute(
759 - "data-sn-three-line",
760 - "1"
761 - );
762 -
763 - var head=
764 - label.closest(
765 - ".arsn-area-head"
766 - );
767 -
768 - if(head){
769 - head.style.setProperty(
770 - "width",
771 - "100%",
772 - "important"
773 - );
774 -
775 - head.style.setProperty(
776 - "max-width",
777 - "100%",
778 - "important"
779 - );
780 -
781 - head.style.setProperty(
782 - "box-sizing",
783 - "border-box",
784 - "important"
785 - );
786 - }
787 - });
788 - }
789 -
790 - /* =======================================================
791 - PLACEHOLDER BADGE
792 - ======================================================= */
793 -
794 - function applyPlaceholderBadge(){
795 - if(!PLACEHOLDER)return;
796 -
797 - if(
798 - document.querySelector(
799 - ".sn-coming-soon-badge"
800 - )
801 - ){
802 - return;
803 - }
804 -
805 - var title=
806 - document.querySelector(
807 - "#document-title"
808 - )||
809 - document.querySelector(
810 - "h1"
811 - );
812 -
813 - if(!title)return;
814 -
815 - var badge=
816 - document.createElement(
817 - "span"
818 - );
819 -
820 - badge.className=
821 - "sn-coming-soon-badge";
822 -
823 - badge.textContent=
824 - PLACEHOLDER_LABEL;
825 -
826 - badge.setAttribute(
827 - "aria-label",
828 - PLACEHOLDER_LABEL
316 + function boxLike(el){
317 + if(!visible(el)||excluded(el))return false;
318 + var s=getComputedStyle(el);
319 + var r=el.getBoundingClientRect();
320 + var border=
321 + num(s.borderTopWidth)+num(s.borderRightWidth)+
322 + num(s.borderBottomWidth)+num(s.borderLeftWidth);
323 + var radius=Math.max(
324 + num(s.borderTopLeftRadius),num(s.borderTopRightRadius),
325 + num(s.borderBottomLeftRadius),num(s.borderBottomRightRadius)
829 829   );
830 -
831 - title.appendChild(
832 - badge
833 - );
327 + var bg=s.backgroundColor&&s.backgroundColor!=="rgba(0, 0, 0, 0)"&&s.backgroundColor!=="transparent";
328 + var shadow=s.boxShadow&&s.boxShadow!=="none";
329 + return namedLikeBox(el)||border>=1||(bg&&radius>=3)||(shadow&&r.width>=180);
834 834   }
835 835  
836 - /* =======================================================
837 - DETAIL PAGE OWN-ACCENT PROPAGATION
838 - ======================================================= */
332 + function pickTarget(child){
333 + if(!visible(child))return null;
334 + if(boxLike(child))return child;
839 839  
840 - function parseRGB(value){
841 - var match=String(value||"").match(
842 - /rgba?\(\s*([\d.]+)\s*,\s*([\d.]+)\s*,\s*([\d.]+)/i
843 - );
844 -
845 - if(!match)return null;
846 -
847 - return [
848 - Number(match[1]),
849 - Number(match[2]),
850 - Number(match[3])
851 - ];
852 - }
853 -
854 - function distance(a,b){
855 - return Math.sqrt(
856 - Math.pow(a[0]-b[0],2)+
857 - Math.pow(a[1]-b[1],2)+
858 - Math.pow(a[2]-b[2],2)
859 - );
860 - }
861 -
862 - function paletteMatch(cssColor){
863 - var rgb=parseRGB(cssColor);
864 -
865 - if(!rgb)return null;
866 -
867 - var palette=[
868 - {hex:"#21b6d7",rgb:[33,182,215]},
869 - {hex:"#e94b13",rgb:[233,75,19]},
870 - {hex:"#f0aa00",rgb:[240,170,0]},
871 - {hex:"#38b76a",rgb:[56,183,106]}
872 - ];
873 -
874 - var best=null;
875 - var bestDistance=Infinity;
876 -
877 - palette.forEach(function(item){
878 - var d=distance(rgb,item.rgb);
879 -
880 - if(d<bestDistance){
881 - best=item;
882 - bestDistance=d;
883 - }
336 + var cr=child.getBoundingClientRect();
337 + var q=[];
338 + Array.from(child.children||[]).forEach(function(el){
339 + q.push({el:el,depth:1});
884 884   });
885 885  
886 - return bestDistance<=30
887 - ?best
888 - :null;
889 - }
342 + var best=null,bestScore=-1;
890 890  
891 - function propagateDetailAccents(){
892 - if(PAGE_KIND!=="detail")return;
344 + while(q.length){
345 + var item=q.shift();
346 + var el=item.el;
347 + if(!visible(el))continue;
893 893  
894 - Array.from(
895 - root.querySelectorAll(
896 - ".arsn-call,.dmp-call,.ido-call,.pp-call,"+
897 - ".arsn-source,.dmp-source,.ido-source,.pp-source"
898 - )
899 - ).forEach(function(el){
900 - if(!visible(el))return;
349 + var r=el.getBoundingClientRect();
901 901  
902 - var style=getComputedStyle(el);
903 -
904 - if(
905 - num(style.borderTopWidth)>=2
906 - ){
907 - var match=
908 - paletteMatch(
909 - style.borderTopColor
910 - );
911 -
912 - if(match){
913 - el.style.setProperty(
914 - "border-left",
915 - "4px solid "+match.hex,
916 - "important"
917 - );
351 + if(r.width>=cr.width*.72&&boxLike(el)){
352 + var widthFit=1-Math.min(1,Math.abs(cr.width-r.width)/Math.max(1,cr.width));
353 + var topFit=1-Math.min(1,Math.abs(cr.top-r.top)/80);
354 + var score=widthFit*5+topFit*2+Math.min(r.height,600)/600;
355 + if(score>bestScore){
356 + best=el;
357 + bestScore=score;
918 918   }
919 919   }
920 - });
921 921  
922 - // Warning families: explicit safety override.
923 - Array.from(
924 - root.querySelectorAll(
925 - ".arsn-warn,.dmp-warn,.ido-warn,.pp-warn,"+
926 - ".warn,.warning,.warningmessage,.errormessage"
927 - )
928 - ).forEach(function(el){
929 - if(!visible(el))return;
930 -
931 - el.style.setProperty(
932 - "border-left",
933 - "4px solid #e94b13",
934 - "important"
935 - );
936 - });
937 -
938 - // Info families: explicit orientation override.
939 - Array.from(
940 - root.querySelectorAll(
941 - ".arsn-info,.dmp-info,.ido-info,.pp-info,.infomessage"
942 - )
943 - ).forEach(function(el){
944 - if(!visible(el))return;
945 -
946 - el.style.setProperty(
947 - "border-left",
948 - "4px solid #21b6d7",
949 - "important"
950 - );
951 - });
952 - }
953 -
954 - /* =======================================================
955 - OVERVIEW SEMANTIC THEME PALETTE
956 - ======================================================= */
957 -
958 - function smallestThemeHeaders(){
959 - return Array.from(
960 - root.querySelectorAll(
961 - "div,span,p,strong,h3,h4,h5,h6"
962 - )
963 - ).filter(function(el){
964 - if(!visible(el))return false;
965 - if(!themeFor(el.textContent))return false;
966 -
967 - return !Array.from(
968 - el.children||[]
969 - ).some(function(child){
970 - return !!themeFor(
971 - child.textContent
972 - );
973 - });
974 - });
975 - }
976 -
977 - function findOverviewCard(header){
978 - var node=header.parentElement;
979 - var candidates=[];
980 -
981 - while(node&&node!==root){
982 - var rect=node.getBoundingClientRect();
983 - var style=getComputedStyle(node);
984 -
985 - var border=
986 - num(style.borderTopWidth)+
987 - num(style.borderRightWidth)+
988 - num(style.borderBottomWidth)+
989 - num(style.borderLeftWidth);
990 -
991 - if(
992 - rect.width>=220&&
993 - rect.width<=800&&
994 - rect.height>=120&&
995 - border>=1
996 - ){
997 - candidates.push(node);
361 + if(item.depth<3){
362 + Array.from(el.children||[]).forEach(function(next){
363 + q.push({el:next,depth:item.depth+1});
364 + });
998 998   }
999 -
1000 - node=node.parentElement;
1001 1001   }
1002 1002  
1003 - if(!candidates.length)return null;
1004 -
1005 - candidates.sort(function(a,b){
1006 - return (
1007 - b.getBoundingClientRect().height-
1008 - a.getBoundingClientRect().height
1009 - );
1010 - });
1011 -
1012 - return candidates[0];
368 + return best;
1013 1013   }
1014 1014  
1015 - function rowCandidates(link,card){
1016 - var result=[];
1017 - var cardRect=
1018 - card.getBoundingClientRect();
1019 -
1020 - var node=link;
1021 -
1022 - while(node&&node!==card){
1023 - if(visible(node)){
1024 - var rect=
1025 - node.getBoundingClientRect();
1026 -
1027 - if(
1028 - rect.height<=105&&
1029 - rect.width>=
1030 - cardRect.width*.50&&
1031 - rect.width<=
1032 - cardRect.width*1.03
1033 - ){
1034 - result.push(node);
1035 - }
1036 - }
1037 -
1038 - node=node.parentElement;
1039 - }
1040 -
1041 - return result;
1042 - }
1043 -
1044 - function chooseOuterRow(
1045 - candidates,
1046 - link
1047 - ){
1048 - if(!candidates.length){
1049 - return link;
1050 - }
1051 -
1052 - var bordered=
1053 - candidates.filter(function(el){
1054 - return (
1055 - num(
1056 - getComputedStyle(el)
1057 - .borderLeftWidth
1058 - )>=1
1059 - );
1060 - });
1061 -
1062 - var pool=
1063 - bordered.length
1064 - ?bordered
1065 - :candidates;
1066 -
1067 - pool.sort(function(a,b){
1068 - var ar=
1069 - a.getBoundingClientRect();
1070 -
1071 - var br=
1072 - b.getBoundingClientRect();
1073 -
1074 - return (
1075 - ar.left-br.left||
1076 - br.width-ar.width
1077 - );
371 + function reset(){
372 + managed.forEach(function(el){
373 + el.style.removeProperty("min-height");
374 + el.removeAttribute("data-sn-equal-height-managed");
1078 1078   });
1079 -
1080 - return pool[0]||link;
376 + managed.clear();
1081 1081   }
1082 1082  
1083 - function applyOverviewPalette(){
1084 - if(PAGE_KIND!=="overview"){
1085 - return [];
379 + function horizontalLayout(parent){
380 + if(!visible(parent))return false;
381 + var s=getComputedStyle(parent);
382 + if(s.display==="grid"||s.display==="inline-grid")return true;
383 + if(s.display==="flex"||s.display==="inline-flex"){
384 + return s.flexDirection==="row"||s.flexDirection==="row-reverse";
1086 1086   }
1087 -
1088 - var headers=
1089 - smallestThemeHeaders()
1090 - .map(function(el){
1091 - return {
1092 - el:el,
1093 - theme:
1094 - themeFor(
1095 - el.textContent
1096 - ),
1097 - card:
1098 - findOverviewCard(
1099 - el
1100 - )
1101 - };
1102 - })
1103 - .filter(function(row){
1104 - return !!row.card;
1105 - });
1106 -
1107 - var unique=[];
1108 - var seenHeaders=new Set();
1109 -
1110 - headers.forEach(function(row){
1111 - var key=
1112 - row.theme.name+
1113 - "|"+
1114 - Math.round(
1115 - row.card
1116 - .getBoundingClientRect()
1117 - .left
1118 - )+
1119 - "|"+
1120 - Math.round(
1121 - row.el
1122 - .getBoundingClientRect()
1123 - .top
1124 - );
1125 -
1126 - if(!seenHeaders.has(key)){
1127 - seenHeaders.add(key);
1128 - unique.push(row);
1129 - }
1130 - });
1131 -
1132 - unique.forEach(function(row){
1133 - var headerRect=
1134 - row.el
1135 - .getBoundingClientRect();
1136 -
1137 - row.el.style.setProperty(
1138 - "background",
1139 - row.theme.bg,
1140 - "important"
1141 - );
1142 -
1143 - row.el.style.setProperty(
1144 - "color",
1145 - row.theme.text,
1146 - "important"
1147 - );
1148 -
1149 - row.el.style.setProperty(
1150 - "text-align",
1151 - "left",
1152 - "important"
1153 - );
1154 -
1155 - row.el.style.setProperty(
1156 - "word-spacing",
1157 - "normal",
1158 - "important"
1159 - );
1160 -
1161 - var later=
1162 - unique
1163 - .filter(function(other){
1164 - return (
1165 - other.card===row.card&&
1166 - other.el
1167 - .getBoundingClientRect()
1168 - .top>
1169 - headerRect.top+2
1170 - );
1171 - })
1172 - .sort(function(a,b){
1173 - return (
1174 - a.el
1175 - .getBoundingClientRect()
1176 - .top-
1177 - b.el
1178 - .getBoundingClientRect()
1179 - .top
1180 - );
1181 - });
1182 -
1183 - var stopTop=
1184 - later.length
1185 - ?later[0].el
1186 - .getBoundingClientRect()
1187 - .top
1188 - :Infinity;
1189 -
1190 - Array.from(
1191 - row.card.querySelectorAll("a")
1192 - ).forEach(function(link){
1193 - if(!visible(link))return;
1194 -
1195 - var rect=
1196 - link.getBoundingClientRect();
1197 -
1198 - if(
1199 - rect.top<=
1200 - headerRect.bottom-2||
1201 - rect.top>=
1202 - stopTop-2
1203 - ){
1204 - return;
1205 - }
1206 -
1207 - var candidates=
1208 - rowCandidates(
1209 - link,
1210 - row.card
1211 - );
1212 -
1213 - var target=
1214 - chooseOuterRow(
1215 - candidates,
1216 - link
1217 - );
1218 -
1219 - candidates.forEach(function(el){
1220 - el.style.setProperty(
1221 - "border-left",
1222 - "0 solid transparent",
1223 - "important"
1224 - );
1225 - });
1226 -
1227 - target.style.setProperty(
1228 - "border-left",
1229 - "3px solid "+
1230 - row.theme.accent,
1231 - "important"
1232 - );
1233 -
1234 - target.style.setProperty(
1235 - "box-sizing",
1236 - "border-box",
1237 - "important"
1238 - );
1239 - });
1240 - });
1241 -
1242 - return unique;
386 + return false;
1243 1243   }
1244 1244  
1245 - /* =======================================================
1246 - OVERVIEW CARD HEIGHT + FIRST THEMATIC ROW
1247 - ======================================================= */
1248 -
1249 - function alignOverviewCards(headers){
1250 - if(
1251 - PAGE_KIND!=="overview"||
1252 - window.innerWidth<=MOBILE_MAX
1253 - ){
1254 - return;
1255 - }
1256 -
1257 - var cards=[];
1258 - var seen=new Set();
1259 -
1260 - headers.forEach(function(row){
1261 - if(!seen.has(row.card)){
1262 - seen.add(row.card);
1263 - cards.push(row.card);
1264 - }
1265 - });
1266 -
1267 - if(cards.length<2){
1268 - return;
1269 - }
1270 -
1271 - // Group cards by actual top position.
389 + function rowGroups(entries){
1272 1272   var groups=[];
1273 -
1274 - cards.forEach(function(card){
1275 - var top=
1276 - card.getBoundingClientRect().top;
1277 -
391 + entries.slice().sort(function(a,b){
392 + return a.rect.top-b.rect.top||a.rect.left-b.rect.left;
393 + }).forEach(function(entry){
1278 1278   var group=null;
1279 -
1280 1280   for(var i=0;i<groups.length;i++){
1281 - if(
1282 - Math.abs(
1283 - groups[i].top-top
1284 - )<=ROW_TOLERANCE
1285 - ){
396 + if(Math.abs(groups[i].top-entry.rect.top)<=ROW_TOLERANCE){
1286 1286   group=groups[i];
1287 1287   break;
1288 1288   }
1289 1289   }
1290 -
1291 1291   if(!group){
1292 - group={
1293 - top:top,
1294 - cards:[]
1295 - };
402 + group={top:entry.rect.top,entries:[]};
1296 1296   groups.push(group);
1297 1297   }
1298 -
1299 - group.cards.push(card);
405 + group.entries.push(entry);
1300 1300   });
407 + return groups;
408 + }
1301 1301  
1302 - groups.forEach(function(group){
1303 - if(group.cards.length<2){
1304 - return;
1305 - }
410 + function run(){
411 + reset();
1306 1306  
1307 - var firstHeaders=
1308 - group.cards.map(function(card){
1309 - var candidates=
1310 - headers
1311 - .filter(function(row){
1312 - return row.card===card;
1313 - })
1314 - .sort(function(a,b){
1315 - return (
1316 - a.el
1317 - .getBoundingClientRect()
1318 - .top-
1319 - b.el
1320 - .getBoundingClientRect()
1321 - .top
1322 - );
1323 - });
413 + if(window.innerWidth<=MOBILE_MAX)return;
1324 1324  
1325 - return candidates.length
1326 - ?candidates[0]
1327 - :null;
1328 - });
415 + var parents=Array.from(root.querySelectorAll("*")).filter(function(el){
416 + return el.children&&el.children.length>=2&&horizontalLayout(el);
417 + });
1329 1329  
1330 - if(
1331 - !firstHeaders.some(function(row){
1332 - return !row;
1333 - })
1334 - ){
1335 - var targetTop=
1336 - Math.max.apply(
1337 - Math,
1338 - firstHeaders.map(function(row){
1339 - return (
1340 - row.el
1341 - .getBoundingClientRect()
1342 - .top-
1343 - row.card
1344 - .getBoundingClientRect()
1345 - .top
1346 - );
1347 - })
1348 - );
419 + parents.forEach(function(parent){
420 + var entries=[];
1349 1349  
1350 - firstHeaders.forEach(function(row){
1351 - var relativeTop=
1352 - row.el
1353 - .getBoundingClientRect()
1354 - .top-
1355 - row.card
1356 - .getBoundingClientRect()
1357 - .top;
1358 -
1359 - var delta=
1360 - targetTop-relativeTop;
1361 -
1362 - if(delta>1){
1363 - saveStyle(
1364 - row.el,
1365 - originalMargin,
1366 - "margin-top"
1367 - );
1368 -
1369 - var current=
1370 - num(
1371 - getComputedStyle(
1372 - row.el
1373 - ).marginTop
1374 - );
1375 -
1376 - row.el.style.setProperty(
1377 - "margin-top",
1378 - (
1379 - current+delta
1380 - )+"px"
1381 - );
1382 -
1383 - row.el.setAttribute(
1384 - "data-sn-master-first-row",
1385 - "1"
1386 - );
1387 -
1388 - managedMargin.add(
1389 - row.el
1390 - );
1391 - }
422 + Array.from(parent.children).forEach(function(child){
423 + if(!visible(child))return;
424 + var target=pickTarget(child);
425 + if(!target)return;
426 + entries.push({
427 + target:target,
428 + rect:target.getBoundingClientRect()
1392 1392   });
1393 - }
1394 -
1395 - var maxHeight=0;
1396 -
1397 - group.cards.forEach(function(card){
1398 - maxHeight=
1399 - Math.max(
1400 - maxHeight,
1401 - card
1402 - .getBoundingClientRect()
1403 - .height
1404 - );
1405 1405   });
1406 1406  
1407 - maxHeight=
1408 - Math.ceil(maxHeight);
432 + if(entries.length<2)return;
1409 1409  
1410 - group.cards.forEach(function(card){
1411 - saveStyle(
1412 - card,
1413 - originalHeight,
1414 - "min-height"
1415 - );
434 + rowGroups(entries).forEach(function(group){
435 + if(group.entries.length<2)return;
1416 1416  
1417 - card.style.setProperty(
1418 - "min-height",
1419 - maxHeight+"px"
1420 - );
437 + var lefts=group.entries.map(function(e){return e.rect.left;}).sort(function(a,b){return a-b;});
438 + if(lefts[lefts.length-1]-lefts[0]<80)return;
1421 1421  
1422 - card.setAttribute(
1423 - "data-sn-master-equal-height",
1424 - "1"
1425 - );
440 + var targets=[];
441 + var seen=new Set();
1426 1426  
1427 - managedHeight.add(
1428 - card
1429 - );
1430 - });
1431 - });
1432 - }
1433 -
1434 - /* =======================================================
1435 - DETAIL GRID EQUAL HEIGHT, DESKTOP ONLY
1436 - ======================================================= */
1437 -
1438 - function equaliseDetailGrids(){
1439 - if(
1440 - PAGE_KIND!=="detail"||
1441 - window.innerWidth<=MOBILE_MAX
1442 - ){
1443 - return;
1444 - }
1445 -
1446 - var selectors=[
1447 - ".arsn-grid",
1448 - ".arsn-grid-2",
1449 - ".arsn-grid-3",
1450 - ".dmp-grid",
1451 - ".ido-grid",
1452 - ".pp-grid"
1453 - ];
1454 -
1455 - selectors.forEach(function(selector){
1456 - Array.from(
1457 - root.querySelectorAll(selector)
1458 - ).forEach(function(grid){
1459 - var children=
1460 - Array.from(
1461 - grid.children||[]
1462 - ).filter(visible);
1463 -
1464 - if(children.length<2){
1465 - return;
1466 - }
1467 -
1468 - var groups=[];
1469 -
1470 - children.forEach(function(child){
1471 - var top=
1472 - child
1473 - .getBoundingClientRect()
1474 - .top;
1475 -
1476 - var group=null;
1477 -
1478 - for(var i=0;i<groups.length;i++){
1479 - if(
1480 - Math.abs(
1481 - groups[i].top-top
1482 - )<=ROW_TOLERANCE
1483 - ){
1484 - group=groups[i];
1485 - break;
1486 - }
443 + group.entries.forEach(function(e){
444 + if(!seen.has(e.target)){
445 + seen.add(e.target);
446 + targets.push(e.target);
1487 1487   }
448 + });
1488 1488  
1489 - if(!group){
1490 - group={
1491 - top:top,
1492 - items:[]
1493 - };
1494 - groups.push(group);
1495 - }
450 + if(targets.length<2)return;
1496 1496  
1497 - group.items.push(child);
452 + var max=0;
453 + targets.forEach(function(el){
454 + max=Math.max(max,el.getBoundingClientRect().height);
1498 1498   });
1499 1499  
1500 - groups.forEach(function(group){
1501 - if(group.items.length<2){
1502 - return;
1503 - }
457 + max=Math.ceil(max);
458 + if(max<MIN_H)return;
1504 1504  
1505 - var maxHeight=0;
1506 -
1507 - group.items.forEach(function(item){
1508 - maxHeight=
1509 - Math.max(
1510 - maxHeight,
1511 - item
1512 - .getBoundingClientRect()
1513 - .height
1514 - );
1515 - });
1516 -
1517 - maxHeight=
1518 - Math.ceil(maxHeight);
1519 -
1520 - group.items.forEach(function(item){
1521 - saveStyle(
1522 - item,
1523 - originalHeight,
1524 - "min-height"
1525 - );
1526 -
1527 - item.style.setProperty(
1528 - "min-height",
1529 - maxHeight+"px"
1530 - );
1531 -
1532 - item.setAttribute(
1533 - "data-sn-master-equal-height",
1534 - "1"
1535 - );
1536 -
1537 - managedHeight.add(item);
1538 - });
460 + targets.forEach(function(el){
461 + el.style.setProperty("min-height",max+"px");
462 + el.setAttribute("data-sn-equal-height-managed","1");
463 + managed.add(el);
1539 1539   });
1540 1540   });
1541 1541   });
1542 1542   }
1543 1543  
1544 - /* =======================================================
1545 - RUN / RESPONSIVE SCHEDULING
1546 - ======================================================= */
1547 -
1548 - function run(){
1549 - if(running)return;
1550 -
1551 - running=true;
1552 -
1553 - try{
1554 - resetRuntime();
1555 - applyPlaceholderBadge();
1556 - propagateDetailAccents();
1557 -
1558 - var headers=
1559 - applyOverviewPalette();
1560 -
1561 - makeThreeLineAreaLabels();
1562 - makeFilledRedOrangeCTAsBorderless();
1563 -
1564 - if(
1565 - window.innerWidth>
1566 - MOBILE_MAX
1567 - ){
1568 - alignOverviewCards(
1569 - headers
1570 - );
1571 -
1572 - equaliseDetailGrids();
1573 - }
1574 - }finally{
1575 - running=false;
1576 - }
469 + function schedule(){
470 + if(raf)cancelAnimationFrame(raf);
471 + raf=requestAnimationFrame(function(){
472 + raf=requestAnimationFrame(function(){
473 + raf=0;
474 + run();
475 + });
476 + });
1577 1577   }
1578 1578  
1579 - function onResize(){
1580 - if(resizeTimer){
1581 - clearTimeout(
1582 - resizeTimer
1583 - );
1584 - }
479 + addEventListener("resize",schedule,{passive:true});
480 + addEventListener("load",schedule,{once:true});
1585 1585  
1586 - resizeTimer=
1587 - setTimeout(
1588 - function(){
1589 - resizeTimer=0;
1590 - run();
1591 - },
1592 - RESIZE_DEBOUNCE
1593 - );
1594 - }
482 + root.addEventListener("click",function(){
483 + setTimeout(schedule,0);
484 + },true);
1595 1595  
1596 - async function waitForReady(){
1597 - if(
1598 - document.readyState!=="complete"
1599 - ){
1600 - await new Promise(function(resolve){
1601 - window.addEventListener(
1602 - "load",
1603 - resolve,
1604 - {once:true}
1605 - );
1606 - });
1607 - }
1608 -
1609 - if(
1610 - document.fonts&&
1611 - document.fonts.ready
1612 - ){
1613 - try{
1614 - await document.fonts.ready;
1615 - }catch(error){}
1616 - }
1617 -
1618 - var images=
1619 - Array.from(
1620 - root.querySelectorAll("img")
1621 - );
1622 -
1623 - await Promise.all(
1624 - images.map(function(img){
1625 - if(img.complete){
1626 - return Promise.resolve();
1627 - }
1628 -
1629 - return new Promise(function(resolve){
1630 - var done=function(){
1631 - resolve();
1632 - };
1633 -
1634 - img.addEventListener(
1635 - "load",
1636 - done,
1637 - {once:true}
1638 - );
1639 -
1640 - img.addEventListener(
1641 - "error",
1642 - done,
1643 - {once:true}
1644 - );
1645 - });
1646 - })
1647 - );
1648 -
1649 - run();
486 + if(document.fonts&&document.fonts.ready){
487 + document.fonts.ready.then(schedule);
1650 1650   }
1651 1651  
1652 - window.addEventListener(
1653 - "resize",
1654 - onResize,
1655 - {passive:true}
1656 - );
1657 -
1658 - waitForReady();
490 + schedule();
491 + setTimeout(schedule,250);
492 + setTimeout(schedule,900);
1659 1659  })();
1660 1660  </script>
1661 -
1662 -<!-- SN_SERVICE_NAVIGATOR_MASTER_STYLE_END -->
495 +<!-- SN_HORIZONTAL_BOX_HARMONIZER_END -->
1663 1663  {{/html}}
1664 1664