| 
									
										
										
										
											2016-06-23 09:47:54 -07:00
										 |  |  | /** | 
					
						
							|  |  |  |  * @license | 
					
						
							|  |  |  |  * Copyright Google Inc. All Rights Reserved. | 
					
						
							|  |  |  |  * | 
					
						
							|  |  |  |  * Use of this source code is governed by an MIT-style license that can be | 
					
						
							|  |  |  |  * found in the LICENSE file at https://angular.io/license
 | 
					
						
							|  |  |  |  */ | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-04-28 17:50:03 -07:00
										 |  |  | import {Injector} from '../di'; | 
					
						
							| 
									
										
										
										
											2017-03-14 09:16:15 -07:00
										 |  |  | import {DebugContext} from '../view/index'; | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-09-22 19:51:03 +02:00
										 |  |  | export class EventListener { | 
					
						
							|  |  |  |   constructor(public name: string, public callback: Function) {} | 
					
						
							|  |  |  | } | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-05-25 15:00:05 -07:00
										 |  |  | /** | 
					
						
							| 
									
										
										
										
											2016-06-27 12:27:23 -07:00
										 |  |  |  * @experimental All debugging apis are currently experimental. | 
					
						
							| 
									
										
										
										
											2016-05-25 15:00:05 -07:00
										 |  |  |  */ | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  | export class DebugNode { | 
					
						
							|  |  |  |   nativeNode: any; | 
					
						
							|  |  |  |   listeners: EventListener[]; | 
					
						
							| 
									
										
										
										
											2017-03-29 09:34:45 -07:00
										 |  |  |   parent: DebugElement|null; | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-03-29 09:34:45 -07:00
										 |  |  |   constructor(nativeNode: any, parent: DebugNode|null, private _debugContext: DebugContext) { | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  |     this.nativeNode = nativeNode; | 
					
						
							| 
									
										
										
										
											2016-11-03 16:58:27 -07:00
										 |  |  |     if (parent && parent instanceof DebugElement) { | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  |       parent.addChild(this); | 
					
						
							|  |  |  |     } else { | 
					
						
							|  |  |  |       this.parent = null; | 
					
						
							|  |  |  |     } | 
					
						
							|  |  |  |     this.listeners = []; | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-03-29 09:34:45 -07:00
										 |  |  |   get injector(): Injector { return this._debugContext.injector; } | 
					
						
							| 
									
										
										
										
											2016-01-06 14:13:44 -08:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-03-29 09:34:45 -07:00
										 |  |  |   get componentInstance(): any { return this._debugContext.component; } | 
					
						
							| 
									
										
										
										
											2016-01-06 14:13:44 -08:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-03-29 09:34:45 -07:00
										 |  |  |   get context(): any { return this._debugContext.context; } | 
					
						
							| 
									
										
										
										
											2016-04-28 14:00:31 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-03-29 09:34:45 -07:00
										 |  |  |   get references(): {[key: string]: any} { return this._debugContext.references; } | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-03-29 09:34:45 -07:00
										 |  |  |   get providerTokens(): any[] { return this._debugContext.providerTokens; } | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-05-25 15:00:05 -07:00
										 |  |  | /** | 
					
						
							| 
									
										
										
										
											2016-06-27 12:27:23 -07:00
										 |  |  |  * @experimental All debugging apis are currently experimental. | 
					
						
							| 
									
										
										
										
											2016-05-25 15:00:05 -07:00
										 |  |  |  */ | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  | export class DebugElement extends DebugNode { | 
					
						
							|  |  |  |   name: string; | 
					
						
							| 
									
										
										
										
											2016-06-03 10:51:13 -07:00
										 |  |  |   properties: {[key: string]: any}; | 
					
						
							| 
									
										
										
										
											2017-03-29 09:34:45 -07:00
										 |  |  |   attributes: {[key: string]: string | null}; | 
					
						
							| 
									
										
										
										
											2016-06-01 16:57:12 -07:00
										 |  |  |   classes: {[key: string]: boolean}; | 
					
						
							| 
									
										
										
										
											2017-03-29 09:34:45 -07:00
										 |  |  |   styles: {[key: string]: string | null}; | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  |   childNodes: DebugNode[]; | 
					
						
							|  |  |  |   nativeElement: any; | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2017-03-14 09:16:15 -07:00
										 |  |  |   constructor(nativeNode: any, parent: any, _debugContext: DebugContext) { | 
					
						
							|  |  |  |     super(nativeNode, parent, _debugContext); | 
					
						
							| 
									
										
										
										
											2016-01-06 14:13:44 -08:00
										 |  |  |     this.properties = {}; | 
					
						
							|  |  |  |     this.attributes = {}; | 
					
						
							| 
									
										
										
										
											2016-06-01 16:57:12 -07:00
										 |  |  |     this.classes = {}; | 
					
						
							|  |  |  |     this.styles = {}; | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  |     this.childNodes = []; | 
					
						
							|  |  |  |     this.nativeElement = nativeNode; | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   addChild(child: DebugNode) { | 
					
						
							| 
									
										
										
										
											2016-11-03 16:58:27 -07:00
										 |  |  |     if (child) { | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  |       this.childNodes.push(child); | 
					
						
							|  |  |  |       child.parent = this; | 
					
						
							|  |  |  |     } | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   removeChild(child: DebugNode) { | 
					
						
							| 
									
										
										
										
											2016-11-03 16:58:27 -07:00
										 |  |  |     const childIndex = this.childNodes.indexOf(child); | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  |     if (childIndex !== -1) { | 
					
						
							|  |  |  |       child.parent = null; | 
					
						
							|  |  |  |       this.childNodes.splice(childIndex, 1); | 
					
						
							|  |  |  |     } | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   insertChildrenAfter(child: DebugNode, newChildren: DebugNode[]) { | 
					
						
							| 
									
										
										
										
											2016-11-03 16:58:27 -07:00
										 |  |  |     const siblingIndex = this.childNodes.indexOf(child); | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  |     if (siblingIndex !== -1) { | 
					
						
							| 
									
										
										
										
											2017-02-14 21:03:18 -08:00
										 |  |  |       this.childNodes.splice(siblingIndex + 1, 0, ...newChildren); | 
					
						
							|  |  |  |       newChildren.forEach(c => { | 
					
						
							|  |  |  |         if (c.parent) { | 
					
						
							|  |  |  |           c.parent.removeChild(c); | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  |         } | 
					
						
							| 
									
										
										
										
											2017-02-14 21:03:18 -08:00
										 |  |  |         c.parent = this; | 
					
						
							|  |  |  |       }); | 
					
						
							|  |  |  |     } | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   insertBefore(refChild: DebugNode, newChild: DebugNode): void { | 
					
						
							|  |  |  |     const refIndex = this.childNodes.indexOf(refChild); | 
					
						
							|  |  |  |     if (refIndex === -1) { | 
					
						
							|  |  |  |       this.addChild(newChild); | 
					
						
							|  |  |  |     } else { | 
					
						
							|  |  |  |       if (newChild.parent) { | 
					
						
							|  |  |  |         newChild.parent.removeChild(newChild); | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  |       } | 
					
						
							| 
									
										
										
										
											2017-02-14 21:03:18 -08:00
										 |  |  |       newChild.parent = this; | 
					
						
							|  |  |  |       this.childNodes.splice(refIndex, 0, newChild); | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  |     } | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   query(predicate: Predicate<DebugElement>): DebugElement { | 
					
						
							| 
									
										
										
										
											2016-11-03 16:58:27 -07:00
										 |  |  |     const results = this.queryAll(predicate); | 
					
						
							|  |  |  |     return results[0] || null; | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   queryAll(predicate: Predicate<DebugElement>): DebugElement[] { | 
					
						
							| 
									
										
										
										
											2016-11-03 16:58:27 -07:00
										 |  |  |     const matches: DebugElement[] = []; | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  |     _queryElementChildren(this, predicate, matches); | 
					
						
							|  |  |  |     return matches; | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   queryAllNodes(predicate: Predicate<DebugNode>): DebugNode[] { | 
					
						
							| 
									
										
										
										
											2016-11-03 16:58:27 -07:00
										 |  |  |     const matches: DebugNode[] = []; | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  |     _queryNodeChildren(this, predicate, matches); | 
					
						
							|  |  |  |     return matches; | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   get children(): DebugElement[] { | 
					
						
							| 
									
										
										
										
											2016-11-03 16:58:27 -07:00
										 |  |  |     return this.childNodes.filter((node) => node instanceof DebugElement) as DebugElement[]; | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-01-06 14:13:44 -08:00
										 |  |  |   triggerEventHandler(eventName: string, eventObj: any) { | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  |     this.listeners.forEach((listener) => { | 
					
						
							|  |  |  |       if (listener.name == eventName) { | 
					
						
							|  |  |  |         listener.callback(eventObj); | 
					
						
							|  |  |  |       } | 
					
						
							|  |  |  |     }); | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-05-25 15:00:05 -07:00
										 |  |  | /** | 
					
						
							|  |  |  |  * @experimental | 
					
						
							|  |  |  |  */ | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  | export function asNativeElements(debugEls: DebugElement[]): any { | 
					
						
							|  |  |  |   return debugEls.map((el) => el.nativeElement); | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-06-08 16:38:52 -07:00
										 |  |  | function _queryElementChildren( | 
					
						
							|  |  |  |     element: DebugElement, predicate: Predicate<DebugElement>, matches: DebugElement[]) { | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  |   element.childNodes.forEach(node => { | 
					
						
							|  |  |  |     if (node instanceof DebugElement) { | 
					
						
							|  |  |  |       if (predicate(node)) { | 
					
						
							|  |  |  |         matches.push(node); | 
					
						
							|  |  |  |       } | 
					
						
							|  |  |  |       _queryElementChildren(node, predicate, matches); | 
					
						
							|  |  |  |     } | 
					
						
							|  |  |  |   }); | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-06-08 16:38:52 -07:00
										 |  |  | function _queryNodeChildren( | 
					
						
							|  |  |  |     parentNode: DebugNode, predicate: Predicate<DebugNode>, matches: DebugNode[]) { | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  |   if (parentNode instanceof DebugElement) { | 
					
						
							|  |  |  |     parentNode.childNodes.forEach(node => { | 
					
						
							|  |  |  |       if (predicate(node)) { | 
					
						
							|  |  |  |         matches.push(node); | 
					
						
							|  |  |  |       } | 
					
						
							|  |  |  |       if (node instanceof DebugElement) { | 
					
						
							|  |  |  |         _queryNodeChildren(node, predicate, matches); | 
					
						
							|  |  |  |       } | 
					
						
							|  |  |  |     }); | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | // Need to keep the nodes in a global Map so that multiple angular apps are supported.
 | 
					
						
							| 
									
										
										
										
											2016-11-03 16:58:27 -07:00
										 |  |  | const _nativeNodeToDebugNode = new Map<any, DebugNode>(); | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-05-25 15:00:05 -07:00
										 |  |  | /** | 
					
						
							|  |  |  |  * @experimental | 
					
						
							|  |  |  |  */ | 
					
						
							| 
									
										
										
										
											2017-03-29 09:34:45 -07:00
										 |  |  | export function getDebugNode(nativeNode: any): DebugNode|null { | 
					
						
							|  |  |  |   return _nativeNodeToDebugNode.get(nativeNode) || null; | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | export function getAllDebugNodes(): DebugNode[] { | 
					
						
							| 
									
										
										
										
											2016-11-03 16:58:27 -07:00
										 |  |  |   return Array.from(_nativeNodeToDebugNode.values()); | 
					
						
							| 
									
										
										
										
											2016-01-13 21:35:21 -08:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | export function indexDebugNode(node: DebugNode) { | 
					
						
							|  |  |  |   _nativeNodeToDebugNode.set(node.nativeNode, node); | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | export function removeDebugNodeFromIndex(node: DebugNode) { | 
					
						
							|  |  |  |   _nativeNodeToDebugNode.delete(node.nativeNode); | 
					
						
							|  |  |  | } | 
					
						
							| 
									
										
										
										
											2017-03-01 14:10:59 -08:00
										 |  |  | 
 | 
					
						
							|  |  |  | /** | 
					
						
							|  |  |  |  * A boolean-valued function over a value, possibly including context information | 
					
						
							|  |  |  |  * regarding that value's position in an array. | 
					
						
							|  |  |  |  * | 
					
						
							|  |  |  |  * @experimental All debugging apis are currently experimental. | 
					
						
							|  |  |  |  */ | 
					
						
							| 
									
										
										
										
											2017-03-29 09:34:45 -07:00
										 |  |  | export interface Predicate<T> { (value: T): boolean; } |