diff --git a/src/app/app.component.html b/src/app/app.component.html index 11e0c3cdafcb2d20da5f0a8b14df7263cbaf035d..b2c03e2846ae9553519646a49d42f9dd42c73260 100644 --- a/src/app/app.component.html +++ b/src/app/app.component.html @@ -1,8 +1,9 @@ +<script src="models/rescale.ts"></script> <div fxLayout="column" fxFill appTheme> + <header class="header" id="header_rescale"> + <app-header #header></app-header> + </header> <div id="rescale_screen"> - <header class="header" id="header_rescale"> - <app-header #header></app-header> - </header> <div class="main_container"> <div class="inner_main_container"> <main fxFlex class="app-component"> @@ -10,22 +11,22 @@ </main> </div> </div> - <footer role="contentinfo" class="footer" id="footer_rescale"> - <app-footer></app-footer> - </footer> </div> - <div class="rescale_overlay" id="overlay_rescale" aria-hidden="true;"> - <button mat-icon-button (click)="getRescale().deactivateScale()"> - <mat-icon>arrow_back</mat-icon> + <footer role="contentinfo" class="footer" id="footer_rescale"> + <app-footer></app-footer> + </footer> + <div class="rescale_overlay" id="overlay_rescale" aria-hidden="true"> + <button mat-icon-button (click)="getRescale().toggleState()" title="toggle"> + <mat-icon>{{getRescale().getState()==1?'fullscreen':'fullscreen_exit'}}</mat-icon> </button> - <button mat-icon-button (click)="getRescale().scaleUp()"> + <button mat-icon-button (click)="getRescale().scaleUp()" title="Zoom +"> <mat-icon>zoom_in</mat-icon> </button> - <button mat-icon-button (click)="getRescale().scaleDown()"> + <button mat-icon-button (click)="getRescale().scaleDown()" title="Zoom -"> <mat-icon>zoom_out</mat-icon> </button> - <button mat-icon-button (click)="getRescale().scaleUndo()"> - <mat-icon>undo</mat-icon> + <button mat-icon-button (click)="getRescale().scaleUndo()" title="Reset Zoom"> + <mat-icon>refresh</mat-icon> </button> </div> </div> diff --git a/src/app/app.component.scss b/src/app/app.component.scss index dd9d8b1fd57c7aa66779caad9288a967a7dd9e3d..0825e8bbcd93a264c5d53d16c2ac8518b877cd80 100644 --- a/src/app/app.component.scss +++ b/src/app/app.component.scss @@ -34,6 +34,7 @@ main { left:0; top:0; z-index:2; + transition:all 0.2s ease-in-out; } .footer{ @@ -42,19 +43,21 @@ main { left:0; bottom:0; z-index:2; + transition:all 0.2s ease-in-out; } .rescale_overlay{ width:190px; height:50px; - border-radius:25px; + border-radius:0px 25px 25px 0px; background-color:var(--surface); position:fixed; - left:15px; + left:-100px; top:15px; z-index:2; display:none; box-shadow:0px 2px 4px rgba(0,0,0,0.5); + transition:all 0.2s ease-in-out; } .rescale_overlay>button{ diff --git a/src/app/components/creator/room-creator-page/room-creator-page.component.html b/src/app/components/creator/room-creator-page/room-creator-page.component.html index 8d877b403df30cdc18822794eacff9231a09fcac..6c5f0f7b027508b4e4a2ce10cd0d126cf83713ea 100644 --- a/src/app/components/creator/room-creator-page/room-creator-page.component.html +++ b/src/app/components/creator/room-creator-page/room-creator-page.component.html @@ -93,6 +93,7 @@ </mat-card> <div *ngIf="!isLoading && !room">{{ 'room-page.room-not-found' | translate }}</div> </div> + <button id="live_announcer-button" tabIndex="-1" (click)="announce()" class="visually-hidden">{{ 'room-page.live-announcer' | translate }}</button> </div> <div class="visually-hidden"> diff --git a/src/app/components/creator/room-creator-page/room-creator-page.component.ts b/src/app/components/creator/room-creator-page/room-creator-page.component.ts index ca50f08af55d8cde7fa9abf5b322f93832216bdb..fa6f258398399ad74357c924dd170665b3441f49 100644 --- a/src/app/components/creator/room-creator-page/room-creator-page.component.ts +++ b/src/app/components/creator/room-creator-page/room-creator-page.component.ts @@ -1,4 +1,4 @@ -import { Component, OnInit, Renderer2, OnDestroy } from '@angular/core'; +import { Component, OnInit, Renderer2, OnDestroy, AfterContentInit } from '@angular/core'; import { RoomService } from '../../../services/http/room.service'; import { ActivatedRoute } from '@angular/router'; import { RoomPageComponent } from '../../shared/room-page/room-page.component'; @@ -25,7 +25,7 @@ import { KeyboardKey } from '../../../utils/keyboard/keys'; templateUrl: './room-creator-page.component.html', styleUrls: ['./room-creator-page.component.scss'] }) -export class RoomCreatorPageComponent extends RoomPageComponent implements OnInit, OnDestroy { +export class RoomCreatorPageComponent extends RoomPageComponent implements OnInit, OnDestroy, AfterContentInit { room: Room; updRoom: Room; commentThreshold: number; @@ -53,13 +53,18 @@ export class RoomCreatorPageComponent extends RoomPageComponent implements OnIni langService.langEmitter.subscribe(lang => translateService.use(lang)); } + ngAfterContentInit(): void { + setTimeout( () => { + document.getElementById('live_announcer-button').focus(); + }, 700); + } + ngOnInit() { window.scroll(0, 0); this.translateService.use(localStorage.getItem('currentLang')); this.route.params.subscribe(params => { this.initializeRoom(params['roomId']); }); - this.announce(); this.listenerFn = this._r.listen(document, 'keyup', (event) => { if (KeyboardUtils.isKeyEvent(event, KeyboardKey.Digit1) === true && this.eventService.focusOnInput === false) { document.getElementById('question_answer-button').focus(); @@ -68,6 +73,7 @@ export class RoomCreatorPageComponent extends RoomPageComponent implements OnIni } else if (KeyboardUtils.isKeyEvent(event, KeyboardKey.Digit4) === true && this.eventService.focusOnInput === false) { document.getElementById('settings-menu').focus(); } else if (KeyboardUtils.isKeyEvent(event, KeyboardKey.Digit8) === true && this.eventService.focusOnInput === false) { + this.liveAnnouncer.clear(); this.liveAnnouncer.announce('Aktueller Sitzungs-Name: ' + this.room.name + '. ' + 'Aktueller Sitzungs-Code: ' + this.room.shortId.slice(0, 8)); } else if ( @@ -87,6 +93,7 @@ export class RoomCreatorPageComponent extends RoomPageComponent implements OnIni } public announce() { + this.liveAnnouncer.clear(); this.liveAnnouncer.announce('Du befindest dich in der von dir erstellten Sitzung. ' + 'Drücke die Taste 1 um auf die Fragen-Übersicht zu gelangen, ' + 'die Taste 2 um das Sitzungs-Menü zu öffnen, die Taste 3 um in die Moderationsübersicht zu gelangen, ' + @@ -95,8 +102,6 @@ export class RoomCreatorPageComponent extends RoomPageComponent implements OnIni 'oder die Taste 9 um diese Ansage zu wiederholen.', 'assertive'); } - - afterRoomLoadHook() { if (this.moderationEnabled) { this.viewModuleCount = this.viewModuleCount + 1; diff --git a/src/app/components/home/_dialogs/cookies/cookies.component.ts b/src/app/components/home/_dialogs/cookies/cookies.component.ts index ebfec2b8fccfdabc913e4ce1ae34c7c314328c8a..8e33833d8d2b4ed5ff22a02842558246c8972260 100644 --- a/src/app/components/home/_dialogs/cookies/cookies.component.ts +++ b/src/app/components/home/_dialogs/cookies/cookies.component.ts @@ -31,6 +31,9 @@ export class CookiesComponent implements OnInit { acceptCookies() { localStorage.setItem('cookieAccepted', 'true'); this.dialogRef.close(); + setTimeout( () => { + document.getElementById('live_announcer-button').focus(); + }, 500); } exitApp() { diff --git a/src/app/components/home/home-page/home-page.component.html b/src/app/components/home/home-page/home-page.component.html index cefc04fa308d87cf5cf575f2ded7d59f6da64f47..7787e5fb0512d3e8fe959e73d32f5907a09fa65f 100644 --- a/src/app/components/home/home-page/home-page.component.html +++ b/src/app/components/home/home-page/home-page.component.html @@ -24,4 +24,5 @@ </mat-card-content> </mat-card> </div> + <button id="live_announcer-button" tabIndex="-1" (click)="announce()" class="visually-hidden">{{ 'home-page.live-announcer' | translate }}</button> </div> diff --git a/src/app/components/home/home-page/home-page.component.ts b/src/app/components/home/home-page/home-page.component.ts index 805d85df8d1aef57c470b06736d42ca4dcff16ad..4c80a678b9fa4ffdc343a07eb0a6305d67a50dab 100644 --- a/src/app/components/home/home-page/home-page.component.ts +++ b/src/app/components/home/home-page/home-page.component.ts @@ -1,4 +1,4 @@ -import { Component, OnInit, OnDestroy, Renderer2 } from '@angular/core'; +import { Component, OnInit, OnDestroy, Renderer2, AfterContentInit } from '@angular/core'; import { EventService } from '../../../services/util/event.service'; import { LiveAnnouncer } from '@angular/cdk/a11y'; import { KeyboardUtils } from '../../../utils/keyboard'; @@ -9,7 +9,7 @@ import { KeyboardKey } from '../../../utils/keyboard/keys'; templateUrl: './home-page.component.html', styleUrls: ['./home-page.component.scss'] }) -export class HomePageComponent implements OnInit, OnDestroy { +export class HomePageComponent implements OnInit, OnDestroy, AfterContentInit { deviceType: string; listenerFn: () => void; @@ -21,9 +21,14 @@ export class HomePageComponent implements OnInit, OnDestroy { ) { } + ngAfterContentInit(): void { + setTimeout( () => { + document.getElementById('live_announcer-button').focus(); + }, 500); + } + ngOnInit() { this.deviceType = localStorage.getItem('deviceType'); - this.announce(); this.listenerFn = this._r.listen(document, 'keyup', (event) => { if (KeyboardUtils.isKeyEvent(event, KeyboardKey.Digit1) === true && this.eventService.focusOnInput === false) { document.getElementById('session_id-input').focus(); @@ -48,7 +53,7 @@ export class HomePageComponent implements OnInit, OnDestroy { } public announce() { - // this.liveAnnouncer.announce('Willkommen auf dieser Seite' + document.getElementById('announcer_text').textContent, 'assertive'); + this.liveAnnouncer.clear(); this.liveAnnouncer.announce('Du befindest dich auf der Startseite von fragpunktjetzt. ' + 'Drücke die Taste 1 um einen Sitzungs-Code einzugeben, die Taste 2 um in die Benutzer-Anmeldung ' + 'oder das Sitzungs-Menü zu gelangen, die Taste 3 um eine neue Sitzung zu erstellen, ' + diff --git a/src/app/components/home/user-home/user-home.component.html b/src/app/components/home/user-home/user-home.component.html index 91368fa404cfae06ec4c37d3a02090d12b88933e..ed885a33caf7f99b09842b4d5815f5b1e71a9a05 100644 --- a/src/app/components/home/user-home/user-home.component.html +++ b/src/app/components/home/user-home/user-home.component.html @@ -12,5 +12,6 @@ <div fxLayout="row" fxLayoutAlign="center" fxLayoutGap="15px"> <app-room-list [user]="user"></app-room-list> </div> + <button id="live_announcer-button" tabIndex="-1" (click)="announce()" class="visually-hidden">{{ 'home-page.live-announcer-user' | translate }}</button> </div> diff --git a/src/app/components/home/user-home/user-home.component.ts b/src/app/components/home/user-home/user-home.component.ts index 843a5d47df0ecca5a8cc552813e99ecd8baff0ce..0a1769e1abc267b983d771e8f81dfa8a85dbf000 100644 --- a/src/app/components/home/user-home/user-home.component.ts +++ b/src/app/components/home/user-home/user-home.component.ts @@ -1,4 +1,4 @@ -import { Component, OnInit, OnDestroy, Renderer2 } from '@angular/core'; +import { Component, OnInit, OnDestroy, Renderer2, AfterContentInit } from '@angular/core'; import { MatDialog } from '@angular/material'; import { TranslateService } from '@ngx-translate/core'; import { LanguageService } from '../../../services/util/language.service'; @@ -16,7 +16,7 @@ import { KeyboardKey } from '../../../utils/keyboard/keys'; templateUrl: './user-home.component.html', styleUrls: [ './user-home.component.scss' ] }) -export class UserHomeComponent implements OnInit, OnDestroy { +export class UserHomeComponent implements OnInit, OnDestroy, AfterContentInit { user: User; creatorRole: UserRole = UserRole.CREATOR; participantRole: UserRole = UserRole.PARTICIPANT; @@ -35,10 +35,14 @@ export class UserHomeComponent implements OnInit, OnDestroy { langService.langEmitter.subscribe(lang => translateService.use(lang)); } + ngAfterContentInit(): void { + setTimeout( () => { + document.getElementById('live_announcer-button').focus(); + }, 700); + } ngOnInit() { this.translateService.use(localStorage.getItem('currentLang')); this.authenticationService.watchUser.subscribe(newUser => this.user = newUser); - this.announce(); this.listenerFn = this._r.listen(document, 'keyup', (event) => { if (KeyboardUtils.isKeyEvent(event, KeyboardKey.Digit1) === true && this.eventService.focusOnInput === false) { document.getElementById('session_id-input').focus(); @@ -59,6 +63,7 @@ export class UserHomeComponent implements OnInit, OnDestroy { } public announce() { + this.liveAnnouncer.clear(); this.liveAnnouncer.announce('Du befindest dich auf deiner Benutzer-Seite. ' + 'Drücke die Taste 1 um einen Sitzungs-Code einzugeben, die Taste 2 um auf das Sitzungs-Menü zu gelangen, ' + 'die Taste 3 um eine neue Sitzung zu erstellen, die Taste 0 um zurück zur Startseite zu gelangen, ' + diff --git a/src/app/components/moderator/moderator-comment-list/moderator-comment-list.component.html b/src/app/components/moderator/moderator-comment-list/moderator-comment-list.component.html index 7a657879196ab8e43a398e78d248c9158f3130ae..c52e0d1190b45ba74feba7248c427ad78b278783 100644 --- a/src/app/components/moderator/moderator-comment-list/moderator-comment-list.component.html +++ b/src/app/components/moderator/moderator-comment-list/moderator-comment-list.component.html @@ -9,7 +9,8 @@ (input)="searchComments()" [(ngModel)]="searchInput" aria-labelledby="search-box-input-description"/> <mat-placeholder class="placeholder">{{ searchPlaceholder }}</mat-placeholder> - <button mat-icon-button class="searchBarButton close" *ngIf="searchInput !== '' || search" + <button id="search_close-button" + mat-icon-button class="searchBarButton close" *ngIf="searchInput !== '' || search" (click)="hideCommentsList=false; searchInput = ''; search = false; searchPlaceholder = '';"> <mat-icon>close</mat-icon> </button> @@ -25,13 +26,15 @@ <mat-icon class="searchBarIcon">search</mat-icon> </button> - <button mat-icon-button class="searchBarButton" + <button id="sort-button" + mat-icon-button class="searchBarButton" *ngIf="!searchBox.value && comments && comments.length > 0 && !search" [matMenuTriggerFor]="sortMenu" matTooltip="{{ 'comment-list.sort-comments' | translate }}"> <mat-icon class="searchBarIcon">swap_vert</mat-icon> </button> - <button mat-icon-button class="searchBarButton" + <button id="filter-button" + mat-icon-button class="searchBarButton" *ngIf="!searchBox.value && comments && comments.length > 0 && !search" [matMenuTriggerFor]="filterMenu" matTooltip="{{ 'comment-list.filter-comments' | translate }}"> <mat-icon class="searchBarIcon">filter_list</mat-icon> diff --git a/src/app/components/moderator/moderator-comment-page/moderator-comment-page.component.html b/src/app/components/moderator/moderator-comment-page/moderator-comment-page.component.html index 7bf34b687e5916014e4209b409db403eb13a5e02..8777583be336b642b9ca061a80c83dad0b68c3fa 100644 --- a/src/app/components/moderator/moderator-comment-page/moderator-comment-page.component.html +++ b/src/app/components/moderator/moderator-comment-page/moderator-comment-page.component.html @@ -2,6 +2,6 @@ <div fxLayout="row" fxLayoutAlign="center"> <app-moderator-comment-list [user]="user" [roomId]="roomId" comments></app-moderator-comment-list> </div> - </div> - - \ No newline at end of file + <button id="live_announcer-button" tabIndex="-1" (click)="announce()" class="visually-hidden">{{ 'comment-page.live-announcer-moderation' | translate }}</button> +</div> + diff --git a/src/app/components/moderator/moderator-comment-page/moderator-comment-page.component.ts b/src/app/components/moderator/moderator-comment-page/moderator-comment-page.component.ts index c657955aef9625f20d1751d6e36796a147318ebb..aee8fc94e0a7e4216888e6cc800c25fd204e2a06 100644 --- a/src/app/components/moderator/moderator-comment-page/moderator-comment-page.component.ts +++ b/src/app/components/moderator/moderator-comment-page/moderator-comment-page.component.ts @@ -1,25 +1,77 @@ -import { Component, OnInit } from '@angular/core'; +import { Component, OnInit, Renderer2, OnDestroy, AfterContentInit } from '@angular/core'; import { ActivatedRoute } from '@angular/router'; import { User } from '../../../models/user'; import { NotificationService } from '../../../services/util/notification.service'; import { AuthenticationService } from '../../../services/http/authentication.service'; +import { LiveAnnouncer } from '@angular/cdk/a11y'; +import { EventService } from '../../../services/util/event.service'; +import { KeyboardUtils } from '../../../utils/keyboard'; +import { KeyboardKey } from '../../../utils/keyboard/keys'; @Component({ selector: 'app-moderator-comment-page', templateUrl: './moderator-comment-page.component.html', styleUrls: ['./moderator-comment-page.component.scss'] }) -export class ModeratorCommentPageComponent implements OnInit { +export class ModeratorCommentPageComponent implements OnInit, OnDestroy, AfterContentInit { roomId: string; user: User; + listenerFn: () => void; + constructor(private route: ActivatedRoute, private notification: NotificationService, - private authenticationService: AuthenticationService) { } + private authenticationService: AuthenticationService, + public eventService: EventService, + private _r: Renderer2, + private liveAnnouncer: LiveAnnouncer) { } + ngAfterContentInit(): void { + setTimeout( () => { + document.getElementById('live_announcer-button').focus(); + }, 500); + } ngOnInit(): void { this.roomId = localStorage.getItem('roomId'); this.user = this.authenticationService.getUser(); + this.announce(); + this.listenerFn = this._r.listen(document, 'keyup', (event) => { + if (KeyboardUtils.isKeyEvent(event, KeyboardKey.Digit1) === true && this.eventService.focusOnInput === false) { + document.getElementById('searchBox').focus(); + } else if (KeyboardUtils.isKeyEvent(event, KeyboardKey.Digit3) === true && this.eventService.focusOnInput === false) { + document.getElementById('sort-button').focus(); + } else if (KeyboardUtils.isKeyEvent(event, KeyboardKey.Digit4) === true && this.eventService.focusOnInput === false) { + document.getElementById('filter-button').focus(); + } else if (KeyboardUtils.isKeyEvent(event, KeyboardKey.Digit8) === true && this.eventService.focusOnInput === false) { + this.liveAnnouncer.announce('Aktueller Sitzungs-' + document.getElementById('shortId-header').textContent); + } else if ( + KeyboardUtils.isKeyEvent(event, KeyboardKey.Digit9, KeyboardKey.Escape) === true && + this.eventService.focusOnInput === false) { + this.announce(); + } else if ( + document.getElementById('search_close-button') && + KeyboardUtils.isKeyEvent(event, KeyboardKey.Escape) === true && + this.eventService.focusOnInput === true) { + document.getElementById('search_close-button').click(); + } else if (KeyboardUtils.isKeyEvent(event, KeyboardKey.Escape) === true && this.eventService.focusOnInput === true) { + this.eventService.makeFocusOnInputFalse(); + document.getElementById('sort-button').focus(); + } + }); } + ngOnDestroy() { + this.listenerFn(); + this.eventService.makeFocusOnInputFalse(); + } + + public announce() { + this.liveAnnouncer.clear(); + this.liveAnnouncer.announce('Du befindest dich auf der Moderations-Seite deiner Sitzung. ' + + 'Drücke die Taste 2 um auf das Sitzungs-Menü zu gelangen, ' + + 'die Taste 8 um den aktuellen Sitzungs-Code zu hören, oder die Taste 0 um zurück zur Benutzer-Seite zu gelangen. ' + + 'Sobald mehrere Fragen vorhanden sind kannst du Fragen suchen und filtern. Mit Taste 1 gelangst du in das Suchfeld,' + + 'durch drücken der Escape-Taste wird die Sucheingabe gelöscht. Drücke die Taste 3 um Fragen zu sortieren, ' + + 'die Taste 4 um Fragen zu filtern, oder die Taste 9 um diese Ansage zu wiederholen.', 'assertive'); + } } diff --git a/src/app/components/moderator/room-moderator-page/room-moderator-page.component.html b/src/app/components/moderator/room-moderator-page/room-moderator-page.component.html index 66fa3bc4c56ecf253714d18ceeb5619ff9dfb644..5a348364c1be5d1838f85abb4da4a709a2dc2b77 100644 --- a/src/app/components/moderator/room-moderator-page/room-moderator-page.component.html +++ b/src/app/components/moderator/room-moderator-page/room-moderator-page.component.html @@ -6,7 +6,7 @@ <span class="fill-remaining-space"></span> <mat-card-header fxLayoutAlign="center"> <mat-card-title fxLayoutAlign="center"> - <h2>{{ room.name }}</h2> + <h1>{{ room.name }}</h1> </mat-card-title> <mat-card-subtitle fxLayoutAlign="center"> <mat-icon *ngIf="moderationEnabled" class="gavel"> @@ -24,25 +24,27 @@ </div> <mat-divider></mat-divider> <mat-card-content *ngIf="room.description" fxLayoutAlign="center"> - <h4>{{room.description.trim()}}</h4> + <h3>{{room.description.trim()}}</h3> </mat-card-content> <mat-grid-list cols="{{viewModuleCount}}" rowHeight="1:1"> <mat-grid-tile> - <button mat-icon-button [disableRipple]="true" + <button id="question_answer-button" + mat-icon-button [disableRipple]="true" routerLink="/moderator/room/{{ room.shortId }}/comments"> <mat-icon matBadge="{{commentCounter}}" class="main-icon" [ngClass]="{'desktop' : deviceType === 'desktop'}">question_answer </mat-icon> - <h3>{{ 'room-page.public-stream' | translate}}</h3> <!-- *ngIf="deviceType === 'desktop'" --> + <h2>{{ 'room-page.public-stream' | translate}}</h2> <!-- *ngIf="deviceType === 'desktop'" --> </button> </mat-grid-tile> <mat-grid-tile *ngIf="moderationEnabled"> - <button mat-icon-button [disableRipple]="true" + <button id="gavel-button" + mat-icon-button [disableRipple]="true" routerLink="/moderator/room/{{ room.shortId }}/moderator/comments"> <mat-icon matBadge="{{moderatorCommentCounter}}" class="main-icon" [ngClass]="{'desktop' : deviceType === 'desktop'}">gavel </mat-icon> - <h3>{{ 'room-page.moderating-stream' | translate}}</h3> <!-- *ngIf="deviceType === 'desktop'" --> + <h2>{{ 'room-page.moderating-stream' | translate}}</h2> <!-- *ngIf="deviceType === 'desktop'" --> </button> </mat-grid-tile> <!-- <mat-grid-tile> @@ -57,4 +59,5 @@ </mat-card> </div> - </div> + <button id="live_announcer-button" tabIndex="-1" (click)="announce()" class="visually-hidden">{{ 'room-page.live-announcer' | translate }}</button> +</div> diff --git a/src/app/components/moderator/room-moderator-page/room-moderator-page.component.scss b/src/app/components/moderator/room-moderator-page/room-moderator-page.component.scss index a6e46c6d4e1ada7013c894b469791d554ccd4e49..c5fbc7d110ef8b22166ebb6fed99629cb84df2f1 100644 --- a/src/app/components/moderator/room-moderator-page/room-moderator-page.component.scss +++ b/src/app/components/moderator/room-moderator-page/room-moderator-page.component.scss @@ -79,7 +79,7 @@ mat-grid-list { margin-bottom: 20px !important; } -h2 { +h1 { font-size: large; color: var(--on-surface)!important; } @@ -88,7 +88,7 @@ p { color: var(--on-surface)!important; } -h4 { +h3 { font-size: medium; color: var(--on-surface)!important; padding: 0 1% 0 1%; diff --git a/src/app/components/moderator/room-moderator-page/room-moderator-page.component.ts b/src/app/components/moderator/room-moderator-page/room-moderator-page.component.ts index b123e904f44190c47740d4e9a6bf4c98c6809563..5449ff2679b7656b8a47d591023d955d0e0c52da 100644 --- a/src/app/components/moderator/room-moderator-page/room-moderator-page.component.ts +++ b/src/app/components/moderator/room-moderator-page/room-moderator-page.component.ts @@ -1,4 +1,4 @@ -import { Component, OnInit } from '@angular/core'; +import { Component, OnInit, Renderer2, OnDestroy, AfterContentInit } from '@angular/core'; import { Room } from '../../../models/room'; import { RoomPageComponent } from '../../shared/room-page/room-page.component'; import { Location } from '@angular/common'; @@ -10,13 +10,17 @@ import { WsCommentServiceService } from '../../../services/websockets/ws-comment import { CommentService } from '../../../services/http/comment.service'; import { Message } from '@stomp/stompjs'; import { NotificationService } from '../../../services/util/notification.service'; +import { LiveAnnouncer } from '@angular/cdk/a11y'; +import { EventService } from '../../../services/util/event.service'; +import { KeyboardUtils } from '../../../utils/keyboard'; +import { KeyboardKey } from '../../../utils/keyboard/keys'; @Component({ selector: 'app-room-moderator-page', templateUrl: './room-moderator-page.component.html', styleUrls: ['./room-moderator-page.component.scss'] }) -export class RoomModeratorPageComponent extends RoomPageComponent implements OnInit { +export class RoomModeratorPageComponent extends RoomPageComponent implements OnInit, OnDestroy, AfterContentInit { room: Room; isLoading = true; @@ -24,6 +28,7 @@ export class RoomModeratorPageComponent extends RoomPageComponent implements OnI moderatorCommentCounter: number; viewModuleCount = 1; + listenerFn: () => void; constructor(protected location: Location, protected roomService: RoomService, @@ -32,7 +37,10 @@ export class RoomModeratorPageComponent extends RoomPageComponent implements OnI protected langService: LanguageService, protected wsCommentService: WsCommentServiceService, protected commentService: CommentService, - protected notification: NotificationService) { + protected notification: NotificationService, + public eventService: EventService, + private liveAnnouncer: LiveAnnouncer, + private _r: Renderer2) { super(roomService, route, location, wsCommentService, commentService); langService.langEmitter.subscribe(lang => translateService.use(lang)); } @@ -83,12 +91,50 @@ export class RoomModeratorPageComponent extends RoomPageComponent implements OnI }); } + ngAfterContentInit(): void { + setTimeout( () => { + document.getElementById('live_announcer-button').focus(); + }, 700); + } + ngOnInit() { window.scroll(0, 0); this.route.params.subscribe(params => { this.initializeRoom(params['roomId']); }); this.translateService.use(localStorage.getItem('currentLang')); + this.listenerFn = this._r.listen(document, 'keyup', (event) => { + if (KeyboardUtils.isKeyEvent(event, KeyboardKey.Digit1) === true && this.eventService.focusOnInput === false) { + document.getElementById('question_answer-button').focus(); + } else if (KeyboardUtils.isKeyEvent(event, KeyboardKey.Digit3) === true && this.eventService.focusOnInput === false) { + document.getElementById('gavel-button').focus(); + } else if (KeyboardUtils.isKeyEvent(event, KeyboardKey.Digit8) === true && this.eventService.focusOnInput === false) { + this.liveAnnouncer.clear(); + this.liveAnnouncer.announce('Aktueller Sitzungs-Name: ' + this.room.name + '. ' + + 'Aktueller Sitzungs-Code: ' + this.room.shortId.slice(0, 8)); + } else if ( + KeyboardUtils.isKeyEvent(event, KeyboardKey.Digit9, KeyboardKey.Escape) === true && + this.eventService.focusOnInput === false) { + this.announce(); + } else if (KeyboardUtils.isKeyEvent(event, KeyboardKey.Escape) === true && this.eventService.focusOnInput === true) { + this.eventService.makeFocusOnInputFalse(); + document.getElementById('question_answer-button').focus(); + } + }); + } + + ngOnDestroy() { + this.listenerFn(); + this.eventService.makeFocusOnInputFalse(); + } + + public announce() { + this.liveAnnouncer.announce('Du befindest dich in der Sitzung in der du als Moderator gewählt wurdest. ' + + 'Drücke die Taste 1 um auf die Fragen-Übersicht zu gelangen, ' + + 'die Taste 2 um das Sitzungs-Menü zu öffnen, die Taste 3 um in die Moderationsübersicht zu gelangen, ' + + 'die Taste 4 um Einstellungen an der Sitzung vorzunehmen, ' + + 'die Taste 8 um den aktuellen Sitzungs-Code zu hören, die Taste 0 um auf den Zurück-Button zu gelangen, ' + + 'oder die Taste 9 um diese Ansage zu wiederholen.', 'assertive'); } copyShortId(): void { diff --git a/src/app/components/participant/room-participant-page/room-participant-page.component.html b/src/app/components/participant/room-participant-page/room-participant-page.component.html index a34bbfaca2a4b91da2ad513d96dec013fc659bc8..1fb712bf0e2624966c795403c51f33008e63f6eb 100644 --- a/src/app/components/participant/room-participant-page/room-participant-page.component.html +++ b/src/app/components/participant/room-participant-page/room-participant-page.component.html @@ -48,6 +48,7 @@ </mat-card> </div> + <button id="live_announcer-button" tabIndex="-1" (click)="announce()" class="visually-hidden">{{ 'room-page.live-announcer' | translate }}</button> </div> <!--Hidden Div's for a11y-Descriptions--> diff --git a/src/app/components/participant/room-participant-page/room-participant-page.component.ts b/src/app/components/participant/room-participant-page/room-participant-page.component.ts index e2a5589aee5289fc7d8ba37012147c5b92f81eef..78912bb65fc2a34105a7f2ed6f3193e0ebdbb8a5 100644 --- a/src/app/components/participant/room-participant-page/room-participant-page.component.ts +++ b/src/app/components/participant/room-participant-page/room-participant-page.component.ts @@ -1,4 +1,4 @@ -import { Component, OnInit, OnDestroy, Renderer2 } from '@angular/core'; +import { Component, OnInit, OnDestroy, Renderer2, AfterContentInit } from '@angular/core'; import { Room } from '../../../models/room'; import { User } from '../../../models/user'; import { UserRole } from '../../../models/user-roles.enum'; @@ -21,7 +21,7 @@ import { KeyboardKey } from '../../../utils/keyboard/keys'; templateUrl: './room-participant-page.component.html', styleUrls: ['./room-participant-page.component.scss'] }) -export class RoomParticipantPageComponent extends RoomPageComponent implements OnInit, OnDestroy { +export class RoomParticipantPageComponent extends RoomPageComponent implements OnInit, OnDestroy, AfterContentInit { room: Room; isLoading = true; @@ -45,18 +45,23 @@ export class RoomParticipantPageComponent extends RoomPageComponent implements O langService.langEmitter.subscribe(lang => translateService.use(lang)); } + ngAfterContentInit(): void { + setTimeout( () => { + document.getElementById('live_announcer-button').focus(); + }, 700); + } + ngOnInit() { window.scroll(0, 0); this.route.params.subscribe(params => { this.initializeRoom(params['roomId']); }); this.translateService.use(localStorage.getItem('currentLang')); - this.announce(); - this.listenerFn = this._r.listen(document, 'keyup', (event) => { if (KeyboardUtils.isKeyEvent(event, KeyboardKey.Digit1) === true && this.eventService.focusOnInput === false) { document.getElementById('question_answer-button').focus(); } else if (KeyboardUtils.isKeyEvent(event, KeyboardKey.Digit8) === true && this.eventService.focusOnInput === false) { + this.liveAnnouncer.clear(); this.liveAnnouncer.announce('Aktueller Sitzungs-Code:' + this.room.shortId.slice(0, 8)); } else if ( KeyboardUtils.isKeyEvent(event, KeyboardKey.Escape, KeyboardKey.Digit9) === true && this.eventService.focusOnInput === false @@ -75,7 +80,7 @@ export class RoomParticipantPageComponent extends RoomPageComponent implements O } public announce() { - // this.liveAnnouncer.announce('Willkommen auf dieser Seite' + document.getElementById('announcer_text').textContent, 'assertive'); + this.liveAnnouncer.clear(); this.liveAnnouncer.announce('Du befindest dich in der Sitzung mit dem von dir eingegebenen Sitzungs-Code. ' + 'Drücke die Taste 1 um eine Frage zu stellen, die Taste 2 für das Sitzungs-Menü, ' + 'die Taste 8 um den aktuellen Sitzungs-Code zu hören, die Taste 0 um auf den Zurück-Button zu gelangen, ' + diff --git a/src/app/components/shared/comment-page/comment-page.component.html b/src/app/components/shared/comment-page/comment-page.component.html index 6f6989296bcf0c49bb62287727c9d25143bd3c93..09107768983cdaf27bbbaeb0e48272c446fefb4c 100644 --- a/src/app/components/shared/comment-page/comment-page.component.html +++ b/src/app/components/shared/comment-page/comment-page.component.html @@ -1,6 +1,7 @@ <div fxLayout="column" fxLayoutAlign="center" fxLayoutGap="20px"> <div fxLayout="row" fxLayoutAlign="center"> <app-comment-list [user]="user" [roomId]="roomId" comments></app-comment-list> + <button id="live_announcer-button" tabIndex="-1" (click)="announce()" class="visually-hidden">{{ 'comment-page.live-announcer' | translate }}</button> </div> </div> diff --git a/src/app/components/shared/comment-page/comment-page.component.ts b/src/app/components/shared/comment-page/comment-page.component.ts index b071510ef6b0f3e9960c5aa627d51bcbf9d5cf44..b7909fb5b3b32aa114d52d612a5d1e45f5cd6340 100644 --- a/src/app/components/shared/comment-page/comment-page.component.ts +++ b/src/app/components/shared/comment-page/comment-page.component.ts @@ -1,4 +1,4 @@ -import { Component, OnInit, OnDestroy, Renderer2 } from '@angular/core'; +import { Component, OnInit, OnDestroy, Renderer2, AfterContentInit } from '@angular/core'; import { ActivatedRoute } from '@angular/router'; import { User } from '../../../models/user'; import { NotificationService } from '../../../services/util/notification.service'; @@ -13,9 +13,8 @@ import { KeyboardKey } from '../../../utils/keyboard/keys'; templateUrl: './comment-page.component.html', styleUrls: ['./comment-page.component.scss'] }) -export class CommentPageComponent implements OnInit, OnDestroy { +export class CommentPageComponent implements OnInit, OnDestroy, AfterContentInit { roomId: string; - shortId: string; user: User; listenerFn: () => void; @@ -27,11 +26,14 @@ export class CommentPageComponent implements OnInit, OnDestroy { private liveAnnouncer: LiveAnnouncer, private _r: Renderer2) { } + ngAfterContentInit(): void { + setTimeout( () => { + document.getElementById('live_announcer-button').focus(); + }, 800); + } ngOnInit(): void { this.roomId = localStorage.getItem('roomId'); - this.shortId = localStorage.getItem('shortId'); this.user = this.authenticationService.getUser(); - this.announce(); this.listenerFn = this._r.listen(document, 'keyup', (event) => { if (KeyboardUtils.isKeyEvent(event, KeyboardKey.Digit1) === true && this.eventService.focusOnInput === false) { if (document.getElementById('add_comment-button')) { @@ -46,7 +48,8 @@ export class CommentPageComponent implements OnInit, OnDestroy { } else if (KeyboardUtils.isKeyEvent(event, KeyboardKey.Digit5) === true && this.eventService.focusOnInput === false) { document.getElementById('filter-button').focus(); } else if (KeyboardUtils.isKeyEvent(event, KeyboardKey.Digit8) === true && this.eventService.focusOnInput === false) { - this.liveAnnouncer.announce('Aktueller Sitzungs-Code:' + this.shortId.slice(0, 8)); + this.liveAnnouncer.clear(); + this.liveAnnouncer.announce('Aktueller Sitzungs-' + document.getElementById('shortId-header').textContent); } else if ( KeyboardUtils.isKeyEvent(event, KeyboardKey.Digit9, KeyboardKey.Escape) === true && this.eventService.focusOnInput === false @@ -76,12 +79,13 @@ export class CommentPageComponent implements OnInit, OnDestroy { } public announce() { + this.liveAnnouncer.clear(); this.liveAnnouncer.announce('Du befindest dich auf der Fragen-Seite deiner Sitzung. ' + 'Drücke die Taste 1 um eine Frage zu stellen, die Taste 2 um auf das Sitzungs-Menü zu gelangen, ' + 'die Taste 8 um den aktuellen Sitzungs-Code zu hören, die Taste 0 um zurück zur Benutzer-Seite zu gelangen. ' + - 'Sobald mehrere Fragen vorhanden sind, kannst du Fragen suchen und filtern. Mit Taste 3 gelangst du in das Suchfeld,' + + 'Sobald mehrere Fragen vorhanden sind kannst du Fragen suchen und filtern. Mit Taste 3 gelangst du in das Suchfeld,' + 'durch drücken der Escape-Taste wird die Sucheingabe gelöscht. Drücke die Taste 4 um Fragen zu sortieren, ' + - 'oder die Taste 5 um Fragen zu filtern, oder die Taste 9 um diese Ansage zu wiederholen.', 'assertive'); + 'die Taste 5 um Fragen zu filtern, oder die Taste 9 um diese Ansage zu wiederholen.', 'assertive'); } } diff --git a/src/app/components/shared/footer/footer.component.ts b/src/app/components/shared/footer/footer.component.ts index 744a662c84f4767e9fb1642155007e0c0d14ea9b..276cdcfd47d0c9a1f2cea44daed92d02601c7103 100644 --- a/src/app/components/shared/footer/footer.component.ts +++ b/src/app/components/shared/footer/footer.component.ts @@ -50,6 +50,7 @@ export class FooterComponent implements OnInit { ngOnInit() { if (!this.themeService.getTheme()['source']['_value']) { this.themeService.activate('dark'); + this.themeClass = 'dark'; } this.deviceType = localStorage.getItem('deviceType'); this.translateService.use(localStorage.getItem('currentLang')); @@ -57,6 +58,7 @@ export class FooterComponent implements OnInit { this.open = message; }); this.themes = this.themeService.getThemes(); + this.updateScale(this.themeService.getThemeByKey(this.themeClass)); this.cookieAccepted = localStorage.getItem('cookieAccepted') === 'true'; if (!localStorage.getItem('cookieAccepted')) { @@ -132,7 +134,12 @@ export class FooterComponent implements OnInit { changeTheme(theme: Theme) { this.themeClass = theme.key; this.themeService.activate(theme.key); + this.updateScale(theme); + } + + updateScale(theme: Theme) { AppComponent.rescale.setInitialScale(theme.scale); + AppComponent.rescale.setDefaultScale(theme.scale); } getLanguage(): string { diff --git a/src/app/components/shared/header/header.component.html b/src/app/components/shared/header/header.component.html index fca0eb5e4851228862b5314a8b05f221869fae5c..ec5e1809a326d53b842cdd7c21a87743f556dc9b 100644 --- a/src/app/components/shared/header/header.component.html +++ b/src/app/components/shared/header/header.component.html @@ -5,7 +5,7 @@ <mat-icon class="header-icons">arrow_back</mat-icon> </button> <button mat-icon-button aria-hidden="true"> - <mat-icon class="header-icons" (click)="getRescale().activeScale();">format_size</mat-icon> + <mat-icon class="header-icons" (click)="getRescale().toggleState();">format_size</mat-icon> </button> <span class="fill-remaining-space"></span> @@ -23,7 +23,7 @@ gavel </mat-icon> </span> - <h2 *ngIf="router.url.includes('comments')" fxLayoutAlign="center center"> + <h2 id="shortId-header" *ngIf="router.url.includes('comments')" fxLayoutAlign="center center"> {{'header.id' | translate}}: {{ shortId.slice(0, 4) }} {{ shortId.slice(4, 8) }} </h2> <span class="fill-remaining-space"></span> diff --git a/src/app/components/shared/room-join/room-join.component.html b/src/app/components/shared/room-join/room-join.component.html index 5c04c8e63dedf96eb01a76537852195cc0361142..cbbb17f8ff9816cc2bc404d0cb8896c71634c494 100644 --- a/src/app/components/shared/room-join/room-join.component.html +++ b/src/app/components/shared/room-join/room-join.component.html @@ -16,7 +16,7 @@ /> <mat-placeholder class="placeholder">{{ 'home-page.session-id' | translate}}</mat-placeholder> <mat-hint align="end"><span aria-hidden="true">{{ roomId.value.length - (roomId.value.split(' ').length -1) }} / 8</span></mat-hint> - <mat-error *ngIf="roomFormControl.hasError('required')">{{ 'home-page.please-enter' | translate}}</mat-error> + <mat-error *ngIf="roomFormControl.hasError('required')" aria-hidden="true">{{ 'home-page.please-enter' | translate}}</mat-error> <mat-error *ngIf="roomFormControl.hasError('pattern')">{{ 'home-page.only-numbers' | translate}}</mat-error> </mat-form-field> <button [disabled]="cookiesDisabled()" id="session_enter-button" mat-fab type="submit" aria-labelledby="join-button-label"> diff --git a/src/app/models/rescale.ts b/src/app/models/rescale.ts index 92e72538a5a2512a0ab1bc85f0ad2f1cddcb4ab9..2f91cf9029c5dd38beca3dca42c9621733ac749e 100644 --- a/src/app/models/rescale.ts +++ b/src/app/models/rescale.ts @@ -1,9 +1,20 @@ +import { KeyboardUtils } from '../utils/keyboard'; +import { KeyboardKey } from '../utils/keyboard/keys'; export class Rescale { public scale = 1; public cachedScale = 1; private f; + public defaultScale = 1; + + private state = 0; + + public setDefaultScale(defaultScale: number) { + this.scale = defaultScale; + this.defaultScale = defaultScale; + this.scaleUpdate(); + } public scaleUp() { this.setScale(this.scale + 0.1); @@ -14,7 +25,7 @@ export class Rescale { } public scaleUndo() { - this.setScale(1); + this.setScale(this.defaultScale); } public setScale(scale: number) { @@ -35,27 +46,121 @@ export class Rescale { document.getElementById('rescale_screen').style.zoom = this.scale + ''; } - public activeScale() { - window.addEventListener('keydown', this.f = e => { - if (e.key === 'Escape') { - this.deactivateScale(); - } - }); - this.setScale(this.cachedScale); - this.setStateScale(true); + public toggleState() { + this.state++; + if (this.state >= 3) { + this.state = 0; + } + this.updateState(); + } + + public toggleBetweenRescale() { + if (this.state === 1) { + this.activateFull(); + } else if (this.state === 2) { + this.activate(); + } } - public deactivateScale() { + public getState(): number { + return this.state; + } + + private updateState() { + switch (this.state) { + case 0: + this.reset(); + break; + case 1: + this.activate(); + break; + case 2: + this.activateFull(); + break; + default: break; + } + } + + public reset() { window.removeEventListener('keydown', this.f); + this.f = null; this.cachedScale = this.scale; - this.scaleUndo(); - this.setStateScale(false); + this.scaleUpdate(); + this.toggleHeader(true); + this.toggleFooter(true); + this.toggleRescaler(false); + this.state = 0; + } + + public activate() { + this.createKeyListener(); + this.setScale(this.cachedScale); + this.toggleHeader(true); + this.toggleFooter(true); + this.setOffsetRescaler(0, 75); + this.toggleRescaler(true); + this.state = 1; + } + + public activateFull() { + this.createKeyListener(); + this.toggleHeader(false); + this.toggleFooter(false); + this.setOffsetRescaler(0, 15); + this.toggleRescaler(true); + this.state = 2; + } + + private createKeyListener() { + if (!this.f) { + window.addEventListener('keydown', this.f = e => { + if (KeyboardUtils.isKeyEvent(e, KeyboardKey.Escape)) { + this.state--; + this.updateState(); + } + }); + } + } + + private toggleHeader(b: boolean) { + if (b) { + this.getElem('header_rescale').style.display = 'block'; + setTimeout(() => { + this.getElem('header_rescale').style.top = '0px'; + }, 1); + } else { + this.getElem('header_rescale').style.top = '-60px'; + setTimeout(() => { + this.getElem('header_rescale').style.display = 'none'; + }, 200); + } + } + + private toggleFooter(b: boolean) { + if (b) { + this.getElem('footer_rescale').style.display = 'block'; + setTimeout(() => { + this.getElem('footer_rescale').style.bottom = '0px'; + }, 1); + } else { + this.getElem('footer_rescale').style.bottom = '-60px'; + setTimeout(() => { + this.getElem('footer_rescale').style.display = 'none'; + }, 200); + } + } + + private getElem(name: string): HTMLElement { + return document.getElementById(name); + } + + private toggleRescaler(b: boolean) { + this.getElem('overlay_rescale').style.display = (b ? 'block' : 'none'); } - private setStateScale(b: boolean) { - document.getElementById('header_rescale').style.display = (b ? 'none' : 'block'); - document.getElementById('footer_rescale').style.display = (b ? 'none' : 'block'); - document.getElementById('overlay_rescale').style.display = (b ? 'block' : 'none'); + private setOffsetRescaler(x: number, y: number) { + document.getElementById('overlay_rescale').style.left = x + 'px'; + document.getElementById('overlay_rescale').style.top = y + 'px'; } } diff --git a/src/assets/i18n/creator/de.json b/src/assets/i18n/creator/de.json index 65c9f61b07ac8338a9cbb8635e3c388ab518c71f..b2bc08d4ba16e7ad0ee0c39a78e5ad60cf1bb961 100644 --- a/src/assets/i18n/creator/de.json +++ b/src/assets/i18n/creator/de.json @@ -61,6 +61,8 @@ "error-title": "Bitte gib einen Titel ein.", "export": "Exportieren", "export-description": "Exportieren", + "live-announcer": "Du befindest dich jetzt auf der Fragen-Seite. Um Informationen zu Tastenkombinationen zu erhalten drücke jetzt die Enter-Taste oder rufe die Ansage zu einem späteren Zeitpunkt mit der Escape-Taste auf.", + "live-announcer-moderation": "Du befindest dich jetzt auf der Moderations-Seite. Um Informationen zu Tastenkombinationen zu erhalten drücke jetzt die Enter-Taste oder rufe die Ansage zu einem späteren Zeitpunkt mit der Escape-Taste auf.", "mark-correct": "Frage bejahen", "mark-favorite": "Als Kandidat für einen Bonus markieren", "mark-not-correct": "Frage nicht bejahen", @@ -158,6 +160,7 @@ "email-error": "E-Mail Adresse ist ungültig.", "export-comments": "Fragen exportieren", "general": "Sitzung", + "live-announcer": "Du befindest dich jetzt in der Sitzung. Um Informationen zu Tastenkombinationen zu erhalten drücke jetzt die Enter-Taste oder rufe die Ansage zu einem späteren Zeitpunkt mit der Escape-Taste auf.", "live-feedback": "Live Feedback", "moderating-stream": "Moderation", "moderator-added": "Moderator wurde hinzugefügt.", diff --git a/src/assets/i18n/creator/en.json b/src/assets/i18n/creator/en.json index aa15f7a0b27e39d2194af16f8655e2bcec585f52..b9dea368645636d550db70d791f10d42a145b7ed 100644 --- a/src/assets/i18n/creator/en.json +++ b/src/assets/i18n/creator/en.json @@ -62,6 +62,8 @@ "error-title": "Please enter a title.", "export": "Export", "export-description": "Export", + "live-announcer": "You are now on the questions page. To get information about key combinations press the Enter key or call the announcement later with the Escape key.", + "live-announcer-moderation": "You are now on the moderation page. To get information about key combinations press the Enter key or call the announcement later with the Escape key.", "mark-correct": "Mark as correct", "mark-favorite": "Mark as bonus question", "mark-not-correct": "Mark not as correct", @@ -159,6 +161,7 @@ "email-error": "E-Mail is invalid.", "export-comments": "Export questions", "general": "Session", + "live-announcer": "You're in the session now. To get information about key combinations press the Enter key or call the announcement later with the Escape key.", "live-feedback": "Live feedback", "moderating-stream": "Moderation", "moderator-added": "Moderator was added.", diff --git a/src/assets/i18n/home/de.json b/src/assets/i18n/home/de.json index 2f53310f0394cdf04267d4268ce2d85a5a308c84..6bf7166ae924ddb2f9b0a8468731078622fd5a8c 100644 --- a/src/assets/i18n/home/de.json +++ b/src/assets/i18n/home/de.json @@ -76,11 +76,13 @@ "home-page": { "accessibility-create": "Erstellt eine neue Sitzung.", "accessibility-join-button": "Betritt die Sitzung, deren Code du eingegeben hast.", - "accessibility-join-input": "Hier kannst du den Code der Sitzung eingeben der du beitreten möchtest.", + "accessibility-join-input": "Hier kannst du den Code der Sitzung eingeben der du beitreten möchtest. Den Code sagt dir dein Dozent.", "create-session": "Neue Sitzung", "created-1": "Die Sitzung '", "created-2": "' wurde erstellt.", "exactly-8": "Der Sitzungs-Code ist eine Kombination aus genau 8 Ziffern.", + "live-announcer": "Willkommen auf der Seite fragpunktjetzt. Um Informationen zu Tastenkombinationen zu erhalten drücke jetzt die Enter-Taste oder rufe die Ansage zu einem späteren Zeitpunkt mit der Escape-Taste auf.", + "live-announcer-user": "Du befindest dich jetzt auf der Benutzer-Seite. Um Informationen zu Tastenkombinationen zu erhalten drücke jetzt die Enter-Taste oder rufe die Ansage zu einem späteren Zeitpunkt mit der Escape-Taste auf.", "install": "Installieren", "no-empty-name": "Bitte gib einen Namen für die Sitzung ein.", "no-room-found": "Es wurde keine Sitzung mit diesem Code gefunden.", diff --git a/src/assets/i18n/home/en.json b/src/assets/i18n/home/en.json index d803be9b18d0ff3bfd22393a8902af335c191e3f..5cfd858167829acb70be59412758485060b202b4 100644 --- a/src/assets/i18n/home/en.json +++ b/src/assets/i18n/home/en.json @@ -82,6 +82,9 @@ "created-1": "Session '", "created-2": "' successfully created", "exactly-8": "A session key has exactly 8 digits.", + "accessibility-join-input": "Here you can enter the key of the session you want to join. Your lecturer will tell you the session key.", + "live-announcer": "Welcome to fragpunktjetzt. To get information about key combinations press the Enter key or call the announcement later with the Escape key.", + "live-announcer-user": "You are now on the user page. To get information about key combinations press the Enter key or call the announcement later with the Escape key.", "install": "Install", "no-empty-name": "Please enter a name.", "no-room-found": "No session found with this key", diff --git a/src/assets/i18n/participant/de.json b/src/assets/i18n/participant/de.json index 4306a30c338862bad4f9ebf675bab82d815ca9ca..f9ac08f7265b19549ed99d9c3422e9e75016002c 100644 --- a/src/assets/i18n/participant/de.json +++ b/src/assets/i18n/participant/de.json @@ -58,6 +58,7 @@ "error-both-fields": "Bitte fülle alle Felder aus.", "error-comment": "Bitte gib deine Frage ein.", "error-title": "Bitte gib einen Titel ein.", + "live-announcer": "Du befindest dich jetzt auf der Fragen-Seite. Um Informationen zu Tastenkombinationen zu erhalten drücke jetzt die Enter-Taste oder rufe die Ansage zu einem späteren Zeitpunkt mit der Escape-Taste auf.", "mark-not-correct": "Dozent hat die Frage bejaht.", "mark-not-favorite": "Bonus-Frage: Dozent hält die Frage für besonders interessant.", "mark-not-wrong": "Dozent hat die Frage verneint", @@ -85,6 +86,7 @@ "description": "Beschreibung der Sitzung", "give-feedback": "Feedback geben", "learn": "Lernen", + "live-announcer": "Du befindest dich jetzt in der Sitzung. Um Informationen zu Tastenkombinationen zu erhalten drücke jetzt die Enter-Taste oder rufe die Ansage zu einem späteren Zeitpunkt mit der Escape-Taste auf.", "live-feedback": "Live Feedback", "session-id": "Code" }, diff --git a/src/assets/i18n/participant/en.json b/src/assets/i18n/participant/en.json index 079ea15c73892d39fb0d1a81d7639cb99aa34e7f..acc3ee0cee006f79b08f782478a4d7c0c519dfd3 100644 --- a/src/assets/i18n/participant/en.json +++ b/src/assets/i18n/participant/en.json @@ -58,6 +58,7 @@ "error-both-fields": "Please fill in all fields.", "error-comment": "Please enter a question.", "error-title": "Please enter a title.", + "live-announcer": "You are now on the questions page. To get information about key combinations press the Enter key or call the announcement later with the Escape key.", "mark-not-correct": "Marked as correct by the professor", "mark-not-favorite": "Bonus question: Your professor intends to give a bonus for that question.", "mark-not-wrong": "Marked as wrong by the professor", @@ -85,6 +86,7 @@ "description": "Description", "give-feedback": "Give feedback", "learn": "Learn", + "live-announcer": "You're in the session now. To get information about key combinations press the Enter key or call the announcement later with the Escape key.", "live-feedback": "Live feedback", "session-id": "Key" }, diff --git a/src/theme/theme.service.ts b/src/theme/theme.service.ts index 9393193ffc926ca994813ec3f52fc64db64f003e..697d7de66cc800eb8360338f962ba2df8d85f246 100644 --- a/src/theme/theme.service.ts +++ b/src/theme/theme.service.ts @@ -38,4 +38,11 @@ export class ThemeService { public getThemes(): Theme[] { return this.themes; } + + public getThemeByKey(key: string): Theme { + for (let i = 0; i < this.themes.length; i++) { + if (this.themes[i].key === key) {return this.themes[i]; } + } + return null; + } }