MOBILE-2376 siteplugins: Support quiz access rules
parent
bf658df6b4
commit
d7dd3acd8e
|
@ -24,6 +24,7 @@ import { FormGroup, FormBuilder } from '@angular/forms';
|
||||||
})
|
})
|
||||||
export class AddonModQuizAccessOfflineAttemptsComponent implements OnInit {
|
export class AddonModQuizAccessOfflineAttemptsComponent implements OnInit {
|
||||||
|
|
||||||
|
@Input() rule: string; // The name of the rule.
|
||||||
@Input() quiz: any; // The quiz the rule belongs to.
|
@Input() quiz: any; // The quiz the rule belongs to.
|
||||||
@Input() attempt: any; // The attempt being started/continued.
|
@Input() attempt: any; // The attempt being started/continued.
|
||||||
@Input() prefetch: boolean; // Whether the user is prefetching the quiz.
|
@Input() prefetch: boolean; // Whether the user is prefetching the quiz.
|
||||||
|
|
|
@ -24,6 +24,7 @@ import { FormGroup, FormBuilder } from '@angular/forms';
|
||||||
})
|
})
|
||||||
export class AddonModQuizAccessPasswordComponent implements OnInit {
|
export class AddonModQuizAccessPasswordComponent implements OnInit {
|
||||||
|
|
||||||
|
@Input() rule: string; // The name of the rule.
|
||||||
@Input() quiz: any; // The quiz the rule belongs to.
|
@Input() quiz: any; // The quiz the rule belongs to.
|
||||||
@Input() attempt: any; // The attempt being started/continued.
|
@Input() attempt: any; // The attempt being started/continued.
|
||||||
@Input() prefetch: boolean; // Whether the user is prefetching the quiz.
|
@Input() prefetch: boolean; // Whether the user is prefetching the quiz.
|
||||||
|
|
|
@ -24,6 +24,7 @@ import { FormGroup } from '@angular/forms';
|
||||||
})
|
})
|
||||||
export class AddonModQuizAccessTimeLimitComponent {
|
export class AddonModQuizAccessTimeLimitComponent {
|
||||||
|
|
||||||
|
@Input() rule: string; // The name of the rule.
|
||||||
@Input() quiz: any; // The quiz the rule belongs to.
|
@Input() quiz: any; // The quiz the rule belongs to.
|
||||||
@Input() attempt: any; // The attempt being started/continued.
|
@Input() attempt: any; // The attempt being started/continued.
|
||||||
@Input() prefetch: boolean; // Whether the user is prefetching the quiz.
|
@Input() prefetch: boolean; // Whether the user is prefetching the quiz.
|
||||||
|
|
|
@ -12,8 +12,8 @@
|
||||||
<core-loading [hideUntil]="loaded">
|
<core-loading [hideUntil]="loaded">
|
||||||
<form ion-list [formGroup]="preflightForm" (ngSubmit)="sendData()">
|
<form ion-list [formGroup]="preflightForm" (ngSubmit)="sendData()">
|
||||||
<!-- Access rules. -->
|
<!-- Access rules. -->
|
||||||
<ng-container *ngFor="let componentClass of accessRulesComponent; let last = last">
|
<ng-container *ngFor="let data of accessRulesData; let last = last">
|
||||||
<core-dynamic-component [component]="componentClass" [data]="data">
|
<core-dynamic-component [component]="data.component" [data]="data.data">
|
||||||
<p padding>Couldn't find the directive to render this access rule.</p>
|
<p padding>Couldn't find the directive to render this access rule.</p>
|
||||||
</core-dynamic-component>
|
</core-dynamic-component>
|
||||||
<ion-item-divider color="light" *ngIf="!last"></ion-item-divider>
|
<ion-item-divider color="light" *ngIf="!last"></ion-item-divider>
|
||||||
|
|
|
@ -34,8 +34,7 @@ export class AddonModQuizPreflightModalPage implements OnInit {
|
||||||
|
|
||||||
preflightForm: FormGroup;
|
preflightForm: FormGroup;
|
||||||
title: string;
|
title: string;
|
||||||
accessRulesComponent: any[] = [];
|
accessRulesData: {component: any, data: any}[] = []; // Components and data for each access rule.
|
||||||
data: any;
|
|
||||||
loaded: boolean;
|
loaded: boolean;
|
||||||
|
|
||||||
protected quiz: any;
|
protected quiz: any;
|
||||||
|
@ -43,7 +42,6 @@ export class AddonModQuizPreflightModalPage implements OnInit {
|
||||||
protected prefetch: boolean;
|
protected prefetch: boolean;
|
||||||
protected siteId: string;
|
protected siteId: string;
|
||||||
protected rules: string[];
|
protected rules: string[];
|
||||||
protected renderedRules: string[] = [];
|
|
||||||
|
|
||||||
constructor(params: NavParams, fb: FormBuilder, translate: TranslateService, sitesProvider: CoreSitesProvider,
|
constructor(params: NavParams, fb: FormBuilder, translate: TranslateService, sitesProvider: CoreSitesProvider,
|
||||||
protected viewCtrl: ViewController, protected accessRuleDelegate: AddonModQuizAccessRuleDelegate,
|
protected viewCtrl: ViewController, protected accessRuleDelegate: AddonModQuizAccessRuleDelegate,
|
||||||
|
@ -58,15 +56,6 @@ export class AddonModQuizPreflightModalPage implements OnInit {
|
||||||
|
|
||||||
// Create an empty form group. The controls will be added by the access rules components.
|
// Create an empty form group. The controls will be added by the access rules components.
|
||||||
this.preflightForm = fb.group({});
|
this.preflightForm = fb.group({});
|
||||||
|
|
||||||
// Create the data to pass to the access rules components.
|
|
||||||
this.data = {
|
|
||||||
quiz: this.quiz,
|
|
||||||
attempt: this.attempt,
|
|
||||||
prefetch: this.prefetch,
|
|
||||||
form: this.preflightForm,
|
|
||||||
siteId: this.siteId
|
|
||||||
};
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -83,8 +72,17 @@ export class AddonModQuizPreflightModalPage implements OnInit {
|
||||||
if (required) {
|
if (required) {
|
||||||
return this.accessRuleDelegate.getPreflightComponent(rule, this.injector).then((component) => {
|
return this.accessRuleDelegate.getPreflightComponent(rule, this.injector).then((component) => {
|
||||||
if (component) {
|
if (component) {
|
||||||
this.renderedRules.push(rule);
|
this.accessRulesData.push({
|
||||||
this.accessRulesComponent.push(component);
|
component: component,
|
||||||
|
data: {
|
||||||
|
rule: rule,
|
||||||
|
quiz: this.quiz,
|
||||||
|
attempt: this.attempt,
|
||||||
|
prefetch: this.prefetch,
|
||||||
|
form: this.preflightForm,
|
||||||
|
siteId: this.siteId
|
||||||
|
}
|
||||||
|
});
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
|
@ -78,6 +78,7 @@ import { CoreSitePluginsCourseFormatComponent } from '@core/siteplugins/componen
|
||||||
import { CoreSitePluginsQuestionComponent } from '@core/siteplugins/components/question/question';
|
import { CoreSitePluginsQuestionComponent } from '@core/siteplugins/components/question/question';
|
||||||
import { CoreSitePluginsQuestionBehaviourComponent } from '@core/siteplugins/components/question-behaviour/question-behaviour';
|
import { CoreSitePluginsQuestionBehaviourComponent } from '@core/siteplugins/components/question-behaviour/question-behaviour';
|
||||||
import { CoreSitePluginsUserProfileFieldComponent } from '@core/siteplugins/components/user-profile-field/user-profile-field';
|
import { CoreSitePluginsUserProfileFieldComponent } from '@core/siteplugins/components/user-profile-field/user-profile-field';
|
||||||
|
import { CoreSitePluginsQuizAccessRuleComponent } from '@core/siteplugins/components/quiz-access-rule/quiz-access-rule';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Service to provide functionalities regarding compiling dynamic HTML and Javascript.
|
* Service to provide functionalities regarding compiling dynamic HTML and Javascript.
|
||||||
|
@ -209,6 +210,7 @@ export class CoreCompileProvider {
|
||||||
instance['CoreSitePluginsQuestionComponent'] = CoreSitePluginsQuestionComponent;
|
instance['CoreSitePluginsQuestionComponent'] = CoreSitePluginsQuestionComponent;
|
||||||
instance['CoreSitePluginsQuestionBehaviourComponent'] = CoreSitePluginsQuestionBehaviourComponent;
|
instance['CoreSitePluginsQuestionBehaviourComponent'] = CoreSitePluginsQuestionBehaviourComponent;
|
||||||
instance['CoreSitePluginsUserProfileFieldComponent'] = CoreSitePluginsUserProfileFieldComponent;
|
instance['CoreSitePluginsUserProfileFieldComponent'] = CoreSitePluginsUserProfileFieldComponent;
|
||||||
|
instance['CoreSitePluginsQuizAccessRuleComponent'] = CoreSitePluginsQuizAccessRuleComponent;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
@ -15,7 +15,7 @@
|
||||||
import { Injector } from '@angular/core';
|
import { Injector } from '@angular/core';
|
||||||
import { CoreCourseFormatHandler } from '@core/course/providers/format-delegate';
|
import { CoreCourseFormatHandler } from '@core/course/providers/format-delegate';
|
||||||
import { CoreSitePluginsBaseHandler } from './base-handler';
|
import { CoreSitePluginsBaseHandler } from './base-handler';
|
||||||
import { CoreSitePluginsCourseFormatComponent } from '../components/course-format/course-format';
|
import { CoreSitePluginsCourseFormatComponent } from '../../components/course-format/course-format';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Handler to support a course format using a site plugin.
|
* Handler to support a course format using a site plugin.
|
|
@ -13,10 +13,10 @@
|
||||||
// limitations under the License.
|
// limitations under the License.
|
||||||
|
|
||||||
import { Injector } from '@angular/core';
|
import { Injector } from '@angular/core';
|
||||||
import { CoreSitePluginsProvider } from '../providers/siteplugins';
|
import { CoreSitePluginsProvider } from '../../providers/siteplugins';
|
||||||
import { CoreCourseOptionsHandler, CoreCourseOptionsHandlerData } from '@core/course/providers/options-delegate';
|
import { CoreCourseOptionsHandler, CoreCourseOptionsHandlerData } from '@core/course/providers/options-delegate';
|
||||||
import { CoreSitePluginsBaseHandler } from './base-handler';
|
import { CoreSitePluginsBaseHandler } from './base-handler';
|
||||||
import { CoreSitePluginsCourseOptionComponent } from '../components/course-option/course-option';
|
import { CoreSitePluginsCourseOptionComponent } from '../../components/course-option/course-option';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Handler to display a site plugin in course options.
|
* Handler to display a site plugin in course options.
|
|
@ -16,7 +16,7 @@ import { Injector } from '@angular/core';
|
||||||
import { NavController, NavOptions } from 'ionic-angular';
|
import { NavController, NavOptions } from 'ionic-angular';
|
||||||
import { CoreCourseModuleHandler, CoreCourseModuleHandlerData } from '@core/course/providers/module-delegate';
|
import { CoreCourseModuleHandler, CoreCourseModuleHandlerData } from '@core/course/providers/module-delegate';
|
||||||
import { CoreSitePluginsBaseHandler } from './base-handler';
|
import { CoreSitePluginsBaseHandler } from './base-handler';
|
||||||
import { CoreSitePluginsModuleIndexComponent } from '../components/module-index/module-index';
|
import { CoreSitePluginsModuleIndexComponent } from '../../components/module-index/module-index';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Handler to support a module using a site plugin.
|
* Handler to support a module using a site plugin.
|
|
@ -13,7 +13,7 @@
|
||||||
// limitations under the License.
|
// limitations under the License.
|
||||||
|
|
||||||
import { Injector } from '@angular/core';
|
import { Injector } from '@angular/core';
|
||||||
import { CoreSitePluginsProvider } from '../providers/siteplugins';
|
import { CoreSitePluginsProvider } from '../../providers/siteplugins';
|
||||||
import { CoreCourseModulePrefetchHandlerBase } from '@core/course/classes/module-prefetch-handler';
|
import { CoreCourseModulePrefetchHandlerBase } from '@core/course/classes/module-prefetch-handler';
|
||||||
|
|
||||||
/**
|
/**
|
|
@ -14,7 +14,7 @@
|
||||||
|
|
||||||
import { Injector } from '@angular/core';
|
import { Injector } from '@angular/core';
|
||||||
import { CoreQuestionBehaviourDefaultHandler } from '@core/question/providers/default-behaviour-handler';
|
import { CoreQuestionBehaviourDefaultHandler } from '@core/question/providers/default-behaviour-handler';
|
||||||
import { CoreSitePluginsQuestionBehaviourComponent } from '../components/question-behaviour/question-behaviour';
|
import { CoreSitePluginsQuestionBehaviourComponent } from '../../components/question-behaviour/question-behaviour';
|
||||||
import { CoreQuestionProvider } from '@core/question/providers/question';
|
import { CoreQuestionProvider } from '@core/question/providers/question';
|
||||||
|
|
||||||
/**
|
/**
|
|
@ -14,7 +14,7 @@
|
||||||
|
|
||||||
import { Injector } from '@angular/core';
|
import { Injector } from '@angular/core';
|
||||||
import { CoreQuestionDefaultHandler } from '@core/question/providers/default-question-handler';
|
import { CoreQuestionDefaultHandler } from '@core/question/providers/default-question-handler';
|
||||||
import { CoreSitePluginsQuestionComponent } from '../components/question/question';
|
import { CoreSitePluginsQuestionComponent } from '../../components/question/question';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Handler to display a question site plugin.
|
* Handler to display a question site plugin.
|
|
@ -0,0 +1,110 @@
|
||||||
|
// (C) Copyright 2015 Martin Dougiamas
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
|
||||||
|
import { Injector } from '@angular/core';
|
||||||
|
import { CoreQuestionDefaultHandler } from '@core/question/providers/default-question-handler';
|
||||||
|
import { CoreSitePluginsQuizAccessRuleComponent } from '../../components/quiz-access-rule/quiz-access-rule';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handler to display a quiz access rule site plugin.
|
||||||
|
*/
|
||||||
|
export class CoreSitePluginsQuizAccessRuleHandler extends CoreQuestionDefaultHandler {
|
||||||
|
|
||||||
|
constructor(public name: string, public ruleName: string, public hasTemplate: boolean) {
|
||||||
|
super();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Whether the rule requires a preflight check when prefetch/start/continue an attempt.
|
||||||
|
*
|
||||||
|
* @param {any} quiz The quiz the rule belongs to.
|
||||||
|
* @param {any} [attempt] The attempt started/continued. If not supplied, user is starting a new attempt.
|
||||||
|
* @param {boolean} [prefetch] Whether the user is prefetching the quiz.
|
||||||
|
* @param {string} [siteId] Site ID. If not defined, current site.
|
||||||
|
* @return {boolean|Promise<boolean>} Whether the rule requires a preflight check.
|
||||||
|
*/
|
||||||
|
isPreflightCheckRequired(quiz: any, attempt?: any, prefetch?: boolean, siteId?: string): boolean | Promise<boolean> {
|
||||||
|
return this.hasTemplate;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Add preflight data that doesn't require user interaction. The data should be added to the preflightData param.
|
||||||
|
*
|
||||||
|
* @param {any} quiz The quiz the rule belongs to.
|
||||||
|
* @param {any} preflightData Object where to add the preflight data.
|
||||||
|
* @param {any} [attempt] The attempt started/continued. If not supplied, user is starting a new attempt.
|
||||||
|
* @param {boolean} [prefetch] Whether the user is prefetching the quiz.
|
||||||
|
* @param {string} [siteId] Site ID. If not defined, current site.
|
||||||
|
* @return {void|Promise<any>} Promise resolved when done if async, void if it's synchronous.
|
||||||
|
*/
|
||||||
|
getFixedPreflightData(quiz: any, preflightData: any, attempt?: any, prefetch?: boolean, siteId?: string): void | Promise<any> {
|
||||||
|
// Nothing to do.
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Return the Component to use to display the access rule preflight.
|
||||||
|
* Implement this if your access rule requires a preflight check with user interaction.
|
||||||
|
* It's recommended to return the class of the component, but you can also return an instance of the component.
|
||||||
|
*
|
||||||
|
* @param {Injector} injector Injector.
|
||||||
|
* @return {any|Promise<any>} The component (or promise resolved with component) to use, undefined if not found.
|
||||||
|
*/
|
||||||
|
getPreflightComponent(injector: Injector): any | Promise<any> {
|
||||||
|
if (this.hasTemplate) {
|
||||||
|
return CoreSitePluginsQuizAccessRuleComponent;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function called when the preflight check has passed. This is a chance to record that fact in some way.
|
||||||
|
*
|
||||||
|
* @param {any} quiz The quiz the rule belongs to.
|
||||||
|
* @param {any} attempt The attempt started/continued.
|
||||||
|
* @param {any} preflightData Preflight data gathered.
|
||||||
|
* @param {boolean} [prefetch] Whether the user is prefetching the quiz.
|
||||||
|
* @param {string} [siteId] Site ID. If not defined, current site.
|
||||||
|
* @return {void|Promise<any>} Promise resolved when done if async, void if it's synchronous.
|
||||||
|
*/
|
||||||
|
notifyPreflightCheckPassed(quiz: any, attempt: any, preflightData: any, prefetch?: boolean, siteId?: string)
|
||||||
|
: void | Promise<any> {
|
||||||
|
// Nothing to do.
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Function called when the preflight check fails. This is a chance to record that fact in some way.
|
||||||
|
*
|
||||||
|
* @param {any} quiz The quiz the rule belongs to.
|
||||||
|
* @param {any} attempt The attempt started/continued.
|
||||||
|
* @param {any} preflightData Preflight data gathered.
|
||||||
|
* @param {boolean} [prefetch] Whether the user is prefetching the quiz.
|
||||||
|
* @param {string} [siteId] Site ID. If not defined, current site.
|
||||||
|
* @return {void|Promise<any>} Promise resolved when done if async, void if it's synchronous.
|
||||||
|
*/
|
||||||
|
notifyPreflightCheckFailed(quiz: any, attempt: any, preflightData: any, prefetch?: boolean, siteId?: string)
|
||||||
|
: void | Promise<any> {
|
||||||
|
// Nothing to do.
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Whether or not the time left of an attempt should be displayed.
|
||||||
|
*
|
||||||
|
* @param {any} attempt The attempt.
|
||||||
|
* @param {number} endTime The attempt end time (in seconds).
|
||||||
|
* @param {number} timeNow The current time in seconds.
|
||||||
|
* @return {boolean} Whether it should be displayed.
|
||||||
|
*/
|
||||||
|
shouldShowTimeLeft(attempt: any, endTime: number, timeNow: number): boolean {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
|
@ -14,7 +14,7 @@
|
||||||
|
|
||||||
import { NavController } from 'ionic-angular';
|
import { NavController } from 'ionic-angular';
|
||||||
import { CoreUserDelegate, CoreUserProfileHandler, CoreUserProfileHandlerData } from '@core/user/providers/user-delegate';
|
import { CoreUserDelegate, CoreUserProfileHandler, CoreUserProfileHandlerData } from '@core/user/providers/user-delegate';
|
||||||
import { CoreSitePluginsProvider } from '../providers/siteplugins';
|
import { CoreSitePluginsProvider } from '../../providers/siteplugins';
|
||||||
import { CoreSitePluginsBaseHandler } from './base-handler';
|
import { CoreSitePluginsBaseHandler } from './base-handler';
|
||||||
|
|
||||||
/**
|
/**
|
|
@ -15,7 +15,7 @@
|
||||||
import { Injector } from '@angular/core';
|
import { Injector } from '@angular/core';
|
||||||
import { CoreUserProfileFieldHandler, CoreUserProfileFieldHandlerData } from '@core/user/providers/user-profile-field-delegate';
|
import { CoreUserProfileFieldHandler, CoreUserProfileFieldHandlerData } from '@core/user/providers/user-profile-field-delegate';
|
||||||
import { CoreSitePluginsBaseHandler } from './base-handler';
|
import { CoreSitePluginsBaseHandler } from './base-handler';
|
||||||
import { CoreSitePluginsUserProfileFieldComponent } from '../components/user-profile-field/user-profile-field';
|
import { CoreSitePluginsUserProfileFieldComponent } from '../../components/user-profile-field/user-profile-field';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Handler to display a site plugin in the user profile.
|
* Handler to display a site plugin in the user profile.
|
|
@ -25,6 +25,7 @@ import { CoreSitePluginsCourseFormatComponent } from './course-format/course-for
|
||||||
import { CoreSitePluginsUserProfileFieldComponent } from './user-profile-field/user-profile-field';
|
import { CoreSitePluginsUserProfileFieldComponent } from './user-profile-field/user-profile-field';
|
||||||
import { CoreSitePluginsQuestionComponent } from './question/question';
|
import { CoreSitePluginsQuestionComponent } from './question/question';
|
||||||
import { CoreSitePluginsQuestionBehaviourComponent } from './question-behaviour/question-behaviour';
|
import { CoreSitePluginsQuestionBehaviourComponent } from './question-behaviour/question-behaviour';
|
||||||
|
import { CoreSitePluginsQuizAccessRuleComponent } from './quiz-access-rule/quiz-access-rule';
|
||||||
|
|
||||||
@NgModule({
|
@NgModule({
|
||||||
declarations: [
|
declarations: [
|
||||||
|
@ -34,7 +35,8 @@ import { CoreSitePluginsQuestionBehaviourComponent } from './question-behaviour/
|
||||||
CoreSitePluginsCourseFormatComponent,
|
CoreSitePluginsCourseFormatComponent,
|
||||||
CoreSitePluginsUserProfileFieldComponent,
|
CoreSitePluginsUserProfileFieldComponent,
|
||||||
CoreSitePluginsQuestionComponent,
|
CoreSitePluginsQuestionComponent,
|
||||||
CoreSitePluginsQuestionBehaviourComponent
|
CoreSitePluginsQuestionBehaviourComponent,
|
||||||
|
CoreSitePluginsQuizAccessRuleComponent
|
||||||
],
|
],
|
||||||
imports: [
|
imports: [
|
||||||
CommonModule,
|
CommonModule,
|
||||||
|
@ -52,7 +54,8 @@ import { CoreSitePluginsQuestionBehaviourComponent } from './question-behaviour/
|
||||||
CoreSitePluginsCourseFormatComponent,
|
CoreSitePluginsCourseFormatComponent,
|
||||||
CoreSitePluginsUserProfileFieldComponent,
|
CoreSitePluginsUserProfileFieldComponent,
|
||||||
CoreSitePluginsQuestionComponent,
|
CoreSitePluginsQuestionComponent,
|
||||||
CoreSitePluginsQuestionBehaviourComponent
|
CoreSitePluginsQuestionBehaviourComponent,
|
||||||
|
CoreSitePluginsQuizAccessRuleComponent
|
||||||
],
|
],
|
||||||
entryComponents: [
|
entryComponents: [
|
||||||
CoreSitePluginsModuleIndexComponent,
|
CoreSitePluginsModuleIndexComponent,
|
||||||
|
@ -60,7 +63,8 @@ import { CoreSitePluginsQuestionBehaviourComponent } from './question-behaviour/
|
||||||
CoreSitePluginsCourseFormatComponent,
|
CoreSitePluginsCourseFormatComponent,
|
||||||
CoreSitePluginsUserProfileFieldComponent,
|
CoreSitePluginsUserProfileFieldComponent,
|
||||||
CoreSitePluginsQuestionComponent,
|
CoreSitePluginsQuestionComponent,
|
||||||
CoreSitePluginsQuestionBehaviourComponent
|
CoreSitePluginsQuestionBehaviourComponent,
|
||||||
|
CoreSitePluginsQuizAccessRuleComponent
|
||||||
]
|
]
|
||||||
})
|
})
|
||||||
export class CoreSitePluginsComponentsModule {}
|
export class CoreSitePluginsComponentsModule {}
|
||||||
|
|
|
@ -0,0 +1 @@
|
||||||
|
<core-compile-html [text]="content" [jsData]="jsData" (created)="componentCreated($event)"></core-compile-html>
|
|
@ -0,0 +1,57 @@
|
||||||
|
// (C) Copyright 2015 Martin Dougiamas
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
|
||||||
|
import { Component, OnInit, Input } from '@angular/core';
|
||||||
|
import { CoreSitePluginsProvider } from '../../providers/siteplugins';
|
||||||
|
import { CoreSitePluginsCompileInitComponent } from '../../classes/compile-init-component';
|
||||||
|
import { FormGroup } from '@angular/forms';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Component that displays a quiz access rule created using a site plugin.
|
||||||
|
*/
|
||||||
|
@Component({
|
||||||
|
selector: 'core-site-plugins-quiz-access-rule',
|
||||||
|
templateUrl: 'quiz-access-rule.html',
|
||||||
|
})
|
||||||
|
export class CoreSitePluginsQuizAccessRuleComponent extends CoreSitePluginsCompileInitComponent implements OnInit {
|
||||||
|
@Input() rule: string; // The name of the rule.
|
||||||
|
@Input() quiz: any; // The quiz the rule belongs to.
|
||||||
|
@Input() attempt: any; // The attempt being started/continued.
|
||||||
|
@Input() prefetch: boolean; // Whether the user is prefetching the quiz.
|
||||||
|
@Input() siteId: string; // Site ID.
|
||||||
|
@Input() form: FormGroup; // Form where to add the form control.
|
||||||
|
|
||||||
|
constructor(sitePluginsProvider: CoreSitePluginsProvider) {
|
||||||
|
super(sitePluginsProvider);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Component being initialized.
|
||||||
|
*/
|
||||||
|
ngOnInit(): void {
|
||||||
|
// Pass the input and output data to the component.
|
||||||
|
this.jsData = {
|
||||||
|
rule: this.rule,
|
||||||
|
quiz: this.quiz,
|
||||||
|
attempt: this.attempt,
|
||||||
|
prefetch: this.prefetch,
|
||||||
|
siteId: this.siteId,
|
||||||
|
form: this.form
|
||||||
|
};
|
||||||
|
|
||||||
|
if (this.rule) {
|
||||||
|
this.getHandlerData(this.rule);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -39,19 +39,21 @@ import { CoreSettingsDelegate } from '@core/settings/providers/delegate';
|
||||||
import { CoreQuestionDelegate } from '@core/question/providers/delegate';
|
import { CoreQuestionDelegate } from '@core/question/providers/delegate';
|
||||||
import { CoreQuestionBehaviourDelegate } from '@core/question/providers/behaviour-delegate';
|
import { CoreQuestionBehaviourDelegate } from '@core/question/providers/behaviour-delegate';
|
||||||
import { AddonMessageOutputDelegate } from '@addon/messageoutput/providers/delegate';
|
import { AddonMessageOutputDelegate } from '@addon/messageoutput/providers/delegate';
|
||||||
|
import { AddonModQuizAccessRuleDelegate } from '@addon/mod/quiz/providers/access-rules-delegate';
|
||||||
|
|
||||||
// Handler classes.
|
// Handler classes.
|
||||||
import { CoreSitePluginsCourseFormatHandler } from '../classes/course-format-handler';
|
import { CoreSitePluginsCourseFormatHandler } from '../classes/handlers/course-format-handler';
|
||||||
import { CoreSitePluginsCourseOptionHandler } from '../classes/course-option-handler';
|
import { CoreSitePluginsCourseOptionHandler } from '../classes/handlers/course-option-handler';
|
||||||
import { CoreSitePluginsModuleHandler } from '../classes/module-handler';
|
import { CoreSitePluginsModuleHandler } from '../classes/handlers/module-handler';
|
||||||
import { CoreSitePluginsModulePrefetchHandler } from '../classes/module-prefetch-handler';
|
import { CoreSitePluginsModulePrefetchHandler } from '../classes/handlers/module-prefetch-handler';
|
||||||
import { CoreSitePluginsMainMenuHandler } from '../classes/main-menu-handler';
|
import { CoreSitePluginsMainMenuHandler } from '../classes/handlers/main-menu-handler';
|
||||||
import { CoreSitePluginsUserProfileHandler } from '../classes/user-handler';
|
import { CoreSitePluginsUserProfileHandler } from '../classes/handlers/user-handler';
|
||||||
import { CoreSitePluginsUserProfileFieldHandler } from '../classes/user-profile-field-handler';
|
import { CoreSitePluginsUserProfileFieldHandler } from '../classes/handlers/user-profile-field-handler';
|
||||||
import { CoreSitePluginsSettingsHandler } from '../classes/settings-handler';
|
import { CoreSitePluginsSettingsHandler } from '../classes/handlers/settings-handler';
|
||||||
import { CoreSitePluginsQuestionHandler } from '../classes/question-handler';
|
import { CoreSitePluginsQuestionHandler } from '../classes/handlers/question-handler';
|
||||||
import { CoreSitePluginsQuestionBehaviourHandler } from '../classes/question-behaviour-handler';
|
import { CoreSitePluginsQuestionBehaviourHandler } from '../classes/handlers/question-behaviour-handler';
|
||||||
import { CoreSitePluginsMessageOutputHandler } from '../classes/message-output-handler';
|
import { CoreSitePluginsMessageOutputHandler } from '../classes/handlers/message-output-handler';
|
||||||
|
import { CoreSitePluginsQuizAccessRuleHandler } from '../classes/handlers/quiz-access-rule-handler';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Helper service to provide functionalities regarding site plugins. It basically has the features to load and register site
|
* Helper service to provide functionalities regarding site plugins. It basically has the features to load and register site
|
||||||
|
@ -76,7 +78,8 @@ export class CoreSitePluginsHelperProvider {
|
||||||
private textUtils: CoreTextUtilsProvider, private filepoolProvider: CoreFilepoolProvider,
|
private textUtils: CoreTextUtilsProvider, private filepoolProvider: CoreFilepoolProvider,
|
||||||
private settingsDelegate: CoreSettingsDelegate, private questionDelegate: CoreQuestionDelegate,
|
private settingsDelegate: CoreSettingsDelegate, private questionDelegate: CoreQuestionDelegate,
|
||||||
private questionBehaviourDelegate: CoreQuestionBehaviourDelegate, private questionProvider: CoreQuestionProvider,
|
private questionBehaviourDelegate: CoreQuestionBehaviourDelegate, private questionProvider: CoreQuestionProvider,
|
||||||
private messageOutputDelegate: AddonMessageOutputDelegate) {
|
private messageOutputDelegate: AddonMessageOutputDelegate,
|
||||||
|
private accessRulesDelegate: AddonModQuizAccessRuleDelegate) {
|
||||||
|
|
||||||
this.logger = logger.getInstance('CoreSitePluginsHelperProvider');
|
this.logger = logger.getInstance('CoreSitePluginsHelperProvider');
|
||||||
|
|
||||||
|
@ -462,6 +465,10 @@ export class CoreSitePluginsHelperProvider {
|
||||||
promise = Promise.resolve(this.registerMessageOutputHandler(plugin, handlerName, handlerSchema, result));
|
promise = Promise.resolve(this.registerMessageOutputHandler(plugin, handlerName, handlerSchema, result));
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case 'AddonModQuizAccessRuleDelegate':
|
||||||
|
promise = Promise.resolve(this.registerQuizAccessRuleHandler(plugin, handlerName, handlerSchema, result));
|
||||||
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
// Nothing to do.
|
// Nothing to do.
|
||||||
promise = Promise.resolve();
|
promise = Promise.resolve();
|
||||||
|
@ -504,7 +511,7 @@ export class CoreSitePluginsHelperProvider {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Given a handler in an plugin, register it in the course options delegate.
|
* Given a handler in a plugin, register it in the course options delegate.
|
||||||
*
|
*
|
||||||
* @param {any} plugin Data of the plugin.
|
* @param {any} plugin Data of the plugin.
|
||||||
* @param {string} handlerName Name of the handler in the plugin.
|
* @param {string} handlerName Name of the handler in the plugin.
|
||||||
|
@ -533,7 +540,7 @@ export class CoreSitePluginsHelperProvider {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Given a handler in an plugin, register it in the main menu delegate.
|
* Given a handler in a plugin, register it in the main menu delegate.
|
||||||
*
|
*
|
||||||
* @param {any} plugin Data of the plugin.
|
* @param {any} plugin Data of the plugin.
|
||||||
* @param {string} handlerName Name of the handler in the plugin.
|
* @param {string} handlerName Name of the handler in the plugin.
|
||||||
|
@ -562,7 +569,7 @@ export class CoreSitePluginsHelperProvider {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Given a handler in an plugin, register it in the message output delegate.
|
* Given a handler in a plugin, register it in the message output delegate.
|
||||||
*
|
*
|
||||||
* @param {any} plugin Data of the plugin.
|
* @param {any} plugin Data of the plugin.
|
||||||
* @param {string} handlerName Name of the handler in the plugin.
|
* @param {string} handlerName Name of the handler in the plugin.
|
||||||
|
@ -592,7 +599,7 @@ export class CoreSitePluginsHelperProvider {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Given a handler in an plugin, register it in the module delegate.
|
* Given a handler in a plugin, register it in the module delegate.
|
||||||
*
|
*
|
||||||
* @param {any} plugin Data of the plugin.
|
* @param {any} plugin Data of the plugin.
|
||||||
* @param {string} handlerName Name of the handler in the plugin.
|
* @param {string} handlerName Name of the handler in the plugin.
|
||||||
|
@ -626,7 +633,7 @@ export class CoreSitePluginsHelperProvider {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Given a handler in an plugin, register it in the question delegate.
|
* Given a handler in a plugin, register it in the question delegate.
|
||||||
*
|
*
|
||||||
* @param {any} plugin Data of the plugin.
|
* @param {any} plugin Data of the plugin.
|
||||||
* @param {string} handlerName Name of the handler in the plugin.
|
* @param {string} handlerName Name of the handler in the plugin.
|
||||||
|
@ -675,7 +682,7 @@ export class CoreSitePluginsHelperProvider {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Given a handler in an plugin, register it in the question behaviour delegate.
|
* Given a handler in a plugin, register it in the question behaviour delegate.
|
||||||
*
|
*
|
||||||
* @param {any} plugin Data of the plugin.
|
* @param {any} plugin Data of the plugin.
|
||||||
* @param {string} handlerName Name of the handler in the plugin.
|
* @param {string} handlerName Name of the handler in the plugin.
|
||||||
|
@ -721,12 +728,61 @@ export class CoreSitePluginsHelperProvider {
|
||||||
|
|
||||||
return plugin.component;
|
return plugin.component;
|
||||||
}).catch((err) => {
|
}).catch((err) => {
|
||||||
this.logger.error('Error executing main method for question', handlerSchema.method, err);
|
this.logger.error('Error executing main method for question behaviour', handlerSchema.method, err);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Given a handler in an plugin, register it in the settings delegate.
|
* Given a handler in a plugin, register it in the quiz access rule delegate.
|
||||||
|
*
|
||||||
|
* @param {any} plugin Data of the plugin.
|
||||||
|
* @param {string} handlerName Name of the handler in the plugin.
|
||||||
|
* @param {any} handlerSchema Data about the handler.
|
||||||
|
* @param {any} initResult Result of the init WS call.
|
||||||
|
* @return {string|Promise<string>} A string (or a promise resolved with a string) to identify the handler.
|
||||||
|
*/
|
||||||
|
protected registerQuizAccessRuleHandler(plugin: any, handlerName: string, handlerSchema: any, initResult: any)
|
||||||
|
: string | Promise<string> {
|
||||||
|
if (!handlerSchema.method) {
|
||||||
|
// Required data not provided, stop.
|
||||||
|
this.logger.warn('Ignore site plugin because it doesn\'t provide method', plugin, handlerSchema);
|
||||||
|
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
this.logger.debug('Register site plugin in quiz access rule delegate:', plugin, handlerSchema, initResult);
|
||||||
|
|
||||||
|
// Execute the main method and its JS. The template returned will be used in the access rule component.
|
||||||
|
return this.executeMethodAndJS(plugin, handlerSchema.method).then((result) => {
|
||||||
|
// Create and register the handler.
|
||||||
|
const uniqueName = this.sitePluginsProvider.getHandlerUniqueName(plugin, handlerName),
|
||||||
|
ruleName = plugin.component,
|
||||||
|
ruleHandler = new CoreSitePluginsQuizAccessRuleHandler(uniqueName, ruleName, result.templates.length);
|
||||||
|
|
||||||
|
// Store in handlerSchema some data required by the component.
|
||||||
|
handlerSchema.methodTemplates = result.templates;
|
||||||
|
handlerSchema.methodJSResult = result.jsResult;
|
||||||
|
|
||||||
|
if (result && result.jsResult) {
|
||||||
|
// Override default handler functions with the result of the method JS.
|
||||||
|
for (const property in ruleHandler) {
|
||||||
|
if (property != 'constructor' && typeof ruleHandler[property] == 'function' &&
|
||||||
|
typeof result.jsResult[property] == 'function') {
|
||||||
|
ruleHandler[property] = result.jsResult[property].bind(ruleHandler);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
this.accessRulesDelegate.registerHandler(ruleHandler);
|
||||||
|
|
||||||
|
return ruleName;
|
||||||
|
}).catch((err) => {
|
||||||
|
this.logger.error('Error executing main method for quiz access rule', handlerSchema.method, err);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Given a handler in a plugin, register it in the settings delegate.
|
||||||
*
|
*
|
||||||
* @param {any} plugin Data of the plugin.
|
* @param {any} plugin Data of the plugin.
|
||||||
* @param {string} handlerName Name of the handler in the plugin.
|
* @param {string} handlerName Name of the handler in the plugin.
|
||||||
|
@ -755,7 +811,7 @@ export class CoreSitePluginsHelperProvider {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Given a handler in an plugin, register it in the user profile delegate.
|
* Given a handler in a plugin, register it in the user profile delegate.
|
||||||
*
|
*
|
||||||
* @param {any} plugin Data of the plugin.
|
* @param {any} plugin Data of the plugin.
|
||||||
* @param {string} handlerName Name of the handler in the plugin.
|
* @param {string} handlerName Name of the handler in the plugin.
|
||||||
|
@ -784,7 +840,7 @@ export class CoreSitePluginsHelperProvider {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Given a handler in an plugin, register it in the user profile field delegate.
|
* Given a handler in a plugin, register it in the user profile field delegate.
|
||||||
*
|
*
|
||||||
* @param {any} plugin Data of the plugin.
|
* @param {any} plugin Data of the plugin.
|
||||||
* @param {string} handlerName Name of the handler in the plugin.
|
* @param {string} handlerName Name of the handler in the plugin.
|
||||||
|
|
Loading…
Reference in New Issue