diff --git a/src/app/about/about.component.ts b/src/app/about/about.component.ts
index cd480ad4c47b2677e719d7b6728d4cccc943968a..c3e67665098348b03d0cb23dacac7105257732fd 100644
--- a/src/app/about/about.component.ts
+++ b/src/app/about/about.component.ts
@@ -6,8 +6,8 @@ import { Component, Inject } from '@angular/core';
 export class AboutComponent {
 
   constructor(
-    @Inject('APP_NAME') private appName: string,
-    @Inject('APP_PUBLISHER') private appPublisher: string,
-    @Inject('APP_VERSION') private appVersion: string
+    @Inject('APP_NAME') public appName: string,
+    @Inject('APP_PUBLISHER') public appPublisher: string,
+    @Inject('APP_VERSION') public appVersion: string
   ) { }
 }
diff --git a/src/app/app.component.ts b/src/app/app.component.ts
index 38945859bf657b6795909d3b74b53c805b98cbe7..3ac1b21b34d3112dff58b62b5ec35e9643a4c8f8 100644
--- a/src/app/app.component.ts
+++ b/src/app/app.component.ts
@@ -30,7 +30,7 @@ export class AppComponent implements OnInit {
     });
 
     this.bs.getSysConfig().subscribe(sc => {
-      this.mds.setSysConfig(sc);
+      this.mds.setCostumTextsApp(sc);
       // restore login status if stored in localStorage
       const loginToken = localStorage.getItem('lt');
       if (loginToken !== null) {
@@ -56,6 +56,7 @@ export class AppComponent implements OnInit {
           this.bs.getLoginData(loginToken, personToken, bookletDbId).subscribe(ld => {
             if (ld instanceof ServerError) {
               this.mds.setNewLoginData();
+              this.mds.setCostumTextsLogin();
             } else {
               const loginData = ld as LoginData;
               loginData.logintoken = loginToken;
@@ -65,13 +66,16 @@ export class AppComponent implements OnInit {
                 loginData.booklet = 0;
               }
               this.mds.setNewLoginData(loginData);
+              this.mds.setCostumTextsLogin(loginData.costumTexts);
             }
           });
         } else {
           this.mds.setNewLoginData();
+          this.mds.setCostumTextsLogin();
         }
       } else {
         this.mds.setNewLoginData();
+        this.mds.setCostumTextsLogin();
       }
     });
   }
diff --git a/src/app/app.interfaces.ts b/src/app/app.interfaces.ts
index 956860ff993f9d6310e2a2f5c1a2dbc176280800..5696e4a0be8736fc54e7e2b60f29800856d28903 100644
--- a/src/app/app.interfaces.ts
+++ b/src/app/app.interfaces.ts
@@ -23,6 +23,7 @@ export interface LoginData {
   code: string;
   booklet: number;
   bookletlabel: string;
+  costumTexts: KeyValuePair;
 }
 
 export interface BookletStatus {
@@ -45,13 +46,3 @@ export interface KeyValuePair {
 export interface KeyValuePairNumber {
   [K: string]: number;
 }
-
-export enum SysConfigKey {
-  testEndButtonText = 'testEndButtonText',
-  bookletSelectPrompt = 'bookletSelectPrompt',
-  bookletSelectTitle = 'bookletSelectTitle',
-  bookletSelectPromptOne = 'bookletSelectPromptOne',
-  bookletSelectPromptMany = 'bookletSelectPromptMany',
-  codeInputTitle = 'codeInputTitle',
-  codeInputPrompt = 'codeInputPrompt'
-}
diff --git a/src/app/app.module.ts b/src/app/app.module.ts
index c66d1aa36c36b0a32c747bb0ed560f1cd97fb0d8..f5ca540c10b54cdf5c5fc37ca77743a1b311f7a2 100644
--- a/src/app/app.module.ts
+++ b/src/app/app.module.ts
@@ -18,6 +18,7 @@ import { LocationStrategy, HashLocationStrategy } from '@angular/common';
 import { FlexLayoutModule } from '@angular/flex-layout';
 import { ErrormsgComponent } from './errormsg/errormsg.component';
 import { httpInterceptorProviders } from './app.interceptor';
+import { CustomTextPipe } from './custom-text.pipe';
 
 
 @NgModule({
@@ -25,7 +26,8 @@ import { httpInterceptorProviders } from './app.interceptor';
     AppComponent,
     StartComponent,
     AboutComponent,
-    ErrormsgComponent
+    ErrormsgComponent,
+    CustomTextPipe
   ],
   imports: [
     BrowserModule,
diff --git a/src/app/custom-text.pipe.spec.ts b/src/app/custom-text.pipe.spec.ts
new file mode 100644
index 0000000000000000000000000000000000000000..72be11de02c2bb2795f98901cadc4b0697911b78
--- /dev/null
+++ b/src/app/custom-text.pipe.spec.ts
@@ -0,0 +1,8 @@
+import { CustomTextPipe } from './custom-text.pipe';
+
+describe('CustomTextPipe', () => {
+  it('create an instance', () => {
+    const pipe = new CustomTextPipe();
+    expect(pipe).toBeTruthy();
+  });
+});
diff --git a/src/app/custom-text.pipe.ts b/src/app/custom-text.pipe.ts
new file mode 100644
index 0000000000000000000000000000000000000000..4dff10b2301b8338ba78768d255019e077c287af
--- /dev/null
+++ b/src/app/custom-text.pipe.ts
@@ -0,0 +1,14 @@
+import { Pipe, PipeTransform } from '@angular/core';
+import { MainDataService } from './maindata.service';
+
+@Pipe({
+  name: 'customText'
+})
+export class CustomTextPipe implements PipeTransform {
+
+  constructor ( private mds: MainDataService ) {}
+
+  transform(valueForChangeDetection: any, key: string): string {
+    return this.mds.getCostumText(key);
+  }
+}
diff --git a/src/app/errormsg/errormsg.component.ts b/src/app/errormsg/errormsg.component.ts
index 7498ff8d60ea9eda9df10e5f12cace33c6840bc0..94527f5d8c5f299686f2d378a26e3f0b898c5f43 100644
--- a/src/app/errormsg/errormsg.component.ts
+++ b/src/app/errormsg/errormsg.component.ts
@@ -9,7 +9,7 @@ import { Subscription } from 'rxjs';
   styleUrls: ['./errormsg.component.css']
 })
 export class ErrormsgComponent implements OnInit, OnDestroy {
-  private errorMsg: ServerError = null;
+  public errorMsg: ServerError = null;
   private globalErrorMsgSubscription: Subscription = null;
 
   constructor(
diff --git a/src/app/iqb-common/message-dialog/message-dialog.component.ts b/src/app/iqb-common/message-dialog/message-dialog.component.ts
index 948aaff56c21afcb27c6fbae5f1a56e7ea494176..18377c47c9998a942adc287f79c428a810f317d9 100644
--- a/src/app/iqb-common/message-dialog/message-dialog.component.ts
+++ b/src/app/iqb-common/message-dialog/message-dialog.component.ts
@@ -1,6 +1,12 @@
 import { MatDialog, MatDialogRef, MAT_DIALOG_DATA } from '@angular/material';
 import { Component, OnInit, Inject } from '@angular/core';
 
+export enum MessageType {
+  error,
+  warning,
+  info
+}
+
 @Component({
   templateUrl: './message-dialog.component.html',
   styleUrls: ['./message-dialog.component.css']
@@ -32,12 +38,6 @@ export class MessageDialogComponent implements OnInit {
   }
 }
 
-export enum MessageType {
-  error,
-  warning,
-  info
-}
-
 export interface MessageDialogData {
   type: MessageType;
   title: string;
diff --git a/src/app/maindata.service.ts b/src/app/maindata.service.ts
index 2e533be66d32583be5a5be12a65720830379c9f1..4a2e1f778c1b485211bf3ee1d9617f3284d82931 100644
--- a/src/app/maindata.service.ts
+++ b/src/app/maindata.service.ts
@@ -2,13 +2,13 @@ import { KeyValuePair } from './test-controller/test-controller.interfaces';
 import { ServerError, BackendService } from './backend.service';
 import { BehaviorSubject, Subject, forkJoin } from 'rxjs';
 import { Injectable } from '@angular/core';
-import { LoginData, SysConfigKey } from './app.interfaces';
+import { LoginData } from './app.interfaces';
 
 @Injectable({
   providedIn: 'root'
 })
 export class MainDataService {
-  private standardLoginData: Readonly<LoginData> = {
+  private static defaultLoginData: LoginData = {
     logintoken: '',
     persontoken: '',
     mode: '',
@@ -18,12 +18,40 @@ export class MainDataService {
     booklets: null,
     code: '',
     booklet: 0,
-    bookletlabel: ''
+    bookletlabel: '',
+    costumTexts: {}
+  };
+  private static defaultCostumTexts = {
+    'app_title': 'IQB-Testcenter',
+    'app_loginErrorMsg': 'Die Anmeldedaten sind nicht korrekt.',
+    'login_testEndButtonText': 'Test beenden',
+    'login_bookletSelectPrompt': 'Bitte wählen',
+    'login_bookletSelectTitle': 'Bitte wählen',
+    'login_bookletSelectPromptOne': 'Bitte klick auf die Schaltfläche links, um den Test zu starten!',
+    'login_bookletSelectPromptMany': 'Bitte klick auf eine der Schaltflächen links, um einen Test zu starten!',
+    'login_codeInputPrompt': 'Bitte Log-in eingeben, der auf dem Zettel steht!',
+    'login_codeInputTitle': 'Log-in eingeben',
+    'booklet_msgPresentationNotCompleteTitle':
+        'Weiterblättern nicht möglich',
+    'booklet_msgPresentationNotCompleteText':
+        'Du kannst erst weiterblättern, wenn Audio-Dateien vollständig abgespielt wurden '
+        + 'und wenn du in allen Fenstern bis ganz nach unten gescrollt hast.',
+    'booklet_codeToEnterTitle': 'Freigabecode',
+    'booklet_codeToEnterPrompt': 'Bitte gib den Code ein, der angesagt wurde!',
+    'booklet_msgSoonTimeOver5Minutes': 'Du hast noch 5 Minuten Zeit für die Bearbeitung der Aufgaben in diesem Abschnitt.',
+    'booklet_msgSoonTimeOver1Minute': 'Du hast noch 1 Minute Zeit für die Bearbeitung der Aufgaben in diesem Abschnitt.',
+    'booklet_msgTimerStarted': 'Die Bearbeitungszeit für diesen Abschnitt hat begonnen: ',
+    'booklet_msgTimerCancelled': 'Die Bearbeitung des Abschnittes wurde abgebrochen.',
+    'booklet_msgTimeOver': 'Die Bearbeitung des Abschnittes ist beendet.',
+    'booklet_warningLeaveTimerBlockTitle': 'Aufgabenabschnitt verlassen?',
+    'booklet_warningLeaveTimerBlockPrompt': 'Wenn du jetzt weiterblätterst, ist die Bearbeitungszeit beendet und du kannst nicht zurück.',
   };
 
-  public loginData$ = new BehaviorSubject<LoginData>(this.standardLoginData);
+  public loginData$ = new BehaviorSubject<LoginData>(MainDataService.defaultLoginData);
   public globalErrorMsg$ = new BehaviorSubject<ServerError>(null);
-  private _sysConfig: KeyValuePair = null;
+  public refreshCostumTexts = false;
+  private _costumTextsApp: KeyValuePair = {};
+  private _costumTextsLogin: KeyValuePair = {};
 
   // set by app.component.ts
   public postMessage$ = new Subject<MessageEvent>();
@@ -33,16 +61,17 @@ export class MainDataService {
   // ensures consistency
   setNewLoginData(logindata?: LoginData) {
     const myLoginData: LoginData = {
-      logintoken: this.standardLoginData.logintoken,
-      persontoken: this.standardLoginData.persontoken,
-      mode: this.standardLoginData.mode,
-      groupname: this.standardLoginData.groupname,
-      loginname: this.standardLoginData.loginname,
-      workspaceName: this.standardLoginData.workspaceName,
-      booklets: this.standardLoginData.booklets,
-      code: this.standardLoginData.code,
-      booklet: this.standardLoginData.booklet,
-      bookletlabel: this.standardLoginData.bookletlabel
+      logintoken: MainDataService.defaultLoginData.logintoken,
+      persontoken: MainDataService.defaultLoginData.persontoken,
+      mode: MainDataService.defaultLoginData.mode,
+      groupname: MainDataService.defaultLoginData.groupname,
+      loginname: MainDataService.defaultLoginData.loginname,
+      workspaceName: MainDataService.defaultLoginData.workspaceName,
+      booklets: MainDataService.defaultLoginData.booklets,
+      code: MainDataService.defaultLoginData.code,
+      booklet: MainDataService.defaultLoginData.booklet,
+      bookletlabel: MainDataService.defaultLoginData.bookletlabel,
+      costumTexts: MainDataService.defaultLoginData.costumTexts // always ignored except right after getting from backend!
     };
 
     if (logindata) {
@@ -138,25 +167,30 @@ export class MainDataService {
   }
 
   // +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
-  setSysConfig(sc: KeyValuePair) {
-    this._sysConfig = sc;
+  setCostumTextsApp(sc: KeyValuePair = {}) {
+    this.refreshCostumTexts = false;
+    this._costumTextsApp = sc;
+    this.refreshCostumTexts = true;
   }
-
-  getSysConfigValue(key: SysConfigKey): string {
-    if (this._sysConfig !== null) {
-      if (this._sysConfig.hasOwnProperty(key)) {
-        return this._sysConfig[key];
+  setCostumTextsLogin(sc: KeyValuePair = {}) {
+    this.refreshCostumTexts = false;
+    this._costumTextsLogin = sc;
+    this.refreshCostumTexts = true;
+  }
+  getCostumText(key: string): string {
+    if (this._costumTextsLogin) {
+      if (this._costumTextsLogin.hasOwnProperty(key)) {
+        return this._costumTextsLogin[key];
+      }
+    }
+    if (this._costumTextsApp) {
+      if (this._costumTextsApp.hasOwnProperty(key)) {
+        return this._costumTextsApp[key];
       }
     }
-    switch (key) {
-      case SysConfigKey.testEndButtonText: return 'Test beenden';
-      case SysConfigKey.bookletSelectPrompt: return 'Bitte wählen';
-      case SysConfigKey.bookletSelectTitle: return 'Bitte wählen';
-      case SysConfigKey.bookletSelectPromptOne: return 'Bitte klick auf die Schaltfläche links, um den Test zu starten!';
-      case SysConfigKey.bookletSelectPromptMany: return 'Bitte klick auf eine der Schaltflächen links, um einen Test zu starten!';
-      case SysConfigKey.codeInputPrompt: return 'Bitte den Personencode eingeben!';
-      case SysConfigKey.codeInputTitle: return 'Personencode eingeben';
+    if (MainDataService.defaultCostumTexts.hasOwnProperty(key)) {
+        return MainDataService.defaultCostumTexts[key];
     }
-    return '?';
+    return key;
   }
 }
diff --git a/src/app/start/start.component.html b/src/app/start/start.component.html
index dd49b9d771c4e56915a713e15d14486d9541ef6a..05d7d47632cad2b876ce09d62f249d861ca157c6 100644
--- a/src/app/start/start.component.html
+++ b/src/app/start/start.component.html
@@ -34,7 +34,7 @@
     <!-- - - - - - - - - - - - - - - - - -->
     <mat-card fxFlex="0 0 400px" *ngIf="showCodeForm">
       <form [formGroup]="codeinputform" (ngSubmit)="codeinput()">
-        <mat-card-title>{{ codeInputTitle }}</mat-card-title>
+        <mat-card-title>{{ showCodeForm | customText:'login_codeInputTitle' }}</mat-card-title>
         <mat-card-content>
           <mat-form-field>
             <input matInput formControlName="code" placeholder="Personen-Code"(keyup.enter)="codeinput()">
@@ -49,7 +49,7 @@
 
     <!-- - - - - - - - - - - - - - - - - -->
     <mat-card fxFlex="0 0 400px" fxLayout="column" *ngIf="showBookletButtons">
-      <mat-card-title>{{ bookletSelectTitle }}</mat-card-title>
+      <mat-card-title>{{ showBookletButtons | customText:'login_bookletSelectTitle' }}</mat-card-title>
       <mat-card-content>
         <div fxLayout="row" fxLayoutGap="10px" fxLayout="column">
           <p *ngIf="bookletlist.length === 0">
@@ -73,7 +73,7 @@
       <mat-card-content>
         <div fxLayout="column" fxLayoutGap="20px">
           <button mat-raised-button color="primary" [routerLink]="['/t']">Zum Test zurückkehren</button>
-          <button mat-raised-button color="primary" (click)="stopBooklet()">{{ testEndButtonText }}</button>
+          <button mat-raised-button color="primary" (click)="stopBooklet()">{{ showTestRunningButtons | customText:'login_testEndButtonText' }}</button>
           <button mat-raised-button color="foreground" (click)="resetLogin()">Neu anmelden</button>
         </div>
       </mat-card-content>
@@ -82,7 +82,7 @@
     <!-- XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX -->
     <!-- XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX -->
     <mat-card fxFlex="0 2 400px" fxLayout="column" class="status">
-      <mat-card-title>IQB-Testcenter</mat-card-title>
+      <mat-card-title>{{ mds.refreshCostumTexts | customText:'app_title' }}</mat-card-title>
 
       <!-- - - - - - - - - - - - - - - - - -->
       <mat-card-content>
@@ -110,18 +110,18 @@
         <!-- - - - - - - - - - - - - - - - - -->
         <div *ngIf="showCodeForm">
           <p>Für das Starten eines Tests ist die Eingabe eines Personen-Codes nötig.</p>
-          <p>{{ codeInputPrompt }}</p>
+          <p>{{ showCodeForm | customText:'login_codeInputPrompt' }}</p>
         </div>
 
         <!-- - - - - - - - - - - - - - - - - -->
         <div *ngIf="showBookletButtons">
-          <p>{{ bookletSelectPrompt }}</p>
+          <p>{{ showBookletButtons | customText:'login_bookletSelectPrompt' }}</p>
         </div>
 
         <!-- - - - - - - - - - - - - - - - - -->
         <div *ngIf="showTestRunningButtons">
-            <p>Es wird gerade ein Test ausgeführt. Bitte wählen Sie durch Klicken auf eine der beiden Schaltflächen
-              links, ob der Test fortgesetzt oder beendet werden soll!</p>
+            <p>Es wird gerade ein Test ausgeführt. Bitte durch Klicken auf eine der beiden Schaltflächen
+              links wählen, ob der Test fortgesetzt oder beendet werden soll!</p>
         </div>
         <div class="error-msg">{{ (mds.globalErrorMsg$ | async)?.labelNice }}</div>
 
diff --git a/src/app/start/start.component.ts b/src/app/start/start.component.ts
index e6176aeda64d32e2fb1666f369831036f6659ffa..76d5327f0a7fbf7652d34d302b0e98dcd525e4cd 100644
--- a/src/app/start/start.component.ts
+++ b/src/app/start/start.component.ts
@@ -1,4 +1,3 @@
-import { SysConfigKey } from './../app.interfaces';
 import { MainDataService } from './../maindata.service';
 import { Subscription, BehaviorSubject, forkJoin } from 'rxjs';
 import { MessageDialogComponent, MessageDialogData, MessageType } from './../iqb-common';
@@ -15,26 +14,24 @@ import { StartButtonData } from './start-button-data.class';
   styleUrls: ['./start.component.css']
 })
 export class StartComponent implements OnInit, OnDestroy {
+  public dataLoading = false;
+  public showLoginForm = true;
+  public showCodeForm = false;
+  public showBookletButtons = false;
+  public bookletlist: StartButtonData[] = [];
+  public showTestRunningButtons = false;
+
   private loginDataSubscription: Subscription = null;
-  private dataLoading = false;
 
   // for template
-  private showLoginForm = true;
-  private showCodeForm = false;
-  private showBookletButtons = false;
-  private bookletlist: StartButtonData[] = [];
-  private showTestRunningButtons = false;
   private validCodes = [];
   private loginStatusText = ['nicht angemeldet'];
 
   private testtakerloginform: FormGroup;
   private codeinputform: FormGroup;
   private lastloginname = '';
-  private testEndButtonText = 'Test beenden';
   private bookletSelectPrompt = 'Bitte wählen';
   private bookletSelectTitle = 'Bitte wählen';
-  private codeInputPrompt = '';
-  private codeInputTitle = '';
 
   // ??
   // private sessiondata: PersonBooklets;
@@ -44,7 +41,7 @@ export class StartComponent implements OnInit, OnDestroy {
 
 
   constructor(private fb: FormBuilder,
-    private mds: MainDataService,
+    public mds: MainDataService,
     public messsageDialog: MatDialog,
     private router: Router,
     private bs: BackendService) {
@@ -110,8 +107,6 @@ export class StartComponent implements OnInit, OnDestroy {
             } else {
               // code not yet given
               // code prompt
-              this.codeInputTitle = this.mds.getSysConfigValue(SysConfigKey.codeInputTitle);
-              this.codeInputPrompt = this.mds.getSysConfigValue(SysConfigKey.codeInputPrompt);
               this.showCodeForm = true;
               this.showBookletButtons = false;
             }
@@ -148,10 +143,8 @@ export class StartComponent implements OnInit, OnDestroy {
                 this.bookletSelectPrompt = (allOk.length > 1) ? 'Testhefte beendet' : 'Testheft beendet';
                 this.bookletSelectTitle = 'Beendet';
               } else if (numberOfOpenBooklets === 1) {
-                this.bookletSelectPrompt = this.mds.getSysConfigValue(SysConfigKey.bookletSelectPromptOne);
                 this.bookletSelectTitle = 'Bitte starten';
               } else {
-                this.bookletSelectPrompt = this.mds.getSysConfigValue(SysConfigKey.bookletSelectPromptMany);
                 this.bookletSelectTitle = 'Bitte wählen';
               }
             });
@@ -192,6 +185,7 @@ export class StartComponent implements OnInit, OnDestroy {
           // no change in other data
         } else {
           this.mds.globalErrorMsg$.next(null);
+          this.mds.setCostumTextsLogin(loginData.costumTexts);
           this.mds.setNewLoginData(loginData);
         }
         this.dataLoading = false;
@@ -206,8 +200,8 @@ export class StartComponent implements OnInit, OnDestroy {
       this.messsageDialog.open(MessageDialogComponent, {
         width: '400px',
         data: <MessageDialogData>{
-          title: 'Eingabe Personen-Code: Leer',
-          content: this.codeInputPrompt,
+          title: this.mds.getCostumText('login_codeInputTitle') + ': Leer',
+          content: this.mds.getCostumText('login_codeInputPrompt'),
           type: MessageType.error
         }
       });
@@ -215,8 +209,8 @@ export class StartComponent implements OnInit, OnDestroy {
       this.messsageDialog.open(MessageDialogComponent, {
         width: '400px',
         data: <MessageDialogData>{
-          title: 'Eingabe Personen-Code: Ungültig',
-          content: this.codeInputPrompt,
+          title: this.mds.getCostumText('login_codeInputTitle') + ': Ungültig',
+          content: this.mds.getCostumText('login_codeInputPrompt'),
           type: MessageType.error
         }
       });
@@ -250,6 +244,7 @@ export class StartComponent implements OnInit, OnDestroy {
 
   // # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # #
   resetLogin() {
+    this.mds.setCostumTextsLogin();
     this.mds.setNewLoginData();
   }
 
diff --git a/src/app/sys-check/questionnaire/questionnaire.component.html b/src/app/sys-check/questionnaire/questionnaire.component.html
index 480de7f9b4547ff76bd4846c1bf48d55e0688066..2e0e1828a8c41227feff37f595889afd45b73c2a 100644
--- a/src/app/sys-check/questionnaire/questionnaire.component.html
+++ b/src/app/sys-check/questionnaire/questionnaire.component.html
@@ -1,6 +1,3 @@
-<div class="spinner-container" *ngIf="dataLoading">
-  <mat-spinner></mat-spinner>
-</div>
 <div class="step-body" #questionnaireBody>
   <div [formGroup]="form" class="formList" fxLayout="column">
     <div *ngFor="let q of questions">
diff --git a/src/app/sys-check/report/report.component.html b/src/app/sys-check/report/report.component.html
index 6f6b7c68bb0e3f2d0ad127bb17bfd21d78e93326..051dc06db92e9063c9e3cd84fa232dbca000a66c 100644
--- a/src/app/sys-check/report/report.component.html
+++ b/src/app/sys-check/report/report.component.html
@@ -1,6 +1,3 @@
-<div class="spinner-container" *ngIf="dataLoading">
-  <mat-spinner></mat-spinner>
-</div>
 <div class="step-body">
   <h2>Computer-Info</h2>
   <p *ngFor="let rd of environmentData">{{ rd.label }}: {{ rd.value }}</p>
diff --git a/src/app/sys-check/run.component.html b/src/app/sys-check/run.component.html
index a59d4804534b1c607766c6ff1f9a1fe846fb6ee4..020fe22761c4134e45d67e9e94415c123d0b9bf7 100644
--- a/src/app/sys-check/run.component.html
+++ b/src/app/sys-check/run.component.html
@@ -4,9 +4,6 @@
   </a>
 </div>
 <div class="pagetitle">{{ pagetitle }}</div>
-<div class="spinner-container" *ngIf="dataLoading">
-  <mat-spinner></mat-spinner>
-</div>
 <tc-navi-buttons></tc-navi-buttons>
 <div class="page-body">
   <div class="sheetofpaper">
diff --git a/src/app/sys-check/start.component.ts b/src/app/sys-check/start.component.ts
index 7c376ae05aca8c317d733cb21be9c7384804c895..b0bd20c4d9df0c2ef75f75998074d65086d3bf08 100644
--- a/src/app/sys-check/start.component.ts
+++ b/src/app/sys-check/start.component.ts
@@ -12,7 +12,7 @@ import { Component, OnInit } from '@angular/core';
 
 export class StartComponent implements OnInit {
   checkConfigList: CheckConfig[] = [];
-  private dataLoading = false;
+  public dataLoading = false;
 
   constructor(
     private bs: BackendService,
diff --git a/src/app/sys-check/unit-check/tc-navi-buttons/tc-navi-buttons.component.ts b/src/app/sys-check/unit-check/tc-navi-buttons/tc-navi-buttons.component.ts
index 687a4fe43fe20c791b2930d6a5c1afb1e2629637..0ab43c27e7d486efc3e8154239565879b2325646 100644
--- a/src/app/sys-check/unit-check/tc-navi-buttons/tc-navi-buttons.component.ts
+++ b/src/app/sys-check/unit-check/tc-navi-buttons/tc-navi-buttons.component.ts
@@ -7,7 +7,7 @@ import { Component, OnInit } from '@angular/core';
   styleUrls: ['./tc-navi-buttons.component.css']
 })
 export class TcNaviButtonsComponent {
-  private showPageNaviButtons = true;
+  public showPageNaviButtons = true;
   private pagePrevEnabled = false;
   private pageNextEnabled = false;
 
diff --git a/src/app/sys-check/unit-check/unit-check.component.ts b/src/app/sys-check/unit-check/unit-check.component.ts
index e7577dc9f70e0bfe38c0fc3addb3c8b25ae3d230..35017696d2d6cf560815436bfbe6714b2693047d 100644
--- a/src/app/sys-check/unit-check/unit-check.component.ts
+++ b/src/app/sys-check/unit-check/unit-check.component.ts
@@ -33,7 +33,7 @@ export class UnitCheckComponent implements OnInit, OnDestroy {
 
   private pendingItemDefinition$ = new BehaviorSubject(null);
 
-  private dataLoading = false;
+  public dataLoading = false;
 
   constructor(
     private ds: SyscheckDataService,
diff --git a/src/app/test-controller/test-controller.classes.ts b/src/app/test-controller/test-controller.classes.ts
index a213f4a73a69f08d467dfdaab9858dbaca35f7ca..a9db5cb199fce1df126d3709c572af73b2d110a3 100644
--- a/src/app/test-controller/test-controller.classes.ts
+++ b/src/app/test-controller/test-controller.classes.ts
@@ -99,7 +99,6 @@ export class TestletContentElement {
 export class UnitDef extends TestletContentElement {
   readonly alias: string;
   readonly naviButtonLabel: string;
-  readonly reportStatus: boolean;
   playerId: string;
   statusResponses: 'no' | 'some' | 'all';
   statusPresentation: 'no' | 'partly' | 'full';
@@ -111,13 +110,11 @@ export class UnitDef extends TestletContentElement {
     id: string,
     title: string,
     alias: string,
-    naviButtonLabel: string,
-    reportStatus: boolean,
+    naviButtonLabel: string
     ) {
       super(sequenceId, id, title);
       this.alias = alias;
       this.naviButtonLabel = naviButtonLabel;
-      this.reportStatus = reportStatus;
       this.statusResponses = 'no';
       this.statusPresentation = 'no';
   }
@@ -182,9 +179,8 @@ export class Testlet extends TestletContentElement {
     id: string,
     title: string,
     alias: string,
-    naviButtonLabel: string,
-    reportStatus: boolean): UnitDef {
-    const newChild = new UnitDef(sequenceId, id, title, alias, naviButtonLabel, reportStatus);
+    naviButtonLabel: string): UnitDef {
+    const newChild = new UnitDef(sequenceId, id, title, alias, naviButtonLabel);
     this.children.push(newChild);
     return newChild;
   }
diff --git a/src/app/test-controller/test-controller.component.ts b/src/app/test-controller/test-controller.component.ts
index ed5c1de90449426b070490c8540bd3ef4dddad44..0582b199f45b3e30ee3d283207a8e5b6f7f98b9e 100644
--- a/src/app/test-controller/test-controller.component.ts
+++ b/src/app/test-controller/test-controller.component.ts
@@ -22,7 +22,9 @@ export class TestControllerComponent implements OnInit, OnDestroy {
   private navigationRequestSubsription: Subscription = null;
   private maxTimerSubscription: Subscription = null;
 
-  private dataLoading = false;
+  public dataLoading = false;
+  public showProgress = true;
+
   private lastUnitSequenceId = 0;
   private lastTestletIndex = 0;
   private timerValue: MaxTimerData = null;
@@ -30,19 +32,26 @@ export class TestControllerComponent implements OnInit, OnDestroy {
   private allUnitIds: string[] = [];
   private progressValue = 0;
   private loadedUnitCount = 0;
-  private showProgress = true;
 
   constructor (
-    private tcs: TestControllerService,
-    private reviewDialog: MatDialog,
-    private bs: BackendService,
     private mds: MainDataService,
+    public tcs: TestControllerService,
+    private bs: BackendService,
+    private reviewDialog: MatDialog,
     private snackBar: MatSnackBar,
     private router: Router
   ) {
     // this.unitPosSubsription = this.tcs.currentUnitPos$.subscribe(u => this.updateStatus());
   }
 
+  private getCostumText(key: string): string {
+    const value = this.tcs.getCostumText(key);
+    if (value.length > 0) {
+      return value;
+    } else {
+      return this.mds.getCostumText(key);
+    }
+  }
   // ''''''''''''''''''''''''''''''''''''''''''''''''''''
   // private: recursive reading testlets/units from xml
   // ''''''''''''''''''''''''''''''''''''''''''''''''''''
@@ -94,20 +103,6 @@ export class TestControllerComponent implements OnInit, OnDestroy {
 
       for (let childIndex = 0; childIndex < childElements.length; childIndex++) {
         if (childElements[childIndex].nodeName === 'Unit') {
-          let reportstatus: string = childElements[childIndex].getAttribute('reportStatus');
-          if ((typeof reportstatus !== 'undefined') && (reportstatus !== null)) {
-            if (reportstatus.length > 0) {
-              reportstatus = reportstatus.substr(0, 1).toLowerCase();
-              if ((reportstatus === 'y') || (reportstatus === 'j')) {
-                reportstatus = 't';
-              }
-            } else {
-              reportstatus = 'n';
-            }
-          } else {
-            reportstatus = 'n';
-          }
-
           const myUnitId = childElements[childIndex].getAttribute('id');
           let myUnitAlias = childElements[childIndex].getAttribute('alias');
           if (!myUnitAlias) {
@@ -123,7 +118,7 @@ export class TestControllerComponent implements OnInit, OnDestroy {
 
           const newUnit = targetTestlet.addUnit(this.lastUnitSequenceId, myUnitId,
                 childElements[childIndex].getAttribute('label'), myUnitAliasClear,
-                childElements[childIndex].getAttribute('labelshort'), reportstatus === 't');
+                childElements[childIndex].getAttribute('labelshort'));
           this.lastUnitSequenceId += 1;
 
         } else if (childElements[childIndex].nodeName === 'Testlet') {
@@ -163,6 +158,21 @@ export class TestControllerComponent implements OnInit, OnDestroy {
 
           const unitsElements = oDOM.documentElement.getElementsByTagName('Units');
           if (unitsElements.length > 0) {
+            const costumTextsElements = oDOM.documentElement.getElementsByTagName('CostumTexts');
+            if (costumTextsElements.length > 0) {
+              const costumTexts = costumTextsElements[0].children;
+              const costumTextsForBooklet = {};
+              for (let childIndex = 0; childIndex < costumTexts.length; childIndex++) {
+                if (costumTexts[childIndex].nodeName === 'Text') {
+                  const costumTextKey = costumTexts[childIndex].getAttribute('key');
+                  if ((typeof costumTextKey !== 'undefined') && (costumTextKey !== null)) {
+                    costumTextsForBooklet[costumTextKey] = costumTexts[childIndex].textContent;
+                  }
+                }
+              }
+              this.tcs.setCostumTexts(costumTextsForBooklet);
+            }
+
             const bookletConfigElements = oDOM.documentElement.getElementsByTagName('BookletConfig');
             if (bookletConfigElements.length > 0) {
               const bookletConfigs = bookletConfigElements[0].children;
@@ -181,6 +191,13 @@ export class TestControllerComponent implements OnInit, OnDestroy {
                       this.tcs.showNavButtons = true;
                     }
                   }
+                } else if (bookletConfigs[childIndex].nodeName === 'LockOnlyIfResponsesComplete') {
+                  const configParameter = bookletConfigs[childIndex].getAttribute('parameter');
+                  if ((typeof configParameter !== 'undefined') && (configParameter !== null)) {
+                    if (configParameter === '1') {
+                      this.tcs.LockOnlyIfResponsesComplete = true;
+                    }
+                  }
                 }
               }
             }
@@ -251,7 +268,7 @@ export class TestControllerComponent implements OnInit, OnDestroy {
             if (myUnitData.restorepoint) {
               this.tcs.newUnitRestorePoint(myUnit.id, sequenceId, JSON.parse(myUnitData.restorepoint), false);
             }
-            let playerId = '';
+            let playerId = null;
             let definitionRef = '';
 
             try {
@@ -278,12 +295,12 @@ export class TestControllerComponent implements OnInit, OnDestroy {
               }
             } catch (error) {
               console.log('error parsing xml for unit "' + myUnit.id + '": ' + error.toString());
-              playerId = '';
+              playerId = null;
               definitionRef = '';
             }
             this.incrementProgressValueBy1();
 
-            if (playerId.length > 0) {
+            if (playerId) {
               myUnit.playerId = playerId;
 
               return this.loadPlayerOk(playerId).pipe(
@@ -323,10 +340,10 @@ export class TestControllerComponent implements OnInit, OnDestroy {
 
     this.maxTimerSubscription = this.tcs.maxTimeTimer$.subscribe(maxTimerData => {
       if (maxTimerData.type === MaxTimerDataType.STARTED) {
-        this.snackBar.open('Bearbeitungszeit hat begonnen: ' + maxTimerData.timeLeftMinString, '', {duration: 3000});
+        this.snackBar.open(this.getCostumText('booklet_msgTimerStarted') + maxTimerData.timeLeftMinString, '', {duration: 3000});
         this.timerValue = maxTimerData;
       } else if (maxTimerData.type === MaxTimerDataType.ENDED) {
-        this.snackBar.open('Bearbeitungszeit beendet', '', {duration: 3000});
+        this.snackBar.open(this.getCostumText('booklet_msgTimeOver'), '', {duration: 3000});
         this.tcs.rootTestlet.setTimeLeftNull(maxTimerData.testletId);
         this.tcs.LastMaxTimerState[maxTimerData.testletId] = 0;
         this.tcs.setBookletState(LastStateKey.MAXTIMELEFT, JSON.stringify(this.tcs.LastMaxTimerState));
@@ -336,7 +353,7 @@ export class TestControllerComponent implements OnInit, OnDestroy {
           this.tcs.setUnitNavigationRequest('#next');
         }
       } else if (maxTimerData.type === MaxTimerDataType.CANCELLED) {
-        this.snackBar.open('Bearbeitungszeit abgebrochen', '', {duration: 3000});
+        this.snackBar.open(this.getCostumText('booklet_msgTimerCancelled'), '', {duration: 3000});
         this.tcs.rootTestlet.setTimeLeftNull(maxTimerData.testletId);
         this.tcs.LastMaxTimerState[maxTimerData.testletId] = 0;
         this.tcs.setBookletState(LastStateKey.MAXTIMELEFT, JSON.stringify(this.tcs.LastMaxTimerState));
@@ -348,9 +365,9 @@ export class TestControllerComponent implements OnInit, OnDestroy {
           this.tcs.setBookletState(LastStateKey.MAXTIMELEFT, JSON.stringify(this.tcs.LastMaxTimerState));
         }
         if ((maxTimerData.timeLeftSeconds / 60) === 5) {
-          this.snackBar.open('Bearbeitungszeit noch ca. 5 min', '', {duration: 3000});
+          this.snackBar.open(this.getCostumText('booklet_msgSoonTimeOver5Minutes'), '', {duration: 3000});
         } else if ((maxTimerData.timeLeftSeconds / 60) === 1) {
-          this.snackBar.open('Bearbeitungszeit noch ca. 1 min', '', {duration: 3000});
+          this.snackBar.open(this.getCostumText('booklet_msgSoonTimeOver1Minute'), '', {duration: 3000});
         }
       }
     });
@@ -372,7 +389,6 @@ export class TestControllerComponent implements OnInit, OnDestroy {
                 startWith = this.tcs.minUnitSequenceId - 1;
               }
               const nextUnitSequenceId = this.tcs.rootTestlet.getNextUnlockedUnitSequenceId(startWith);
-              console.log('getNextUnlockedUnitSequenceId: ' + nextUnitSequenceId.toString());
               if (nextUnitSequenceId > 0) {
                 this.router.navigateByUrl('/t/u/' + (nextUnitSequenceId).toString());
               }
diff --git a/src/app/test-controller/test-controller.interfaces.ts b/src/app/test-controller/test-controller.interfaces.ts
index dd66d041032b73996b6970c84d13b752cc283543..512acc44fdea760b2bbba9866090a1ccbebde0bc 100644
--- a/src/app/test-controller/test-controller.interfaces.ts
+++ b/src/app/test-controller/test-controller.interfaces.ts
@@ -18,6 +18,7 @@ export interface UnitRestorePointData {
 // testcontroller restrictions +++++++++++++++++++++++++++++++++++
 export interface StartLockData {
     title: string;
+    prompt: string;
     codes: CodeInputData[];
 }
 
diff --git a/src/app/test-controller/test-controller.service.ts b/src/app/test-controller/test-controller.service.ts
index bc8ca035c20c15a59ab85969d4b6f45a2f91e7d3..53a69e34b57bc5bdeaf3e512abc49aea6522ac1b 100644
--- a/src/app/test-controller/test-controller.service.ts
+++ b/src/app/test-controller/test-controller.service.ts
@@ -36,6 +36,7 @@ export class TestControllerService {
   public unitListForNaviButtons$ = new BehaviorSubject<UnitNaviButtonData[]>([]);
   public navPolicyNextOnlyIfPresentationComplete = false;
   public showNavButtons = false;
+  public LockOnlyIfResponsesComplete = false;
 
   public get currentUnitSequenceId(): number {
     return this._currentUnitSequenceId;
@@ -72,6 +73,7 @@ export class TestControllerService {
 
   private restorePointsToSave$ = new Subject<UnitRestorePointData>();
   private responsesToSave$ = new Subject<UnitResponseData>();
+  private _costumTexts: KeyValuePair = {};
 
   constructor (
     private bs: BackendService
@@ -125,6 +127,7 @@ export class TestControllerService {
     this.unitListForNaviButtons$.next([]);
     this.navPolicyNextOnlyIfPresentationComplete = false;
     this.showNavButtons = false;
+    this._costumTexts = {};
   }
 
   // 7777777777777777777777777777777777777777777777777777777777777777777777
@@ -297,7 +300,19 @@ export class TestControllerService {
     if (this.rootTestlet) {
       this.minUnitSequenceId = this.rootTestlet.getFirstUnlockedUnitSequenceId(startWith);
       this.maxUnitSequenceId = this.rootTestlet.getLastUnlockedUnitSequenceId(startWith);
-      console.log('updateMinMaxUnitSequenceId: ' + this.minUnitSequenceId.toString() + '/' + this.maxUnitSequenceId.toString());
     }
   }
+
+  // 7777777777777777777777777777777777777777777777777777777777777777777777
+  public setCostumTexts(sc: KeyValuePair = {}) {
+    this._costumTexts = sc;
+  }
+  public getCostumText(key: string): string {
+    if (this._costumTexts) {
+      if (this._costumTexts.hasOwnProperty(key)) {
+        return this._costumTexts[key];
+      }
+    }
+    return '';
+  }
 }
diff --git a/src/app/test-controller/unithost/unit-routing-guards.ts b/src/app/test-controller/unithost/unit-routing-guards.ts
index 5110ceb728604616874083881f75e048cc426ea2..9221949c1708834c896beb09b72375d96a3eb1db 100644
--- a/src/app/test-controller/unithost/unit-routing-guards.ts
+++ b/src/app/test-controller/unithost/unit-routing-guards.ts
@@ -1,4 +1,3 @@
-import { FormGroup } from '@angular/forms';
 import { StartLockInputComponent } from '../start-lock-input/start-lock-input.component';
 import { ConfirmDialogComponent, ConfirmDialogData } from '../../iqb-common/confirm-dialog/confirm-dialog.component';
 import { MatDialog, MatSnackBar } from '@angular/material';
@@ -6,20 +5,31 @@ import { TestControllerService } from '../test-controller.service';
 import { switchMap, map } from 'rxjs/operators';
 import { UnithostComponent } from './unithost.component';
 import { Injectable } from '@angular/core';
-import { CanActivate, CanDeactivate, ActivatedRouteSnapshot, RouterStateSnapshot, Resolve } from '@angular/router';
+import { CanActivate, CanDeactivate, ActivatedRouteSnapshot, RouterStateSnapshot } from '@angular/router';
 import { Observable, of } from 'rxjs';
-import { UnitDef, UnitControllerData, Testlet } from '../test-controller.classes';
-import { CodeInputData, LogEntryKey, StartLockData, KeyValuePair, LastStateKey } from '../test-controller.interfaces';
+import { UnitControllerData } from '../test-controller.classes';
+import { CodeInputData, LogEntryKey, StartLockData } from '../test-controller.interfaces';
+import { MainDataService } from 'src/app/maindata.service';
 
 @Injectable()
 export class UnitActivateGuard implements CanActivate {
   constructor(
     private tcs: TestControllerService,
+    private mds: MainDataService,
     public startLockDialog: MatDialog,
     public confirmDialog: MatDialog,
     private snackBar: MatSnackBar
   ) {}
 
+  private getCostumText(key: string): string {
+    const value = this.tcs.getCostumText(key);
+    if (value.length > 0) {
+      return value;
+    } else {
+      return this.mds.getCostumText(key);
+    }
+  }
+
   // ****************************************************************************************
   checkAndSolve_PresentationCompleteCode(newUnit: UnitControllerData): Observable<Boolean> {
     let checkPC = this.tcs.navPolicyNextOnlyIfPresentationComplete && this.tcs.currentUnitSequenceId > 0;
@@ -38,16 +48,16 @@ export class UnitActivateGuard implements CanActivate {
               width: '500px',
               // height: '300px',
               data:  <ConfirmDialogData>{
-                title: 'Weiterblättern nicht möglich',
-                content: 'Bitte warte das Abspielen des Audiotextes ab bzw. schau dir alle Seiten vollständig an! ' +
-                  'Erst dann kannst Du weiterblättern.',
+                title: this.getCostumText('booklet_msgPresentationNotCompleteTitle'),
+                content: this.getCostumText('booklet_msgPresentationNotCompleteText'),
                 confirmbuttonlabel: 'OK',
                 confirmbuttonreturn: false
               }
             });
             return dialogCDRef.afterClosed().pipe(map(ok => false));
           } else {
-            this.snackBar.open('Im Hot-Modus dürfte hier nicht weitergeblättert werden.', 'Weiterblättern', {duration: 3000});
+            this.snackBar.open('Im Hot-Modus dürfte hier nicht weitergeblättert werden (PresentationNotComplete).',
+                'Weiterblättern', {duration: 3000});
             return of(true);
           }
         }
@@ -57,16 +67,16 @@ export class UnitActivateGuard implements CanActivate {
             width: '500px',
             // height: '300px',
             data:  <ConfirmDialogData>{
-              title: 'Weiterblättern nicht möglich',
-              content: 'Bitte warte das Abspielen des Audiotextes ab bzw. schau dir alle Seiten vollständig an! ' +
-                'Erst dann kannst Du weiterblättern.',
+              title: this.getCostumText('booklet_msgPresentationNotCompleteTitle'),
+              content: this.getCostumText('booklet_msgPresentationNotCompleteText'),
               confirmbuttonlabel: 'OK',
               confirmbuttonreturn: false
             }
           });
           return dialogCDRef.afterClosed().pipe(map(ok => false));
         } else {
-          this.snackBar.open('Im Hot-Modus dürfte hier nicht weitergeblättert werden.', 'Weiterblättern', {duration: 3000});
+          this.snackBar.open('Im Hot-Modus dürfte hier nicht weitergeblättert werden (PresentationNotComplete).',
+              'Weiterblättern', {duration: 3000});
           return of(true);
         }
       }
@@ -92,7 +102,8 @@ export class UnitActivateGuard implements CanActivate {
         const dialogRef = this.startLockDialog.open(StartLockInputComponent, {
           width: '500px',
           data: <StartLockData>{
-            title: 'Freigabecodes',
+            title: this.getCostumText('booklet_codeToEnterTitle'),
+            prompt: this.getCostumText('booklet_codeToEnterPrompt'),
             codes: myCodes
           }
         });
@@ -117,7 +128,7 @@ export class UnitActivateGuard implements CanActivate {
                   return of(true);
 
                 } else {
-                  this.snackBar.open('Die Eingabe war nicht korrekt.', 'Freigabewort', {duration: 3000});
+                  this.snackBar.open('Die Eingabe war nicht korrekt.', this.getCostumText('booklet_codeToEnterTitle'), {duration: 3000});
                   return of(false);
                 }
               }
@@ -146,8 +157,8 @@ export class UnitActivateGuard implements CanActivate {
           width: '500px',
           // height: '300px',
           data:  <ConfirmDialogData>{
-            title: 'Aufgabenbereich verlassen?',
-            content: 'Wenn du jetzt weiterblätterst, ist die Bearbeitungszeit beendet und du kannst nicht zurück.',
+            title: this.getCostumText('booklet_warningLeaveTimerBlockTitle'),
+            content: this.getCostumText('booklet_warningLeaveTimerBlockPrompt'),
             confirmbuttonlabel: 'Trotzdem weiter',
             confirmbuttonreturn: true
           }
@@ -187,9 +198,8 @@ export class UnitActivateGuard implements CanActivate {
           width: '500px',
           // height: '300px',
           data:  <ConfirmDialogData>{
-            title: 'Aufgabenbereich verlassen?',
-            content: 'Wenn du jetzt weiterblätterst, ist die Bearbeitungszeit des vorherigen Aufgabenbereiches' +
-                    ' beendet und du kannst nicht zurück.',
+            title: this.getCostumText('booklet_warningLeaveTimerBlockTitle'),
+            content: this.getCostumText('booklet_warningLeaveTimerBlockTextPrompt'),
             confirmbuttonlabel: 'Trotzdem weiter',
             confirmbuttonreturn: true
           }
diff --git a/src/app/test-controller/unithost/unithost.component.html b/src/app/test-controller/unithost/unithost.component.html
index f3a8677407a602041cb0432ad4eb47665bf8f795..cb22160a00eeaf5c3007948ca50f52c7814d00c4 100644
--- a/src/app/test-controller/unithost/unithost.component.html
+++ b/src/app/test-controller/unithost/unithost.component.html
@@ -1,6 +1,3 @@
-<div class="spinner-container" *ngIf="dataLoading">
-    <mat-spinner></mat-spinner>
-</div>
 <div id="unit-title" fxLayoutAlign="center center">
     {{ unitTitle }}
 </div>
diff --git a/src/app/test-controller/unithost/unithost.component.ts b/src/app/test-controller/unithost/unithost.component.ts
index e7ca20c74673ca0216029895a6354b7105fefe5a..6d19f7d59228a3007f49e5917045487aa5789804 100644
--- a/src/app/test-controller/unithost/unithost.component.ts
+++ b/src/app/test-controller/unithost/unithost.component.ts
@@ -22,9 +22,11 @@ export class UnithostComponent implements OnInit, OnDestroy {
   public leaveWarningText = 'Du hast den Hörtext noch nicht vollständig gehört. Nach dem ' +
           'Verlassen der Aufgabe wird der Hörtext nicht noch einmal gestartet. Trotzdem die Aufgabe verlassen?';
 
+  public unitTitle = '';
+  public showPageNav = false;
+
   private myUnitSequenceId = -1;
   private myUnitDbKey = '';
-  private unitTitle = '';
 
   // :::::::::::::::::::::
   private postMessageSubscription: Subscription = null;
@@ -35,7 +37,6 @@ export class UnithostComponent implements OnInit, OnDestroy {
 
   private itemplayerValidPages: string[] = [];
   private itemplayerCurrentPage = '';
-  private showPageNav = false;
   private pageList: PageData[] = [];
 
 
diff --git a/src/environments/environment.build.ts b/src/environments/environment.build.ts
index 4689fb3d77542bbe7ac803cc9e0b1f69f1daa622..cbe7d0cb085a7df39d16c0255707654890aac2b2 100644
--- a/src/environments/environment.build.ts
+++ b/src/environments/environment.build.ts
@@ -5,5 +5,5 @@ export const environment = {
   testcenterUrl: '/',
   appName: 'IQB-Testcenter',
   appPublisher: 'IQB - Institut zur Qualitätsentwicklung im Bildungswesen',
-  appVersion: '0.18.1 - 19.3.2019'
+  appVersion: '1.0 - 24.3.2019'
 };
diff --git a/src/environments/environment.prod.ts b/src/environments/environment.prod.ts
index 3612073bc31cd4c1f5d6cbb00318521e9a61bd8a..680a2432afd6b0480b2edcba099e786cb7285a28 100644
--- a/src/environments/environment.prod.ts
+++ b/src/environments/environment.prod.ts
@@ -1,3 +1,9 @@
+// ng build --prod
+
 export const environment = {
-  production: true
+  production: true,
+  testcenterUrl: '/',
+  appName: 'IQB-Testcenter',
+  appPublisher: 'IQB - Institut zur Qualitätsentwicklung im Bildungswesen',
+  appVersion: '1.0 - 24.3.2019'
 };
diff --git a/src/environments/environment.ts b/src/environments/environment.ts
index 50ce032506acf3e19931c5eb9d37c03ae74b6cbf..f3f9076c646351f6fd2da2c3cd5fa5f04d871922 100644
--- a/src/environments/environment.ts
+++ b/src/environments/environment.ts
@@ -5,6 +5,7 @@
 export const environment = {
   production: false,
   testcenterUrl: 'https://www.iqb-testcenter.de/',
+  // testcenterUrl: 'https://itemdb2.iqb.hu-berlin.de/',
   appName: 'IQB-Testcenter',
   appPublisher: 'IQB - Institut zur Qualitätsentwicklung im Bildungswesen',
   appVersion: '0 (dev)'