forked from CIT/Vmeda.Online
		
	MOBILE-2201 tag: Area delegate and helpers for handlers
This commit is contained in:
		
							parent
							
								
									75929f6b4f
								
							
						
					
					
						commit
						7546ac9e28
					
				| @ -16,11 +16,13 @@ import { NgModule } from '@angular/core'; | |||||||
| import { CommonModule } from '@angular/common'; | import { CommonModule } from '@angular/common'; | ||||||
| import { IonicModule } from 'ionic-angular'; | import { IonicModule } from 'ionic-angular'; | ||||||
| import { TranslateModule } from '@ngx-translate/core'; | import { TranslateModule } from '@ngx-translate/core'; | ||||||
|  | import { CoreTagFeedComponent } from './feed/feed'; | ||||||
| import { CoreTagListComponent } from './list/list'; | import { CoreTagListComponent } from './list/list'; | ||||||
| import { CoreDirectivesModule } from '@directives/directives.module'; | import { CoreDirectivesModule } from '@directives/directives.module'; | ||||||
| 
 | 
 | ||||||
| @NgModule({ | @NgModule({ | ||||||
|     declarations: [ |     declarations: [ | ||||||
|  |         CoreTagFeedComponent, | ||||||
|         CoreTagListComponent |         CoreTagListComponent | ||||||
|     ], |     ], | ||||||
|     imports: [ |     imports: [ | ||||||
| @ -32,9 +34,11 @@ import { CoreDirectivesModule } from '@directives/directives.module'; | |||||||
|     providers: [ |     providers: [ | ||||||
|     ], |     ], | ||||||
|     exports: [ |     exports: [ | ||||||
|  |         CoreTagFeedComponent, | ||||||
|         CoreTagListComponent |         CoreTagListComponent | ||||||
|     ], |     ], | ||||||
|     entryComponents: [ |     entryComponents: [ | ||||||
|  |         CoreTagFeedComponent | ||||||
|     ] |     ] | ||||||
| }) | }) | ||||||
| export class CoreTagComponentsModule {} | export class CoreTagComponentsModule {} | ||||||
|  | |||||||
							
								
								
									
										8
									
								
								src/core/tag/components/feed/core-tag-feed.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										8
									
								
								src/core/tag/components/feed/core-tag-feed.html
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,8 @@ | |||||||
|  | <a ion-item text-wrap *ngFor="let item of items" [href]="item.url" core-link [capture]="true"> | ||||||
|  |     <ion-avatar item-start *ngIf="item.avatarUrl"> | ||||||
|  |         <img [src]="item.avatarUrl" core-external-content alt="" role="presentation" onError="this.src='assets/img/user-avatar.png'"> | ||||||
|  |     </ion-avatar> | ||||||
|  |     <img item-start *ngIf="item.iconUrl" [src]="item.iconUrl" core-external-content alt="" role="presentation" class="core-module-icon"> | ||||||
|  |     <h2>{{ item.heading }}</h2> | ||||||
|  |     <p *ngFor="let text of item.details">{{ text }}</p> | ||||||
|  | </a> | ||||||
							
								
								
									
										26
									
								
								src/core/tag/components/feed/feed.ts
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										26
									
								
								src/core/tag/components/feed/feed.ts
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,26 @@ | |||||||
|  | // (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, Input } from '@angular/core'; | ||||||
|  | 
 | ||||||
|  | /** | ||||||
|  |  * Component to render a tag area that uses the "core_tag/tagfeed" web template. | ||||||
|  |  */ | ||||||
|  | @Component({ | ||||||
|  |     selector: 'core-tag-feed', | ||||||
|  |     templateUrl: 'core-tag-feed.html' | ||||||
|  | }) | ||||||
|  | export class CoreTagFeedComponent { | ||||||
|  |     @Input() items: any[]; // Area items to render.
 | ||||||
|  | } | ||||||
							
								
								
									
										98
									
								
								src/core/tag/providers/area-delegate.ts
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										98
									
								
								src/core/tag/providers/area-delegate.ts
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,98 @@ | |||||||
|  | // (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 { Injectable, Injector } from '@angular/core'; | ||||||
|  | import { CoreEventsProvider } from '@providers/events'; | ||||||
|  | import { CoreLoggerProvider } from '@providers/logger'; | ||||||
|  | import { CoreSitesProvider } from '@providers/sites'; | ||||||
|  | import { CoreDelegate, CoreDelegateHandler } from '@classes/delegate'; | ||||||
|  | 
 | ||||||
|  | /** | ||||||
|  |  * Interface that all tag area handlers must implement. | ||||||
|  |  */ | ||||||
|  | export interface CoreTagAreaHandler extends CoreDelegateHandler { | ||||||
|  |     /** | ||||||
|  |      * Component and item type separated by a slash. E.g. 'core/course_modules'. | ||||||
|  |      * @type {string} | ||||||
|  |      */ | ||||||
|  |     type: string; | ||||||
|  | 
 | ||||||
|  |     /** | ||||||
|  |      * Parses the rendered content of a tag index and returns the items. | ||||||
|  |      * | ||||||
|  |      * @param {string} content Rendered content. | ||||||
|  |      * @return {any[]|Promise<any[]>} Area items (or promise resolved with the items). | ||||||
|  |      */ | ||||||
|  |     parseContent(content: string): any[] | Promise<any[]>; | ||||||
|  | 
 | ||||||
|  |     /** | ||||||
|  |      * Get the component to use to display items. | ||||||
|  |      * | ||||||
|  |      * @param {Injector} injector Injector. | ||||||
|  |      * @return {any|Promise<any>} The component (or promise resolved with component) to use, undefined if not found. | ||||||
|  |      */ | ||||||
|  |     getComponent(injector: Injector): any | Promise<any>; | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | /** | ||||||
|  |  * Delegate to register tag area handlers. | ||||||
|  |  */ | ||||||
|  | @Injectable() | ||||||
|  | export class CoreTagAreaDelegate extends CoreDelegate { | ||||||
|  | 
 | ||||||
|  |     protected handlerNameProperty = 'type'; | ||||||
|  | 
 | ||||||
|  |     constructor(logger: CoreLoggerProvider, sitesProvider: CoreSitesProvider, eventsProvider: CoreEventsProvider) { | ||||||
|  |         super('CoreTagAreaDelegate', logger, sitesProvider, eventsProvider); | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     /** | ||||||
|  |      * Returns the display name string for this area. | ||||||
|  |      * | ||||||
|  |      * @param {string} component Component name. | ||||||
|  |      * @param {string} itemType Item type. | ||||||
|  |      * @return {string} String key. | ||||||
|  |      */ | ||||||
|  |     getDisplayNameKey(component: string, itemType: string): string { | ||||||
|  |         return (component == 'core' ? 'core.tag' : 'addon.' + component) + '.tagarea_' + itemType; | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     /** | ||||||
|  |      * Parses the rendered content of a tag index and returns the items. | ||||||
|  |      * | ||||||
|  |      * @param {string} component Component name. | ||||||
|  |      * @param {string} itemType Item type. | ||||||
|  |      * @param {string} content Rendered content. | ||||||
|  |      * @return {Promise<any[]>} Promise resolved with the area items, or undefined if not found. | ||||||
|  |      */ | ||||||
|  |     parseContent(component: string, itemType: string, content: string): Promise<any[]> { | ||||||
|  |         const type = component + '/' + itemType; | ||||||
|  | 
 | ||||||
|  |         return Promise.resolve(this.executeFunctionOnEnabled(type, 'parseContent', [content])); | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     /** | ||||||
|  |      * Get the component to use to display an area item. | ||||||
|  |      * | ||||||
|  |      * @param {string} component Component name. | ||||||
|  |      * @param {string} itemType Item type. | ||||||
|  |      * @param {Injector} injector Injector. | ||||||
|  |      * @return {Promise<any>} The component (or promise resolved with component) to use, undefined if not found. | ||||||
|  |      */ | ||||||
|  |     getComponent(component: string, itemType: string, injector: Injector): Promise<any> { | ||||||
|  |         const type = component + '/' + itemType; | ||||||
|  | 
 | ||||||
|  |         return Promise.resolve(this.executeFunctionOnEnabled(type, 'getComponent', [injector])); | ||||||
|  |     } | ||||||
|  | } | ||||||
							
								
								
									
										81
									
								
								src/core/tag/providers/helper.ts
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										81
									
								
								src/core/tag/providers/helper.ts
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,81 @@ | |||||||
|  | // (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 { Injectable } from '@angular/core'; | ||||||
|  | import { CoreDomUtilsProvider } from '@providers/utils/dom'; | ||||||
|  | 
 | ||||||
|  | /** | ||||||
|  |  * Service with helper functions for tags. | ||||||
|  |  */ | ||||||
|  | @Injectable() | ||||||
|  | export class CoreTagHelperProvider { | ||||||
|  | 
 | ||||||
|  |     constructor(protected domUtils: CoreDomUtilsProvider) {} | ||||||
|  | 
 | ||||||
|  |     /** | ||||||
|  |      * Parses the rendered content of the "core_tag/tagfeed" web template and returns the items. | ||||||
|  |      * | ||||||
|  |      * @param {string} content Rendered content. | ||||||
|  |      * @return {any[]} Area items. | ||||||
|  |      */ | ||||||
|  |     parseFeedContent(content: string): any[] { | ||||||
|  |         const items = []; | ||||||
|  |         const element = this.domUtils.convertToElement(content); | ||||||
|  | 
 | ||||||
|  |         Array.from(element.querySelectorAll('ul.tag_feed > li.media')).forEach((itemElement) => { | ||||||
|  |             const item: any = { details: [] }; | ||||||
|  | 
 | ||||||
|  |             Array.from(itemElement.querySelectorAll('div.media-body > div')).forEach((div: HTMLElement) => { | ||||||
|  |                 if (div.classList.contains('media-heading')) { | ||||||
|  |                     item.heading = div.innerText.trim(); | ||||||
|  |                     const link = div.querySelector('a'); | ||||||
|  |                     if (link) { | ||||||
|  |                         item.url = link.getAttribute('href'); | ||||||
|  |                     } | ||||||
|  |                 } else { | ||||||
|  |                     // Separate details by lines.
 | ||||||
|  |                     const lines = ['']; | ||||||
|  |                     Array.from(div.childNodes).forEach((childNode: Node) => { | ||||||
|  |                         if (childNode.nodeType == Node.TEXT_NODE) { | ||||||
|  |                             lines[lines.length - 1] += childNode.textContent; | ||||||
|  |                         } else if (childNode.nodeType == Node.ELEMENT_NODE) { | ||||||
|  |                             const childElement = childNode as HTMLElement; | ||||||
|  |                             if (childElement.tagName == 'BR') { | ||||||
|  |                                 lines.push(''); | ||||||
|  |                             } else { | ||||||
|  |                                 lines[lines.length - 1] += childElement.innerText; | ||||||
|  |                             } | ||||||
|  |                         } | ||||||
|  |                     }); | ||||||
|  |                     item.details.push(...lines.map((line) => line.trim()).filter((line) => line != '')); | ||||||
|  |                 } | ||||||
|  |             }); | ||||||
|  | 
 | ||||||
|  |             const image = itemElement.querySelector('div.itemimage img'); | ||||||
|  |             if (image) { | ||||||
|  |                 if (image.classList.contains('userpicture')) { | ||||||
|  |                     item.avatarUrl = image.getAttribute('src'); | ||||||
|  |                 } else { | ||||||
|  |                     item.iconUrl = image.getAttribute('src'); | ||||||
|  |                 } | ||||||
|  |             } | ||||||
|  | 
 | ||||||
|  |             if (item.heading && item.url) { | ||||||
|  |                 items.push(item); | ||||||
|  |             } | ||||||
|  |         }); | ||||||
|  | 
 | ||||||
|  |         return items; | ||||||
|  |     } | ||||||
|  | } | ||||||
| @ -14,6 +14,8 @@ | |||||||
| 
 | 
 | ||||||
| import { NgModule } from '@angular/core'; | import { NgModule } from '@angular/core'; | ||||||
| import { CoreTagProvider } from './providers/tag'; | import { CoreTagProvider } from './providers/tag'; | ||||||
|  | import { CoreTagHelperProvider } from './providers/helper'; | ||||||
|  | import { CoreTagAreaDelegate } from './providers/area-delegate'; | ||||||
| 
 | 
 | ||||||
| @NgModule({ | @NgModule({ | ||||||
|     declarations: [ |     declarations: [ | ||||||
| @ -22,6 +24,8 @@ import { CoreTagProvider } from './providers/tag'; | |||||||
|     ], |     ], | ||||||
|     providers: [ |     providers: [ | ||||||
|         CoreTagProvider, |         CoreTagProvider, | ||||||
|  |         CoreTagHelperProvider, | ||||||
|  |         CoreTagAreaDelegate | ||||||
|     ] |     ] | ||||||
| }) | }) | ||||||
| export class CoreTagModule { | export class CoreTagModule { | ||||||
|  | |||||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user