Extract list items management from grades
parent
98910cf465
commit
adc026cd50
|
@ -8,18 +8,18 @@
|
|||
</ion-header>
|
||||
<ion-content>
|
||||
<core-split-view>
|
||||
<ion-refresher slot="fixed" [disabled]="!gradesTableLoaded" (ionRefresh)="refreshGradesTable($event.target)">
|
||||
<ion-refresher slot="fixed" [disabled]="!grades.loaded" (ionRefresh)="refreshGrades($event.target)">
|
||||
<ion-refresher-content pullingText="{{ 'core.pulltorefresh' | translate }}"></ion-refresher-content>
|
||||
</ion-refresher>
|
||||
<core-loading [hideUntil]="gradesTableLoaded" class="safe-area-page">
|
||||
<core-empty-box *ngIf="!gradesTable" icon="stats" [message]="'core.grades.nogradesreturned' | translate">
|
||||
<core-loading [hideUntil]="grades.loaded" class="safe-area-page">
|
||||
<core-empty-box *ngIf="grades.empty" icon="stats" [message]="'core.grades.nogradesreturned' | translate">
|
||||
</core-empty-box>
|
||||
<div *ngIf="gradesTable" class="core-grades-container">
|
||||
<div *ngIf="!grades.empty" class="core-grades-container">
|
||||
<table cellspacing="0" cellpadding="0" class="core-grades-table">
|
||||
<thead>
|
||||
<tr>
|
||||
<th
|
||||
*ngFor="let column of gradesTable.columns"
|
||||
*ngFor="let column of grades.columns"
|
||||
id="{{column.name}}"
|
||||
class="ion-text-start"
|
||||
[class.ion-hide-md-down]="column.hiddenPhone"
|
||||
|
@ -31,8 +31,8 @@
|
|||
</thead>
|
||||
<tbody>
|
||||
<tr
|
||||
*ngFor="let row of gradesTable.rows"
|
||||
(click)="row.itemtype != 'category' && gotoGrade(row.id)"
|
||||
*ngFor="let row of grades.rows"
|
||||
(click)="row.itemtype != 'category' && grades.select(row)"
|
||||
[class]="row.rowclass"
|
||||
[ngClass]='{"core-grades-grade-clickable": row.itemtype != "category"}'
|
||||
>
|
||||
|
@ -45,14 +45,14 @@
|
|||
<th
|
||||
class="core-grades-table-gradeitem ion-text-start"
|
||||
[class.column-itemname]="row.itemtype == 'category'"
|
||||
[class.core-selected-item]="activeGradeId == row.id"
|
||||
[class.core-selected-item]="grades.isSelected(row)"
|
||||
[attr.colspan]="row.colspan"
|
||||
>
|
||||
<ion-icon *ngIf="row.icon" name="{{row.icon}}" slot="start"></ion-icon>
|
||||
<img *ngIf="row.image" [src]="row.image" slot="start" />
|
||||
<span [innerHTML]="row.gradeitem"></span>
|
||||
</th>
|
||||
<ng-container *ngFor="let column of gradesTable.columns">
|
||||
<ng-container *ngFor="let column of grades.columns">
|
||||
<td
|
||||
*ngIf="column.name != 'gradeitem' && row[column.name] != undefined"
|
||||
[class]="'ion-text-start core-grades-table-' + column.name"
|
||||
|
|
|
@ -12,20 +12,24 @@
|
|||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
import { ActivatedRoute } from '@angular/router';
|
||||
import { Component, OnDestroy, OnInit, ViewChild } from '@angular/core';
|
||||
import { ActivatedRoute, ActivatedRouteSnapshot, Params } from '@angular/router';
|
||||
import { AfterViewInit, Component, OnDestroy, ViewChild } from '@angular/core';
|
||||
import { IonRefresher } from '@ionic/angular';
|
||||
import { Subscription } from 'rxjs';
|
||||
|
||||
import { CoreDomUtils } from '@services/utils/dom';
|
||||
import { CoreGrades } from '@features/grades/services/grades';
|
||||
import { CoreGradesFormattedTable, CoreGradesHelper } from '@features/grades/services/grades-helper';
|
||||
import { CoreNavigator } from '@services/navigator';
|
||||
import {
|
||||
CoreGradesFormattedTable,
|
||||
CoreGradesFormattedTableColumn,
|
||||
CoreGradesFormattedTableRow,
|
||||
CoreGradesFormattedTableRowFilled,
|
||||
CoreGradesHelper,
|
||||
} from '@features/grades/services/grades-helper';
|
||||
import { CoreSites } from '@services/sites';
|
||||
import { CoreUtils } from '@services/utils/utils';
|
||||
import { CoreScreen } from '@services/screen';
|
||||
import { CoreSplitViewComponent } from '@components/split-view/split-view';
|
||||
import { CoreObject } from '@singletons/object';
|
||||
import { CorePageItemsListManager } from '@classes/page-items-list-manager';
|
||||
|
||||
/**
|
||||
* Page that displays a course grades.
|
||||
|
@ -35,116 +39,147 @@ import { CoreObject } from '@singletons/object';
|
|||
templateUrl: 'course.html',
|
||||
styleUrls: ['course.scss'],
|
||||
})
|
||||
export class CoreGradesCoursePage implements OnInit, OnDestroy {
|
||||
export class CoreGradesCoursePage implements AfterViewInit, OnDestroy {
|
||||
|
||||
courseId: number;
|
||||
userId: number;
|
||||
gradesTable?: CoreGradesFormattedTable;
|
||||
gradesTableLoaded = false;
|
||||
activeGradeId?: number;
|
||||
layoutSubscription?: Subscription;
|
||||
grades: CoreGradesCourseManager;
|
||||
|
||||
@ViewChild(CoreSplitViewComponent) splitView?: CoreSplitViewComponent;
|
||||
@ViewChild(CoreSplitViewComponent) splitView!: CoreSplitViewComponent;
|
||||
|
||||
constructor(private route: ActivatedRoute) {
|
||||
this.courseId = route.snapshot.params.courseId;
|
||||
this.userId = route.snapshot.queryParams.userId ?? CoreSites.instance.getCurrentSiteUserId();
|
||||
constructor(route: ActivatedRoute) {
|
||||
const courseId = parseInt(route.snapshot.params.courseId);
|
||||
const userId = parseInt(route.snapshot.queryParams.userId ?? CoreSites.instance.getCurrentSiteUserId());
|
||||
|
||||
this.grades = new CoreGradesCourseManager(CoreGradesCoursePage, courseId, userId);
|
||||
}
|
||||
|
||||
/**
|
||||
* @inheritdoc
|
||||
*/
|
||||
async ngOnInit(): Promise<void> {
|
||||
this.layoutSubscription = CoreScreen.instance.layoutObservable.subscribe(() => this.updateActiveGrade());
|
||||
async ngAfterViewInit(): Promise<void> {
|
||||
await this.fetchInitialGrades();
|
||||
|
||||
await this.fetchGradesTable();
|
||||
|
||||
// Add log in Moodle.
|
||||
await CoreUtils.instance.ignoreErrors(CoreGrades.instance.logCourseGradesView(this.courseId, this.userId));
|
||||
}
|
||||
|
||||
/**
|
||||
* @inheritdoc
|
||||
*/
|
||||
ionViewWillEnter(): void {
|
||||
this.updateActiveGrade();
|
||||
this.grades.watchSplitViewOutlet(this.splitView);
|
||||
this.grades.start();
|
||||
}
|
||||
|
||||
/**
|
||||
* @inheritdoc
|
||||
*/
|
||||
ngOnDestroy(): void {
|
||||
this.layoutSubscription?.unsubscribe();
|
||||
this.grades.destroy();
|
||||
}
|
||||
|
||||
/**
|
||||
* Fetch all the data required for the view.
|
||||
*/
|
||||
async fetchGradesTable(): Promise<void> {
|
||||
try {
|
||||
const table = await CoreGrades.instance.getCourseGradesTable(this.courseId, this.userId);
|
||||
|
||||
this.gradesTable = CoreGradesHelper.instance.formatGradesTable(table);
|
||||
} catch (error) {
|
||||
CoreDomUtils.instance.showErrorModalDefault(error, 'Error loading grades');
|
||||
|
||||
this.gradesTable = { rows: [], columns: [] };
|
||||
} finally {
|
||||
this.gradesTableLoaded = true;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Refresh data.
|
||||
* Refresh grades.
|
||||
*
|
||||
* @param refresher Refresher.
|
||||
*/
|
||||
async refreshGradesTable(refresher: IonRefresher): Promise<void> {
|
||||
await CoreUtils.instance.ignoreErrors(CoreGrades.instance.invalidateCourseGradesData(this.courseId, this.userId));
|
||||
await CoreUtils.instance.ignoreErrors(this.fetchGradesTable());
|
||||
async refreshGrades(refresher: IonRefresher): Promise<void> {
|
||||
const { courseId, userId } = this.grades;
|
||||
|
||||
refresher.complete();
|
||||
await CoreUtils.instance.ignoreErrors(CoreGrades.instance.invalidateCourseGradesData(courseId, userId));
|
||||
await CoreUtils.instance.ignoreErrors(this.fetchGrades());
|
||||
|
||||
refresher?.complete();
|
||||
}
|
||||
|
||||
/**
|
||||
* Navigate to the grade of the selected item.
|
||||
*
|
||||
* @param gradeId Grade item ID where to navigate.
|
||||
* Obtain the initial table of grades.
|
||||
*/
|
||||
async gotoGrade(gradeId: number): Promise<void> {
|
||||
const path = this.activeGradeId ? `../${gradeId}` : gradeId.toString();
|
||||
private async fetchInitialGrades(): Promise<void> {
|
||||
try {
|
||||
await this.fetchGrades();
|
||||
} catch (error) {
|
||||
CoreDomUtils.instance.showErrorModalDefault(error, 'Error loading course');
|
||||
|
||||
await CoreNavigator.instance.navigate(path, {
|
||||
params: CoreObject.withoutEmpty({ userId: this.userId }),
|
||||
});
|
||||
|
||||
this.updateActiveGrade(gradeId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Update active grade.
|
||||
*
|
||||
* @param activeGradeId Active grade id.
|
||||
*/
|
||||
private updateActiveGrade(activeGradeId?: number): void {
|
||||
if (CoreScreen.instance.isMobile || this.splitView?.isNested) {
|
||||
delete this.activeGradeId;
|
||||
|
||||
return;
|
||||
this.grades.setTable({ columns: [], rows: [] });
|
||||
}
|
||||
|
||||
this.activeGradeId = activeGradeId ?? this.guessActiveGrade();
|
||||
}
|
||||
|
||||
/**
|
||||
* Guess active grade looking at the current route.
|
||||
*
|
||||
* @return Active grade id.
|
||||
* Update the table of grades.
|
||||
*/
|
||||
private guessActiveGrade(): number | undefined {
|
||||
const gradeId = parseInt(this.route.snapshot?.firstChild?.params.gradeId);
|
||||
private async fetchGrades(): Promise<void> {
|
||||
const table = await CoreGrades.instance.getCourseGradesTable(this.grades.courseId!, this.grades.userId);
|
||||
const formattedTable = await CoreGradesHelper.instance.formatGradesTable(table);
|
||||
|
||||
return isNaN(gradeId) ? undefined : gradeId;
|
||||
this.grades.setTable(formattedTable);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Helper to manage the table of grades.
|
||||
*/
|
||||
class CoreGradesCourseManager extends CorePageItemsListManager<CoreGradesFormattedTableRowFilled> {
|
||||
|
||||
courseId: number;
|
||||
userId: number;
|
||||
columns?: CoreGradesFormattedTableColumn[];
|
||||
rows?: CoreGradesFormattedTableRow[];
|
||||
|
||||
constructor(pageComponent: unknown, courseId: number, userId: number) {
|
||||
super(pageComponent);
|
||||
|
||||
this.courseId = courseId;
|
||||
this.userId = userId;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set grades table.
|
||||
*
|
||||
* @param table Grades table.
|
||||
*/
|
||||
setTable(table: CoreGradesFormattedTable): void {
|
||||
this.columns = table.columns;
|
||||
this.rows = table.rows;
|
||||
|
||||
this.setItems(table.rows.filter(this.isFilledRow));
|
||||
}
|
||||
|
||||
/**
|
||||
* @inheritdoc
|
||||
*/
|
||||
protected getDefaultItem(): CoreGradesFormattedTableRowFilled | null {
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* @inheritdoc
|
||||
*/
|
||||
protected getItemPath(row: CoreGradesFormattedTableRowFilled): string {
|
||||
return row.id.toString();
|
||||
}
|
||||
|
||||
/**
|
||||
* @inheritdoc
|
||||
*/
|
||||
protected getItemQueryParams(): Params {
|
||||
return CoreObject.withoutEmpty({ userId: this.userId });
|
||||
}
|
||||
|
||||
/**
|
||||
* @inheritdoc
|
||||
*/
|
||||
protected getSelectedItemPath(route: ActivatedRouteSnapshot): string | null {
|
||||
return route.params.gradeId ?? null;
|
||||
}
|
||||
|
||||
/**
|
||||
* @inheritdoc
|
||||
*/
|
||||
protected async logActivity(): Promise<void> {
|
||||
await CoreGrades.instance.logCourseGradesView(this.courseId!, this.userId!);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check whether the given row is filled or not.
|
||||
*
|
||||
* @param row Grades table row.
|
||||
* @return Whether the given row is filled or not.
|
||||
*/
|
||||
private isFilledRow(row: CoreGradesFormattedTableRow): row is CoreGradesFormattedTableRowFilled {
|
||||
return 'id' in row;
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -8,34 +8,34 @@
|
|||
</ion-header>
|
||||
<ion-content>
|
||||
<core-split-view>
|
||||
<ion-refresher slot="fixed" [disabled]="!gradesLoaded" (ionRefresh)="refreshGrades($event.target)">
|
||||
<ion-refresher slot="fixed" [disabled]="!courses.loaded" (ionRefresh)="refreshCourses($event.target)">
|
||||
<ion-refresher-content pullingText="{{ 'core.pulltorefresh' | translate }}"></ion-refresher-content>
|
||||
</ion-refresher>
|
||||
<core-loading [hideUntil]="gradesLoaded">
|
||||
<core-loading [hideUntil]="courses.loaded">
|
||||
<core-empty-box
|
||||
*ngIf="grades && grades.length == 0"
|
||||
*ngIf="courses.empty"
|
||||
icon="stats"
|
||||
[message]="'core.grades.nogradesreturned' | translate"
|
||||
></core-empty-box>
|
||||
|
||||
<ion-list *ngIf="grades && grades.length > 0">
|
||||
<ion-list *ngIf="!courses.empty">
|
||||
<ion-item
|
||||
*ngFor="let grade of grades"
|
||||
[title]="grade.courseFullName"
|
||||
[class.core-selected-item]="grade.courseid === this.activeCourseId"
|
||||
*ngFor="let course of courses.items"
|
||||
[title]="course.courseFullName"
|
||||
[class.core-selected-item]="courses.isSelected(course)"
|
||||
class="ion-text-wrap"
|
||||
button
|
||||
detail
|
||||
(click)="openCourse(grade.courseid)"
|
||||
(click)="courses.select(course)"
|
||||
>
|
||||
<ion-label>
|
||||
<core-format-text
|
||||
[text]="grade.courseFullName"
|
||||
[contextInstanceId]="grade.courseid"
|
||||
[text]="course.courseFullName"
|
||||
[contextInstanceId]="course.courseid"
|
||||
contextLevel="course"
|
||||
></core-format-text>
|
||||
</ion-label>
|
||||
<ion-badge slot="end" color="light">{{grade.grade}}</ion-badge>
|
||||
<ion-badge slot="end" color="light">{{course.grade}}</ion-badge>
|
||||
</ion-item>
|
||||
</ion-list>
|
||||
</core-loading>
|
||||
|
|
|
@ -12,17 +12,16 @@
|
|||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
import { Component, OnDestroy, OnInit } from '@angular/core';
|
||||
import { IonRefresher } from '@ionic/angular';
|
||||
import { Subscription } from 'rxjs';
|
||||
import { AfterViewInit, Component, OnDestroy, ViewChild } from '@angular/core';
|
||||
import { ActivatedRouteSnapshot } from '@angular/router';
|
||||
import { CorePageItemsListManager } from '@classes/page-items-list-manager';
|
||||
|
||||
import { CoreDomUtils } from '@services/utils/dom';
|
||||
import { CoreSplitViewComponent } from '@components/split-view/split-view';
|
||||
import { CoreGrades } from '@features/grades/services/grades';
|
||||
import { CoreGradesHelper, CoreGradesGradeOverviewWithCourseData } from '@features/grades/services/grades-helper';
|
||||
import { CoreNavigator } from '@services/navigator';
|
||||
import { CoreScreen } from '@services/screen';
|
||||
import { CoreGradesGradeOverviewWithCourseData, CoreGradesHelper } from '@features/grades/services/grades-helper';
|
||||
import { IonRefresher } from '@ionic/angular';
|
||||
import { CoreDomUtils } from '@services/utils/dom';
|
||||
import { CoreUtils } from '@services/utils/utils';
|
||||
import { ActivatedRoute } from '@angular/router';
|
||||
|
||||
/**
|
||||
* Page that displays courses grades (main menu option).
|
||||
|
@ -31,113 +30,92 @@ import { ActivatedRoute } from '@angular/router';
|
|||
selector: 'page-core-grades-courses',
|
||||
templateUrl: 'courses.html',
|
||||
})
|
||||
export class CoreGradesCoursesPage implements OnInit, OnDestroy {
|
||||
export class CoreGradesCoursesPage implements OnDestroy, AfterViewInit {
|
||||
|
||||
grades?: CoreGradesGradeOverviewWithCourseData[];
|
||||
gradesLoaded = false;
|
||||
activeCourseId?: number;
|
||||
layoutSubscription?: Subscription;
|
||||
courses: CoreGradesCoursesManager = new CoreGradesCoursesManager(CoreGradesCoursesPage);
|
||||
|
||||
constructor(private route: ActivatedRoute) {}
|
||||
@ViewChild(CoreSplitViewComponent) splitView!: CoreSplitViewComponent;
|
||||
|
||||
/**
|
||||
* @inheritdoc
|
||||
*/
|
||||
async ngOnInit(): Promise<void> {
|
||||
this.layoutSubscription = CoreScreen.instance.layoutObservable.subscribe(() => this.updateActiveCourse());
|
||||
this.updateActiveCourse();
|
||||
async ngAfterViewInit(): Promise<void> {
|
||||
await this.fetchInitialCourses();
|
||||
|
||||
await this.fetchGrades();
|
||||
|
||||
if (!CoreScreen.instance.isMobile && !this.activeCourseId && this.grades && this.grades.length > 0) {
|
||||
this.openCourse(this.grades[0].courseid);
|
||||
}
|
||||
|
||||
// Add log in Moodle.
|
||||
await CoreUtils.instance.ignoreErrors(CoreGrades.instance.logCoursesGradesView());
|
||||
}
|
||||
|
||||
/**
|
||||
* @inheritdoc
|
||||
*/
|
||||
ionViewWillEnter(): void {
|
||||
this.updateActiveCourse();
|
||||
this.courses.watchSplitViewOutlet(this.splitView);
|
||||
this.courses.start();
|
||||
}
|
||||
|
||||
/**
|
||||
* @inheritdoc
|
||||
*/
|
||||
ngOnDestroy(): void {
|
||||
this.layoutSubscription?.unsubscribe();
|
||||
this.courses.destroy();
|
||||
}
|
||||
|
||||
/**
|
||||
* Fetch all the data required for the view.
|
||||
*/
|
||||
async fetchGrades(): Promise<void> {
|
||||
try {
|
||||
const grades = await CoreGrades.instance.getCoursesGrades();
|
||||
const gradesWithCourseData = await CoreGradesHelper.instance.getGradesCourseData(grades);
|
||||
|
||||
this.grades = gradesWithCourseData;
|
||||
} catch (error) {
|
||||
CoreDomUtils.instance.showErrorModalDefault(error, 'Error loading grades');
|
||||
|
||||
this.grades = [];
|
||||
} finally {
|
||||
this.gradesLoaded = true;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Refresh data.
|
||||
* Refresh courses.
|
||||
*
|
||||
* @param refresher Refresher.
|
||||
*/
|
||||
async refreshGrades(refresher: IonRefresher): Promise<void> {
|
||||
async refreshCourses(refresher: IonRefresher): Promise<void> {
|
||||
await CoreUtils.instance.ignoreErrors(CoreGrades.instance.invalidateCoursesGradesData());
|
||||
await CoreUtils.instance.ignoreErrors(this.fetchGrades());
|
||||
await CoreUtils.instance.ignoreErrors(this.fetchCourses());
|
||||
|
||||
refresher.complete();
|
||||
refresher?.complete();
|
||||
}
|
||||
|
||||
/**
|
||||
* Navigate to the grades of the selected course.
|
||||
*
|
||||
* @param courseId Course Id where to navigate.
|
||||
* Obtain the initial list of courses.
|
||||
*/
|
||||
async openCourse(courseId: number): Promise<void> {
|
||||
const path = this.activeCourseId ? `../${courseId}` : courseId.toString();
|
||||
private async fetchInitialCourses(): Promise<void> {
|
||||
try {
|
||||
await this.fetchCourses();
|
||||
} catch (error) {
|
||||
CoreDomUtils.instance.showErrorModalDefault(error, 'Error loading courses');
|
||||
|
||||
await CoreNavigator.instance.navigate(path);
|
||||
|
||||
this.updateActiveCourse(courseId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Update active course.
|
||||
*
|
||||
* @param activeCourseId Active course id.
|
||||
*/
|
||||
private updateActiveCourse(activeCourseId?: number): void {
|
||||
if (CoreScreen.instance.isMobile) {
|
||||
delete this.activeCourseId;
|
||||
|
||||
return;
|
||||
this.courses.setItems([]);
|
||||
}
|
||||
|
||||
this.activeCourseId = activeCourseId ?? this.guessActiveCourse();
|
||||
}
|
||||
|
||||
/**
|
||||
* Guess active course looking at the current route.
|
||||
*
|
||||
* @return Active course id.
|
||||
* Update the list of courses.
|
||||
*/
|
||||
private guessActiveCourse(): number | undefined {
|
||||
const courseId = parseInt(this.route.snapshot?.firstChild?.params.courseId);
|
||||
private async fetchCourses(): Promise<void> {
|
||||
const grades = await CoreGrades.instance.getCoursesGrades();
|
||||
const courses = await CoreGradesHelper.instance.getGradesCourseData(grades);
|
||||
|
||||
return isNaN(courseId) ? undefined : courseId;
|
||||
this.courses.setItems(courses);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Helper class to manage courses.
|
||||
*/
|
||||
class CoreGradesCoursesManager extends CorePageItemsListManager<CoreGradesGradeOverviewWithCourseData> {
|
||||
|
||||
/**
|
||||
* @inheritdoc
|
||||
*/
|
||||
protected getItemPath(courseGrade: CoreGradesGradeOverviewWithCourseData): string {
|
||||
return courseGrade.courseid.toString();
|
||||
}
|
||||
|
||||
/**
|
||||
* @inheritdoc
|
||||
*/
|
||||
protected getSelectedItemPath(route: ActivatedRouteSnapshot): string | null {
|
||||
const courseId = parseInt(route?.params.courseId);
|
||||
|
||||
return isNaN(courseId) ? null : courseId.toString();
|
||||
}
|
||||
|
||||
/**
|
||||
* @inheritdoc
|
||||
*/
|
||||
protected async logActivity(): Promise<void> {
|
||||
await CoreGrades.instance.logCoursesGradesView();
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -38,9 +38,9 @@ export class CoreGradesGradePage implements OnInit {
|
|||
gradeLoaded = false;
|
||||
|
||||
constructor(route: ActivatedRoute) {
|
||||
this.courseId = route.snapshot.params.courseId ?? route.snapshot.parent?.params.courseId;
|
||||
this.gradeId = route.snapshot.params.gradeId;
|
||||
this.userId = route.snapshot.queryParams.userId ?? CoreSites.instance.getCurrentSiteUserId();
|
||||
this.courseId = parseInt(route.snapshot.params.courseId ?? route.snapshot.parent?.params.courseId);
|
||||
this.gradeId = parseInt(route.snapshot.params.gradeId);
|
||||
this.userId = parseInt(route.snapshot.queryParams.userId ?? CoreSites.instance.getCurrentSiteUserId());
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -144,9 +144,9 @@ export class CoreGradesHelperProvider {
|
|||
*/
|
||||
formatGradesTable(table: CoreGradesTable): CoreGradesFormattedTable {
|
||||
const maxDepth = table.maxdepth;
|
||||
const formatted: CoreGradesFormattedTable = {
|
||||
columns: [],
|
||||
rows: [],
|
||||
const formatted = {
|
||||
columns: [] as any[],
|
||||
rows: [] as any[],
|
||||
};
|
||||
|
||||
// Columns, in order.
|
||||
|
@ -673,9 +673,21 @@ export class CoreGradesHelper extends makeSingleton(CoreGradesHelperProvider) {}
|
|||
export type CoreGradesFormattedRow = any;
|
||||
export type CoreGradesFormattedRowForTable = any;
|
||||
export type CoreGradesFormattedItem = any;
|
||||
export type CoreGradesFormattedTableColumn = any;
|
||||
export type CoreGradesFormattedTableRow = CoreGradesFormattedTableRowFilled | CoreGradesFormattedTableRowEmpty;
|
||||
export type CoreGradesFormattedTable = {
|
||||
columns: any[];
|
||||
rows: any[];
|
||||
columns: CoreGradesFormattedTableColumn[];
|
||||
rows: CoreGradesFormattedTableRow[];
|
||||
};
|
||||
export type CoreGradesFormattedTableRowFilled = {
|
||||
// @todo complete types.
|
||||
id: number;
|
||||
itemtype: 'category' | 'leader';
|
||||
grade: unknown;
|
||||
percentage: unknown;
|
||||
};
|
||||
type CoreGradesFormattedTableRowEmpty ={
|
||||
//
|
||||
};
|
||||
|
||||
/**
|
||||
|
|
Loading…
Reference in New Issue