@@ -10,6 +10,7 @@ var url = require('url');
1010import { List , MapWrapper , ListWrapper , StringMapWrapper } from 'angular2/src/facade/collection' ;
1111import { DomAdapter , setRootDomAdapter } from './dom_adapter' ;
1212import { BaseException , isPresent , isBlank } from 'angular2/src/facade/lang' ;
13+ import { SelectorMatcher , CssSelector } from 'angular2/src/core/compiler/selector' ;
1314
1415var _attrToPropMap = {
1516 'inner-html' : 'innerHTML' ,
@@ -35,27 +36,55 @@ export class Parse5DomAdapter extends DomAdapter {
3536 throw _notImplemented ( 'query' ) ;
3637 }
3738 querySelector ( el , selector :string ) {
38- throw _notImplemented ( 'querySelector' ) ;
39+ return this . querySelectorAll ( el , selector ) [ 0 ] ;
3940 }
4041 querySelectorAll ( el , selector :string ) {
41- //TODO: use selector class from core. For now, only works for .classname ...
4242 var res = ListWrapper . create ( ) ;
43- var _recursive = ( result , node , className ) => {
44- if ( this . hasClass ( node , className ) ) {
43+ var _recursive = ( result , node , selector , matcher ) => {
44+ if ( this . elementMatches ( node , selector , matcher ) ) {
4545 ListWrapper . push ( result , node ) ;
4646 }
4747 var cNodes = node . childNodes ;
4848 if ( cNodes && cNodes . length > 0 ) {
4949 for ( var i = 0 ; i < cNodes . length ; i ++ ) {
50- _recursive ( result , cNodes [ i ] , className ) ;
50+ _recursive ( result , cNodes [ i ] , selector , matcher ) ;
5151 }
5252 }
5353 } ;
54- _recursive ( res , el , selector . substring ( 1 ) ) ;
54+ var matcher = new SelectorMatcher ( ) ;
55+ matcher . addSelectable ( CssSelector . parse ( selector ) ) ;
56+ _recursive ( res , el , selector , matcher ) ;
5557 return res ;
5658 }
59+ elementMatches ( node , selector :string , matcher = null ) :boolean {
60+ var result = false ;
61+ if ( selector && selector . charAt ( 0 ) == "#" ) {
62+ result = this . getAttribute ( node , 'id' ) == selector . substring ( 1 ) ;
63+ } else if ( selector ) {
64+ var result = false ;
65+ if ( matcher == null ) {
66+ matcher = new SelectorMatcher ( ) ;
67+ matcher . addSelectable ( CssSelector . parse ( selector ) ) ;
68+ }
69+
70+ var cssSelector = new CssSelector ( ) ;
71+ cssSelector . setElement ( this . tagName ( node ) ) ;
72+ if ( node . attribs ) {
73+ for ( var attrName in node . attribs ) {
74+ cssSelector . addAttribute ( attrName , node . attribs [ attrName ] ) ;
75+ }
76+ }
77+ var classList = this . classList ( node ) ;
78+ for ( var i = 0 ; i < classList . length ; i ++ ) {
79+ cssSelector . addClassName ( classList [ i ] ) ;
80+ }
81+
82+ matcher . match ( cssSelector , function ( selector , cb ) { result = true ; } ) ;
83+ }
84+ return result ;
85+ }
5786 on ( el , evt , listener ) {
58- throw _notImplemented ( 'on' ) ;
87+ //Do nothing, in order to not break forms integration tests
5988 }
6089 dispatchEvent ( el , evt ) {
6190 throw _notImplemented ( 'dispatchEvent' ) ;
@@ -316,7 +345,7 @@ export class Parse5DomAdapter extends DomAdapter {
316345 return res ;
317346 }
318347 getAttribute ( element , attribute :string ) {
319- return element . attribs . hasOwnProperty ( attribute ) ? element . attribs [ attribute ] : null ;
348+ return element . attribs && element . attribs . hasOwnProperty ( attribute ) ? element . attribs [ attribute ] : null ;
320349 }
321350 setAttribute ( element , attribute :string , value :string ) {
322351 if ( attribute ) {
@@ -341,14 +370,6 @@ export class Parse5DomAdapter extends DomAdapter {
341370 }
342371 return defDoc ;
343372 }
344- elementMatches ( n , selector :string ) :boolean {
345- //TODO: use selector class from core.
346- if ( selector && selector . charAt ( 0 ) == "." ) {
347- return this . hasClass ( n , selector . substring ( 1 ) ) ;
348- } else {
349- return n . tagName == selector ;
350- }
351- }
352373 isTemplateElement ( el :any ) :boolean {
353374 return this . isElementNode ( el ) && this . tagName ( el ) === "template" ;
354375 }
0 commit comments