MOBILE-3744 a11y: Improve some aria roles
parent
632e7dfc0c
commit
9f42b80b06
|
@ -18,7 +18,7 @@
|
||||||
<ion-label>
|
<ion-label>
|
||||||
<div class="large-avatar">
|
<div class="large-avatar">
|
||||||
<img class="avatar" [src]="conversation!.imageurl" core-external-content [alt]="conversation!.name"
|
<img class="avatar" [src]="conversation!.imageurl" core-external-content [alt]="conversation!.name"
|
||||||
role="presentation" onError="this.src='assets/img/group-avatar.png'">
|
onError="this.src='assets/img/group-avatar.png'">
|
||||||
</div>
|
</div>
|
||||||
<h2>
|
<h2>
|
||||||
<core-format-text [text]="conversation!.name" contextLevel="system" [contextInstanceId]="0"></core-format-text>
|
<core-format-text [text]="conversation!.name" contextLevel="system" [contextInstanceId]="0"></core-format-text>
|
||||||
|
|
|
@ -6,7 +6,7 @@
|
||||||
<ion-title>
|
<ion-title>
|
||||||
<div class="toolbar-title">
|
<div class="toolbar-title">
|
||||||
<img *ngIf="loaded && !otherMember && conversationImage" class="core-bar-button-image" [src]="conversationImage"
|
<img *ngIf="loaded && !otherMember && conversationImage" class="core-bar-button-image" [src]="conversationImage"
|
||||||
[alt]="title" onError="this.src='assets/img/group-avatar.png'" core-external-content role="presentation"
|
alt="" onError="this.src='assets/img/group-avatar.png'" core-external-content role="presentation"
|
||||||
[siteId]="siteId || null">
|
[siteId]="siteId || null">
|
||||||
<core-user-avatar *ngIf="loaded && otherMember" class="core-bar-button-image" [user]="otherMember"
|
<core-user-avatar *ngIf="loaded && otherMember" class="core-bar-button-image" [user]="otherMember"
|
||||||
[linkProfile]="false" [checkOnline]="otherMember.showonlinestatus" (click)="showInfo && viewInfo()">
|
[linkProfile]="false" [checkOnline]="otherMember.showonlinestatus" (click)="showInfo && viewInfo()">
|
||||||
|
|
|
@ -34,7 +34,7 @@
|
||||||
<!-- Favourite conversations. -->
|
<!-- Favourite conversations. -->
|
||||||
<ion-item-divider class="ion-text-wrap core-expandable" (click)="toggle(favourites)" sticky="true"
|
<ion-item-divider class="ion-text-wrap core-expandable" (click)="toggle(favourites)" sticky="true"
|
||||||
[attr.aria-label]="(favourites.expanded ? 'core.collapse' : 'core.expand') | translate"
|
[attr.aria-label]="(favourites.expanded ? 'core.collapse' : 'core.expand') | translate"
|
||||||
[attr.aria-expanded]="favourites.expanded">
|
[attr.aria-expanded]="favourites.expanded" role="heading">
|
||||||
<ion-icon *ngIf="!favourites.expanded" name="fas-caret-right" slot="start" aria-hidden="true"></ion-icon>
|
<ion-icon *ngIf="!favourites.expanded" name="fas-caret-right" slot="start" aria-hidden="true"></ion-icon>
|
||||||
<ion-icon *ngIf="favourites.expanded" name="fas-caret-down" slot="start" aria-hidden="true"></ion-icon>
|
<ion-icon *ngIf="favourites.expanded" name="fas-caret-down" slot="start" aria-hidden="true"></ion-icon>
|
||||||
<ion-label>{{ 'core.favourites' | translate }} ({{ favourites.count }})</ion-label>
|
<ion-label>{{ 'core.favourites' | translate }} ({{ favourites.count }})</ion-label>
|
||||||
|
@ -57,7 +57,7 @@
|
||||||
<!-- Group conversations. -->
|
<!-- Group conversations. -->
|
||||||
<ion-item-divider class="ion-text-wrap core-expandable" (click)="toggle(group)" sticky="true"
|
<ion-item-divider class="ion-text-wrap core-expandable" (click)="toggle(group)" sticky="true"
|
||||||
[attr.aria-label]="(group.expanded ? 'core.collapse' : 'core.expand') | translate"
|
[attr.aria-label]="(group.expanded ? 'core.collapse' : 'core.expand') | translate"
|
||||||
[attr.aria-expanded]="group.expanded">
|
[attr.aria-expanded]="group.expanded" role="heading">
|
||||||
<ion-icon *ngIf="!group.expanded" name="fas-caret-right" slot="start" aria-hidden="true"></ion-icon>
|
<ion-icon *ngIf="!group.expanded" name="fas-caret-right" slot="start" aria-hidden="true"></ion-icon>
|
||||||
<ion-icon *ngIf="group.expanded" name="fas-caret-down" slot="start" aria-hidden="true"></ion-icon>
|
<ion-icon *ngIf="group.expanded" name="fas-caret-down" slot="start" aria-hidden="true"></ion-icon>
|
||||||
<ion-label>{{ 'addon.messages.groupconversations' | translate }} ({{ group.count }})</ion-label>
|
<ion-label>{{ 'addon.messages.groupconversations' | translate }} ({{ group.count }})</ion-label>
|
||||||
|
@ -79,7 +79,7 @@
|
||||||
|
|
||||||
<ion-item-divider class="ion-text-wrap core-expandable" (click)="toggle(individual)" sticky="true"
|
<ion-item-divider class="ion-text-wrap core-expandable" (click)="toggle(individual)" sticky="true"
|
||||||
[attr.aria-label]="(individual.expanded ? 'core.collapse' : 'core.expand') | translate"
|
[attr.aria-label]="(individual.expanded ? 'core.collapse' : 'core.expand') | translate"
|
||||||
[attr.aria-expanded]="individual.expanded">
|
[attr.aria-expanded]="individual.expanded" role="heading">
|
||||||
<ion-icon *ngIf="!individual.expanded" name="fas-caret-right" slot="start" aria-hidden="true"></ion-icon>
|
<ion-icon *ngIf="!individual.expanded" name="fas-caret-right" slot="start" aria-hidden="true"></ion-icon>
|
||||||
<ion-icon *ngIf="individual.expanded" name="fas-caret-down" slot="start" aria-hidden="true"></ion-icon>
|
<ion-icon *ngIf="individual.expanded" name="fas-caret-down" slot="start" aria-hidden="true"></ion-icon>
|
||||||
<ion-label>{{ 'addon.messages.individualconversations' | translate }} ({{ individual.count }})</ion-label>
|
<ion-label>{{ 'addon.messages.individualconversations' | translate }} ({{ individual.count }})</ion-label>
|
||||||
|
|
|
@ -32,7 +32,7 @@ component="mod_data" [itemId]="entry.id" area="database_entry" [courseId]="datab
|
||||||
|
|
||||||
<a *ngIf="action == 'userpicture'" core-user-link [courseId]="database.course" [userId]="entry.userid" [title]="entry.fullname">
|
<a *ngIf="action == 'userpicture'" core-user-link [courseId]="database.course" [userId]="entry.userid" [title]="entry.fullname">
|
||||||
<img class="avatar-round" [src]="userPicture" [alt]="'core.pictureof' | translate:{$a: entry.fullname}" core-external-content
|
<img class="avatar-round" [src]="userPicture" [alt]="'core.pictureof' | translate:{$a: entry.fullname}" core-external-content
|
||||||
onError="this.src='assets/img/user-avatar.png'" role="presentation">
|
onError="this.src='assets/img/user-avatar.png'">
|
||||||
</a>
|
</a>
|
||||||
|
|
||||||
<a *ngIf="action == 'user' && entry" core-user-link [courseId]="database.course" [userId]="entry.userid" [title]="entry.fullname">
|
<a *ngIf="action == 'user' && entry" core-user-link [courseId]="database.course" [userId]="entry.userid" [title]="entry.fullname">
|
||||||
|
|
|
@ -59,7 +59,7 @@
|
||||||
</ng-container>
|
</ng-container>
|
||||||
|
|
||||||
<ion-textarea *ngIf="item.templateName == 'textarea'" [required]="item.required"
|
<ion-textarea *ngIf="item.templateName == 'textarea'" [required]="item.required"
|
||||||
name="{{item.typ}}_{{item.id}}" [attr.aria-multiline]="true" [(ngModel)]="item.value">
|
name="{{item.typ}}_{{item.id}}" [(ngModel)]="item.value">
|
||||||
</ion-textarea>
|
</ion-textarea>
|
||||||
|
|
||||||
<ion-select *ngIf="item.templateName == 'multichoice-d'" [required]="item.required"
|
<ion-select *ngIf="item.templateName == 'multichoice-d'" [required]="item.required"
|
||||||
|
|
|
@ -25,8 +25,8 @@
|
||||||
(contentChanged)="onMessageChange($event)">
|
(contentChanged)="onMessageChange($event)">
|
||||||
</core-rich-text-editor>
|
</core-rich-text-editor>
|
||||||
</ion-item>
|
</ion-item>
|
||||||
<ion-item-divider class="ion-text-wrap core-expandable" (click)="toggleAdvanced()"
|
<ion-item-divider class="ion-text-wrap core-expandable" (click)="toggleAdvanced()" role="heading"
|
||||||
[attr.aria-expanded]="advanced" [attr.aria-label]="(advanced ? 'core.hideadvanced' : 'core.showadvanced') |translate">
|
[attr.aria-expanded]="advanced" [attr.aria-label]="(advanced ? 'core.hideadvanced' : 'core.showadvanced') | translate">
|
||||||
<ion-icon *ngIf="!advanced" name="fa-caret-right" slot="start" aria-hidden="true"></ion-icon>
|
<ion-icon *ngIf="!advanced" name="fa-caret-right" slot="start" aria-hidden="true"></ion-icon>
|
||||||
<ion-icon *ngIf="advanced" name="fa-caret-down" slot="start" aria-hidden="true"></ion-icon>
|
<ion-icon *ngIf="advanced" name="fa-caret-down" slot="start" aria-hidden="true"></ion-icon>
|
||||||
<ion-label>{{ 'addon.mod_forum.advanced' | translate }}</ion-label>
|
<ion-label>{{ 'addon.mod_forum.advanced' | translate }}</ion-label>
|
||||||
|
|
|
@ -71,7 +71,7 @@
|
||||||
<ion-button *ngIf="sortingAvailable" id="addon-mod-forum-sort-order-button"
|
<ion-button *ngIf="sortingAvailable" id="addon-mod-forum-sort-order-button"
|
||||||
class="core-button-select button-no-uppercase"
|
class="core-button-select button-no-uppercase"
|
||||||
aria-haspopup="true" aria-controls="addon-mod-forum-sort-order-selector"
|
aria-haspopup="true" aria-controls="addon-mod-forum-sort-order-selector"
|
||||||
[attr.aria-label]="('core.sort' | translate)" [attr.aria-expanded]="sortOrderSelectorExpanded"
|
[attr.aria-label]="('core.sort' | translate)"
|
||||||
(click)="showSortOrderSelector()">
|
(click)="showSortOrderSelector()">
|
||||||
<span class="core-button-select-text">{{ selectedSortOrder.label | translate }}</span>
|
<span class="core-button-select-text">{{ selectedSortOrder.label | translate }}</span>
|
||||||
<div class="select-icon" slot="end"><div class="select-icon-inner"></div></div>
|
<div class="select-icon" slot="end"><div class="select-icon-inner"></div></div>
|
||||||
|
|
|
@ -79,7 +79,6 @@ export class AddonModForumIndexComponent extends CoreCourseModuleMainActivityCom
|
||||||
sortingAvailable!: boolean;
|
sortingAvailable!: boolean;
|
||||||
sortOrders: AddonModForumSortOrder[] = [];
|
sortOrders: AddonModForumSortOrder[] = [];
|
||||||
selectedSortOrder: AddonModForumSortOrder | null = null;
|
selectedSortOrder: AddonModForumSortOrder | null = null;
|
||||||
sortOrderSelectorExpanded = false;
|
|
||||||
canPin = false;
|
canPin = false;
|
||||||
|
|
||||||
protected syncEventName = AddonModForumSyncProvider.AUTO_SYNCED;
|
protected syncEventName = AddonModForumSyncProvider.AUTO_SYNCED;
|
||||||
|
@ -637,12 +636,8 @@ export class AddonModForumIndexComponent extends CoreCourseModuleMainActivityCom
|
||||||
|
|
||||||
modal.present();
|
modal.present();
|
||||||
|
|
||||||
this.sortOrderSelectorExpanded = true;
|
|
||||||
|
|
||||||
const result = await modal.onDidDismiss<AddonModForumSortOrder>();
|
const result = await modal.onDidDismiss<AddonModForumSortOrder>();
|
||||||
|
|
||||||
this.sortOrderSelectorExpanded = false;
|
|
||||||
|
|
||||||
if (result.data && result.data.value != this.selectedSortOrder?.value) {
|
if (result.data && result.data.value != this.selectedSortOrder?.value) {
|
||||||
this.selectedSortOrder = result.data;
|
this.selectedSortOrder = result.data;
|
||||||
this.page = 0;
|
this.page = 0;
|
||||||
|
|
|
@ -11,9 +11,9 @@
|
||||||
<ion-content>
|
<ion-content>
|
||||||
<ion-list id="addon-mod-forum-sort-selector" role="menu" aria-labelledby="addon-mod-forum-sort-order-button">
|
<ion-list id="addon-mod-forum-sort-selector" role="menu" aria-labelledby="addon-mod-forum-sort-order-button">
|
||||||
<ng-container *ngFor="let sortOrder of sortOrders">
|
<ng-container *ngFor="let sortOrder of sortOrders">
|
||||||
<ion-item class="ion-text-wrap" detail="false" role="menuitem"
|
<ion-item class="ion-text-wrap" detail="false" role="combobox" button aria-haspopup="dialog"
|
||||||
[class.core-selected-item]="selected == sortOrder.value" [attr.aria-label]="sortOrder.label | translate"
|
[attr.aria-current]="selected == sortOrder.value ? 'page' : 'false'"
|
||||||
(click)="selectSortOrder(sortOrder)">
|
[attr.aria-label]="sortOrder.label | translate" (click)="selectSortOrder(sortOrder)">
|
||||||
<ion-label>
|
<ion-label>
|
||||||
<h2>{{ sortOrder.label | translate }}</h2>
|
<h2>{{ sortOrder.label | translate }}</h2>
|
||||||
</ion-label>
|
</ion-label>
|
||||||
|
|
|
@ -32,7 +32,7 @@
|
||||||
</core-rich-text-editor>
|
</core-rich-text-editor>
|
||||||
</ion-item>
|
</ion-item>
|
||||||
<ion-item-divider class="ion-text-wrap core-expandable" (click)="toggleAdvanced()" [attr.aria-expanded]="advanced"
|
<ion-item-divider class="ion-text-wrap core-expandable" (click)="toggleAdvanced()" [attr.aria-expanded]="advanced"
|
||||||
[attr.aria-label]="(advanced ? 'core.hideadvanced' : 'core.showadvanced') |translate">
|
[attr.aria-label]="(advanced ? 'core.hideadvanced' : 'core.showadvanced') |translate" role="heading">
|
||||||
<ion-icon *ngIf="!advanced" name="fa-caret-right" slot="start" aria-hidden="true"></ion-icon>
|
<ion-icon *ngIf="!advanced" name="fa-caret-right" slot="start" aria-hidden="true"></ion-icon>
|
||||||
<ion-icon *ngIf="advanced" name="fa-caret-down" slot="start" aria-hidden="true"></ion-icon>
|
<ion-icon *ngIf="advanced" name="fa-caret-down" slot="start" aria-hidden="true"></ion-icon>
|
||||||
<ion-label>{{ 'addon.mod_forum.advanced' | translate }}</ion-label>
|
<ion-label>{{ 'addon.mod_forum.advanced' | translate }}</ion-label>
|
||||||
|
|
|
@ -11,7 +11,7 @@
|
||||||
|
|
||||||
<ion-buttons slot="end">
|
<ion-buttons slot="end">
|
||||||
<ion-button id="addon-mod_quiz-connection-error-button" [hidden]="!autoSaveError" (click)="showConnectionError($event)"
|
<ion-button id="addon-mod_quiz-connection-error-button" [hidden]="!autoSaveError" (click)="showConnectionError($event)"
|
||||||
[attr.aria-label]="'addon.mod_quiz.connectionerror' | translate" aria-haspopup="true">
|
[attr.aria-label]="'addon.mod_quiz.connectionerror' | translate" aria-haspopup="dialog">
|
||||||
<ion-icon name="fas-exclamation-circle" slot="icon-only" aria-hidden="true"></ion-icon>
|
<ion-icon name="fas-exclamation-circle" slot="icon-only" aria-hidden="true"></ion-icon>
|
||||||
</ion-button>
|
</ion-button>
|
||||||
<ion-button *ngIf="navigation.length" [attr.aria-label]="'addon.mod_quiz.opentoc' | translate"
|
<ion-button *ngIf="navigation.length" [attr.aria-label]="'addon.mod_quiz.opentoc' | translate"
|
||||||
|
|
|
@ -32,7 +32,7 @@
|
||||||
<ion-label position="stacked">
|
<ion-label position="stacked">
|
||||||
{{ 'addon.mod_workshop_assessment_accumulative.dimensioncommentfor' | translate : {'$a': field.dimtitle } }}
|
{{ 'addon.mod_workshop_assessment_accumulative.dimensioncommentfor' | translate : {'$a': field.dimtitle } }}
|
||||||
</ion-label>
|
</ion-label>
|
||||||
<ion-textarea aria-multiline="true" [(ngModel)]="selectedValues[n].peercomment" core-auto-rows></ion-textarea>
|
<ion-textarea [(ngModel)]="selectedValues[n].peercomment" core-auto-rows></ion-textarea>
|
||||||
</ion-item>
|
</ion-item>
|
||||||
<ion-item *ngIf="!edit" class="ion-text-wrap">
|
<ion-item *ngIf="!edit" class="ion-text-wrap">
|
||||||
<ion-label>
|
<ion-label>
|
||||||
|
|
|
@ -14,7 +14,7 @@
|
||||||
{{ 'addon.mod_workshop_assessment_comments.dimensioncommentfor' | translate : {'$a': field.dimtitle } }}
|
{{ 'addon.mod_workshop_assessment_comments.dimensioncommentfor' | translate : {'$a': field.dimtitle } }}
|
||||||
</span>
|
</span>
|
||||||
</ion-label>
|
</ion-label>
|
||||||
<ion-textarea aria-multiline="true" [(ngModel)]="selectedValues[n].peercomment" core-auto-rows></ion-textarea>
|
<ion-textarea [(ngModel)]="selectedValues[n].peercomment" core-auto-rows></ion-textarea>
|
||||||
<core-input-errors *ngIf="fieldErrors['peercomment_' + n]" [errorText]="fieldErrors['peercomment_' + n]">
|
<core-input-errors *ngIf="fieldErrors['peercomment_' + n]" [errorText]="fieldErrors['peercomment_' + n]">
|
||||||
</core-input-errors>
|
</core-input-errors>
|
||||||
</ion-item>
|
</ion-item>
|
||||||
|
|
|
@ -35,7 +35,7 @@
|
||||||
<ion-label position="stacked">
|
<ion-label position="stacked">
|
||||||
{{ 'addon.mod_workshop_assessment_numerrors.dimensioncommentfor' | translate : {'$a': field.dimtitle } }}
|
{{ 'addon.mod_workshop_assessment_numerrors.dimensioncommentfor' | translate : {'$a': field.dimtitle } }}
|
||||||
</ion-label>
|
</ion-label>
|
||||||
<ion-textarea aria-multiline="true" [(ngModel)]="selectedValues[n].peercomment" [name]="'peercomment_' + n"
|
<ion-textarea [(ngModel)]="selectedValues[n].peercomment" [name]="'peercomment_' + n"
|
||||||
core-auto-rows>
|
core-auto-rows>
|
||||||
</ion-textarea>
|
</ion-textarea>
|
||||||
</ion-item>
|
</ion-item>
|
||||||
|
|
|
@ -22,7 +22,7 @@
|
||||||
<ion-textarea *ngIf="essayQuestion.isPlainText" class="core-question-textarea"
|
<ion-textarea *ngIf="essayQuestion.isPlainText" class="core-question-textarea"
|
||||||
[ngClass]='{"core-monospaced": essayQuestion.isMonospaced}'
|
[ngClass]='{"core-monospaced": essayQuestion.isMonospaced}'
|
||||||
placeholder="{{ 'core.question.answer' | translate }}"
|
placeholder="{{ 'core.question.answer' | translate }}"
|
||||||
[attr.name]="essayQuestion.textarea.name" aria-multiline="true" [ngModel]="essayQuestion.textarea.text">
|
[attr.name]="essayQuestion.textarea.name" [ngModel]="essayQuestion.textarea.text">
|
||||||
</ion-textarea>
|
</ion-textarea>
|
||||||
<!-- Rich text editor. -->
|
<!-- Rich text editor. -->
|
||||||
<core-rich-text-editor *ngIf="!essayQuestion.isPlainText" placeholder="{{ 'core.question.answer' | translate }}"
|
<core-rich-text-editor *ngIf="!essayQuestion.isPlainText" placeholder="{{ 'core.question.answer' | translate }}"
|
||||||
|
|
|
@ -35,7 +35,6 @@ export class CoreContextMenuComponent implements OnInit, OnDestroy {
|
||||||
@Input('aria-label') ariaLabel?: string; // Aria label to be shown on the top of the popover.
|
@Input('aria-label') ariaLabel?: string; // Aria label to be shown on the top of the popover.
|
||||||
|
|
||||||
hideMenu = true; // It will be unhidden when items are added.
|
hideMenu = true; // It will be unhidden when items are added.
|
||||||
expanded = false;
|
|
||||||
uniqueId: string;
|
uniqueId: string;
|
||||||
|
|
||||||
protected items: CoreContextMenuItemComponent[] = [];
|
protected items: CoreContextMenuItemComponent[] = [];
|
||||||
|
@ -43,6 +42,7 @@ export class CoreContextMenuComponent implements OnInit, OnDestroy {
|
||||||
protected itemsChangedStream: Subject<void>; // Stream to update the hideMenu boolean when items change.
|
protected itemsChangedStream: Subject<void>; // Stream to update the hideMenu boolean when items change.
|
||||||
protected instanceId: string;
|
protected instanceId: string;
|
||||||
protected parentContextMenu?: CoreContextMenuComponent;
|
protected parentContextMenu?: CoreContextMenuComponent;
|
||||||
|
protected expanded = false;
|
||||||
|
|
||||||
constructor(
|
constructor(
|
||||||
elementRef: ElementRef,
|
elementRef: ElementRef,
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
<ion-button [hidden]="hideMenu" fill="clear" [attr.aria-label]="ariaLabel"
|
<ion-button [hidden]="hideMenu" fill="clear" [attr.aria-label]="ariaLabel" (click)="showContextMenu($event)" aria-haspopup="true"
|
||||||
(click)="showContextMenu($event)" aria-haspopup="true" [attr.aria-expanded]="expanded" [attr.aria-controls]="uniqueId">
|
[attr.aria-controls]="uniqueId">
|
||||||
<ion-icon [name]="icon" slot="icon-only" aria-hidden="true">
|
<ion-icon [name]="icon" slot="icon-only" aria-hidden="true">
|
||||||
</ion-icon>
|
</ion-icon>
|
||||||
</ion-button>
|
</ion-button>
|
||||||
|
|
|
@ -1,8 +1,7 @@
|
||||||
<div class="core-empty-box ion-padding" [class.core-empty-box-inline]="(!image && !icon) || inline">
|
<div class="core-empty-box ion-padding" [class.core-empty-box-inline]="(!image && !icon) || inline">
|
||||||
<div class="core-empty-box-content">
|
<div class="core-empty-box-content">
|
||||||
<img *ngIf="image && !icon" [src]="image" role="presentation" aria-hidden="true">
|
<img *ngIf="image && !icon" [src]="image" role="presentation" alt="">
|
||||||
<ion-icon *ngIf="icon" [name]="icon" [class.icon-flip-rtl]="flipIconRtl" role="presentation" aria-hidden="true">
|
<ion-icon *ngIf="icon" [name]="icon" [class.icon-flip-rtl]="flipIconRtl" aria-hidden="true"></ion-icon>
|
||||||
</ion-icon>
|
|
||||||
<p *ngIf="message" [class.ion-padding-top]="image || icon">{{ message }}</p>
|
<p *ngIf="message" [class.ion-padding-top]="image || icon">{{ message }}</p>
|
||||||
<ng-content></ng-content>
|
<ng-content></ng-content>
|
||||||
</div>
|
</div>
|
||||||
|
|
|
@ -1,8 +1,7 @@
|
||||||
<form #messageForm>
|
<form #messageForm>
|
||||||
<textarea class="core-send-message-input" [autofocus]="showKeyboard" [placeholder]="placeholder" rows="1" core-auto-rows
|
<textarea class="core-send-message-input" [autofocus]="showKeyboard" [placeholder]="placeholder" rows="1" core-auto-rows
|
||||||
[(ngModel)]="message" name="message" (onResize)="textareaResized()" (keydown.enter)="enterClicked($event)"
|
[(ngModel)]="message" name="message" (onResize)="textareaResized()" (keydown.enter)="enterClicked($event)"
|
||||||
(keydown.control.enter)="enterClicked($event, 'control')" (keydown.meta.enter)="enterClicked($event, 'meta')"
|
(keydown.control.enter)="enterClicked($event, 'control')" (keydown.meta.enter)="enterClicked($event, 'meta')"></textarea>
|
||||||
aria-multiline="true"></textarea>
|
|
||||||
<ion-buttons>
|
<ion-buttons>
|
||||||
<ion-button fill="clear" type="submit" [disabled]="!message || sendDisabled"
|
<ion-button fill="clear" type="submit" [disabled]="!message || sendDisabled"
|
||||||
[attr.aria-label]="'core.send' | translate" [core-suppress-events] (onClick)="submitForm($event)">
|
[attr.aria-label]="'core.send' | translate" [core-suppress-events] (onClick)="submitForm($event)">
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
<img *ngIf="avatarUrl" [src]="avatarUrl" [alt]="'core.pictureof' | translate:{$a: fullname}" core-external-content
|
<img *ngIf="avatarUrl" [src]="avatarUrl" [alt]="'core.pictureof' | translate:{$a: fullname}" core-external-content
|
||||||
onError="this.src='assets/img/user-avatar.png'" role="presentation" (click)="gotoProfile($event)">
|
onError="this.src='assets/img/user-avatar.png'" (click)="gotoProfile($event)">
|
||||||
|
|
||||||
<img *ngIf="!avatarUrl" src="assets/img/user-avatar.png" [alt]="'core.pictureof' | translate:{$a: fullname}" role="presentation"
|
<img *ngIf="!avatarUrl" src="assets/img/user-avatar.png" [alt]="'core.pictureof' | translate:{$a: fullname}"
|
||||||
(click)="gotoProfile($event)">
|
(click)="gotoProfile($event)">
|
||||||
|
|
||||||
<span *ngIf="checkOnline && isOnline()" class="contact-status online"></span>
|
<span *ngIf="checkOnline && isOnline()" class="contact-status online"></span>
|
||||||
|
|
|
@ -18,7 +18,7 @@
|
||||||
<ion-item *ngFor="let site of sites" (click)="siteClicked(site.id)" detail="false">
|
<ion-item *ngFor="let site of sites" (click)="siteClicked(site.id)" detail="false">
|
||||||
<ion-avatar slot="start">
|
<ion-avatar slot="start">
|
||||||
<img [src]="site.avatar" core-external-content [siteId]="site.id"
|
<img [src]="site.avatar" core-external-content [siteId]="site.id"
|
||||||
alt="{{ 'core.pictureof' | translate:{$a: site.fullName} }}" role="presentation"
|
alt="{{ 'core.pictureof' | translate:{$a: site.fullName} }}"
|
||||||
onError="this.src='assets/img/user-avatar.png'">
|
onError="this.src='assets/img/user-avatar.png'">
|
||||||
</ion-avatar>
|
</ion-avatar>
|
||||||
<ion-label>
|
<ion-label>
|
||||||
|
|
|
@ -20,8 +20,7 @@
|
||||||
class="ion-text-wrap clearfix ion-justify-content-between core-button-selector-row"
|
class="ion-text-wrap clearfix ion-justify-content-between core-button-selector-row"
|
||||||
[class.core-section-download]="downloadEnabled">
|
[class.core-section-download]="downloadEnabled">
|
||||||
<ion-button class="core-button-select button-no-uppercase" (click)="showSectionSelector()"
|
<ion-button class="core-button-select button-no-uppercase" (click)="showSectionSelector()"
|
||||||
aria-haspopup="true" [attr.aria-expanded]="sectionSelectorExpanded"
|
aria-haspopup="listbox" id="core-course-section-button" expand="block">
|
||||||
id="core-course-section-button" expand="block">
|
|
||||||
<ion-icon name="fas-folder" slot="start" aria-hidden="true"></ion-icon>
|
<ion-icon name="fas-folder" slot="start" aria-hidden="true"></ion-icon>
|
||||||
<span class="sr-only" *ngIf="selectedSection">{{ 'core.course.sections' | translate }}:</span>
|
<span class="sr-only" *ngIf="selectedSection">{{ 'core.course.sections' | translate }}:</span>
|
||||||
<span class="core-button-select-text">
|
<span class="core-button-select-text">
|
||||||
|
|
|
@ -91,7 +91,6 @@ export class CoreCourseFormatComponent implements OnInit, OnChanges, OnDestroy {
|
||||||
|
|
||||||
canLoadMore = false;
|
canLoadMore = false;
|
||||||
showSectionId = 0;
|
showSectionId = 0;
|
||||||
sectionSelectorExpanded = false;
|
|
||||||
data: Record<string, unknown> = {}; // Data to pass to the components.
|
data: Record<string, unknown> = {}; // Data to pass to the components.
|
||||||
|
|
||||||
displaySectionSelector?: boolean;
|
displaySectionSelector?: boolean;
|
||||||
|
@ -109,6 +108,7 @@ export class CoreCourseFormatComponent implements OnInit, OnChanges, OnDestroy {
|
||||||
protected sectionStatusObserver?: CoreEventObserver;
|
protected sectionStatusObserver?: CoreEventObserver;
|
||||||
protected selectTabObserver?: CoreEventObserver;
|
protected selectTabObserver?: CoreEventObserver;
|
||||||
protected lastCourseFormat?: string;
|
protected lastCourseFormat?: string;
|
||||||
|
protected sectionSelectorExpanded = false;
|
||||||
|
|
||||||
constructor(
|
constructor(
|
||||||
protected content: IonContent,
|
protected content: IonContent,
|
||||||
|
|
|
@ -1,3 +1,3 @@
|
||||||
<button *ngIf="completion" (click)="completionClicked($event)">
|
<button *ngIf="completion" (click)="completionClicked($event)" [title]="completionDescription">
|
||||||
<img [src]="completionImage" [alt]="completionDescription">
|
<img [src]="completionImage" role="presentation" alt="">
|
||||||
</button>
|
</button>
|
||||||
|
|
|
@ -16,7 +16,7 @@
|
||||||
<ion-content class="ion-padding">
|
<ion-content class="ion-padding">
|
||||||
<div>
|
<div>
|
||||||
<div class="ion-text-center ion-padding core-login-site-logo">
|
<div class="ion-text-center ion-padding core-login-site-logo">
|
||||||
<img src="assets/img/login_logo.png" class="avatar-full login-logo" role="presentation">
|
<img src="assets/img/login_logo.png" class="avatar-full login-logo" role="presentation" alt="">
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<h3 class="core-login-onboarding-step">
|
<h3 class="core-login-onboarding-step">
|
||||||
|
|
|
@ -19,8 +19,8 @@
|
||||||
<div class="ion-text-wrap ion-text-center ion-margin-bottom">
|
<div class="ion-text-wrap ion-text-center ion-margin-bottom">
|
||||||
<div class="core-login-site-logo">
|
<div class="core-login-site-logo">
|
||||||
<!-- Show site logo or a default image. -->
|
<!-- Show site logo or a default image. -->
|
||||||
<img *ngIf="logoUrl" [src]="logoUrl" role="presentation" onError="this.src='assets/img/login_logo.png'">
|
<img *ngIf="logoUrl" [src]="logoUrl" role="presentation" alt="" onError="this.src='assets/img/login_logo.png'">
|
||||||
<img *ngIf="!logoUrl" src="assets/img/login_logo.png" role="presentation">
|
<img *ngIf="!logoUrl" src="assets/img/login_logo.png" role="presentation" alt="">
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<h3 *ngIf="siteName" class="ion-padding core-sitename">
|
<h3 *ngIf="siteName" class="ion-padding core-sitename">
|
||||||
|
|
|
@ -11,13 +11,12 @@
|
||||||
<div class="ion-text-wrap ion-text-center ion-margin-bottom" [ngClass]="{'item-avatar-center': showSiteAvatar}">
|
<div class="ion-text-wrap ion-text-center ion-margin-bottom" [ngClass]="{'item-avatar-center': showSiteAvatar}">
|
||||||
<!-- Show user avatar. -->
|
<!-- Show user avatar. -->
|
||||||
<img *ngIf="showSiteAvatar" [src]="userAvatar" class="large-avatar" core-external-content [siteId]="siteId"
|
<img *ngIf="showSiteAvatar" [src]="userAvatar" class="large-avatar" core-external-content [siteId]="siteId"
|
||||||
role="presentation"
|
|
||||||
alt="{{ 'core.pictureof' | translate:{$a: userFullName} }}" onError="this.src='assets/img/user-avatar.png'">
|
alt="{{ 'core.pictureof' | translate:{$a: userFullName} }}" onError="this.src='assets/img/user-avatar.png'">
|
||||||
|
|
||||||
<div class="core-login-site-logo" *ngIf="!showSiteAvatar">
|
<div class="core-login-site-logo" *ngIf="!showSiteAvatar">
|
||||||
<!-- Show site logo or a default image. -->
|
<!-- Show site logo or a default image. -->
|
||||||
<img *ngIf="logoUrl" [src]="logoUrl" role="presentation" onError="this.src='assets/img/login_logo.png'">
|
<img *ngIf="logoUrl" [src]="logoUrl" role="presentation" onError="this.src='assets/img/login_logo.png'" alt="">
|
||||||
<img *ngIf="!logoUrl" src="assets/img/login_logo.png" role="presentation">
|
<img *ngIf="!logoUrl" src="assets/img/login_logo.png" role="presentation" alt="">
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<h6 *ngIf="siteName" class="ion-padding core-sitename">
|
<h6 *ngIf="siteName" class="ion-padding core-sitename">
|
||||||
|
|
|
@ -17,7 +17,7 @@
|
||||||
<ion-content class="ion-padding">
|
<ion-content class="ion-padding">
|
||||||
<div class="ion-text-center ion-padding ion-margin-bottom core-login-site-logo"
|
<div class="ion-text-center ion-padding ion-margin-bottom core-login-site-logo"
|
||||||
[class.hidden]="hasSites || enteredSiteUrl">
|
[class.hidden]="hasSites || enteredSiteUrl">
|
||||||
<img src="assets/img/login_logo.png" class="avatar-full login-logo" role="presentation">
|
<img src="assets/img/login_logo.png" class="avatar-full login-logo" role="presentation" alt="">
|
||||||
</div>
|
</div>
|
||||||
<form [formGroup]="siteForm" (ngSubmit)="connect($event, siteForm.value.siteUrl)" *ngIf="!fixedSites" #siteFormEl>
|
<form [formGroup]="siteForm" (ngSubmit)="connect($event, siteForm.value.siteUrl)" *ngIf="!fixedSites" #siteFormEl>
|
||||||
<!-- Form to input the site URL if there are no fixed sites. -->
|
<!-- Form to input the site URL if there are no fixed sites. -->
|
||||||
|
@ -102,7 +102,7 @@
|
||||||
<ng-container *ngIf="showScanQR && !hasSites && !enteredSiteUrl">
|
<ng-container *ngIf="showScanQR && !hasSites && !enteredSiteUrl">
|
||||||
<div class="ion-text-center ion-padding ion-margin-top">{{ 'core.login.or' | translate }}</div>
|
<div class="ion-text-center ion-padding ion-margin-top">{{ 'core.login.or' | translate }}</div>
|
||||||
<ion-button expand="block" color="light" class="ion-margin" lines="none" (click)="showInstructionsAndScanQR()"
|
<ion-button expand="block" color="light" class="ion-margin" lines="none" (click)="showInstructionsAndScanQR()"
|
||||||
aria-haspopup="true">
|
aria-haspopup="dialog">
|
||||||
<ion-icon slot="start" name="fas-qrcode" aria-hidden="true"></ion-icon>
|
<ion-icon slot="start" name="fas-qrcode" aria-hidden="true"></ion-icon>
|
||||||
<ion-label>{{ 'core.scanqr' | translate }}</ion-label>
|
<ion-label>{{ 'core.scanqr' | translate }}</ion-label>
|
||||||
</ion-button>
|
</ion-button>
|
||||||
|
@ -111,7 +111,7 @@
|
||||||
<!-- Help. -->
|
<!-- Help. -->
|
||||||
<ion-list lines="none" class="ion-margin-top">
|
<ion-list lines="none" class="ion-margin-top">
|
||||||
<ion-item button class="ion-text-center ion-text-wrap core-login-need-help" (click)="showHelp()" detail="false"
|
<ion-item button class="ion-text-center ion-text-wrap core-login-need-help" (click)="showHelp()" detail="false"
|
||||||
aria-haspopup="true">
|
aria-haspopup="dialog">
|
||||||
<ion-label>{{ 'core.needhelp' | translate }}</ion-label>
|
<ion-label>{{ 'core.needhelp' | translate }}</ion-label>
|
||||||
</ion-item>
|
</ion-item>
|
||||||
</ion-list>
|
</ion-list>
|
||||||
|
|
|
@ -21,7 +21,7 @@
|
||||||
<ion-list>
|
<ion-list>
|
||||||
<ion-item button (click)="login(site.id)" *ngFor="let site of sites">
|
<ion-item button (click)="login(site.id)" *ngFor="let site of sites">
|
||||||
<ion-avatar slot="start">
|
<ion-avatar slot="start">
|
||||||
<img [src]="site.avatar" core-external-content [siteId]="site.id" role="presentation"
|
<img [src]="site.avatar" core-external-content [siteId]="site.id"
|
||||||
alt="{{ 'core.pictureof' | translate:{$a: site.fullName} }}" onError="this.src='assets/img/user-avatar.png'">
|
alt="{{ 'core.pictureof' | translate:{$a: site.fullName} }}" onError="this.src='assets/img/user-avatar.png'">
|
||||||
</ion-avatar>
|
</ion-avatar>
|
||||||
<ion-label>
|
<ion-label>
|
||||||
|
|
|
@ -48,8 +48,8 @@ export class CoreLoginHelperProvider {
|
||||||
static readonly OPEN_COURSE = 'open_course';
|
static readonly OPEN_COURSE = 'open_course';
|
||||||
|
|
||||||
static readonly ONBOARDING_DONE = 'onboarding_done';
|
static readonly ONBOARDING_DONE = 'onboarding_done';
|
||||||
static readonly FAQ_URL_IMAGE_HTML = '<img src="assets/img/login/faq_url.png" role="presentation">';
|
static readonly FAQ_URL_IMAGE_HTML = '<img src="assets/img/login/faq_url.png" role="presentation" alt="">';
|
||||||
static readonly FAQ_QRCODE_IMAGE_HTML = '<img src="assets/img/login/faq_qrcode.png" role="presentation">';
|
static readonly FAQ_QRCODE_IMAGE_HTML = '<img src="assets/img/login/faq_qrcode.png" role="presentation" alt="">';
|
||||||
|
|
||||||
protected logger: CoreLogger;
|
protected logger: CoreLogger;
|
||||||
protected isSSOConfirmShown = false;
|
protected isSSOConfirmShown = false;
|
||||||
|
|
|
@ -18,7 +18,7 @@
|
||||||
<ion-item *ngFor="let site of sites" (click)="storeInSite(site.id)" detail="false">
|
<ion-item *ngFor="let site of sites" (click)="storeInSite(site.id)" detail="false">
|
||||||
<ion-avatar slot="start" aria-hidden="true">
|
<ion-avatar slot="start" aria-hidden="true">
|
||||||
<img [src]="site.avatar" core-external-content [siteId]="site.id"
|
<img [src]="site.avatar" core-external-content [siteId]="site.id"
|
||||||
alt="{{ 'core.pictureof' | translate:{$a: site.fullname} }}" role="presentation"
|
alt="{{ 'core.pictureof' | translate:{$a: site.fullname} }}"
|
||||||
onError="this.src='assets/img/user-avatar.png'">
|
onError="this.src='assets/img/user-avatar.png'">
|
||||||
</ion-avatar>
|
</ion-avatar>
|
||||||
<ion-label>
|
<ion-label>
|
||||||
|
|
Loading…
Reference in New Issue