commit
be68ff374e
@ -37,6 +37,7 @@ import {
|
|||||||
AddonModH5PActivityAccessInfo,
|
AddonModH5PActivityAccessInfo,
|
||||||
AddonModH5PActivityData,
|
AddonModH5PActivityData,
|
||||||
AddonModH5PActivityProvider,
|
AddonModH5PActivityProvider,
|
||||||
|
AddonModH5PActivityXAPIData,
|
||||||
} from '../../services/h5pactivity';
|
} from '../../services/h5pactivity';
|
||||||
import {
|
import {
|
||||||
AddonModH5PActivitySync,
|
AddonModH5PActivitySync,
|
||||||
@ -165,7 +166,11 @@ export class AddonModH5PActivityIndexComponent extends CoreCourseModuleMainActiv
|
|||||||
* @return Promise resolved when done.
|
* @return Promise resolved when done.
|
||||||
*/
|
*/
|
||||||
protected async checkHasOffline(): Promise<void> {
|
protected async checkHasOffline(): Promise<void> {
|
||||||
this.hasOffline = await CoreXAPIOffline.contextHasStatements(this.h5pActivity!.context, this.siteId);
|
if (!this.h5pActivity) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
this.hasOffline = await CoreXAPIOffline.contextHasStatements(this.h5pActivity.context, this.siteId);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -174,7 +179,11 @@ export class AddonModH5PActivityIndexComponent extends CoreCourseModuleMainActiv
|
|||||||
* @return Promise resolved when done.
|
* @return Promise resolved when done.
|
||||||
*/
|
*/
|
||||||
protected async fetchAccessInfo(): Promise<void> {
|
protected async fetchAccessInfo(): Promise<void> {
|
||||||
this.accessInfo = await AddonModH5PActivity.getAccessInformation(this.h5pActivity!.id, {
|
if (!this.h5pActivity) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
this.accessInfo = await AddonModH5PActivity.getAccessInformation(this.h5pActivity.id, {
|
||||||
cmId: this.module.id,
|
cmId: this.module.id,
|
||||||
siteId: this.siteId,
|
siteId: this.siteId,
|
||||||
});
|
});
|
||||||
@ -186,12 +195,12 @@ export class AddonModH5PActivityIndexComponent extends CoreCourseModuleMainActiv
|
|||||||
* @return Promise resolved when done.
|
* @return Promise resolved when done.
|
||||||
*/
|
*/
|
||||||
protected async fetchDeployedFileData(): Promise<void> {
|
protected async fetchDeployedFileData(): Promise<void> {
|
||||||
if (!this.siteCanDownload) {
|
if (!this.siteCanDownload || !this.h5pActivity) {
|
||||||
// Cannot download the file, no need to fetch the file data.
|
// Cannot download the file, no need to fetch the file data.
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
this.deployedFile = await AddonModH5PActivity.getDeployedFile(this.h5pActivity!, {
|
this.deployedFile = await AddonModH5PActivity.getDeployedFile(this.h5pActivity, {
|
||||||
displayOptions: this.displayOptions,
|
displayOptions: this.displayOptions,
|
||||||
siteId: this.siteId,
|
siteId: this.siteId,
|
||||||
});
|
});
|
||||||
@ -216,10 +225,14 @@ export class AddonModH5PActivityIndexComponent extends CoreCourseModuleMainActiv
|
|||||||
* @return Promise resolved when done.
|
* @return Promise resolved when done.
|
||||||
*/
|
*/
|
||||||
protected async calculateFileState(): Promise<void> {
|
protected async calculateFileState(): Promise<void> {
|
||||||
|
if (!this.fileUrl || !this.deployedFile) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
this.state = await CoreFilepool.getFileStateByUrl(
|
this.state = await CoreFilepool.getFileStateByUrl(
|
||||||
this.site.getId(),
|
this.site.getId(),
|
||||||
this.fileUrl!,
|
this.fileUrl,
|
||||||
this.deployedFile!.timemodified,
|
this.deployedFile.timemodified,
|
||||||
);
|
);
|
||||||
|
|
||||||
this.showFileState();
|
this.showFileState();
|
||||||
@ -267,6 +280,10 @@ export class AddonModH5PActivityIndexComponent extends CoreCourseModuleMainActiv
|
|||||||
event?.preventDefault();
|
event?.preventDefault();
|
||||||
event?.stopPropagation();
|
event?.stopPropagation();
|
||||||
|
|
||||||
|
if (!this.deployedFile) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
if (!CoreApp.isOnline()) {
|
if (!CoreApp.isOnline()) {
|
||||||
CoreDomUtils.showErrorModal('core.networkerrormsg', true);
|
CoreDomUtils.showErrorModal('core.networkerrormsg', true);
|
||||||
|
|
||||||
@ -275,7 +292,7 @@ export class AddonModH5PActivityIndexComponent extends CoreCourseModuleMainActiv
|
|||||||
|
|
||||||
try {
|
try {
|
||||||
// Confirm the download if needed.
|
// Confirm the download if needed.
|
||||||
await CoreDomUtils.confirmDownloadSize({ size: this.deployedFile!.filesize!, total: true });
|
await CoreDomUtils.confirmDownloadSize({ size: this.deployedFile.filesize || 0, total: true });
|
||||||
|
|
||||||
await this.downloadDeployedFile();
|
await this.downloadDeployedFile();
|
||||||
|
|
||||||
@ -316,17 +333,22 @@ export class AddonModH5PActivityIndexComponent extends CoreCourseModuleMainActiv
|
|||||||
* @return Promise resolved when done.
|
* @return Promise resolved when done.
|
||||||
*/
|
*/
|
||||||
protected async downloadDeployedFile(): Promise<void> {
|
protected async downloadDeployedFile(): Promise<void> {
|
||||||
|
if (!this.fileUrl || !this.deployedFile) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const deployedFile = this.deployedFile;
|
||||||
this.downloading = true;
|
this.downloading = true;
|
||||||
this.progressMessage = 'core.downloading';
|
this.progressMessage = 'core.downloading';
|
||||||
|
|
||||||
try {
|
try {
|
||||||
await CoreFilepool.downloadUrl(
|
await CoreFilepool.downloadUrl(
|
||||||
this.site.getId(),
|
this.site.getId(),
|
||||||
this.fileUrl!,
|
this.fileUrl,
|
||||||
false,
|
false,
|
||||||
this.component,
|
this.component,
|
||||||
this.componentId,
|
this.componentId,
|
||||||
this.deployedFile!.timemodified,
|
deployedFile.timemodified,
|
||||||
(data: DownloadProgressData) => {
|
(data: DownloadProgressData) => {
|
||||||
if (!data) {
|
if (!data) {
|
||||||
return;
|
return;
|
||||||
@ -340,7 +362,7 @@ export class AddonModH5PActivityIndexComponent extends CoreCourseModuleMainActiv
|
|||||||
this.progressMessage = data.message;
|
this.progressMessage = data.message;
|
||||||
} else if (data.loaded !== undefined) {
|
} else if (data.loaded !== undefined) {
|
||||||
// Downloading or unzipping.
|
// Downloading or unzipping.
|
||||||
const totalSize = this.progressMessage == 'core.downloading' ? this.deployedFile!.filesize : data.total;
|
const totalSize = this.progressMessage == 'core.downloading' ? deployedFile.filesize : data.total;
|
||||||
|
|
||||||
if (totalSize !== undefined) {
|
if (totalSize !== undefined) {
|
||||||
const percentageNumber = (Number(data.loaded / totalSize) * 100);
|
const percentageNumber = (Number(data.loaded / totalSize) * 100);
|
||||||
@ -362,11 +384,15 @@ export class AddonModH5PActivityIndexComponent extends CoreCourseModuleMainActiv
|
|||||||
/**
|
/**
|
||||||
* Play the package.
|
* Play the package.
|
||||||
*/
|
*/
|
||||||
play(): void {
|
async play(): Promise<void> {
|
||||||
|
if (!this.h5pActivity) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
this.playing = true;
|
this.playing = true;
|
||||||
|
|
||||||
// Mark the activity as viewed.
|
// Mark the activity as viewed.
|
||||||
AddonModH5PActivity.logView(this.h5pActivity!.id, this.h5pActivity!.name, this.siteId);
|
await AddonModH5PActivity.logView(this.h5pActivity.id, this.h5pActivity.name, this.siteId);
|
||||||
|
|
||||||
CoreCourse.checkModuleCompletion(this.courseId, this.module.completiondata);
|
CoreCourse.checkModuleCompletion(this.courseId, this.module.completiondata);
|
||||||
}
|
}
|
||||||
@ -409,7 +435,8 @@ export class AddonModH5PActivityIndexComponent extends CoreCourseModuleMainActiv
|
|||||||
* @return Promise resolved when done.
|
* @return Promise resolved when done.
|
||||||
*/
|
*/
|
||||||
protected async onIframeMessage(event: MessageEvent): Promise<void> {
|
protected async onIframeMessage(event: MessageEvent): Promise<void> {
|
||||||
if (!event.data || !CoreXAPI.canPostStatementsInSite(this.site) || !this.isCurrentXAPIPost(event.data)) {
|
const data = event.data;
|
||||||
|
if (!data || !this.h5pActivity || !CoreXAPI.canPostStatementsInSite(this.site) || !this.isCurrentXAPIPost(data)) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -417,14 +444,14 @@ export class AddonModH5PActivityIndexComponent extends CoreCourseModuleMainActiv
|
|||||||
const options = {
|
const options = {
|
||||||
offline: this.hasOffline,
|
offline: this.hasOffline,
|
||||||
courseId: this.courseId,
|
courseId: this.courseId,
|
||||||
extra: this.h5pActivity!.name,
|
extra: this.h5pActivity.name,
|
||||||
siteId: this.site.getId(),
|
siteId: this.site.getId(),
|
||||||
};
|
};
|
||||||
|
|
||||||
const sent = await CoreXAPI.postStatements(
|
const sent = await CoreXAPI.postStatements(
|
||||||
this.h5pActivity!.context,
|
this.h5pActivity.context,
|
||||||
event.data.component,
|
data.component,
|
||||||
JSON.stringify(event.data.statements),
|
JSON.stringify(data.statements),
|
||||||
options,
|
options,
|
||||||
);
|
);
|
||||||
|
|
||||||
@ -433,10 +460,16 @@ export class AddonModH5PActivityIndexComponent extends CoreCourseModuleMainActiv
|
|||||||
if (sent) {
|
if (sent) {
|
||||||
try {
|
try {
|
||||||
// Invalidate attempts.
|
// Invalidate attempts.
|
||||||
await AddonModH5PActivity.invalidateUserAttempts(this.h5pActivity!.id, undefined, this.siteId);
|
await AddonModH5PActivity.invalidateUserAttempts(this.h5pActivity.id, undefined, this.siteId);
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
// Ignore errors.
|
// Ignore errors.
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Check if the H5P has ended. Final statements don't include a subContentId.
|
||||||
|
const hasEnded = data.statements.some(statement => !statement.object.id.includes('subContentId='));
|
||||||
|
if (hasEnded) {
|
||||||
|
CoreCourse.checkModuleCompletion(this.courseId, this.module.completiondata);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
CoreDomUtils.showErrorModalDefault(error, 'Error sending tracking data.');
|
CoreDomUtils.showErrorModalDefault(error, 'Error sending tracking data.');
|
||||||
@ -450,7 +483,11 @@ export class AddonModH5PActivityIndexComponent extends CoreCourseModuleMainActiv
|
|||||||
* @return Whether it's an XAPI post statement of the current activity.
|
* @return Whether it's an XAPI post statement of the current activity.
|
||||||
*/
|
*/
|
||||||
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||||
protected isCurrentXAPIPost(data: any): boolean {
|
protected isCurrentXAPIPost(data: any): data is AddonModH5PActivityXAPIData {
|
||||||
|
if (!this.h5pActivity) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
if (data.environment != 'moodleapp' || data.context != 'h5p' || data.action != 'xapi_post_statement' || !data.statements) {
|
if (data.environment != 'moodleapp' || data.context != 'h5p' || data.action != 'xapi_post_statement' || !data.statements) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@ -468,14 +505,21 @@ export class AddonModH5PActivityIndexComponent extends CoreCourseModuleMainActiv
|
|||||||
|
|
||||||
const match = trackingUrl.match(/xapi\/activity\/(\d+)/);
|
const match = trackingUrl.match(/xapi\/activity\/(\d+)/);
|
||||||
|
|
||||||
return match && match[1] == this.h5pActivity!.context;
|
return match && match[1] == this.h5pActivity.context;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @inheritdoc
|
* @inheritdoc
|
||||||
*/
|
*/
|
||||||
protected sync(): Promise<AddonModH5PActivitySyncResult> {
|
protected async sync(): Promise<AddonModH5PActivitySyncResult> {
|
||||||
return AddonModH5PActivitySync.syncActivity(this.h5pActivity!.context, this.site.getId());
|
if (!this.h5pActivity) {
|
||||||
|
return {
|
||||||
|
updated: false,
|
||||||
|
warnings: [],
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
return await AddonModH5PActivitySync.syncActivity(this.h5pActivity.context, this.site.getId());
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -65,7 +65,9 @@ export class AddonModH5PActivityAttemptResultsPage implements OnInit {
|
|||||||
try {
|
try {
|
||||||
await this.fetchData();
|
await this.fetchData();
|
||||||
|
|
||||||
await AddonModH5PActivity.logViewReport(this.h5pActivity!.id, this.h5pActivity!.name, { attemptId: this.attemptId });
|
if (this.h5pActivity) {
|
||||||
|
await AddonModH5PActivity.logViewReport(this.h5pActivity.id, this.h5pActivity.name, { attemptId: this.attemptId });
|
||||||
|
}
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
CoreDomUtils.showErrorModalDefault(error, 'Error loading attempt.');
|
CoreDomUtils.showErrorModalDefault(error, 'Error loading attempt.');
|
||||||
} finally {
|
} finally {
|
||||||
@ -105,8 +107,12 @@ export class AddonModH5PActivityAttemptResultsPage implements OnInit {
|
|||||||
* @return Promise resolved when done.
|
* @return Promise resolved when done.
|
||||||
*/
|
*/
|
||||||
protected async fetchUserProfile(): Promise<void> {
|
protected async fetchUserProfile(): Promise<void> {
|
||||||
|
if (!this.attempt) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
this.user = await CoreUser.getProfile(this.attempt!.userid, this.courseId, true);
|
this.user = await CoreUser.getProfile(this.attempt.userid, this.courseId, true);
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
// Ignore errors.
|
// Ignore errors.
|
||||||
}
|
}
|
||||||
|
@ -68,7 +68,9 @@ export class AddonModH5PActivityUserAttemptsPage implements OnInit {
|
|||||||
try {
|
try {
|
||||||
await this.fetchData();
|
await this.fetchData();
|
||||||
|
|
||||||
await AddonModH5PActivity.logViewReport(this.h5pActivity!.id, this.h5pActivity!.name, { userId: this.userId });
|
if (this.h5pActivity) {
|
||||||
|
await AddonModH5PActivity.logViewReport(this.h5pActivity.id, this.h5pActivity.name, { userId: this.userId });
|
||||||
|
}
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
CoreDomUtils.showErrorModalDefault(error, 'Error loading attempts.');
|
CoreDomUtils.showErrorModalDefault(error, 'Error loading attempts.');
|
||||||
} finally {
|
} finally {
|
||||||
@ -107,7 +109,11 @@ export class AddonModH5PActivityUserAttemptsPage implements OnInit {
|
|||||||
* @return Promise resolved when done.
|
* @return Promise resolved when done.
|
||||||
*/
|
*/
|
||||||
protected async fetchAttempts(): Promise<void> {
|
protected async fetchAttempts(): Promise<void> {
|
||||||
this.attemptsData = await AddonModH5PActivity.getUserAttempts(this.h5pActivity!.id, {
|
if (!this.h5pActivity) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
this.attemptsData = await AddonModH5PActivity.getUserAttempts(this.h5pActivity.id, {
|
||||||
cmId: this.cmId,
|
cmId: this.cmId,
|
||||||
userId: this.userId,
|
userId: this.userId,
|
||||||
});
|
});
|
||||||
|
@ -63,7 +63,9 @@ export class AddonModH5PActivityUsersAttemptsPage implements OnInit {
|
|||||||
try {
|
try {
|
||||||
await this.fetchData();
|
await this.fetchData();
|
||||||
|
|
||||||
await AddonModH5PActivity.logViewReport(this.h5pActivity!.id, this.h5pActivity!.name);
|
if (this.h5pActivity) {
|
||||||
|
await AddonModH5PActivity.logViewReport(this.h5pActivity.id, this.h5pActivity.name);
|
||||||
|
}
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
CoreDomUtils.showErrorModalDefault(error, 'Error loading attempts.');
|
CoreDomUtils.showErrorModalDefault(error, 'Error loading attempts.');
|
||||||
} finally {
|
} finally {
|
||||||
@ -103,16 +105,20 @@ export class AddonModH5PActivityUsersAttemptsPage implements OnInit {
|
|||||||
* @return Promise resolved when done.
|
* @return Promise resolved when done.
|
||||||
*/
|
*/
|
||||||
protected async fetchUsers(refresh?: boolean): Promise<void> {
|
protected async fetchUsers(refresh?: boolean): Promise<void> {
|
||||||
|
if (!this.h5pActivity) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
if (refresh) {
|
if (refresh) {
|
||||||
this.page = 0;
|
this.page = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
const result = await AddonModH5PActivity.getUsersAttempts(this.h5pActivity!.id, {
|
const result = await AddonModH5PActivity.getUsersAttempts(this.h5pActivity.id, {
|
||||||
cmId: this.cmId,
|
cmId: this.cmId,
|
||||||
page: this.page,
|
page: this.page,
|
||||||
});
|
});
|
||||||
|
|
||||||
const formattedUsers = await this.formatUsers(result.users);
|
const formattedUsers = await this.formatUsers(this.h5pActivity, result.users);
|
||||||
|
|
||||||
if (this.page === 0) {
|
if (this.page === 0) {
|
||||||
this.users = formattedUsers;
|
this.users = formattedUsers;
|
||||||
@ -127,17 +133,21 @@ export class AddonModH5PActivityUsersAttemptsPage implements OnInit {
|
|||||||
/**
|
/**
|
||||||
* Format users data.
|
* Format users data.
|
||||||
*
|
*
|
||||||
|
* @param h5pActivity Activity data.
|
||||||
* @param users Users to format.
|
* @param users Users to format.
|
||||||
* @return Formatted users.
|
* @return Formatted users.
|
||||||
*/
|
*/
|
||||||
protected async formatUsers(users: AddonModH5PActivityUserAttempts[]): Promise<AddonModH5PActivityUserAttemptsFormatted[]> {
|
protected async formatUsers(
|
||||||
|
h5pActivity: AddonModH5PActivityData,
|
||||||
|
users: AddonModH5PActivityUserAttempts[],
|
||||||
|
): Promise<AddonModH5PActivityUserAttemptsFormatted[]> {
|
||||||
return await Promise.all(users.map(async (user: AddonModH5PActivityUserAttemptsFormatted) => {
|
return await Promise.all(users.map(async (user: AddonModH5PActivityUserAttemptsFormatted) => {
|
||||||
user.user = await CoreUser.getProfile(user.userid, this.courseId, true);
|
user.user = await CoreUser.getProfile(user.userid, this.courseId, true);
|
||||||
|
|
||||||
// Calculate the score of the user.
|
// Calculate the score of the user.
|
||||||
if (this.h5pActivity!.grademethod === AddonModH5PActivityProvider.GRADEMANUAL) {
|
if (h5pActivity.grademethod === AddonModH5PActivityProvider.GRADEMANUAL) {
|
||||||
// No score.
|
// No score.
|
||||||
} else if (this.h5pActivity!.grademethod === AddonModH5PActivityProvider.GRADEAVERAGEATTEMPT) {
|
} else if (h5pActivity.grademethod === AddonModH5PActivityProvider.GRADEAVERAGEATTEMPT) {
|
||||||
if (user.attempts.length) {
|
if (user.attempts.length) {
|
||||||
// Calculate the average.
|
// Calculate the average.
|
||||||
const sumScores = user.attempts.reduce((sumScores, attempt) =>
|
const sumScores = user.attempts.reduce((sumScores, attempt) =>
|
||||||
|
@ -216,8 +216,8 @@ export class AddonModH5PActivityProvider {
|
|||||||
|
|
||||||
const optionsWithPage: AddonModH5PActivityGetAllUsersAttemptsOptions = {
|
const optionsWithPage: AddonModH5PActivityGetAllUsersAttemptsOptions = {
|
||||||
...options,
|
...options,
|
||||||
page: 0,
|
|
||||||
};
|
};
|
||||||
|
optionsWithPage.page = 0;
|
||||||
let canLoadMore = true;
|
let canLoadMore = true;
|
||||||
let users: AddonModH5PActivityUserAttempts[] = [];
|
let users: AddonModH5PActivityUserAttempts[] = [];
|
||||||
|
|
||||||
@ -225,7 +225,7 @@ export class AddonModH5PActivityProvider {
|
|||||||
try {
|
try {
|
||||||
const result = await this.getUsersAttempts(id, optionsWithPage);
|
const result = await this.getUsersAttempts(id, optionsWithPage);
|
||||||
|
|
||||||
optionsWithPage.page = optionsWithPage.page! + 1;
|
optionsWithPage.page = optionsWithPage.page + 1;
|
||||||
users = users.concat(result.users);
|
users = users.concat(result.users);
|
||||||
canLoadMore = result.canLoadMore;
|
canLoadMore = result.canLoadMore;
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
@ -359,10 +359,11 @@ export class AddonModH5PActivityProvider {
|
|||||||
|
|
||||||
const params: AddonModH5pactivityGetResultsWSParams = {
|
const params: AddonModH5pactivityGetResultsWSParams = {
|
||||||
h5pactivityid: id,
|
h5pactivityid: id,
|
||||||
attemptids: [attemptId],
|
|
||||||
};
|
};
|
||||||
|
params.attemptids = [attemptId];
|
||||||
|
|
||||||
const preSets: CoreSiteWSPreSets = {
|
const preSets: CoreSiteWSPreSets = {
|
||||||
cacheKey: this.getAttemptResultsCacheKey(id, params.attemptids!),
|
cacheKey: this.getAttemptResultsCacheKey(id, params.attemptids),
|
||||||
updateFrequency: CoreSite.FREQUENCY_SOMETIMES,
|
updateFrequency: CoreSite.FREQUENCY_SOMETIMES,
|
||||||
component: AddonModH5PActivityProvider.COMPONENT,
|
component: AddonModH5PActivityProvider.COMPONENT,
|
||||||
componentId: options.cmId,
|
componentId: options.cmId,
|
||||||
@ -610,10 +611,11 @@ export class AddonModH5PActivityProvider {
|
|||||||
try {
|
try {
|
||||||
const params: AddonModH5pactivityGetAttemptsWSParams = {
|
const params: AddonModH5pactivityGetAttemptsWSParams = {
|
||||||
h5pactivityid: id,
|
h5pactivityid: id,
|
||||||
userids: [userId],
|
|
||||||
};
|
};
|
||||||
|
params.userids = [userId];
|
||||||
|
|
||||||
const preSets: CoreSiteWSPreSets = {
|
const preSets: CoreSiteWSPreSets = {
|
||||||
cacheKey: this.getUserAttemptsCacheKey(id, params.userids!),
|
cacheKey: this.getUserAttemptsCacheKey(id, params.userids),
|
||||||
updateFrequency: CoreSite.FREQUENCY_SOMETIMES,
|
updateFrequency: CoreSite.FREQUENCY_SOMETIMES,
|
||||||
component: AddonModH5PActivityProvider.COMPONENT,
|
component: AddonModH5PActivityProvider.COMPONENT,
|
||||||
componentId: options.cmId,
|
componentId: options.cmId,
|
||||||
@ -1128,3 +1130,43 @@ declare module '@singletons/events' {
|
|||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Data to be sent using xAPI.
|
||||||
|
*/
|
||||||
|
export type AddonModH5PActivityXAPIData = {
|
||||||
|
action: string;
|
||||||
|
component: string;
|
||||||
|
context: string;
|
||||||
|
environment: string;
|
||||||
|
statements: AddonModH5PActivityStatement[];
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* xAPI statement.
|
||||||
|
*/
|
||||||
|
export type AddonModH5PActivityStatement = {
|
||||||
|
actor: Record<string, string>;
|
||||||
|
context: Record<string, unknown>;
|
||||||
|
object: {
|
||||||
|
id: string;
|
||||||
|
definition: Record<string, unknown>;
|
||||||
|
objectType: string;
|
||||||
|
};
|
||||||
|
result: {
|
||||||
|
completion: boolean;
|
||||||
|
duration: string;
|
||||||
|
score: {
|
||||||
|
min: number;
|
||||||
|
max: number;
|
||||||
|
raw: number;
|
||||||
|
scaled: number;
|
||||||
|
};
|
||||||
|
success?: boolean;
|
||||||
|
response?: string;
|
||||||
|
};
|
||||||
|
verb: {
|
||||||
|
id: string;
|
||||||
|
display: Record<string, string>;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
@ -203,11 +203,7 @@ export class CoreCourseModuleMainActivityComponent extends CoreCourseModuleMainR
|
|||||||
|
|
||||||
try {
|
try {
|
||||||
if (refresh && this.showCompletion) {
|
if (refresh && this.showCompletion) {
|
||||||
try {
|
await CoreUtils.ignoreErrors(this.fetchModule());
|
||||||
this.module = await CoreCourse.getModule(this.module.id, this.courseId);
|
|
||||||
} catch {
|
|
||||||
// Ignore errors.
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
await this.fetchContent(refresh, sync, showErrors);
|
await this.fetchContent(refresh, sync, showErrors);
|
||||||
|
Loading…
x
Reference in New Issue
Block a user