MOBILE-3620 filter: Implement filters addons
parent
487933cdc7
commit
aa60d8eaeb
|
@ -15,10 +15,12 @@
|
||||||
import { NgModule } from '@angular/core';
|
import { NgModule } from '@angular/core';
|
||||||
|
|
||||||
import { AddonPrivateFilesModule } from './privatefiles/privatefiles.module';
|
import { AddonPrivateFilesModule } from './privatefiles/privatefiles.module';
|
||||||
|
import { AddonFilterModule } from './filter/filter.module';
|
||||||
|
|
||||||
@NgModule({
|
@NgModule({
|
||||||
imports: [
|
imports: [
|
||||||
AddonPrivateFilesModule,
|
AddonPrivateFilesModule,
|
||||||
|
AddonFilterModule,
|
||||||
],
|
],
|
||||||
})
|
})
|
||||||
export class AddonsModule {}
|
export class AddonsModule {}
|
||||||
|
|
|
@ -0,0 +1,34 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { APP_INITIALIZER, NgModule } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDelegate } from '@features/filter/services/filter-delegate';
|
||||||
|
import { AddonFilterActivityNamesHandler } from './services/handlers/activitynames';
|
||||||
|
|
||||||
|
@NgModule({
|
||||||
|
declarations: [
|
||||||
|
],
|
||||||
|
imports: [
|
||||||
|
],
|
||||||
|
providers: [
|
||||||
|
{
|
||||||
|
provide: APP_INITIALIZER,
|
||||||
|
multi: true,
|
||||||
|
deps: [AddonFilterActivityNamesHandler],
|
||||||
|
useFactory: (handler: AddonFilterActivityNamesHandler) => () => CoreFilterDelegate.instance.registerHandler(handler),
|
||||||
|
},
|
||||||
|
],
|
||||||
|
})
|
||||||
|
export class AddonFilterActivityNamesModule {}
|
|
@ -0,0 +1,43 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { Injectable } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDefaultHandler } from '@features/filter/services/handlers/default-filter';
|
||||||
|
import { CoreFilterFormatTextOptions } from '@features/filter/services/filter';
|
||||||
|
import { CoreSite } from '@classes/site';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handler to support the Activity names filter.
|
||||||
|
*/
|
||||||
|
@Injectable({ providedIn: 'root' })
|
||||||
|
export class AddonFilterActivityNamesHandler extends CoreFilterDefaultHandler {
|
||||||
|
|
||||||
|
name = 'AddonFilterActivityNamesHandler';
|
||||||
|
filterName = 'activitynames';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Check if the filter should be applied in a certain site based on some filter options.
|
||||||
|
*
|
||||||
|
* @param options Options.
|
||||||
|
* @param site Site.
|
||||||
|
* @return Whether filter should be applied.
|
||||||
|
*/
|
||||||
|
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
||||||
|
shouldBeApplied(options: CoreFilterFormatTextOptions, site?: CoreSite): boolean {
|
||||||
|
// This filter is handled by Moodle, nothing to do in the app.
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,34 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { APP_INITIALIZER, NgModule } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDelegate } from '@features/filter/services/filter-delegate';
|
||||||
|
import { AddonFilterAlgebraHandler } from './services/handlers/algebra';
|
||||||
|
|
||||||
|
@NgModule({
|
||||||
|
declarations: [
|
||||||
|
],
|
||||||
|
imports: [
|
||||||
|
],
|
||||||
|
providers: [
|
||||||
|
{
|
||||||
|
provide: APP_INITIALIZER,
|
||||||
|
multi: true,
|
||||||
|
deps: [AddonFilterAlgebraHandler],
|
||||||
|
useFactory: (handler: AddonFilterAlgebraHandler) => () => CoreFilterDelegate.instance.registerHandler(handler),
|
||||||
|
},
|
||||||
|
],
|
||||||
|
})
|
||||||
|
export class AddonFilterAlgebraModule {}
|
|
@ -0,0 +1,43 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { Injectable } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDefaultHandler } from '@features/filter/services/handlers/default-filter';
|
||||||
|
import { CoreFilterFormatTextOptions } from '@features/filter/services/filter';
|
||||||
|
import { CoreSite } from '@classes/site';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handler to support the Algebra notation filter.
|
||||||
|
*/
|
||||||
|
@Injectable({ providedIn: 'root' })
|
||||||
|
export class AddonFilterAlgebraHandler extends CoreFilterDefaultHandler {
|
||||||
|
|
||||||
|
name = 'AddonFilterAlgebraHandler';
|
||||||
|
filterName = 'algebra';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Check if the filter should be applied in a certain site based on some filter options.
|
||||||
|
*
|
||||||
|
* @param options Options.
|
||||||
|
* @param site Site.
|
||||||
|
* @return Whether filter should be applied.
|
||||||
|
*/
|
||||||
|
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
||||||
|
shouldBeApplied(options: CoreFilterFormatTextOptions, site?: CoreSite): boolean {
|
||||||
|
// This filter is handled by Moodle, nothing to do in the app.
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,34 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { APP_INITIALIZER, NgModule } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDelegate } from '@features/filter/services/filter-delegate';
|
||||||
|
import { AddonFilterCensorHandler } from './services/handlers/censor';
|
||||||
|
|
||||||
|
@NgModule({
|
||||||
|
declarations: [
|
||||||
|
],
|
||||||
|
imports: [
|
||||||
|
],
|
||||||
|
providers: [
|
||||||
|
{
|
||||||
|
provide: APP_INITIALIZER,
|
||||||
|
multi: true,
|
||||||
|
deps: [AddonFilterCensorHandler],
|
||||||
|
useFactory: (handler: AddonFilterCensorHandler) => () => CoreFilterDelegate.instance.registerHandler(handler),
|
||||||
|
},
|
||||||
|
],
|
||||||
|
})
|
||||||
|
export class AddonFilterCensorModule {}
|
|
@ -0,0 +1,43 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { Injectable } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDefaultHandler } from '@features/filter/services/handlers/default-filter';
|
||||||
|
import { CoreFilterFormatTextOptions } from '@features/filter/services/filter';
|
||||||
|
import { CoreSite } from '@classes/site';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handler to support the Word censorship filter.
|
||||||
|
*/
|
||||||
|
@Injectable({ providedIn: 'root' })
|
||||||
|
export class AddonFilterCensorHandler extends CoreFilterDefaultHandler {
|
||||||
|
|
||||||
|
name = 'AddonFilterCensorHandler';
|
||||||
|
filterName = 'censor';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Check if the filter should be applied in a certain site based on some filter options.
|
||||||
|
*
|
||||||
|
* @param options Options.
|
||||||
|
* @param site Site.
|
||||||
|
* @return Whether filter should be applied.
|
||||||
|
*/
|
||||||
|
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
||||||
|
shouldBeApplied(options: CoreFilterFormatTextOptions, site?: CoreSite): boolean {
|
||||||
|
// This filter is handled by Moodle, nothing to do in the app.
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,34 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { APP_INITIALIZER, NgModule } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDelegate } from '@features/filter/services/filter-delegate';
|
||||||
|
import { AddonFilterDataHandler } from './services/handlers/data';
|
||||||
|
|
||||||
|
@NgModule({
|
||||||
|
declarations: [
|
||||||
|
],
|
||||||
|
imports: [
|
||||||
|
],
|
||||||
|
providers: [
|
||||||
|
{
|
||||||
|
provide: APP_INITIALIZER,
|
||||||
|
multi: true,
|
||||||
|
deps: [AddonFilterDataHandler],
|
||||||
|
useFactory: (handler: AddonFilterDataHandler) => () => CoreFilterDelegate.instance.registerHandler(handler),
|
||||||
|
},
|
||||||
|
],
|
||||||
|
})
|
||||||
|
export class AddonFilterDataModule {}
|
|
@ -0,0 +1,43 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { Injectable } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDefaultHandler } from '@features/filter/services/handlers/default-filter';
|
||||||
|
import { CoreFilterFormatTextOptions } from '@features/filter/services/filter';
|
||||||
|
import { CoreSite } from '@classes/site';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handler to support the Database auto-link filter.
|
||||||
|
*/
|
||||||
|
@Injectable({ providedIn: 'root' })
|
||||||
|
export class AddonFilterDataHandler extends CoreFilterDefaultHandler {
|
||||||
|
|
||||||
|
name = 'AddonFilterDataHandler';
|
||||||
|
filterName = 'data';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Check if the filter should be applied in a certain site based on some filter options.
|
||||||
|
*
|
||||||
|
* @param options Options.
|
||||||
|
* @param site Site.
|
||||||
|
* @return Whether filter should be applied.
|
||||||
|
*/
|
||||||
|
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
||||||
|
shouldBeApplied(options: CoreFilterFormatTextOptions, site?: CoreSite): boolean {
|
||||||
|
// This filter is handled by Moodle, nothing to do in the app.
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,34 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { APP_INITIALIZER, NgModule } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDelegate } from '@features/filter/services/filter-delegate';
|
||||||
|
import { AddonFilterDisplayH5PHandler } from './services/handlers/displayh5p';
|
||||||
|
|
||||||
|
@NgModule({
|
||||||
|
declarations: [
|
||||||
|
],
|
||||||
|
imports: [
|
||||||
|
],
|
||||||
|
providers: [
|
||||||
|
{
|
||||||
|
provide: APP_INITIALIZER,
|
||||||
|
multi: true,
|
||||||
|
deps: [AddonFilterDisplayH5PHandler],
|
||||||
|
useFactory: (handler: AddonFilterDisplayH5PHandler) => () => CoreFilterDelegate.instance.registerHandler(handler),
|
||||||
|
},
|
||||||
|
],
|
||||||
|
})
|
||||||
|
export class AddonFilterDisplayH5PModule {}
|
|
@ -0,0 +1,110 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { Injectable, ViewContainerRef, ComponentFactoryResolver } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDefaultHandler } from '@features/filter/services/handlers/default-filter';
|
||||||
|
import { CoreFilterFilter, CoreFilterFormatTextOptions } from '@features/filter/services/filter';
|
||||||
|
// @todo import { CoreH5PPlayerComponent } from '@core/h5p/components/h5p-player/h5p-player';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handler to support the Display H5P filter.
|
||||||
|
*/
|
||||||
|
@Injectable({ providedIn: 'root' })
|
||||||
|
export class AddonFilterDisplayH5PHandler extends CoreFilterDefaultHandler {
|
||||||
|
|
||||||
|
name = 'AddonFilterDisplayH5PHandler';
|
||||||
|
filterName = 'displayh5p';
|
||||||
|
|
||||||
|
protected template = document.createElement('template'); // A template element to convert HTML to element.
|
||||||
|
|
||||||
|
constructor(protected factoryResolver: ComponentFactoryResolver) {
|
||||||
|
super();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Filter some text.
|
||||||
|
*
|
||||||
|
* @param text The text to filter.
|
||||||
|
* @param filter The filter.
|
||||||
|
* @param options Options passed to the filters.
|
||||||
|
* @param siteId Site ID. If not defined, current site.
|
||||||
|
* @return Filtered text (or promise resolved with the filtered text).
|
||||||
|
*/
|
||||||
|
filter(
|
||||||
|
text: string,
|
||||||
|
filter: CoreFilterFilter, // eslint-disable-line @typescript-eslint/no-unused-vars
|
||||||
|
options: CoreFilterFormatTextOptions, // eslint-disable-line @typescript-eslint/no-unused-vars
|
||||||
|
siteId?: string, // eslint-disable-line @typescript-eslint/no-unused-vars
|
||||||
|
): string | Promise<string> {
|
||||||
|
this.template.innerHTML = text;
|
||||||
|
|
||||||
|
const h5pIframes = <HTMLIFrameElement[]> Array.from(this.template.content.querySelectorAll('iframe.h5p-iframe'));
|
||||||
|
|
||||||
|
// Replace all iframes with an empty div that will be treated in handleHtml.
|
||||||
|
h5pIframes.forEach((iframe) => {
|
||||||
|
const placeholder = document.createElement('div');
|
||||||
|
|
||||||
|
placeholder.classList.add('core-h5p-tmp-placeholder');
|
||||||
|
placeholder.setAttribute('data-player-src', iframe.src);
|
||||||
|
|
||||||
|
iframe.parentElement?.replaceChild(placeholder, iframe);
|
||||||
|
});
|
||||||
|
|
||||||
|
return this.template.innerHTML;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle HTML. This function is called after "filter", and it will receive an HTMLElement containing the text that was
|
||||||
|
* filtered.
|
||||||
|
*
|
||||||
|
* @param container The HTML container to handle.
|
||||||
|
* @param filter The filter.
|
||||||
|
* @param options Options passed to the filters.
|
||||||
|
* @param viewContainerRef The ViewContainerRef where the container is.
|
||||||
|
* @param component Component.
|
||||||
|
* @param componentId Component ID.
|
||||||
|
* @param siteId Site ID. If not defined, current site.
|
||||||
|
* @return If async, promise resolved when done.
|
||||||
|
*/
|
||||||
|
handleHtml(
|
||||||
|
container: HTMLElement, // eslint-disable-line @typescript-eslint/no-unused-vars
|
||||||
|
filter: CoreFilterFilter, // eslint-disable-line @typescript-eslint/no-unused-vars
|
||||||
|
options: CoreFilterFormatTextOptions, // eslint-disable-line @typescript-eslint/no-unused-vars
|
||||||
|
viewContainerRef: ViewContainerRef, // eslint-disable-line @typescript-eslint/no-unused-vars
|
||||||
|
component?: string, // eslint-disable-line @typescript-eslint/no-unused-vars
|
||||||
|
componentId?: string | number, // eslint-disable-line @typescript-eslint/no-unused-vars
|
||||||
|
siteId?: string, // eslint-disable-line @typescript-eslint/no-unused-vars
|
||||||
|
): void | Promise<void> {
|
||||||
|
// @todo
|
||||||
|
|
||||||
|
// const placeholders = <HTMLElement[]> Array.from(container.querySelectorAll('div.core-h5p-tmp-placeholder'));
|
||||||
|
|
||||||
|
// placeholders.forEach((placeholder) => {
|
||||||
|
// const url = placeholder.getAttribute('data-player-src');
|
||||||
|
|
||||||
|
// Create the component to display the player.
|
||||||
|
// const factory = this.factoryResolver.resolveComponentFactory(CoreH5PPlayerComponent);
|
||||||
|
// const componentRef = viewContainerRef.createComponent<CoreH5PPlayerComponent>(factory);
|
||||||
|
|
||||||
|
// componentRef.instance.src = url;
|
||||||
|
// componentRef.instance.component = component;
|
||||||
|
// componentRef.instance.componentId = componentId;
|
||||||
|
|
||||||
|
// // Move the component to its right position.
|
||||||
|
// placeholder.parentElement?.replaceChild(componentRef.instance.elementRef.nativeElement, placeholder);
|
||||||
|
// });
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,34 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { APP_INITIALIZER, NgModule } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDelegate } from '@features/filter/services/filter-delegate';
|
||||||
|
import { AddonFilterEmailProtectHandler } from './services/handlers/emailprotect';
|
||||||
|
|
||||||
|
@NgModule({
|
||||||
|
declarations: [
|
||||||
|
],
|
||||||
|
imports: [
|
||||||
|
],
|
||||||
|
providers: [
|
||||||
|
{
|
||||||
|
provide: APP_INITIALIZER,
|
||||||
|
multi: true,
|
||||||
|
deps: [AddonFilterEmailProtectHandler],
|
||||||
|
useFactory: (handler: AddonFilterEmailProtectHandler) => () => CoreFilterDelegate.instance.registerHandler(handler),
|
||||||
|
},
|
||||||
|
],
|
||||||
|
})
|
||||||
|
export class AddonFilterEmailProtectModule {}
|
|
@ -0,0 +1,43 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { Injectable } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDefaultHandler } from '@features/filter/services/handlers/default-filter';
|
||||||
|
import { CoreFilterFormatTextOptions } from '@features/filter/services/filter';
|
||||||
|
import { CoreSite } from '@classes/site';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handler to support the Email protection filter.
|
||||||
|
*/
|
||||||
|
@Injectable({ providedIn: 'root' })
|
||||||
|
export class AddonFilterEmailProtectHandler extends CoreFilterDefaultHandler {
|
||||||
|
|
||||||
|
name = 'AddonFilterEmailProtectHandler';
|
||||||
|
filterName = 'emailprotect';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Check if the filter should be applied in a certain site based on some filter options.
|
||||||
|
*
|
||||||
|
* @param options Options.
|
||||||
|
* @param site Site.
|
||||||
|
* @return Whether filter should be applied.
|
||||||
|
*/
|
||||||
|
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
||||||
|
shouldBeApplied(options: CoreFilterFormatTextOptions, site?: CoreSite): boolean {
|
||||||
|
// This filter is handled by Moodle, nothing to do in the app.
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,34 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { APP_INITIALIZER, NgModule } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDelegate } from '@features/filter/services/filter-delegate';
|
||||||
|
import { AddonFilterEmoticonHandler } from './services/handlers/emoticon';
|
||||||
|
|
||||||
|
@NgModule({
|
||||||
|
declarations: [
|
||||||
|
],
|
||||||
|
imports: [
|
||||||
|
],
|
||||||
|
providers: [
|
||||||
|
{
|
||||||
|
provide: APP_INITIALIZER,
|
||||||
|
multi: true,
|
||||||
|
deps: [AddonFilterEmoticonHandler],
|
||||||
|
useFactory: (handler: AddonFilterEmoticonHandler) => () => CoreFilterDelegate.instance.registerHandler(handler),
|
||||||
|
},
|
||||||
|
],
|
||||||
|
})
|
||||||
|
export class AddonFilterEmoticonModule {}
|
|
@ -0,0 +1,43 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { Injectable } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDefaultHandler } from '@features/filter/services/handlers/default-filter';
|
||||||
|
import { CoreFilterFormatTextOptions } from '@features/filter/services/filter';
|
||||||
|
import { CoreSite } from '@classes/site';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handler to support the Emoticon filter.
|
||||||
|
*/
|
||||||
|
@Injectable({ providedIn: 'root' })
|
||||||
|
export class AddonFilterEmoticonHandler extends CoreFilterDefaultHandler {
|
||||||
|
|
||||||
|
name = 'AddonFilterEmoticonHandler';
|
||||||
|
filterName = 'emoticon';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Check if the filter should be applied in a certain site based on some filter options.
|
||||||
|
*
|
||||||
|
* @param options Options.
|
||||||
|
* @param site Site.
|
||||||
|
* @return Whether filter should be applied.
|
||||||
|
*/
|
||||||
|
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
||||||
|
shouldBeApplied(options: CoreFilterFormatTextOptions, site?: CoreSite): boolean {
|
||||||
|
// This filter is handled by Moodle, nothing to do in the app.
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,53 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { NgModule } from '@angular/core';
|
||||||
|
|
||||||
|
import { AddonFilterActivityNamesModule } from './activitynames/activitynames.module';
|
||||||
|
import { AddonFilterAlgebraModule } from './algebra/algebra.module';
|
||||||
|
import { AddonFilterCensorModule } from './censor/censor.module';
|
||||||
|
import { AddonFilterDataModule } from './data/data.module';
|
||||||
|
import { AddonFilterDisplayH5PModule } from './displayh5p/displayh5p.module';
|
||||||
|
import { AddonFilterEmailProtectModule } from './emailprotect/emailprotect.module';
|
||||||
|
import { AddonFilterEmoticonModule } from './emoticon/emoticon.module';
|
||||||
|
import { AddonFilterGlossaryModule } from './glossary/glossary.module';
|
||||||
|
import { AddonFilterMathJaxLoaderModule } from './mathjaxloader/mathjaxloader.module';
|
||||||
|
import { AddonFilterMediaPluginModule } from './mediaplugin/mediaplugin.module';
|
||||||
|
import { AddonFilterMultilangModule } from './multilang/multilang.module';
|
||||||
|
import { AddonFilterTexModule } from './tex/tex.module';
|
||||||
|
import { AddonFilterTidyModule } from './tidy/tidy.module';
|
||||||
|
import { AddonFilterUrlToLinkModule } from './urltolink/urltolink.module';
|
||||||
|
|
||||||
|
@NgModule({
|
||||||
|
declarations: [],
|
||||||
|
imports: [
|
||||||
|
AddonFilterActivityNamesModule,
|
||||||
|
AddonFilterAlgebraModule,
|
||||||
|
AddonFilterCensorModule,
|
||||||
|
AddonFilterDataModule,
|
||||||
|
AddonFilterDisplayH5PModule,
|
||||||
|
AddonFilterEmailProtectModule,
|
||||||
|
AddonFilterEmoticonModule,
|
||||||
|
AddonFilterGlossaryModule,
|
||||||
|
AddonFilterMathJaxLoaderModule,
|
||||||
|
AddonFilterMediaPluginModule,
|
||||||
|
AddonFilterMultilangModule,
|
||||||
|
AddonFilterTexModule,
|
||||||
|
AddonFilterTidyModule,
|
||||||
|
AddonFilterUrlToLinkModule,
|
||||||
|
],
|
||||||
|
providers: [],
|
||||||
|
exports: [],
|
||||||
|
})
|
||||||
|
export class AddonFilterModule { }
|
|
@ -0,0 +1,34 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { APP_INITIALIZER, NgModule } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDelegate } from '@features/filter/services/filter-delegate';
|
||||||
|
import { AddonFilterGlossaryHandler } from './services/handlers/glossary';
|
||||||
|
|
||||||
|
@NgModule({
|
||||||
|
declarations: [
|
||||||
|
],
|
||||||
|
imports: [
|
||||||
|
],
|
||||||
|
providers: [
|
||||||
|
{
|
||||||
|
provide: APP_INITIALIZER,
|
||||||
|
multi: true,
|
||||||
|
deps: [AddonFilterGlossaryHandler],
|
||||||
|
useFactory: (handler: AddonFilterGlossaryHandler) => () => CoreFilterDelegate.instance.registerHandler(handler),
|
||||||
|
},
|
||||||
|
],
|
||||||
|
})
|
||||||
|
export class AddonFilterGlossaryModule {}
|
|
@ -0,0 +1,43 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { Injectable } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDefaultHandler } from '@features/filter/services/handlers/default-filter';
|
||||||
|
import { CoreFilterFormatTextOptions } from '@features/filter/services/filter';
|
||||||
|
import { CoreSite } from '@classes/site';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handler to support the Glossary auto-link filter.
|
||||||
|
*/
|
||||||
|
@Injectable({ providedIn: 'root' })
|
||||||
|
export class AddonFilterGlossaryHandler extends CoreFilterDefaultHandler {
|
||||||
|
|
||||||
|
name = 'AddonFilterGlossaryHandler';
|
||||||
|
filterName = 'glossary';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Check if the filter should be applied in a certain site based on some filter options.
|
||||||
|
*
|
||||||
|
* @param options Options.
|
||||||
|
* @param site Site.
|
||||||
|
* @return Whether filter should be applied.
|
||||||
|
*/
|
||||||
|
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
||||||
|
shouldBeApplied(options: CoreFilterFormatTextOptions, site?: CoreSite): boolean {
|
||||||
|
// This filter is handled by Moodle, nothing to do in the app.
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,38 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { APP_INITIALIZER, NgModule } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDelegate } from '@features/filter/services/filter-delegate';
|
||||||
|
import { AddonFilterMathJaxLoaderHandler } from './services/handlers/mathjaxloader';
|
||||||
|
|
||||||
|
@NgModule({
|
||||||
|
declarations: [
|
||||||
|
],
|
||||||
|
imports: [
|
||||||
|
],
|
||||||
|
providers: [
|
||||||
|
{
|
||||||
|
provide: APP_INITIALIZER,
|
||||||
|
multi: true,
|
||||||
|
deps: [AddonFilterMathJaxLoaderHandler],
|
||||||
|
useFactory: (handler: AddonFilterMathJaxLoaderHandler) => async () => {
|
||||||
|
CoreFilterDelegate.instance.registerHandler(handler);
|
||||||
|
|
||||||
|
await handler.initialize();
|
||||||
|
},
|
||||||
|
},
|
||||||
|
],
|
||||||
|
})
|
||||||
|
export class AddonFilterMathJaxLoaderModule {}
|
|
@ -0,0 +1,410 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { Injectable, ViewContainerRef } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDefaultHandler } from '@features/filter/services/handlers/default-filter';
|
||||||
|
import { CoreFilterFilter, CoreFilterFormatTextOptions } from '@features/filter/services/filter';
|
||||||
|
import { CoreLang } from '@services/lang';
|
||||||
|
import { CoreSites } from '@services/sites';
|
||||||
|
import { CoreTextUtils } from '@services/utils/text';
|
||||||
|
import { CoreUtils } from '@services/utils/utils';
|
||||||
|
import { CoreEvents } from '@singletons/events';
|
||||||
|
import { CoreSite } from '@classes/site';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handler to support the MathJax filter.
|
||||||
|
*/
|
||||||
|
@Injectable({ providedIn: 'root' })
|
||||||
|
export class AddonFilterMathJaxLoaderHandler extends CoreFilterDefaultHandler {
|
||||||
|
|
||||||
|
name = 'AddonFilterMathJaxLoaderHandler';
|
||||||
|
filterName = 'mathjaxloader';
|
||||||
|
|
||||||
|
// Default values for MathJax config for sites where we cannot retrieve it.
|
||||||
|
protected readonly DEFAULT_URL = 'https://cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.2/MathJax.js';
|
||||||
|
protected readonly DEFAULT_CONFIG = `
|
||||||
|
MathJax.Hub.Config({
|
||||||
|
extensions: [
|
||||||
|
"Safe.js",
|
||||||
|
"tex2jax.js",
|
||||||
|
"mml2jax.js",
|
||||||
|
"MathEvents.js",
|
||||||
|
"MathZoom.js",
|
||||||
|
"MathMenu.js",
|
||||||
|
"toMathML.js",
|
||||||
|
"TeX/noErrors.js",
|
||||||
|
"TeX/noUndefined.js",
|
||||||
|
"TeX/AMSmath.js",
|
||||||
|
"TeX/AMSsymbols.js",
|
||||||
|
"fast-preview.js",
|
||||||
|
"AssistiveMML.js",
|
||||||
|
"[a11y]/accessibility-menu.js"
|
||||||
|
],
|
||||||
|
jax: ["input/TeX","input/MathML","output/SVG"],
|
||||||
|
showMathMenu: false,
|
||||||
|
errorSettings: { message: ["!"] },
|
||||||
|
skipStartupTypeset: true,
|
||||||
|
messageStyle: "none"
|
||||||
|
});
|
||||||
|
`;
|
||||||
|
|
||||||
|
// List of language codes found in the MathJax/localization/ directory.
|
||||||
|
protected readonly MATHJAX_LANG_CODES = [
|
||||||
|
'ar', 'ast', 'bcc', 'bg', 'br', 'ca', 'cdo', 'ce', 'cs', 'cy', 'da', 'de', 'diq', 'en', 'eo', 'es', 'fa',
|
||||||
|
'fi', 'fr', 'gl', 'he', 'ia', 'it', 'ja', 'kn', 'ko', 'lb', 'lki', 'lt', 'mk', 'nl', 'oc', 'pl', 'pt',
|
||||||
|
'pt-br', 'qqq', 'ru', 'scn', 'sco', 'sk', 'sl', 'sv', 'th', 'tr', 'uk', 'vi', 'zh-hans', 'zh-hant',
|
||||||
|
];
|
||||||
|
|
||||||
|
// List of explicit mappings and known exceptions (moodle => mathjax).
|
||||||
|
protected readonly EXPLICIT_MAPPING = {
|
||||||
|
'zh-tw': 'zh-hant',
|
||||||
|
'zh-cn': 'zh-hans',
|
||||||
|
};
|
||||||
|
|
||||||
|
protected window: MathJaxWindow = window;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Initialize MathJax.
|
||||||
|
*
|
||||||
|
* @return Promise resolved when done.
|
||||||
|
*/
|
||||||
|
async initialize(): Promise<void> {
|
||||||
|
this.loadJS();
|
||||||
|
|
||||||
|
// Update MathJax locale if app language changes.
|
||||||
|
CoreEvents.on(CoreEvents.LANGUAGE_CHANGED, (lang: string) => {
|
||||||
|
if (typeof this.window.MathJax == 'undefined') {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
this.window.MathJax.Hub.Queue(() => {
|
||||||
|
this.window.MathJax.Localization.setLocale(this.mapLanguageCode(lang));
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
// Get the current language.
|
||||||
|
const lang = await CoreLang.instance.getCurrentLanguage();
|
||||||
|
|
||||||
|
// Now call the configure function.
|
||||||
|
this.window.M!.filter_mathjaxloader!.configure({
|
||||||
|
mathjaxconfig: this.DEFAULT_CONFIG,
|
||||||
|
lang: this.mapLanguageCode(lang),
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Filter some text.
|
||||||
|
*
|
||||||
|
* @param text The text to filter.
|
||||||
|
* @param filter The filter.
|
||||||
|
* @param options Options passed to the filters.
|
||||||
|
* @param siteId Site ID. If not defined, current site.
|
||||||
|
* @return Filtered text (or promise resolved with the filtered text).
|
||||||
|
*/
|
||||||
|
async filter(
|
||||||
|
text: string,
|
||||||
|
filter: CoreFilterFilter,
|
||||||
|
options: CoreFilterFormatTextOptions,
|
||||||
|
siteId?: string,
|
||||||
|
): Promise<string> {
|
||||||
|
|
||||||
|
const site = await CoreSites.instance.getSite(siteId);
|
||||||
|
|
||||||
|
// Don't apply this filter if Moodle is 3.7 or higher and the WS already filtered the content.
|
||||||
|
if (!options.wsNotFiltered && site.isVersionGreaterEqualThan('3.7')) {
|
||||||
|
return text;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (text.indexOf('class="filter_mathjaxloader_equation"') != -1) {
|
||||||
|
// The content seems to have treated mathjax already, don't do it.
|
||||||
|
return text;
|
||||||
|
}
|
||||||
|
|
||||||
|
// We cannot get the filter settings, so we cannot know if it can be used as a replacement for the TeX filter.
|
||||||
|
// Assume it cannot (default value).
|
||||||
|
let hasDisplayOrInline = false;
|
||||||
|
if (text.match(/\\[[(]/) || text.match(/\$\$/)) {
|
||||||
|
// Only parse the text if there are mathjax symbols in it.
|
||||||
|
// The recognized math environments are \[ \] and $$ $$ for display mathematics and \( \) for inline mathematics.
|
||||||
|
// Wrap display and inline math environments in nolink spans.
|
||||||
|
const result = this.wrapMathInNoLink(text);
|
||||||
|
text = result.text;
|
||||||
|
hasDisplayOrInline = result.changed;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (hasDisplayOrInline) {
|
||||||
|
return '<span class="filter_mathjaxloader_equation">' + text + '</span>';
|
||||||
|
}
|
||||||
|
|
||||||
|
return text;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle HTML. This function is called after "filter", and it will receive an HTMLElement containing the text that was
|
||||||
|
* filtered.
|
||||||
|
*
|
||||||
|
* @param container The HTML container to handle.
|
||||||
|
* @param filter The filter.
|
||||||
|
* @param options Options passed to the filters.
|
||||||
|
* @param viewContainerRef The ViewContainerRef where the container is.
|
||||||
|
* @param component Component.
|
||||||
|
* @param componentId Component ID.
|
||||||
|
* @param siteId Site ID. If not defined, current site.
|
||||||
|
* @return If async, promise resolved when done.
|
||||||
|
*/
|
||||||
|
async handleHtml(
|
||||||
|
container: HTMLElement,
|
||||||
|
filter: CoreFilterFilter, // eslint-disable-line @typescript-eslint/no-unused-vars
|
||||||
|
options: CoreFilterFormatTextOptions, // eslint-disable-line @typescript-eslint/no-unused-vars
|
||||||
|
viewContainerRef: ViewContainerRef, // eslint-disable-line @typescript-eslint/no-unused-vars
|
||||||
|
component?: string, // eslint-disable-line @typescript-eslint/no-unused-vars
|
||||||
|
componentId?: string | number, // eslint-disable-line @typescript-eslint/no-unused-vars
|
||||||
|
siteId?: string, // eslint-disable-line @typescript-eslint/no-unused-vars
|
||||||
|
): Promise<void> {
|
||||||
|
await this.waitForReady();
|
||||||
|
|
||||||
|
this.window.M!.filter_mathjaxloader!.typeset(container);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Wrap a portion of the $text inside a no link span. The whole text is then returned.
|
||||||
|
*
|
||||||
|
* @param text The text to modify.
|
||||||
|
* @param start The start index of the substring in text that should be wrapped in the span.
|
||||||
|
* @param end The end index of the substring in text that should be wrapped in the span.
|
||||||
|
* @return The whole text with the span inserted around the defined substring.
|
||||||
|
*/
|
||||||
|
protected insertSpan(text: string, start: number, end: number): string {
|
||||||
|
return CoreTextUtils.instance.substrReplace(
|
||||||
|
text,
|
||||||
|
'<span class="nolink">' + text.substr(start, end - start + 1) + '</span>',
|
||||||
|
start,
|
||||||
|
end - start + 1,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Load the JS to make MathJax work in the app. The JS loaded is extracted from Moodle filter's loader JS file.
|
||||||
|
*/
|
||||||
|
protected loadJS(): void {
|
||||||
|
// eslint-disable-next-line @typescript-eslint/no-this-alias
|
||||||
|
const that = this;
|
||||||
|
|
||||||
|
this.window.M = this.window.M || {};
|
||||||
|
this.window.M.filter_mathjaxloader = this.window.M.filter_mathjaxloader || {
|
||||||
|
_lang: '', // eslint-disable-line @typescript-eslint/naming-convention
|
||||||
|
_configured: false, // eslint-disable-line @typescript-eslint/naming-convention
|
||||||
|
// Add the configuration to the head and set the lang.
|
||||||
|
configure: function (params: Record<string, unknown>): void {
|
||||||
|
// Add a js configuration object to the head.
|
||||||
|
const script = document.createElement('script');
|
||||||
|
script.type = 'text/x-mathjax-config';
|
||||||
|
script.text = <string> params.mathjaxconfig;
|
||||||
|
document.head.appendChild(script);
|
||||||
|
|
||||||
|
// Save the lang config until MathJax is actually loaded.
|
||||||
|
this._lang = <string> params.lang; // eslint-disable-line no-underscore-dangle
|
||||||
|
},
|
||||||
|
// Set the correct language for the MathJax menus.
|
||||||
|
_setLocale: function (): void {
|
||||||
|
if (!this._configured) { // eslint-disable-line no-underscore-dangle
|
||||||
|
const lang = this._lang; // eslint-disable-line no-underscore-dangle
|
||||||
|
|
||||||
|
if (typeof that.window.MathJax != 'undefined') {
|
||||||
|
that.window.MathJax.Hub.Queue(() => {
|
||||||
|
that.window.MathJax.Localization.setLocale(lang);
|
||||||
|
});
|
||||||
|
that.window.MathJax.Hub.Configured();
|
||||||
|
this._configured = true; // eslint-disable-line no-underscore-dangle
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
// Called by the filter when an equation is found while rendering the page.
|
||||||
|
typeset: function (container: HTMLElement): void {
|
||||||
|
if (!this._configured) { // eslint-disable-line no-underscore-dangle
|
||||||
|
this._setLocale(); // eslint-disable-line no-underscore-dangle
|
||||||
|
}
|
||||||
|
|
||||||
|
if (typeof that.window.MathJax != 'undefined') {
|
||||||
|
const processDelay = that.window.MathJax.Hub.processSectionDelay;
|
||||||
|
// Set the process section delay to 0 when updating the formula.
|
||||||
|
that.window.MathJax.Hub.processSectionDelay = 0;
|
||||||
|
|
||||||
|
const equations = Array.from(container.querySelectorAll('.filter_mathjaxloader_equation'));
|
||||||
|
equations.forEach((node) => {
|
||||||
|
that.window.MathJax.Hub.Queue(['Typeset', that.window.MathJax.Hub, node]);
|
||||||
|
});
|
||||||
|
|
||||||
|
// Set the delay back to normal after processing.
|
||||||
|
that.window.MathJax.Hub.processSectionDelay = processDelay;
|
||||||
|
}
|
||||||
|
},
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Perform a mapping of the app language code to the equivalent for MathJax.
|
||||||
|
*
|
||||||
|
* @param langCode The app language code.
|
||||||
|
* @return The MathJax language code.
|
||||||
|
*/
|
||||||
|
protected mapLanguageCode(langCode: string): string {
|
||||||
|
|
||||||
|
// If defined, explicit mapping takes the highest precedence.
|
||||||
|
if (this.EXPLICIT_MAPPING[langCode]) {
|
||||||
|
return this.EXPLICIT_MAPPING[langCode];
|
||||||
|
}
|
||||||
|
|
||||||
|
// If there is exact match, it will be probably right.
|
||||||
|
if (this.MATHJAX_LANG_CODES.indexOf(langCode) != -1) {
|
||||||
|
return langCode;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Finally try to find the best matching mathjax pack.
|
||||||
|
const parts = langCode.split('-');
|
||||||
|
if (this.MATHJAX_LANG_CODES.indexOf(parts[0]) != -1) {
|
||||||
|
return parts[0];
|
||||||
|
}
|
||||||
|
|
||||||
|
// No more guessing, use default language.
|
||||||
|
return CoreLang.instance.getDefaultLanguage();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Check if the filter should be applied in a certain site based on some filter options.
|
||||||
|
*
|
||||||
|
* @param options Options.
|
||||||
|
* @param site Site.
|
||||||
|
* @return Whether filter should be applied.
|
||||||
|
*/
|
||||||
|
shouldBeApplied(options: CoreFilterFormatTextOptions, site?: CoreSite): boolean {
|
||||||
|
// Only apply the filter if logged in and we're filtering current site.
|
||||||
|
return !!(site && site.getId() == CoreSites.instance.getCurrentSiteId());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Wait for the MathJax library and our JS object to be loaded.
|
||||||
|
*
|
||||||
|
* @param retries Number of times this has been retried.
|
||||||
|
* @return Promise resolved when ready or if it took too long to load.
|
||||||
|
*/
|
||||||
|
protected async waitForReady(retries: number = 0): Promise<void> {
|
||||||
|
if (this.window.MathJax || retries >= 20) {
|
||||||
|
// Loaded or too many retries, stop.
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const deferred = CoreUtils.instance.promiseDefer<void>();
|
||||||
|
|
||||||
|
setTimeout(async () => {
|
||||||
|
try {
|
||||||
|
await this.waitForReady(retries + 1);
|
||||||
|
} finally {
|
||||||
|
deferred.resolve();
|
||||||
|
}
|
||||||
|
}, 250);
|
||||||
|
|
||||||
|
return deferred.promise;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Find math environments in the $text and wrap them in no link spans
|
||||||
|
* (<span class="nolink"></span>). If math environments are nested, only
|
||||||
|
* the outer environment is wrapped in the span.
|
||||||
|
*
|
||||||
|
* The recognized math environments are \[ \] and $$ $$ for display
|
||||||
|
* mathematics and \( \) for inline mathematics.
|
||||||
|
*
|
||||||
|
* @param text The text to filter.
|
||||||
|
* @return Object containing the potentially modified text and a boolean that is true if any changes were made to the text.
|
||||||
|
*/
|
||||||
|
protected wrapMathInNoLink(text: string): {text: string; changed: boolean} {
|
||||||
|
let len = text.length;
|
||||||
|
let i = 1;
|
||||||
|
let displayStart = -1;
|
||||||
|
let displayBracket = false;
|
||||||
|
let displayDollar = false;
|
||||||
|
let inlineStart = -1;
|
||||||
|
let changesDone = false;
|
||||||
|
|
||||||
|
// Loop over the $text once.
|
||||||
|
while (i < len) {
|
||||||
|
if (displayStart === -1) {
|
||||||
|
// No display math has started yet.
|
||||||
|
if (text[i - 1] === '\\') {
|
||||||
|
|
||||||
|
if (text[i] === '[') {
|
||||||
|
// Display mode \[ begins.
|
||||||
|
displayStart = i - 1;
|
||||||
|
displayBracket = true;
|
||||||
|
} else if (text[i] === '(') {
|
||||||
|
// Inline math \( begins, not nested inside display math.
|
||||||
|
inlineStart = i - 1;
|
||||||
|
} else if (text[i] === ')' && inlineStart > -1) {
|
||||||
|
// Inline math ends, not nested inside display math. Wrap the span around it.
|
||||||
|
text = this.insertSpan(text, inlineStart, i);
|
||||||
|
|
||||||
|
inlineStart = -1; // Reset.
|
||||||
|
i += 28; // The text length changed due to the <span>.
|
||||||
|
len += 28;
|
||||||
|
changesDone = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
} else if (text[i - 1] === '$' && text[i] === '$') {
|
||||||
|
// Display mode $$ begins.
|
||||||
|
displayStart = i - 1;
|
||||||
|
displayDollar = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
} else {
|
||||||
|
// Display math open.
|
||||||
|
if ((text[i - 1] === '\\' && text[i] === ']' && displayBracket) ||
|
||||||
|
(text[i - 1] === '$' && text[i] === '$' && displayDollar)) {
|
||||||
|
// Display math ends, wrap the span around it.
|
||||||
|
text = this.insertSpan(text, displayStart, i);
|
||||||
|
|
||||||
|
displayStart = -1; // Reset.
|
||||||
|
displayBracket = false;
|
||||||
|
displayDollar = false;
|
||||||
|
i += 28; // The text length changed due to the <span>.
|
||||||
|
len += 28;
|
||||||
|
changesDone = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
i++;
|
||||||
|
}
|
||||||
|
|
||||||
|
return {
|
||||||
|
text: text,
|
||||||
|
changed: changesDone,
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
type MathJaxWindow = Window & {
|
||||||
|
MathJax?: any; // eslint-disable-line @typescript-eslint/naming-convention, @typescript-eslint/no-explicit-any
|
||||||
|
M?: { // eslint-disable-line @typescript-eslint/naming-convention
|
||||||
|
filter_mathjaxloader?: { // eslint-disable-line @typescript-eslint/naming-convention
|
||||||
|
_lang: ''; // eslint-disable-line @typescript-eslint/naming-convention
|
||||||
|
_configured: false; // eslint-disable-line @typescript-eslint/naming-convention
|
||||||
|
// Add the configuration to the head and set the lang.
|
||||||
|
configure: (params: Record<string, unknown>) => void;
|
||||||
|
_setLocale: () => void; // eslint-disable-line @typescript-eslint/naming-convention
|
||||||
|
typeset: (container: HTMLElement) => void;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
|
@ -0,0 +1,34 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { APP_INITIALIZER, NgModule } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDelegate } from '@features/filter/services/filter-delegate';
|
||||||
|
import { AddonFilterMediaPluginHandler } from './services/handlers/mediaplugin';
|
||||||
|
|
||||||
|
@NgModule({
|
||||||
|
declarations: [
|
||||||
|
],
|
||||||
|
imports: [
|
||||||
|
],
|
||||||
|
providers: [
|
||||||
|
{
|
||||||
|
provide: APP_INITIALIZER,
|
||||||
|
multi: true,
|
||||||
|
deps: [AddonFilterMediaPluginHandler],
|
||||||
|
useFactory: (handler: AddonFilterMediaPluginHandler) => () => CoreFilterDelegate.instance.registerHandler(handler),
|
||||||
|
},
|
||||||
|
],
|
||||||
|
})
|
||||||
|
export class AddonFilterMediaPluginModule {}
|
|
@ -0,0 +1,98 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { Injectable } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDefaultHandler } from '@features/filter/services/handlers/default-filter';
|
||||||
|
import { CoreFilterFilter, CoreFilterFormatTextOptions } from '@features/filter/services/filter';
|
||||||
|
import { CoreTextUtils } from '@services/utils/text';
|
||||||
|
import { CoreUrlUtils } from '@services/utils/url';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handler to support the Multimedia filter.
|
||||||
|
*/
|
||||||
|
@Injectable({ providedIn: 'root' })
|
||||||
|
export class AddonFilterMediaPluginHandler extends CoreFilterDefaultHandler {
|
||||||
|
|
||||||
|
name = 'AddonFilterMediaPluginHandler';
|
||||||
|
filterName = 'mediaplugin';
|
||||||
|
|
||||||
|
protected template = document.createElement('template'); // A template element to convert HTML to element.
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Filter some text.
|
||||||
|
*
|
||||||
|
* @param text The text to filter.
|
||||||
|
* @param filter The filter.
|
||||||
|
* @param options Options passed to the filters.
|
||||||
|
* @param siteId Site ID. If not defined, current site.
|
||||||
|
* @return Filtered text (or promise resolved with the filtered text).
|
||||||
|
*/
|
||||||
|
filter(
|
||||||
|
text: string,
|
||||||
|
filter: CoreFilterFilter, // eslint-disable-line @typescript-eslint/no-unused-vars
|
||||||
|
options: CoreFilterFormatTextOptions, // eslint-disable-line @typescript-eslint/no-unused-vars
|
||||||
|
siteId?: string, // eslint-disable-line @typescript-eslint/no-unused-vars
|
||||||
|
): string | Promise<string> {
|
||||||
|
this.template.innerHTML = text;
|
||||||
|
|
||||||
|
const videos = Array.from(this.template.content.querySelectorAll('video'));
|
||||||
|
|
||||||
|
videos.forEach((video) => {
|
||||||
|
this.treatVideoFilters(video);
|
||||||
|
});
|
||||||
|
|
||||||
|
return this.template.innerHTML;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Treat video filters. Currently only treating youtube video using video JS.
|
||||||
|
*
|
||||||
|
* @param el Video element.
|
||||||
|
* @param navCtrl NavController to use.
|
||||||
|
*/
|
||||||
|
protected treatVideoFilters(video: HTMLElement): void {
|
||||||
|
// Treat Video JS Youtube video links and translate them to iframes.
|
||||||
|
if (!video.classList.contains('video-js')) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const dataSetupString = video.getAttribute('data-setup') || video.getAttribute('data-setup-lazy') || '{}';
|
||||||
|
const data = <VideoDataSetup> CoreTextUtils.instance.parseJSON(dataSetupString, {});
|
||||||
|
const youtubeUrl = data.techOrder?.[0] == 'youtube' && CoreUrlUtils.instance.getYoutubeEmbedUrl(data.sources?.[0]?.src);
|
||||||
|
|
||||||
|
if (!youtubeUrl) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const iframe = document.createElement('iframe');
|
||||||
|
iframe.id = video.id;
|
||||||
|
iframe.src = youtubeUrl;
|
||||||
|
iframe.setAttribute('frameborder', '0');
|
||||||
|
iframe.setAttribute('allowfullscreen', '1');
|
||||||
|
iframe.width = '100%';
|
||||||
|
iframe.height = '300';
|
||||||
|
|
||||||
|
// Replace video tag by the iframe.
|
||||||
|
video.parentNode?.replaceChild(iframe, video);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
type VideoDataSetup = {
|
||||||
|
techOrder?: string[];
|
||||||
|
sources?: {
|
||||||
|
src?: string;
|
||||||
|
}[];
|
||||||
|
};
|
|
@ -0,0 +1,34 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { APP_INITIALIZER, NgModule } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDelegate } from '@features/filter/services/filter-delegate';
|
||||||
|
import { AddonFilterMultilangHandler } from './services/handlers/multilang';
|
||||||
|
|
||||||
|
@NgModule({
|
||||||
|
declarations: [
|
||||||
|
],
|
||||||
|
imports: [
|
||||||
|
],
|
||||||
|
providers: [
|
||||||
|
{
|
||||||
|
provide: APP_INITIALIZER,
|
||||||
|
multi: true,
|
||||||
|
deps: [AddonFilterMultilangHandler],
|
||||||
|
useFactory: (handler: AddonFilterMultilangHandler) => () => CoreFilterDelegate.instance.registerHandler(handler),
|
||||||
|
},
|
||||||
|
],
|
||||||
|
})
|
||||||
|
export class AddonFilterMultilangModule {}
|
|
@ -0,0 +1,84 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { Injectable } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreLang } from '@services/lang';
|
||||||
|
import { CoreFilterDefaultHandler } from '@features/filter/services/handlers/default-filter';
|
||||||
|
import { CoreFilterFilter, CoreFilterFormatTextOptions } from '@features/filter/services/filter';
|
||||||
|
import { CoreSite } from '@classes/site';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handler to support the Multilang filter.
|
||||||
|
*/
|
||||||
|
@Injectable({ providedIn: 'root' })
|
||||||
|
export class AddonFilterMultilangHandler extends CoreFilterDefaultHandler {
|
||||||
|
|
||||||
|
name = 'AddonFilterMultilangHandler';
|
||||||
|
filterName = 'multilang';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Filter some text.
|
||||||
|
*
|
||||||
|
* @param text The text to filter.
|
||||||
|
* @param filter The filter.
|
||||||
|
* @param options Options passed to the filters.
|
||||||
|
* @param siteId Site ID. If not defined, current site.
|
||||||
|
* @return Filtered text (or promise resolved with the filtered text).
|
||||||
|
*/
|
||||||
|
async filter(
|
||||||
|
text: string,
|
||||||
|
filter: CoreFilterFilter, // eslint-disable-line @typescript-eslint/no-unused-vars
|
||||||
|
options: CoreFilterFormatTextOptions, // eslint-disable-line @typescript-eslint/no-unused-vars
|
||||||
|
siteId?: string, // eslint-disable-line @typescript-eslint/no-unused-vars
|
||||||
|
): Promise<string> {
|
||||||
|
let language = await CoreLang.instance.getCurrentLanguage();
|
||||||
|
|
||||||
|
// Match the current language.
|
||||||
|
const anyLangRegEx = /<(?:lang|span)[^>]+lang="[a-zA-Z0-9_-]+"[^>]*>(.*?)<\/(?:lang|span)>/g;
|
||||||
|
let currentLangRegEx = new RegExp('<(?:lang|span)[^>]+lang="' + language + '"[^>]*>(.*?)</(?:lang|span)>', 'g');
|
||||||
|
|
||||||
|
if (!text.match(currentLangRegEx)) {
|
||||||
|
// Current lang not found. Try to find the first language.
|
||||||
|
const matches = text.match(anyLangRegEx);
|
||||||
|
if (matches?.[0]) {
|
||||||
|
language = matches[0].match(/lang="([a-zA-Z0-9_-]+)"/)?.[1] || language;
|
||||||
|
currentLangRegEx = new RegExp('<(?:lang|span)[^>]+lang="' + language + '"[^>]*>(.*?)</(?:lang|span)>', 'g');
|
||||||
|
} else {
|
||||||
|
// No multi-lang tag found, stop.
|
||||||
|
return text;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Extract contents of current language.
|
||||||
|
text = text.replace(currentLangRegEx, '$1');
|
||||||
|
// Delete the rest of languages
|
||||||
|
text = text.replace(anyLangRegEx, '');
|
||||||
|
|
||||||
|
return text;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Check if the filter should be applied in a certain site based on some filter options.
|
||||||
|
*
|
||||||
|
* @param options Options.
|
||||||
|
* @param site Site.
|
||||||
|
* @return Whether filter should be applied.
|
||||||
|
*/
|
||||||
|
shouldBeApplied(options: CoreFilterFormatTextOptions, site?: CoreSite): boolean {
|
||||||
|
// The filter should be applied if site is older than 3.7 or the WS didn't filter the text.
|
||||||
|
return !!(options.wsNotFiltered || (site && !site.isVersionGreaterEqualThan('3.7')));
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,43 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { Injectable } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDefaultHandler } from '@features/filter/services/handlers/default-filter';
|
||||||
|
import { CoreFilterFormatTextOptions } from '@features/filter/services/filter';
|
||||||
|
import { CoreSite } from '@classes/site';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handler to support the TeX notation filter.
|
||||||
|
*/
|
||||||
|
@Injectable({ providedIn: 'root' })
|
||||||
|
export class AddonFilterTexHandler extends CoreFilterDefaultHandler {
|
||||||
|
|
||||||
|
name = 'AddonFilterTexHandler';
|
||||||
|
filterName = 'tex';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Check if the filter should be applied in a certain site based on some filter options.
|
||||||
|
*
|
||||||
|
* @param options Options.
|
||||||
|
* @param site Site.
|
||||||
|
* @return Whether filter should be applied.
|
||||||
|
*/
|
||||||
|
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
||||||
|
shouldBeApplied(options: CoreFilterFormatTextOptions, site?: CoreSite): boolean {
|
||||||
|
// This filter is handled by Moodle, nothing to do in the app.
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,34 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { APP_INITIALIZER, NgModule } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDelegate } from '@features/filter/services/filter-delegate';
|
||||||
|
import { AddonFilterTexHandler } from './services/handlers/tex';
|
||||||
|
|
||||||
|
@NgModule({
|
||||||
|
declarations: [
|
||||||
|
],
|
||||||
|
imports: [
|
||||||
|
],
|
||||||
|
providers: [
|
||||||
|
{
|
||||||
|
provide: APP_INITIALIZER,
|
||||||
|
multi: true,
|
||||||
|
deps: [AddonFilterTexHandler],
|
||||||
|
useFactory: (handler: AddonFilterTexHandler) => () => CoreFilterDelegate.instance.registerHandler(handler),
|
||||||
|
},
|
||||||
|
],
|
||||||
|
})
|
||||||
|
export class AddonFilterTexModule {}
|
|
@ -0,0 +1,43 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { Injectable } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDefaultHandler } from '@features/filter/services/handlers/default-filter';
|
||||||
|
import { CoreFilterFormatTextOptions } from '@features/filter/services/filter';
|
||||||
|
import { CoreSite } from '@classes/site';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handler to support the HTML tidy filter.
|
||||||
|
*/
|
||||||
|
@Injectable({ providedIn: 'root' })
|
||||||
|
export class AddonFilterTidyHandler extends CoreFilterDefaultHandler {
|
||||||
|
|
||||||
|
name = 'AddonFilterTidyHandler';
|
||||||
|
filterName = 'tidy';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Check if the filter should be applied in a certain site based on some filter options.
|
||||||
|
*
|
||||||
|
* @param options Options.
|
||||||
|
* @param site Site.
|
||||||
|
* @return Whether filter should be applied.
|
||||||
|
*/
|
||||||
|
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
||||||
|
shouldBeApplied(options: CoreFilterFormatTextOptions, site?: CoreSite): boolean {
|
||||||
|
// This filter is handled by Moodle, nothing to do in the app.
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,34 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { APP_INITIALIZER, NgModule } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDelegate } from '@features/filter/services/filter-delegate';
|
||||||
|
import { AddonFilterTidyHandler } from './services/handlers/tidy';
|
||||||
|
|
||||||
|
@NgModule({
|
||||||
|
declarations: [
|
||||||
|
],
|
||||||
|
imports: [
|
||||||
|
],
|
||||||
|
providers: [
|
||||||
|
{
|
||||||
|
provide: APP_INITIALIZER,
|
||||||
|
multi: true,
|
||||||
|
deps: [AddonFilterTidyHandler],
|
||||||
|
useFactory: (handler: AddonFilterTidyHandler) => () => CoreFilterDelegate.instance.registerHandler(handler),
|
||||||
|
},
|
||||||
|
],
|
||||||
|
})
|
||||||
|
export class AddonFilterTidyModule {}
|
|
@ -0,0 +1,43 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { Injectable } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDefaultHandler } from '@features/filter/services/handlers/default-filter';
|
||||||
|
import { CoreFilterFormatTextOptions } from '@features/filter/services/filter';
|
||||||
|
import { CoreSite } from '@classes/site';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handler to support the URL to link and images filter.
|
||||||
|
*/
|
||||||
|
@Injectable({ providedIn: 'root' })
|
||||||
|
export class AddonFilterUrlToLinkHandler extends CoreFilterDefaultHandler {
|
||||||
|
|
||||||
|
name = 'AddonFilterUrlToLinkHandler';
|
||||||
|
filterName = 'urltolink';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Check if the filter should be applied in a certain site based on some filter options.
|
||||||
|
*
|
||||||
|
* @param options Options.
|
||||||
|
* @param site Site.
|
||||||
|
* @return Whether filter should be applied.
|
||||||
|
*/
|
||||||
|
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
||||||
|
shouldBeApplied(options: CoreFilterFormatTextOptions, site?: CoreSite): boolean {
|
||||||
|
// This filter is handled by Moodle, nothing to do in the app.
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,34 @@
|
||||||
|
// (C) Copyright 2015 Moodle Pty Ltd.
|
||||||
|
//
|
||||||
|
// 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 { APP_INITIALIZER, NgModule } from '@angular/core';
|
||||||
|
|
||||||
|
import { CoreFilterDelegate } from '@features/filter/services/filter-delegate';
|
||||||
|
import { AddonFilterUrlToLinkHandler } from './services/handlers/urltolink';
|
||||||
|
|
||||||
|
@NgModule({
|
||||||
|
declarations: [
|
||||||
|
],
|
||||||
|
imports: [
|
||||||
|
],
|
||||||
|
providers: [
|
||||||
|
{
|
||||||
|
provide: APP_INITIALIZER,
|
||||||
|
multi: true,
|
||||||
|
deps: [AddonFilterUrlToLinkHandler],
|
||||||
|
useFactory: (handler: AddonFilterUrlToLinkHandler) => () => CoreFilterDelegate.instance.registerHandler(handler),
|
||||||
|
},
|
||||||
|
],
|
||||||
|
})
|
||||||
|
export class AddonFilterUrlToLinkModule {}
|
|
@ -255,7 +255,7 @@ export class CoreUrlUtilsProvider {
|
||||||
* @param url URL
|
* @param url URL
|
||||||
* @return Youtube Embed Video URL or null if not found.
|
* @return Youtube Embed Video URL or null if not found.
|
||||||
*/
|
*/
|
||||||
getYoutubeEmbedUrl(url: string): string | void {
|
getYoutubeEmbedUrl(url?: string): string | void {
|
||||||
if (!url) {
|
if (!url) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue