1 57 package org.enhydra.apache.html.dom; 58 59 60 import org.w3c.dom.Element ; 61 import org.w3c.dom.Node ; 62 import org.w3c.dom.html.HTMLAnchorElement; 63 import org.w3c.dom.html.HTMLAppletElement; 64 import org.w3c.dom.html.HTMLAreaElement; 65 import org.w3c.dom.html.HTMLCollection; 66 import org.w3c.dom.html.HTMLElement; 67 import org.w3c.dom.html.HTMLFormElement; 68 import org.w3c.dom.html.HTMLImageElement; 69 import org.w3c.dom.html.HTMLObjectElement; 70 import org.w3c.dom.html.HTMLOptionElement; 71 import org.w3c.dom.html.HTMLTableCellElement; 72 import org.w3c.dom.html.HTMLTableRowElement; 73 import org.w3c.dom.html.HTMLTableSectionElement; 74 75 76 101 class HTMLCollectionImpl 102 implements HTMLCollection 103 { 104 105 106 110 static final short ANCHOR = 1; 111 112 113 116 static final short FORM = 2; 117 118 119 122 static final short IMAGE = 3; 123 124 125 129 static final short APPLET = 4; 130 131 132 136 static final short LINK = 5; 137 138 139 143 static final short OPTION = 6; 144 145 146 150 static final short ROW = 7; 151 152 153 158 static final short ELEMENT = 8; 159 160 161 165 static final short AREA = -1; 166 167 168 172 static final short TBODY = -2; 173 174 175 179 static final short CELL = -3; 180 181 182 187 private short _lookingFor; 188 189 190 193 private Element _topLevel; 194 195 196 204 HTMLCollectionImpl( HTMLElement topLevel, short lookingFor ) 205 { 206 if ( topLevel == null ) 207 throw new NullPointerException ( "HTM011 Argument 'topLevel' is null." ); 208 _topLevel = topLevel; 209 _lookingFor = lookingFor; 210 } 211 212 213 219 public final int getLength() 220 { 221 return getLength( _topLevel ); 223 } 224 225 226 234 public final Node item( int index ) 235 { 236 if ( index < 0 ) 237 throw new IllegalArgumentException ( "HTM012 Argument 'index' is negative." ); 238 return item( _topLevel, new CollectionIndex( index ) ); 240 } 241 242 243 252 public final Node namedItem( String name ) 253 { 254 if ( name == null ) 255 throw new NullPointerException ( "HTM013 Argument 'name' is null." ); 256 return namedItem( _topLevel, name ); 258 } 259 260 261 269 private int getLength( Element topLevel ) 270 { 271 int length; 272 Node node; 273 274 synchronized ( topLevel ) 275 { 276 length = 0; 279 node = topLevel.getFirstChild(); 280 while ( node != null ) 281 { 282 if ( node instanceof Element ) 287 { 288 if ( collectionMatch( (Element ) node, null ) ) 289 ++ length; 290 else if ( recurse() ) 291 length += getLength( (Element ) node ); 292 } 293 node = node.getNextSibling(); 294 } 295 } 296 return length; 297 } 298 299 300 316 private Node item( Element topLevel, CollectionIndex index ) 317 { 318 Node node; 319 Node result; 320 321 synchronized ( topLevel ) 322 { 323 node = topLevel.getFirstChild(); 327 while ( node != null ) 328 { 329 if ( node instanceof Element ) 334 { 335 if ( collectionMatch( (Element ) node, null ) ) 336 { 337 if ( index.isZero() ) 338 return node; 339 index.decrement(); 340 } else if ( recurse() ) 341 { 342 result = item( (Element ) node, index ); 343 if ( result != null ) 344 return result; 345 } 346 } 347 node = node.getNextSibling(); 348 } 349 } 350 return null; 351 } 352 353 354 362 private Node namedItem( Element topLevel, String name ) 363 { 364 Node node; 365 Node result; 366 367 synchronized ( topLevel ) 368 { 369 node = topLevel.getFirstChild(); 372 while ( node != null ) 373 { 374 if ( node instanceof Element ) 379 { 380 if ( collectionMatch( (Element ) node, name ) ) 381 return node; 382 else if ( recurse() ) 383 { 384 result = namedItem( (Element ) node, name ); 385 if ( result != null ) 386 return result; 387 } 388 } 389 node = node.getNextSibling(); 390 } 391 return node; 392 } 393 } 394 395 396 404 protected boolean recurse() 405 { 406 return _lookingFor > 0; 407 } 408 409 410 421 protected boolean collectionMatch( Element elem, String name ) 422 { 423 boolean match; 424 425 synchronized ( elem ) 426 { 427 match = false; 432 switch ( _lookingFor ) 433 { 434 case ANCHOR: 435 match = ( elem instanceof HTMLAnchorElement ) && 438 elem.getAttribute( "name" ).length() > 0; 439 break; 440 case FORM: 441 match = ( elem instanceof HTMLFormElement ); 443 break; 444 case IMAGE: 445 match = ( elem instanceof HTMLImageElement ); 447 break; 448 case APPLET: 449 match = ( elem instanceof HTMLAppletElement ) || 453 ( elem instanceof HTMLObjectElement && 454 ( "application/java".equals( elem.getAttribute( "codetype" ) ) || 455 elem.getAttribute( "classid" ).startsWith( "java:" ) ) ); 456 break; 457 case ELEMENT: 458 match = ( elem instanceof HTMLFormControl ); 460 break; 461 case LINK: 462 match = ( ( elem instanceof HTMLAnchorElement || 464 elem instanceof HTMLAreaElement ) && 465 elem.getAttribute( "href" ).length() > 0 ); 466 break; 467 case AREA: 468 match = ( elem instanceof HTMLAreaElement ); 470 break; 471 case OPTION: 472 match = ( elem instanceof HTMLOptionElement ); 474 break; 475 case ROW: 476 match = ( elem instanceof HTMLTableRowElement ); 478 break; 479 case TBODY: 480 match = ( elem instanceof HTMLTableSectionElement && 482 elem.getTagName().equals( "tbody" ) ); 483 break; 484 case CELL: 485 match = ( elem instanceof HTMLTableCellElement ); 487 break; 488 } 489 490 if ( match && name != null ) 494 { 495 if ( elem instanceof HTMLAnchorElement && 498 name.equals( elem.getAttribute( "name" ) ) ) 499 return true; 500 match = name.equals( elem.getAttribute( "id" ) ); 501 } 502 } 503 return match; 504 } 505 506 507 } 508 509 510 519 class CollectionIndex 520 { 521 522 523 528 int getIndex() 529 { 530 return _index; 531 } 532 533 534 537 void decrement() 538 { 539 -- _index; 540 } 541 542 543 548 boolean isZero() 549 { 550 return _index <= 0; 551 } 552 553 554 560 CollectionIndex( int index ) 561 { 562 _index = index; 563 } 564 565 566 569 private int _index; 570 571 572 } 573 | Popular Tags |