From 315808186341d94ddd56fc87a30e58c87bb7bc15 Mon Sep 17 00:00:00 2001
From: jojohoch <joachim.hoch@iqb.hu-berlin.de>
Date: Fri, 4 Feb 2022 09:25:19 +0100
Subject: [PATCH] [player] Calculate the minimum height of a page in separate
 page mode

---
 .../components/layout/layout.component.html   | 19 ++++----
 .../app/components/layout/layout.component.ts |  4 +-
 .../directives/hide-first-child.directive.ts  | 43 ++++++++++++++++---
 3 files changed, 50 insertions(+), 16 deletions(-)

diff --git a/projects/player/src/app/components/layout/layout.component.html b/projects/player/src/app/components/layout/layout.component.html
index 7733756c5..739f8e249 100644
--- a/projects/player/src/app/components/layout/layout.component.html
+++ b/projects/player/src/app/components/layout/layout.component.html
@@ -31,13 +31,14 @@
          [class.center-pages]="layoutAlignment === 'column' || !hasScrollPages"
          [class.left-container]="alwaysVisiblePagePosition === 'left'"
          [style.max-width]="containerMaxWidth.alwaysVisiblePage">
-      <div appHideFirstChild
-           [hideFirstChild]="hidePageLabels"
-           [style.min-height]="'calc(100vh - ' + (alwaysVisiblePage.margin * 2) + 'px)'"
+      <div [style.min-height]="'calc(100vh - ' + (alwaysVisiblePage.margin * 2) + 'px)'"
            [style.background-color]="alwaysVisiblePage.backgroundColor"
            [style.max-width]="alwaysVisiblePage.hasMaxWidth ? alwaysVisiblePage.maxWidth + 'px' : '100%'"
            [style.padding.px]="alwaysVisiblePage.margin">
-        <div class="mat-tab-label">{{'alwaysVisiblePage' | translate}}</div>
+        <div *ngIf="!hidePageLabels"
+             class="mat-tab-label">
+          {{'alwaysVisiblePage' | translate}}
+        </div>
         <app-page [parentArrayIndex]="alwaysVisibleUnitPageIndex"
                   [parentForm]="parentForm"
                   [isLastPage]="false"
@@ -71,12 +72,13 @@
 <ng-template #scrollPagesSeparatedView let-pagesContainer>
   <mat-tab-group appHideFirstChild
                  [hideFirstChild]="hidePageLabels"
+                 (childHeight)="tabHeaderHeight = $event"
                  mat-align-tabs="start"
                  [(selectedIndex)]="selectedIndex"
                  (selectedIndexChange)="onSelectedIndexChange($event)">
     <ng-container *ngFor="let page of scrollPages; let i = index; let last = last">
       <mat-tab [label]="'pageIndication' | translate: {index: i + 1}">
-        <div [style.min-height]="'calc(100vh - ' + (page.margin * 2) + 'px)'"
+        <div [style.min-height]="'calc(100vh - ' + ((page.margin * 2 + tabHeaderHeight)) + 'px)'"
              [style.background-color]="page.backgroundColor"
              [style.padding.px]="page.margin"
              [style.max-width]="page.hasMaxWidth ? page.maxWidth + 'px' : '100%'">
@@ -94,9 +96,7 @@
 
 <ng-template #scrollPagesScrolledView let-pagesContainer>
   <ng-container *ngFor="let page of scrollPages; let i = index; let last = last">
-    <div appHideFirstChild
-         [hideFirstChild]="hidePageLabels"
-         [style.min-height]="'calc(100vh - ' + (page.margin * 2) + 'px)'"
+    <div [style.min-height]="'calc(100vh - ' + (page.margin * 2) + 'px)'"
          [style.background-color]="page.backgroundColor"
          [class.concat-scroll-snap-align]="scrollPageMode === 'concat-scroll-snap'"
          [style.max-width]="page.hasMaxWidth ? page.maxWidth + 'px' : '100%'"
@@ -105,7 +105,8 @@
          [pagesContainer]="pagesContainer"
          [selectIndex]="selectIndex"
          [index]="i">
