commit
a680aba66b
|
@ -74,7 +74,7 @@
|
||||||
</ion-select>
|
</ion-select>
|
||||||
</ion-item>
|
</ion-item>
|
||||||
<ion-item class="ion-text-wrap" (click)="openRespondents()" [detail]="access.canviewreports && completedCount > 0"
|
<ion-item class="ion-text-wrap" (click)="openRespondents()" [detail]="access.canviewreports && completedCount > 0"
|
||||||
button>
|
[button]="access.canviewreports && completedCount > 0">
|
||||||
<ion-label>
|
<ion-label>
|
||||||
<h2>{{ 'addon.mod_feedback.completed_feedbacks' | translate }}</h2>
|
<h2>{{ 'addon.mod_feedback.completed_feedbacks' | translate }}</h2>
|
||||||
</ion-label>
|
</ion-label>
|
||||||
|
|
|
@ -154,8 +154,8 @@
|
||||||
</ion-item>
|
</ion-item>
|
||||||
</ion-card>
|
</ion-card>
|
||||||
|
|
||||||
<ion-card>
|
<ion-card *ngIf="completed">
|
||||||
<ion-grid *ngIf="completed">
|
<ion-grid>
|
||||||
<ion-row class="ion-align-items-center">
|
<ion-row class="ion-align-items-center">
|
||||||
<ion-col *ngIf="access!.canviewanalysis">
|
<ion-col *ngIf="access!.canviewanalysis">
|
||||||
<ion-button expand="block" fill="outline" (click)="showAnalysis()" class="ion-text-wrap">
|
<ion-button expand="block" fill="outline" (click)="showAnalysis()" class="ion-text-wrap">
|
||||||
|
|
|
@ -172,11 +172,12 @@ export class AddonModFeedbackProvider {
|
||||||
return array.concat(responses);
|
return array.concat(responses);
|
||||||
}, <OfflineResponsesArray> []).map((valueEntry) => {
|
}, <OfflineResponsesArray> []).map((valueEntry) => {
|
||||||
const parts = valueEntry.id.split('_');
|
const parts = valueEntry.id.split('_');
|
||||||
|
const item = (parts[1] || '').replace(/\[.*\]/, ''); // Remove [0] and similar.
|
||||||
|
|
||||||
return {
|
return {
|
||||||
...valueEntry,
|
...valueEntry,
|
||||||
typ: parts[0],
|
typ: parts[0],
|
||||||
item: Number(parts[1]),
|
item: Number(item),
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
|
@ -93,9 +93,7 @@ export class AddonModFeedbackPrefetchHandlerService extends CoreCourseActivityPr
|
||||||
* @inheritdoc
|
* @inheritdoc
|
||||||
*/
|
*/
|
||||||
async isDownloadable(module: CoreCourseAnyModuleData, courseId: number): Promise<boolean> {
|
async isDownloadable(module: CoreCourseAnyModuleData, courseId: number): Promise<boolean> {
|
||||||
const feedback = await AddonModFeedback.getFeedback(courseId, module.id, {
|
const feedback = await AddonModFeedback.getFeedback(courseId, module.id);
|
||||||
readingStrategy: CoreSitesReadingStrategy.PREFER_CACHE,
|
|
||||||
});
|
|
||||||
|
|
||||||
const now = CoreTimeUtils.timestamp();
|
const now = CoreTimeUtils.timestamp();
|
||||||
|
|
||||||
|
|
|
@ -80,6 +80,7 @@ export class AddonModH5PActivityIndexComponent extends CoreCourseModuleMainActiv
|
||||||
hasOffline = false;
|
hasOffline = false;
|
||||||
isOpeningPage = false;
|
isOpeningPage = false;
|
||||||
|
|
||||||
|
protected listeningResize = false;
|
||||||
protected fetchContentDefaultError = 'addon.mod_h5pactivity.errorgetactivity';
|
protected fetchContentDefaultError = 'addon.mod_h5pactivity.errorgetactivity';
|
||||||
protected syncEventName = AddonModH5PActivitySyncProvider.AUTO_SYNCED;
|
protected syncEventName = AddonModH5PActivitySyncProvider.AUTO_SYNCED;
|
||||||
protected site: CoreSite;
|
protected site: CoreSite;
|
||||||
|
@ -372,8 +373,7 @@ export class AddonModH5PActivityIndexComponent extends CoreCourseModuleMainActiv
|
||||||
|
|
||||||
CoreCourse.checkModuleCompletion(this.courseId, this.module.completiondata);
|
CoreCourse.checkModuleCompletion(this.courseId, this.module.completiondata);
|
||||||
|
|
||||||
window.addEventListener('resize', this.contentResized.bind(this));
|
this.setResizeListener();
|
||||||
this.contentResized();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -488,6 +488,19 @@ export class AddonModH5PActivityIndexComponent extends CoreCourseModuleMainActiv
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set the resize listener if needed.
|
||||||
|
*/
|
||||||
|
setResizeListener(): void {
|
||||||
|
if (!this.playing || this.listeningResize) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
this.listeningResize = true;
|
||||||
|
window.addEventListener('resize', this.contentResized.bind(this));
|
||||||
|
this.contentResized();
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* On content resize, change visibility of the main menu: show on portrait and hide on landscape.
|
* On content resize, change visibility of the main menu: show on portrait and hide on landscape.
|
||||||
*/
|
*/
|
||||||
|
@ -495,6 +508,25 @@ export class AddonModH5PActivityIndexComponent extends CoreCourseModuleMainActiv
|
||||||
this.mainMenuPage.changeVisibility(Platform.isPortrait());
|
this.mainMenuPage.changeVisibility(Platform.isPortrait());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @inheritdoc
|
||||||
|
*/
|
||||||
|
ionViewDidEnter(): void {
|
||||||
|
this.setResizeListener();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @inheritdoc
|
||||||
|
*/
|
||||||
|
ionViewWillLeave(): void {
|
||||||
|
this.mainMenuPage.changeVisibility(true);
|
||||||
|
|
||||||
|
if (this.listeningResize) {
|
||||||
|
this.listeningResize = false;
|
||||||
|
window.removeEventListener('resize', this.resizeFunction);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Component destroyed.
|
* Component destroyed.
|
||||||
*/
|
*/
|
||||||
|
@ -503,10 +535,6 @@ export class AddonModH5PActivityIndexComponent extends CoreCourseModuleMainActiv
|
||||||
|
|
||||||
this.observer?.off();
|
this.observer?.off();
|
||||||
window.removeEventListener('message', this.messageListenerFunction);
|
window.removeEventListener('message', this.messageListenerFunction);
|
||||||
|
|
||||||
if (this.playing) {
|
|
||||||
window.removeEventListener('resize', this.resizeFunction);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -470,13 +470,13 @@ export class AddonModLessonIndexComponent extends CoreCourseModuleMainActivityCo
|
||||||
/**
|
/**
|
||||||
* Review the lesson.
|
* Review the lesson.
|
||||||
*/
|
*/
|
||||||
review(): void {
|
async review(): Promise<void> {
|
||||||
if (!this.retakeToReview || !this.lesson) {
|
if (!this.retakeToReview || !this.lesson) {
|
||||||
// No retake to review, stop.
|
// No retake to review, stop.
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
CoreNavigator.navigateToSitePath(
|
await CoreNavigator.navigateToSitePath(
|
||||||
`${AddonModLessonModuleHandlerService.PAGE_NAME}/${this.courseId}/${this.module.id}/player`,
|
`${AddonModLessonModuleHandlerService.PAGE_NAME}/${this.courseId}/${this.module.id}/player`,
|
||||||
{
|
{
|
||||||
params: {
|
params: {
|
||||||
|
@ -487,6 +487,8 @@ export class AddonModLessonIndexComponent extends CoreCourseModuleMainActivityCo
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
|
||||||
|
this.retakeToReview = undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
@ -186,13 +186,14 @@
|
||||||
</ion-list>
|
</ion-list>
|
||||||
|
|
||||||
<!-- End of lesson reached. -->
|
<!-- End of lesson reached. -->
|
||||||
|
<ion-card class="core-warning-card" *ngIf="eolData && !processData && eolData.offline?.value">
|
||||||
|
<ion-item>
|
||||||
|
<ion-icon name="fas-exclamation-triangle" slot="start" aria-hidden="true"></ion-icon>
|
||||||
|
<ion-label>{{ 'addon.mod_lesson.finishretakeoffline' | translate }}</ion-label>
|
||||||
|
</ion-item>
|
||||||
|
</ion-card>
|
||||||
|
|
||||||
<ion-card *ngIf="eolData && !processData">
|
<ion-card *ngIf="eolData && !processData">
|
||||||
<div class="core-warning-card" *ngIf="eolData.offline?.value">
|
|
||||||
<ion-item>
|
|
||||||
<ion-icon name="fas-exclamation-triangle" slot="start" aria-hidden="true"></ion-icon>
|
|
||||||
<ion-label>{{ 'addon.mod_lesson.finishretakeoffline' | translate }}</ion-label>
|
|
||||||
</ion-item>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<ion-card-header class="ion-text-wrap" *ngIf="eolData.gradelesson">
|
<ion-card-header class="ion-text-wrap" *ngIf="eolData.gradelesson">
|
||||||
<ion-card-title>{{ 'addon.mod_lesson.congratulations' | translate }}</ion-card-title>
|
<ion-card-title>{{ 'addon.mod_lesson.congratulations' | translate }}</ion-card-title>
|
||||||
|
|
|
@ -272,8 +272,7 @@ export class AddonModLessonPlayerPage implements OnInit, OnDestroy, CanLeave {
|
||||||
// If lesson has offline data already, use offline mode.
|
// If lesson has offline data already, use offline mode.
|
||||||
this.offline = await AddonModLessonOffline.hasOfflineData(this.lesson.id);
|
this.offline = await AddonModLessonOffline.hasOfflineData(this.lesson.id);
|
||||||
|
|
||||||
if (!this.offline && !CoreApp.isOnline() && AddonModLesson.isLessonOffline(this.lesson) &&
|
if (!this.offline && !CoreApp.isOnline() && AddonModLesson.isLessonOffline(this.lesson) && !this.review) {
|
||||||
!this.review) {
|
|
||||||
// Lesson doesn't have offline data, but it allows offline and the device is offline. Use offline mode.
|
// Lesson doesn't have offline data, but it allows offline and the device is offline. Use offline mode.
|
||||||
this.offline = true;
|
this.offline = true;
|
||||||
}
|
}
|
||||||
|
@ -586,11 +585,12 @@ export class AddonModLessonPlayerPage implements OnInit, OnDestroy, CanLeave {
|
||||||
this.originalData = undefined;
|
this.originalData = undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (data.displaymenu && !this.displayMenu) {
|
// Don't display the navigation menu in review mode, using them displays errors.
|
||||||
|
if (data.displaymenu && !this.displayMenu && !this.review) {
|
||||||
// Load the menu.
|
// Load the menu.
|
||||||
this.loadMenu();
|
this.loadMenu();
|
||||||
}
|
}
|
||||||
this.displayMenu = !!data.displaymenu;
|
this.displayMenu = !this.review && !!data.displaymenu;
|
||||||
|
|
||||||
if (!this.firstPageLoaded) {
|
if (!this.firstPageLoaded) {
|
||||||
this.firstPageLoaded = true;
|
this.firstPageLoaded = true;
|
||||||
|
|
|
@ -18,7 +18,7 @@
|
||||||
</ion-toolbar>
|
</ion-toolbar>
|
||||||
</ion-header>
|
</ion-header>
|
||||||
<ion-content>
|
<ion-content>
|
||||||
<core-loading [hideUntil]="loaded">
|
<core-loading [hideUntil]="loaded" class="core-loading-fullheight">
|
||||||
<core-navigation-bar [previous]="previousSco" [next]="nextSco" (action)="loadSco($event)"></core-navigation-bar>
|
<core-navigation-bar [previous]="previousSco" [next]="nextSco" (action)="loadSco($event)"></core-navigation-bar>
|
||||||
|
|
||||||
<core-iframe *ngIf="loaded && src" [src]="src" [iframeWidth]="scormWidth" [iframeHeight]="scormHeight"></core-iframe>
|
<core-iframe *ngIf="loaded && src" [src]="src" [iframeWidth]="scormWidth" [iframeHeight]="scormHeight"></core-iframe>
|
||||||
|
|
|
@ -533,6 +533,22 @@ export class AddonModScormPlayerPage implements OnInit, OnDestroy {
|
||||||
}));
|
}));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @inheritdoc
|
||||||
|
*/
|
||||||
|
ionViewDidEnter(): void {
|
||||||
|
if (this.scorm && this.scorm.popup) {
|
||||||
|
this.mainMenuPage.changeVisibility(false);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @inheritdoc
|
||||||
|
*/
|
||||||
|
ionViewWillLeave(): void {
|
||||||
|
this.mainMenuPage.changeVisibility(true);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Component being destroyed.
|
* Component being destroyed.
|
||||||
*/
|
*/
|
||||||
|
@ -549,8 +565,6 @@ export class AddonModScormPlayerPage implements OnInit, OnDestroy {
|
||||||
this.goOfflineObserver?.off();
|
this.goOfflineObserver?.off();
|
||||||
}, 500);
|
}, 500);
|
||||||
|
|
||||||
this.mainMenuPage.changeVisibility(true);
|
|
||||||
|
|
||||||
// Unblock the SCORM so it can be synced.
|
// Unblock the SCORM so it can be synced.
|
||||||
CoreSync.unblockOperation(AddonModScormProvider.COMPONENT, this.scorm.id, 'player');
|
CoreSync.unblockOperation(AddonModScormProvider.COMPONENT, this.scorm.id, 'player');
|
||||||
}
|
}
|
||||||
|
|
|
@ -345,6 +345,8 @@ export class AddonModWorkshopSyncProvider extends CoreSyncBaseProvider<AddonModW
|
||||||
attachmentsId,
|
attachmentsId,
|
||||||
siteId,
|
siteId,
|
||||||
);
|
);
|
||||||
|
|
||||||
|
break;
|
||||||
case AddonModWorkshopAction.UPDATE:
|
case AddonModWorkshopAction.UPDATE:
|
||||||
await AddonModWorkshop.updateSubmissionOnline(
|
await AddonModWorkshop.updateSubmissionOnline(
|
||||||
submissionId,
|
submissionId,
|
||||||
|
@ -353,6 +355,8 @@ export class AddonModWorkshopSyncProvider extends CoreSyncBaseProvider<AddonModW
|
||||||
attachmentsId,
|
attachmentsId,
|
||||||
siteId,
|
siteId,
|
||||||
);
|
);
|
||||||
|
|
||||||
|
break;
|
||||||
case AddonModWorkshopAction.DELETE:
|
case AddonModWorkshopAction.DELETE:
|
||||||
await AddonModWorkshop.deleteSubmissionOnline(submissionId, siteId);
|
await AddonModWorkshop.deleteSubmissionOnline(submissionId, siteId);
|
||||||
}
|
}
|
||||||
|
|
|
@ -51,8 +51,8 @@
|
||||||
@include margin(10px, 0, 0, 0);
|
@include margin(10px, 0, 0, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
&.core-loading-noheight .core-loading-content {
|
&.core-loading-fullheight .core-loading-content {
|
||||||
height: auto;
|
height: 100%;
|
||||||
}
|
}
|
||||||
|
|
||||||
&.core-loading-loaded {
|
&.core-loading-loaded {
|
||||||
|
|
|
@ -64,4 +64,18 @@ export class CoreCourseModuleMainActivityPage<ActivityType extends CoreCourseMod
|
||||||
this.activityComponent?.ionViewDidLeave();
|
this.activityComponent?.ionViewDidLeave();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* User will enter the page.
|
||||||
|
*/
|
||||||
|
ionViewWillEnter(): void {
|
||||||
|
this.activityComponent?.ionViewWillEnter();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* User will leave the page.
|
||||||
|
*/
|
||||||
|
ionViewWillLeave(): void {
|
||||||
|
this.activityComponent?.ionViewWillLeave();
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -452,4 +452,18 @@ export class CoreCourseModuleMainResourceComponent implements OnInit, OnDestroy,
|
||||||
this.isCurrentView = false;
|
this.isCurrentView = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* User will enter the page that contains the component. This function should be called by the page that contains the component.
|
||||||
|
*/
|
||||||
|
ionViewWillEnter(): void {
|
||||||
|
// To be overridden.
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* User will leave the page that contains the component. This function should be called by the page that contains the component.
|
||||||
|
*/
|
||||||
|
ionViewWillLeave(): void {
|
||||||
|
// To be overridden.
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -9,7 +9,7 @@
|
||||||
</ion-toolbar>
|
</ion-toolbar>
|
||||||
</ion-header>
|
</ion-header>
|
||||||
<ion-content>
|
<ion-content>
|
||||||
<core-loading [hideUntil]="readyToCapture">
|
<core-loading [hideUntil]="readyToCapture" class="core-loading-fullheight">
|
||||||
<div class="core-av-wrapper">
|
<div class="core-av-wrapper">
|
||||||
<!-- Video stream for image and video. -->
|
<!-- Video stream for image and video. -->
|
||||||
<video *ngIf="!isAudio" [hidden]="hasCaptured" class="core-webcam-stream" autoplay #streamVideo></video>
|
<video *ngIf="!isAudio" [hidden]="hasCaptured" class="core-webcam-stream" autoplay #streamVideo></video>
|
||||||
|
|
|
@ -72,7 +72,7 @@ export class CoreH5PIframeComponent implements OnChanges, OnDestroy {
|
||||||
this.subscription = router.events
|
this.subscription = router.events
|
||||||
.pipe(filter(event => event instanceof NavigationEnd))
|
.pipe(filter(event => event instanceof NavigationEnd))
|
||||||
.subscribe((event: NavigationEnd) => {
|
.subscribe((event: NavigationEnd) => {
|
||||||
if (!this.iframeLoadedOnce || event.urlAfterRedirects == this.currentPageRoute) {
|
if (!this.iframeLoadedOnce || event.urlAfterRedirects !== this.currentPageRoute) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue