1 16 package org.apache.html.dom; 17 18 19 import org.w3c.dom.Element ; 20 import org.w3c.dom.Node ; 21 import org.w3c.dom.html.HTMLAnchorElement; 22 import org.w3c.dom.html.HTMLAppletElement; 23 import org.w3c.dom.html.HTMLAreaElement; 24 import org.w3c.dom.html.HTMLCollection; 25 import org.w3c.dom.html.HTMLElement; 26 import org.w3c.dom.html.HTMLFormElement; 27 import org.w3c.dom.html.HTMLImageElement; 28 import org.w3c.dom.html.HTMLObjectElement; 29 import org.w3c.dom.html.HTMLOptionElement; 30 import org.w3c.dom.html.HTMLTableCellElement; 31 import org.w3c.dom.html.HTMLTableRowElement; 32 import org.w3c.dom.html.HTMLTableSectionElement; 33 34 35 61 class HTMLCollectionImpl 62 implements HTMLCollection 63 { 64 65 66 70 static final short ANCHOR = 1; 71 72 73 76 static final short FORM = 2; 77 78 79 82 static final short IMAGE = 3; 83 84 85 89 static final short APPLET = 4; 90 91 92 96 static final short LINK = 5; 97 98 99 103 static final short OPTION = 6; 104 105 106 110 static final short ROW = 7; 111 112 113 118 static final short ELEMENT = 8; 119 120 121 125 static final short AREA = -1; 126 127 128 132 static final short TBODY = -2; 133 134 135 139 static final short CELL = -3; 140 141 142 147 private short _lookingFor; 148 149 150 153 private Element _topLevel; 154 155 156 164 HTMLCollectionImpl( HTMLElement topLevel, short lookingFor ) 165 { 166 if ( topLevel == null ) 167 throw new NullPointerException ( "HTM011 Argument 'topLevel' is null." ); 168 _topLevel = topLevel; 169 _lookingFor = lookingFor; 170 } 171 172 173 179 public final int getLength() 180 { 181 return getLength( _topLevel ); 183 } 184 185 186 194 public final Node item( int index ) 195 { 196 if ( index < 0 ) 197 throw new IllegalArgumentException ( "HTM012 Argument 'index' is negative." ); 198 return item( _topLevel, new CollectionIndex( index ) ); 200 } 201 202 203 212 public final Node namedItem( String name ) 213 { 214 if ( name == null ) 215 throw new NullPointerException ( "HTM013 Argument 'name' is null." ); 216 return namedItem( _topLevel, name ); 218 } 219 220 221 229 private int getLength( Element topLevel ) 230 { 231 int length; 232 Node node; 233 234 synchronized ( topLevel ) 235 { 236 length = 0; 239 node = topLevel.getFirstChild(); 240 while ( node != null ) 241 { 242 if ( node instanceof Element ) 247 { 248 if ( collectionMatch( (Element ) node, null ) ) 249 ++ length; 250 else if ( recurse() ) 251 length += getLength( (Element ) node ); 252 } 253 node = node.getNextSibling(); 254 } 255 } 256 return length; 257 } 258 259 260 276 private Node item( Element topLevel, CollectionIndex index ) 277 { 278 Node node; 279 Node result; 280 281 synchronized ( topLevel ) 282 { 283 node = topLevel.getFirstChild(); 287 while ( node != null ) 288 { 289 if ( node instanceof Element ) 294 { 295 if ( collectionMatch( (Element ) node, null ) ) 296 { 297 if ( index.isZero() ) 298 return node; 299 index.decrement(); 300 } else if ( recurse() ) 301 { 302 result = item( (Element ) node, index ); 303 if ( result != null ) 304 return result; 305 } 306 } 307 node = node.getNextSibling(); 308 } 309 } 310 return null; 311 } 312 313 314 322 private Node namedItem( Element topLevel, String name ) 323 { 324 Node node; 325 Node result; 326 327 synchronized ( topLevel ) 328 { 329 node = topLevel.getFirstChild(); 332 while ( node != null ) 333 { 334 if ( node instanceof Element ) 339 { 340 if ( collectionMatch( (Element ) node, name ) ) 341 return node; 342 else if ( recurse() ) 343 { 344 result = namedItem( (Element ) node, name ); 345 if ( result != null ) 346 return result; 347 } 348 } 349 node = node.getNextSibling(); 350 } 351 return node; 352 } 353 } 354 355 356 364 protected boolean recurse() 365 { 366 return _lookingFor > 0; 367 } 368 369 370 381 protected boolean collectionMatch( Element elem, String name ) 382 { 383 boolean match; 384 385 synchronized ( elem ) 386 { 387 match = false; 392 switch ( _lookingFor ) 393 { 394 case ANCHOR: 395 match = ( elem instanceof HTMLAnchorElement ) && 398 elem.getAttribute( "name" ).length() > 0; 399 break; 400 case FORM: 401 match = ( elem instanceof HTMLFormElement ); 403 break; 404 case IMAGE: 405 match = ( elem instanceof HTMLImageElement ); 407 break; 408 case APPLET: 409 match = ( elem instanceof HTMLAppletElement ) || 413 ( elem instanceof HTMLObjectElement && 414 ( "application/java".equals( elem.getAttribute( "codetype" ) ) || 415 elem.getAttribute( "classid" ).startsWith( "java:" ) ) ); 416 break; 417 case ELEMENT: 418 match = ( elem instanceof HTMLFormControl ); 420 break; 421 case LINK: 422 match = ( ( elem instanceof HTMLAnchorElement || 424 elem instanceof HTMLAreaElement ) && 425 elem.getAttribute( "href" ).length() > 0 ); 426 break; 427 case AREA: 428 match = ( elem instanceof HTMLAreaElement ); 430 break; 431 case OPTION: 432 match = ( elem instanceof HTMLOptionElement ); 434 break; 435 case ROW: 436 match = ( elem instanceof HTMLTableRowElement ); 438 break; 439 case TBODY: 440 match = ( elem instanceof HTMLTableSectionElement && 442 elem.getTagName().equals( "tbody" ) ); 443 break; 444 case CELL: 445 match = ( elem instanceof HTMLTableCellElement ); 447 break; 448 } 449 450 if ( match && name != null ) 454 { 455 if ( elem instanceof HTMLAnchorElement && 458 name.equals( elem.getAttribute( "name" ) ) ) 459 return true; 460 match = name.equals( elem.getAttribute( "id" ) ); 461 } 462 } 463 return match; 464 } 465 466 467 } 468 469 470 481 class CollectionIndex 482 { 483 484 485 490 int getIndex() 491 { 492 return _index; 493 } 494 495 496 499 void decrement() 500 { 501 -- _index; 502 } 503 504 505 510 boolean isZero() 511 { 512 return _index <= 0; 513 } 514 515 516 522 CollectionIndex( int index ) 523 { 524 _index = index; 525 } 526 527 528 531 private int _index; 532 533 534 } 535 | Popular Tags |