1 /* DomHTMLDocument.java -- 2 Copyright (C) 2005 Free Software Foundation, Inc. 3 4 This file is part of GNU Classpath. 5 6 GNU Classpath is free software; you can redistribute it and/or modify 7 it under the terms of the GNU General Public License as published by 8 the Free Software Foundation; either version 2, or (at your option) 9 any later version. 10 11 GNU Classpath is distributed in the hope that it will be useful, but 12 WITHOUT ANY WARRANTY; without even the implied warranty of 13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 14 General Public License for more details. 15 16 You should have received a copy of the GNU General Public License 17 along with GNU Classpath; see the file COPYING. If not, write to the 18 Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 19 02110-1301 USA. 20 21 Linking this library statically or dynamically with other modules is 22 making a combined work based on this library. Thus, the terms and 23 conditions of the GNU General Public License cover the whole 24 combination. 25 26 As a special exception, the copyright holders of this library give you 27 permission to link this library with independent modules to produce an 28 executable, regardless of the license terms of these independent 29 modules, and to copy and distribute the resulting executable under 30 terms of your choice, provided that you also meet, for each linked 31 independent module, the terms and conditions of the license of that 32 module. An independent module is a module which is not derived from 33 or based on this library. If you modify this library, you may extend 34 this exception to your version of the library, but you are not 35 obligated to do so. If you do not wish to do so, delete this 36 exception statement from your version. */ 37 38 package gnu.xml.dom.html2; 39 40 import gnu.xml.dom.DomDocument; 41 import gnu.xml.dom.DomDOMException; 42 import java.lang.reflect.Constructor; 43 import java.net.MalformedURLException; 44 import java.net.URL; 45 import java.util.Collections; 46 import java.util.HashMap; 47 import java.util.HashSet; 48 import java.util.Map; 49 import java.util.Set; 50 import org.w3c.dom.DOMException; 51 import org.w3c.dom.Element; 52 import org.w3c.dom.Node; 53 import org.w3c.dom.NodeList; 54 import org.w3c.dom.html2.HTMLCollection; 55 import org.w3c.dom.html2.HTMLDocument; 56 import org.w3c.dom.html2.HTMLElement; 57 58 /** 59 * An HTML document. 60 * This is the factory object used to create HTML elements. 61 * 62 * @author <a href='mailto:dog@gnu.org'>Chris Burdess</a> 63 */ 64 public class DomHTMLDocument 65 extends DomDocument 66 implements HTMLDocument 67 { 68 69 private static final Class[] ELEMENT_PT = new Class[] { 70 DomHTMLDocument.class, 71 String.class, 72 String.class 73 }; 74 75 private static Map ELEMENT_CLASSES; 76 static 77 { 78 Map map = new HashMap(); 79 map.put("a", DomHTMLAnchorElement.class); 80 map.put("applet", DomHTMLAppletElement.class); 81 map.put("area", DomHTMLAreaElement.class); 82 map.put("base", DomHTMLBaseElement.class); 83 map.put("basefont", DomHTMLBaseFontElement.class); 84 map.put("body", DomHTMLBodyElement.class); 85 map.put("br", DomHTMLBRElement.class); 86 map.put("button", DomHTMLButtonElement.class); 87 map.put("dir", DomHTMLDirectoryElement.class); 88 map.put("div", DomHTMLDivElement.class); 89 map.put("dlist", DomHTMLDListElement.class); 90 map.put("embed", DomHTMLEmbedElement.class); 91 map.put("fieldset", DomHTMLFieldSetElement.class); 92 map.put("font", DomHTMLFontElement.class); 93 map.put("form", DomHTMLFormElement.class); 94 map.put("frame", DomHTMLFrameElement.class); 95 map.put("frameset", DomHTMLFrameSetElement.class); 96 map.put("head", DomHTMLHeadElement.class); 97 map.put("h1", DomHTMLHeadingElement.class); 98 map.put("h2", DomHTMLHeadingElement.class); 99 map.put("h3", DomHTMLHeadingElement.class); 100 map.put("h4", DomHTMLHeadingElement.class); 101 map.put("h5", DomHTMLHeadingElement.class); 102 map.put("h6", DomHTMLHeadingElement.class); 103 map.put("html", DomHTMLHtmlElement.class); 104 map.put("iframe", DomHTMLIFrameElement.class); 105 map.put("img", DomHTMLImageElement.class); 106 map.put("input", DomHTMLInputElement.class); 107 map.put("isindex", DomHTMLIsIndexElement.class); 108 map.put("label", DomHTMLLabelElement.class); 109 map.put("legend", DomHTMLLegendElement.class); 110 map.put("li", DomHTMLLIElement.class); 111 map.put("link", DomHTMLLinkElement.class); 112 map.put("map", DomHTMLMapElement.class); 113 map.put("menu", DomHTMLMenuElement.class); 114 map.put("meta", DomHTMLMetaElement.class); 115 map.put("ins", DomHTMLModElement.class); 116 map.put("del", DomHTMLModElement.class); 117 map.put("object", DomHTMLObjectElement.class); 118 map.put("ol", DomHTMLOListElement.class); 119 map.put("optgroup", DomHTMLOptGroupElement.class); 120 map.put("option", DomHTMLOptionElement.class); 121 map.put("p", DomHTMLParagraphElement.class); 122 map.put("param", DomHTMLParamElement.class); 123 map.put("pre", DomHTMLPreElement.class); 124 map.put("q", DomHTMLQuoteElement.class); 125 map.put("blockquote", DomHTMLQuoteElement.class); 126 map.put("script", DomHTMLScriptElement.class); 127 map.put("select", DomHTMLSelectElement.class); 128 map.put("style", DomHTMLStyleElement.class); 129 map.put("caption", DomHTMLTableCaptionElement.class); 130 map.put("th", DomHTMLTableCellElement.class); 131 map.put("td", DomHTMLTableCellElement.class); 132 map.put("col", DomHTMLTableColElement.class); 133 map.put("colgroup", DomHTMLTableColElement.class); 134 map.put("table", DomHTMLTableElement.class); 135 map.put("tr", DomHTMLTableRowElement.class); 136 map.put("thead", DomHTMLTableSectionElement.class); 137 map.put("tfoot", DomHTMLTableSectionElement.class); 138 map.put("tbody", DomHTMLTableSectionElement.class); 139 map.put("textarea", DomHTMLTextAreaElement.class); 140 map.put("title", DomHTMLTitleElement.class); 141 map.put("ul", DomHTMLUListElement.class); 142 ELEMENT_CLASSES = Collections.unmodifiableMap(map); 143 } 144 145 private static Set HTML_NS_URIS; 146 static 147 { 148 Set set = new HashSet(); 149 set.add("http://www.w3.org/TR/html4/strict"); 150 set.add("http://www.w3.org/TR/html4/loose"); 151 set.add("http://www.w3.org/TR/html4/frameset"); 152 set.add("http://www.w3.org/1999/xhtml"); 153 set.add("http://www.w3.org/TR/xhtml1/strict"); 154 set.add("http://www.w3.org/TR/xhtml1/loose"); 155 set.add("http://www.w3.org/TR/xhtml1/frameset"); 156 HTML_NS_URIS = Collections.unmodifiableSet(set); 157 } 158 159 /** 160 * Convenience constructor. 161 */ DomHTMLDocument()162 public DomHTMLDocument() 163 { 164 this(new DomHTMLImpl()); 165 } 166 167 /** 168 * Constructor. 169 * This is called by the DOMImplementation. 170 */ DomHTMLDocument(DomHTMLImpl impl)171 public DomHTMLDocument(DomHTMLImpl impl) 172 { 173 super(impl); 174 } 175 getChildNodeByName(Node parent, String name)176 private Node getChildNodeByName(Node parent, String name) 177 { 178 for (Node ctx = parent.getFirstChild(); ctx != null; 179 ctx = ctx.getNextSibling()) 180 { 181 if (name.equalsIgnoreCase(ctx.getNodeName())) 182 { 183 return ctx; 184 } 185 } 186 return null; 187 } 188 getTitle()189 public String getTitle() 190 { 191 Node html = getDocumentElement(); 192 if (html != null) 193 { 194 Node head = getChildNodeByName(html, "head"); 195 if (head != null) 196 { 197 Node title = getChildNodeByName(head, "title"); 198 if (title != null) 199 { 200 return title.getTextContent(); 201 } 202 } 203 } 204 return null; 205 } 206 setTitle(String title)207 public void setTitle(String title) 208 { 209 Node html = getDocumentElement(); 210 if (html == null) 211 { 212 html = createElement("html"); 213 appendChild(html); 214 } 215 Node head = getChildNodeByName(html, "head"); 216 if (head == null) 217 { 218 head = createElement("head"); 219 Node first = html.getFirstChild(); 220 if (first != null) 221 { 222 html.insertBefore(first, head); 223 } 224 else 225 { 226 html.appendChild(head); 227 } 228 } 229 Node titleNode = getChildNodeByName(head, "title"); 230 if (titleNode == null) 231 { 232 titleNode = createElement("title"); 233 Node first = head.getFirstChild(); 234 if (first != null) 235 { 236 head.insertBefore(first, titleNode); 237 } 238 else 239 { 240 head.appendChild(titleNode); 241 } 242 } 243 titleNode.setTextContent(title); 244 } 245 getReferrer()246 public String getReferrer() 247 { 248 // TODO getReferrer 249 return null; 250 } 251 getDomain()252 public String getDomain() 253 { 254 try 255 { 256 URL url = new URL(getDocumentURI()); 257 return url.getHost(); 258 } 259 catch (MalformedURLException e) 260 { 261 return null; 262 } 263 } 264 getURL()265 public String getURL() 266 { 267 return getDocumentURI(); 268 } 269 getBody()270 public HTMLElement getBody() 271 { 272 Node html = getDocumentElement(); 273 if (html != null) 274 { 275 Node body = getChildNodeByName(html, "body"); 276 if (body == null) 277 { 278 body = getChildNodeByName(html, "frameset"); 279 } 280 return (HTMLElement) body; 281 } 282 return null; 283 } 284 setBody(HTMLElement body)285 public void setBody(HTMLElement body) 286 { 287 Node html = getDocumentElement(); 288 if (html == null) 289 { 290 html = createElement("html"); 291 appendChild(html); 292 } 293 Node ref = getBody(); 294 if (ref == null) 295 { 296 html.appendChild(body); 297 } 298 else 299 { 300 html.replaceChild(body, ref); 301 } 302 } 303 getImages()304 public HTMLCollection getImages() 305 { 306 DomHTMLCollection ret = new DomHTMLCollection(this, this); 307 ret.addNodeName("img"); 308 ret.evaluate(); 309 return ret; 310 } 311 getApplets()312 public HTMLCollection getApplets() 313 { 314 DomHTMLCollection ret = new DomHTMLCollection(this, this); 315 ret.addNodeName("embed"); 316 ret.addNodeName("object"); 317 ret.addNodeName("applet"); 318 ret.evaluate(); 319 return ret; 320 } 321 getLinks()322 public HTMLCollection getLinks() 323 { 324 DomHTMLCollection ret = new DomHTMLCollection(this, this); 325 ret.addNodeName("area"); 326 ret.addNodeName("a"); 327 ret.evaluate(); 328 return ret; 329 } 330 getForms()331 public HTMLCollection getForms() 332 { 333 DomHTMLCollection ret = new DomHTMLCollection(this, this); 334 ret.addNodeName("form"); 335 ret.evaluate(); 336 return ret; 337 } 338 getAnchors()339 public HTMLCollection getAnchors() 340 { 341 DomHTMLCollection ret = new DomHTMLCollection(this, this); 342 ret.addNodeName("a"); 343 ret.addAttributeName("name"); 344 ret.evaluate(); 345 return ret; 346 } 347 getCookie()348 public String getCookie() 349 { 350 // TODO getCookie 351 return null; 352 } 353 setCookie(String cookie)354 public void setCookie(String cookie) 355 { 356 // TODO setCookie 357 } 358 open()359 public void open() 360 { 361 // TODO open 362 } 363 close()364 public void close() 365 { 366 // TODO close 367 } 368 write(String text)369 public void write(String text) 370 { 371 // TODO write 372 } 373 writeln(String text)374 public void writeln(String text) 375 { 376 // TODO write 377 } 378 getElementsByName(String name)379 public NodeList getElementsByName(String name) 380 { 381 DomHTMLCollection ret = new DomHTMLCollection(this, this); 382 ret.addNodeName(name); 383 ret.evaluate(); 384 return ret; 385 // TODO xhtml: return only form controls (?) 386 } 387 createElement(String tagName)388 public Element createElement(String tagName) 389 { 390 return createElementNS(null, tagName); 391 } 392 createElementNS(String uri, String qName)393 public Element createElementNS(String uri, String qName) 394 { 395 /* If a non-HTML element, use the default implementation. */ 396 if (uri != null && !HTML_NS_URIS.contains(uri)) 397 { 398 return super.createElementNS(uri, qName); 399 } 400 String localName = qName.toLowerCase(); 401 int ci = qName.indexOf(':'); 402 if (ci != -1) 403 { 404 localName = qName.substring(ci + 1); 405 } 406 Class t = (Class) ELEMENT_CLASSES.get(localName); 407 /* If a non-HTML element, use the default implementation. */ 408 if (t == null) 409 { 410 return super.createElementNS(uri, qName); 411 } 412 try 413 { 414 Constructor c = t.getDeclaredConstructor(ELEMENT_PT); 415 Object[] args = new Object[] { this, uri, qName }; 416 return (Element) c.newInstance(args); 417 } 418 catch (Exception e) 419 { 420 DOMException e2 = new DomDOMException(DOMException.TYPE_MISMATCH_ERR); 421 e2.initCause(e); 422 throw e2; 423 } 424 } 425 426 } 427