-      <div class="mat-tab-label">
+      <div *ngIf="!hidePageLabels"
+           class="mat-tab-label">
         {{'pageIndication' | translate: {index: i + 1} }}
       </div>
       <app-page [parentArrayIndex]="scrollPagesIndices[i]"
diff --git a/projects/player/src/app/components/layout/layout.component.ts b/projects/player/src/app/components/layout/layout.component.ts
index 1d8d13785..6fd5fa7d4 100644
--- a/projects/player/src/app/components/layout/layout.component.ts
+++ b/projects/player/src/app/components/layout/layout.component.ts
@@ -51,7 +51,8 @@ export class LayoutComponent implements OnInit, AfterViewInit, OnDestroy {
   alwaysVisiblePagePosition!: 'top' | 'bottom' | 'left' | 'right' ;
   layoutAlignment!: 'row' | 'column';
   scrollPageMode!: 'separate' | 'concat-scroll' | 'concat-scroll-snap';
-  hidePageLabels!: boolean;
+  hidePageLabels: boolean = true;
+  tabHeaderHeight: number = 0;
 
   maxWidth: { alwaysVisiblePage: number, scrollPages: number, allPages: number } =
   { alwaysVisiblePage: 0, scrollPages: 0, allPages: 0 };
@@ -138,7 +139,6 @@ export class LayoutComponent implements OnInit, AfterViewInit, OnDestroy {
     this.layoutAlignment = (this.alwaysVisiblePagePosition === 'left' || this.alwaysVisiblePagePosition === 'right') ?
       'row' : 'column';
     this.scrollPageMode = this.playerConfig.pagingMode ? this.playerConfig.pagingMode : 'separate';
-    this.hidePageLabels = true;
 
     this.maxWidth.alwaysVisiblePage = this.getAbsolutePageWidth(this.alwaysVisiblePage);
     this.maxWidth.scrollPages = this.getScrollPagesWidth();
diff --git a/projects/player/src/app/directives/hide-first-child.directive.ts b/projects/player/src/app/directives/hide-first-child.directive.ts
index 3e8b69026..2c2b5dc56 100644
--- a/projects/player/src/app/directives/hide-first-child.directive.ts
+++ b/projects/player/src/app/directives/hide-first-child.directive.ts
@@ -1,18 +1,51 @@
 import {
-  Directive, ElementRef, Input
+  AfterViewInit,
+  Directive, ElementRef, EventEmitter, Input, OnDestroy, OnInit, Output
 } from '@angular/core';
+import { Subject } from 'rxjs';
+import { takeUntil } from 'rxjs/operators';
+import { NativeEventService } from '../services/native-event.service';
 
 @Directive({
   selector: '[appHideFirstChild]'
 })
-export class HideFirstChildDirective {
+export class HideFirstChildDirective implements OnInit, AfterViewInit, OnDestroy {
   @Input() hideFirstChild!: boolean;
+  @Output() childHeight = new EventEmitter<number>();
 
-  constructor(private elementRef: ElementRef) {}
+  private ngUnsubscribe = new Subject<void>();
+
+  constructor(
+    private elementRef: ElementRef,
+    private nativeEventService: NativeEventService
+  ) {}
 
   ngOnInit(): void {
-    if (this.hideFirstChild && this.elementRef.nativeElement.firstChild) {
-      this.elementRef.nativeElement.firstChild.style.display = 'none';
+    if (this.elementRef.nativeElement.firstChild) {
+      if (this.hideFirstChild) {
+        // default usage: hide element!
+        this.elementRef.nativeElement.firstChild.style.display = 'none';
+      } else {
+        // otherwise: send its height to handle it
+        this.nativeEventService.resize
+          .pipe(takeUntil(this.ngUnsubscribe))
+          .subscribe(() => this.emitHeight());
+      }
+    }
+  }
+
+  ngAfterViewInit(): void {
+    if (this.elementRef.nativeElement.firstChild && !this.hideFirstChild) {
+      this.emitHeight();
     }
   }
+
+  private emitHeight() {
+    this.childHeight.emit(this.elementRef.nativeElement.firstChild.offsetHeight);
+  }
+
+  ngOnDestroy(): void {
+    this.ngUnsubscribe.next();
+    this.ngUnsubscribe.complete();
+  }
 }
-- 
GitLab