/[aagtl_public1]/src/net/htmlparser/jericho/StartTagType.java
aagtl

Contents of /src/net/htmlparser/jericho/StartTagType.java

Parent Directory Parent Directory | Revision Log Revision Log


Revision 2 - (show annotations) (download)
Sun Aug 5 13:48:36 2012 UTC (11 years, 7 months ago) by zoffadmin
File size: 41502 byte(s)
initial import of aagtl source code
1 // Jericho HTML Parser - Java based library for analysing and manipulating HTML
2 // Version 3.2
3 // Copyright (C) 2004-2009 Martin Jericho
4 // http://jericho.htmlparser.net/
5 //
6 // This library is free software; you can redistribute it and/or
7 // modify it under the terms of either one of the following licences:
8 //
9 // 1. The Eclipse Public License (EPL) version 1.0,
10 // included in this distribution in the file licence-epl-1.0.html
11 // or available at http://www.eclipse.org/legal/epl-v10.html
12 //
13 // 2. The GNU Lesser General Public License (LGPL) version 2.1 or later,
14 // included in this distribution in the file licence-lgpl-2.1.txt
15 // or available at http://www.gnu.org/licenses/lgpl.txt
16 //
17 // This library is distributed on an "AS IS" basis,
18 // WITHOUT WARRANTY OF ANY KIND, either express or implied.
19 // See the individual licence texts for more details.
20
21 package net.htmlparser.jericho;
22
23 import java.util.*;
24
25 /**
26 * Defines the syntax for a start tag type.
27 * <p>
28 * A start tag type is any {@link TagType} that {@linkplain #getStartDelimiter() starts} with the character '<code>&lt;</code>'
29 * (as with all tag types), but whose second character is <b>not</b> '<code>/</code>'.
30 * <p>
31 * This includes types for many tags which stand alone, without a {@linkplain #getCorrespondingEndTagType() corresponding end tag},
32 * and would not intuitively be categorised as a "start tag". For example, an HTML {@linkplain #COMMENT comment} in a document
33 * is represented as a single start tag that spans the whole comment, and does not have an end tag at all.
34 * <p>
35 * The singleton instances of all the <a href="TagType.html#Standard">standard</a> start tag types are available in this class as static
36 * <a href="#field_summary">fields</a>.
37 * <p>
38 * Because all <code>StartTagType</code> instaces must be singletons, the '<code>==</code>' operator can be used to test for a particular tag type
39 * instead of the <code>equals(Object)</code> method.
40 *
41 * @see EndTagType
42 */
43 public abstract class StartTagType extends TagType {
44 private final EndTagType correspondingEndTagType;
45 private final boolean hasAttributes;
46 private final boolean isNameAfterPrefixRequired;
47
48 static final String START_DELIMITER_PREFIX="<";
49
50 /**
51 * The tag type given to an {@linkplain Tag#isUnregistered() unregistered} {@linkplain StartTag start tag}
52 * (<code>&lt;<var> &#46;&#46;&#46; </var>&gt;</code>).
53 * <p>
54 * See the documentation of the {@link Tag#isUnregistered()} method for details.
55 * <p>
56 * <dl>
57 * <dt>Properties:</dt>
58 * <dd>
59 * <table class="bordered" style="margin: 15px" cellspacing="0">
60 * <tr><th>Property<th>Value
61 * <tr><td>{@link #getDescription() Description}<td>unregistered
62 * <tr><td>{@link #getStartDelimiter() StartDelimiter}<td><code>&lt;</code>
63 * <tr><td>{@link #getClosingDelimiter() ClosingDelimiter}<td><code>&gt;</code>
64 * <tr><td>{@link #isServerTag() IsServerTag}<td><code>false</code>
65 * <tr><td>{@link #getNamePrefix() NamePrefix}<td><i>(empty&nbsp;string)</i>
66 * <tr><td>{@link #getCorrespondingEndTagType() CorrespondingEndTagType}<td><code>null</code>
67 * <tr><td>{@link #hasAttributes() HasAttributes}<td><code>false</code>
68 * <tr><td>{@link #isNameAfterPrefixRequired() IsNameAfterPrefixRequired}<td><code>false</code>
69 * </table>
70 * <dt>Example:</dt>
71 * <dd><code>&lt;"This is not recognised as any of the predefined tag types in this library"&gt;</code></dd>
72 * </dl>
73 * @see EndTagType#UNREGISTERED
74 */
75 public static final StartTagType UNREGISTERED=StartTagTypeUnregistered.INSTANCE;
76
77 /**
78 * The tag type given to a normal HTML or XML {@linkplain StartTag start tag}
79 * (<code>&lt;<var>name</var><var> &#46;&#46;&#46; </var>&gt;</code>).
80 * <p>
81 * <dl>
82 * <dt>Properties:</dt>
83 * <dd>
84 * <table class="bordered" style="margin: 15px" cellspacing="0">
85 * <tr><th>Property<th>Value
86 * <tr><td>{@link #getDescription() Description}<td>normal
87 * <tr><td>{@link #getStartDelimiter() StartDelimiter}<td><code>&lt;</code>
88 * <tr><td>{@link #getClosingDelimiter() ClosingDelimiter}<td><code>&gt;</code>
89 * <tr><td>{@link #isServerTag() IsServerTag}<td><code>false</code>
90 * <tr><td>{@link #getNamePrefix() NamePrefix}<td><i>(empty&nbsp;string)</i>
91 * <tr><td>{@link #getCorrespondingEndTagType() CorrespondingEndTagType}<td>{@link EndTagType#NORMAL}
92 * <tr><td>{@link #hasAttributes() HasAttributes}<td><code>true</code>
93 * <tr><td>{@link #isNameAfterPrefixRequired() IsNameAfterPrefixRequired}<td><code>true</code>
94 * </table>
95 * <dt>Example:</dt>
96 * <dd><code>&lt;div class="NormalDivTag"&gt;</code></dd>
97 * </dl>
98 */
99 public static final StartTagType NORMAL=StartTagTypeNormal.INSTANCE;
100
101 /**
102 * The tag type given to an HTML <a target="_blank" href="http://www.w3.org/TR/html401/intro/sgmltut.html#h-3.2.4">comment</a>
103 * (<code>&lt;&#33;--<var> &#46;&#46;&#46; </var>--&gt;</code>).
104 * <p>
105 * An HTML comment is an area of the source document enclosed by the delimiters
106 * <code>&lt;!--</code> on the left and <code>--&gt;</code> on the right.
107 * <p>
108 * The <a target="_blank" href="http://www.w3.org/TR/html401/intro/sgmltut.html#h-3.2.4">HTML 4.01 specification section 3.2.4</a>
109 * states that the end of comment delimiter may contain white space between the "<code>--</code>" and "<code>&gt;</code>" characters,
110 * but this library does not recognise end of comment delimiters containing white space.
111 * <p>
112 * In the default configuration, any non-{@linkplain #isServerTag() server} tag appearing within an HTML comment is ignored
113 * by the parser.
114 * See the documentation of the <a href="Tag.html#ParsingProcess">tag parsing process</a> for more information.
115 * <p>
116 * <dl>
117 * <dt>Properties:</dt>
118 * <dd>
119 * <table class="bordered" style="margin: 15px" cellspacing="0">
120 * <tr><th>Property<th>Value
121 * <tr><td>{@link #getDescription() Description}<td>comment
122 * <tr><td>{@link #getStartDelimiter() StartDelimiter}<td><code>&lt;!--</code>
123 * <tr><td>{@link #getClosingDelimiter() ClosingDelimiter}<td><code>--&gt;</code>
124 * <tr><td>{@link #isServerTag() IsServerTag}<td><code>false</code>
125 * <tr><td>{@link #getNamePrefix() NamePrefix}<td><code>!--</code>
126 * <tr><td>{@link #getCorrespondingEndTagType() CorrespondingEndTagType}<td><code>null</code>
127 * <tr><td>{@link #hasAttributes() HasAttributes}<td><code>false</code>
128 * <tr><td>{@link #isNameAfterPrefixRequired() IsNameAfterPrefixRequired}<td><code>false</code>
129 * </table>
130 * <dt>Example:</dt>
131 * <dd><code>&lt;!-- This is a comment --&gt;</code></dd>
132 * </dl>
133 */
134 public static final StartTagType COMMENT=StartTagTypeComment.INSTANCE;
135
136 /**
137 * The tag type given to an <a target="_blank" href="http://www.w3.org/TR/REC-xml/#sec-prolog-dtd">XML declaration</a>
138 * (<code>&lt;&#63;xml<var> &#46;&#46;&#46; </var>&#63;&gt;</code>).
139 * <p>
140 * An XML declaration is often referred to in texts as a special type of processing instruction with the reserved
141 * <a target="_blank" href="http://www.w3.org/TR/REC-xml/#NT-PITarget">PITarget</a> name of "<code>xml</code>".
142 * Technically it is not an {@linkplain #XML_PROCESSING_INSTRUCTION XML processing instruction} at all, but is still a type of
143 * <a target="_blank" href="http://www.w3.org/TR/html401/appendix/notes.html#h-B.3.6">SGML processing instruction</a>.
144 * <p>
145 * According to section <a target="_blank" href="http://www.w3.org/TR/REC-xml/#sec-prolog-dtd">2.8</a> of the XML 1.0 specification,
146 * a valid XML declaration can specify only "version", "encoding" and "standalone" attributes in that order.
147 * This library parses the {@linkplain Attributes attributes} of an XML declaration in the same way as those of a
148 * {@linkplain #NORMAL normal} tag, without checking that they conform to the specification.
149 * <p>
150 * <dl>
151 * <dt>Properties:</dt>
152 * <dd>
153 * <table class="bordered" style="margin: 15px" cellspacing="0">
154 * <tr><th>Property<th>Value
155 * <tr><td>{@link #getDescription() Description}<td>XML declaration
156 * <tr><td>{@link #getStartDelimiter() StartDelimiter}<td><code>&lt;?xml</code>
157 * <tr><td>{@link #getClosingDelimiter() ClosingDelimiter}<td><code>?&gt;</code>
158 * <tr><td>{@link #isServerTag() IsServerTag}<td><code>false</code>
159 * <tr><td>{@link #getNamePrefix() NamePrefix}<td><code>?xml</code>
160 * <tr><td>{@link #getCorrespondingEndTagType() CorrespondingEndTagType}<td><code>null</code>
161 * <tr><td>{@link #hasAttributes() HasAttributes}<td><code>true</code>
162 * <tr><td>{@link #isNameAfterPrefixRequired() IsNameAfterPrefixRequired}<td><code>false</code>
163 * </table>
164 * <dt>Example:</dt>
165 * <dd><code>&lt;?xml version="1.0" encoding="UTF-8"?&gt;</code></dd>
166 * </dl>
167 */
168 public static final StartTagType XML_DECLARATION=StartTagTypeXMLDeclaration.INSTANCE;
169
170 /**
171 * The tag type given to an <a target="_blank" href="http://www.w3.org/TR/REC-xml#sec-pi">XML processing instruction</a>
172 * (<code>&lt;&#63;<var>PITarget</var><var> &#46;&#46;&#46; </var>&#63;&gt;</code>).
173 * <p>
174 * An XML processing instruction is a specific form of
175 * <a target="_blank" href="http://www.w3.org/TR/html401/appendix/notes.html#h-B.3.6">SGML processing instruction</a> with the following
176 * two additional constraints:
177 * <ul>
178 * <li>it must be {@linkplain #getClosingDelimiter() closed} with '<code>?&gt;</code>' instead of just a single
179 * '<code>&gt;</code>' character.
180 * <li>it requires a <a target="_blank" href="http://www.w3.org/TR/REC-xml/#NT-PITarget">PITarget</a>
181 * (essentially a {@linkplain Tag#getName() name} following the '<code>&lt;?</code>' {@linkplain #getStartDelimiter() start delimiter}).
182 * </ul>
183 * <p>
184 * This library does not include a <a href="TagType.html#Predefined">predefined</a> generic tag type for SGML processing instructions
185 * as the only forms in which they are found in HTML documents are the more specific XML processing instruction and
186 * the {@linkplain #XML_DECLARATION XML declaration}, both of which have their own dedicated predefined tag type.
187 * <p>
188 * There is no restriction on the contents of an XML processing instruction. In particular, it can not be assumed that the
189 * processing instruction contains {@linkplain Attributes attributes}, in contrast to the {@linkplain #XML_DECLARATION XML declaration}.
190 * <p>
191 * Note that {@linkplain #register() registering} the {@link PHPTagTypes#PHP_SHORT} tag type overrides this tag type.
192 * This is because they both have the same {@linkplain #getStartDelimiter start delimiter},
193 * so the one registered latest takes <a href="TagType.html#Precedence">precedence</a> over the other.
194 * See the documentation of the {@link PHPTagTypes} class for more information.
195 * <p>
196 * <dl>
197 * <dt>Properties:</dt>
198 * <dd>
199 * <table class="bordered" style="margin: 15px" cellspacing="0">
200 * <tr><th>Property<th>Value
201 * <tr><td>{@link #getDescription() Description}<td>XML processing instruction
202 * <tr><td>{@link #getStartDelimiter() StartDelimiter}<td><code>&lt;?</code>
203 * <tr><td>{@link #getClosingDelimiter() ClosingDelimiter}<td><code>?&gt;</code>
204 * <tr><td>{@link #isServerTag() IsServerTag}<td><code>false</code>
205 * <tr><td>{@link #getNamePrefix() NamePrefix}<td><code>?</code>
206 * <tr><td>{@link #getCorrespondingEndTagType() CorrespondingEndTagType}<td><code>null</code>
207 * <tr><td>{@link #hasAttributes() HasAttributes}<td><code>false</code>
208 * <tr><td>{@link #isNameAfterPrefixRequired() IsNameAfterPrefixRequired}<td><code>true</code>
209 * </table>
210 * <dt>Example:</dt>
211 * <dd><code>&lt;?xml-stylesheet href="standardstyle.css" type="text/css"?&gt;</code></dd>
212 * </dl>
213 */
214 public static final StartTagType XML_PROCESSING_INSTRUCTION=StartTagTypeXMLProcessingInstruction.INSTANCE;
215
216 /**
217 * The tag type given to a <a target="_blank" href="http://www.w3.org/TR/html401/struct/global.html#h-7.2">document type declaration</a>
218 * (<code>&lt;&#33;DOCTYPE<var> &#46;&#46;&#46; </var>&gt;</code>).
219 * <p>
220 * Information about the document type declaration can be found in the
221 * <a target="_blank" href="http://www.w3.org/TR/html401/struct/global.html#h-7.2">HTML 4.01 specification section 7.2</a>, and the
222 * <a target="_blank" href="http://www.w3.org/TR/REC-xml#dt-doctype">XML 1.0 specification section 2.8</a>.
223 * <p>
224 * The "<code>!DOCTYPE</code>" tag name is required to be in upper case in the source document,
225 * but all tag properties are stored in lower case because this library performs all parsing in lower case.
226 * <p>
227 * <dl>
228 * <dt>Properties:</dt>
229 * <dd>
230 * <table class="bordered" style="margin: 15px" cellspacing="0">
231 * <tr><th>Property<th>Value
232 * <tr><td>{@link #getDescription() Description}<td>document type declaration
233 * <tr><td>{@link #getStartDelimiter() StartDelimiter}<td><code>&lt;!doctype</code>
234 * <tr><td>{@link #getClosingDelimiter() ClosingDelimiter}<td><code>&gt;</code>
235 * <tr><td>{@link #isServerTag() IsServerTag}<td><code>false</code>
236 * <tr><td>{@link #getNamePrefix() NamePrefix}<td><code>!doctype</code>
237 * <tr><td>{@link #getCorrespondingEndTagType() CorrespondingEndTagType}<td><code>null</code>
238 * <tr><td>{@link #hasAttributes() HasAttributes}<td><code>false</code>
239 * <tr><td>{@link #isNameAfterPrefixRequired() IsNameAfterPrefixRequired}<td><code>false</code>
240 * </table>
241 * <dt>Example:</dt>
242 * <dd><code>&lt;!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"&gt;</code></dd>
243 * </dl>
244 */
245 public static final StartTagType DOCTYPE_DECLARATION=StartTagTypeDoctypeDeclaration.INSTANCE;
246
247 /**
248 * The tag type given to a <a target="_blank" href="http://www.w3.org/TR/REC-xml/#dt-markupdecl">markup declaration</a>
249 * (<code>&lt;&#33;ELEMENT<var> &#46;&#46;&#46; </var>&gt;</code> | <code>&lt;&#33;ATTLIST<var> &#46;&#46;&#46; </var>&gt;</code> | <code>&lt;&#33;ENTITY<var> &#46;&#46;&#46; </var>&gt;</code> | <code>&lt;&#33;NOTATION<var> &#46;&#46;&#46; </var>&gt;</code>).
250 * <p>
251 * The {@linkplain Tag#getName() name} of a markup declaration tag is must be one of
252 * "<code>!element</code>", "<code>!attlist</code>", "<code>!entity</code>" or "<code>!notation</code>".
253 * These tag names are required to be in upper case in the source document,
254 * but all tag properties are stored in lower case because this library performs all parsing in lower case.
255 * <p>
256 * Markup declarations usually appear inside a
257 * <a target="_blank" href="http://www.w3.org/TR/REC-xml#dt-doctype">document type definition</a> (DTD), which is usually an external
258 * document to the HTML or XML document, but they can also appear directly within the
259 * {@linkplain #DOCTYPE_DECLARATION document type declaration} which is why they must be recognised by the parser.
260 * <p>
261 * <dl>
262 * <dt>Properties:</dt>
263 * <dd>
264 * <table class="bordered" style="margin: 15px" cellspacing="0">
265 * <tr><th>Property<th>Value
266 * <tr><td>{@link #getDescription() Description}<td>markup declaration
267 * <tr><td>{@link #getStartDelimiter() StartDelimiter}<td><code>&lt;!</code>
268 * <tr><td>{@link #getClosingDelimiter() ClosingDelimiter}<td><code>&gt;</code>
269 * <tr><td>{@link #isServerTag() IsServerTag}<td><code>false</code>
270 * <tr><td>{@link #getNamePrefix() NamePrefix}<td><code>!</code>
271 * <tr><td>{@link #getCorrespondingEndTagType() CorrespondingEndTagType}<td><code>null</code>
272 * <tr><td>{@link #hasAttributes() HasAttributes}<td><code>false</code>
273 * <tr><td>{@link #isNameAfterPrefixRequired() IsNameAfterPrefixRequired}<td><code>true</code>
274 * </table>
275 * <dt>Example:</dt>
276 * <dd><code>&lt;!ELEMENT BODY O O (%flow;)* +(INS|DEL) -- document body --&gt;</code></dd>
277 * </dl>
278 */
279 public static final StartTagType MARKUP_DECLARATION=StartTagTypeMarkupDeclaration.INSTANCE;
280
281 /**
282 * The tag type given to a <a target="_blank" href="http://www.w3.org/TR/html401/appendix/notes.html#h-B.3.5">CDATA section</a>
283 * (<code>&lt;&#33;[CDATA[<var> &#46;&#46;&#46; </var>]]&gt;</code>).
284 * <p>
285 * A CDATA section is a specific form of a
286 * <a target="_blank" href="http://www.w3.org/TR/html401/appendix/notes.html#h-B.3.5">marked section</a>.
287 * This library does not include a <a href="TagType.html#Predefined">predefined</a> generic tag type for marked sections,
288 * as the only type of marked sections found in HTML documents are CDATA sections.
289 * <p>
290 * The <a target="_blank" href="http://www.w3.org/TR/html401/appendix/notes.html#h-B.3.5">HTML 4.01 specification section B.3.5</a>
291 * and the <a target="_blank" href="http://www.w3.org/TR/REC-xml/#sec-cdata-sect">XML 1.0 specification section 2.7</a>
292 * contain definitions for a CDATA section.
293 * <p>
294 * There is inconsistency between the SGML and HTML/XML specifications in the definition of a marked section.
295 * SGML requires the presence of a space between the "<code>&lt;![</code>" prefix and the keyword, and allows a space after the keyword.
296 * The XML specification forbids these spaces, and the examples given in the HTML specification do not include them either.
297 * This library only recognises CDATA sections that do not include the spaces.
298 * <p>
299 * The "<code>![CDATA[</code>" tag name is required to be in upper case in the source document according to the HTML/XML specifications,
300 * but all tag properties are stored in lower case because this makes it more efficient for the library to perform case-insensitive
301 * parsing of all tags.
302 * <p>
303 * In the default configuration, any non-{@linkplain #isServerTag() server} tag appearing within a CDATA section is ignored
304 * by the parser.
305 * See the documentation of the <a href="Tag.html#ParsingProcess">tag parsing process</a> for more information.
306 * <p>
307 * <dl>
308 * <dt>Properties:</dt>
309 * <dd>
310 * <table class="bordered" style="margin: 15px" cellspacing="0">
311 * <tr><th>Property<th>Value
312 * <tr><td>{@link #getDescription() Description}<td>CDATA section
313 * <tr><td>{@link #getStartDelimiter() StartDelimiter}<td><code>&lt;![cdata[</code>
314 * <tr><td>{@link #getClosingDelimiter() ClosingDelimiter}<td><code>]]&gt;</code>
315 * <tr><td>{@link #isServerTag() IsServerTag}<td><code>false</code>
316 * <tr><td>{@link #getNamePrefix() NamePrefix}<td><code>![cdata[</code>
317 * <tr><td>{@link #getCorrespondingEndTagType() CorrespondingEndTagType}<td><code>null</code>
318 * <tr><td>{@link #hasAttributes() HasAttributes}<td><code>false</code>
319 * <tr><td>{@link #isNameAfterPrefixRequired() IsNameAfterPrefixRequired}<td><code>false</code>
320 * </table>
321 * <dt>Example:</dt>
322 * <dd>This example shows the recommended practice of enclosing scripts inside a CDATA section:
323 * <div style="margin-top: 0.5em">
324 * <pre>&lt;script type="text/javascript"&gt;<br /> //&lt;![CDATA[<br /> function min(a,b) {return a&lt;b ? a : b;}<br /> //]]&gt<br />&lt;/script&gt;</pre>
325 * </div>
326 * </dl>
327 */
328 public static final StartTagType CDATA_SECTION=StartTagTypeCDATASection.INSTANCE;
329
330 /**
331 * The tag type given to a common server tag
332 * (<code>&lt;%<var> &#46;&#46;&#46; </var>%&gt;</code>).
333 * <p>
334 * Common server tags include
335 * <a target="_blank" href="http://msdn.microsoft.com/asp/">ASP</a>,
336 * <a target="_blank" href="http://java.sun.com/products/jsp/">JSP</a>,
337 * <a target="_blank" href="http://www.modpython.org/">PSP</a>,
338 * <a target="_blank" href="http://au2.php.net/manual/en/configuration.directives.php#ini.asp-tags">ASP-style PHP</a>,
339 * <a target="_blank" href="http://www.rubycentral.com/book/web.html#S2">eRuby</a>, and
340 * <a target="_blank" href="http://www.masonbook.com/book/chapter-2.mhtml#CHP-2-SECT-3.1">Mason substitution</a> tags.
341 * <p>
342 * This tag, the {@linkplain #SERVER_COMMON_ESCAPED escaped common server tag} and the {@linkplain #SERVER_COMMON_COMMENT common server comment tag}
343 * are the only <a href="TagType.html#Standard">standard</a> tag types that define {@linkplain #isServerTag() server tags}.
344 * They are included as standard tag types because of the common server tag's widespread use in many platforms, including those listed above.
345 * <p>
346 * <dl>
347 * <dt>Properties:</dt>
348 * <dd>
349 * <table class="bordered" style="margin: 15px" cellspacing="0">
350 * <tr><th>Property<th>Value
351 * <tr><td>{@link #getDescription() Description}<td>common server tag
352 * <tr><td>{@link #getStartDelimiter() StartDelimiter}<td><code>&lt;%</code>
353 * <tr><td>{@link #getClosingDelimiter() ClosingDelimiter}<td><code>%&gt;</code>
354 * <tr><td>{@link #isServerTag() IsServerTag}<td><code>true</code>
355 * <tr><td>{@link #getNamePrefix() NamePrefix}<td><code>%</code>
356 * <tr><td>{@link #getCorrespondingEndTagType() CorrespondingEndTagType}<td><code>null</code>
357 * <tr><td>{@link #hasAttributes() HasAttributes}<td><code>false</code>
358 * <tr><td>{@link #isNameAfterPrefixRequired() IsNameAfterPrefixRequired}<td><code>false</code>
359 * </table>
360 * <dt>Example:</dt>
361 * <dd><code>&lt;%@ include file="header.html" %&gt;</code></dd>
362 * </dl>
363 */
364 public static final StartTagType SERVER_COMMON=StartTagTypeServerCommon.INSTANCE;
365
366 /**
367 * The tag type given to an escaped common server tag
368 * (<code>&lt;\%<var> &#46;&#46;&#46; </var>%&gt;</code>).
369 * <p>
370 * Some of the platforms that support the {@linkplain #SERVER_COMMON common server tag} also support a mechanism to escape that tag by adding a
371 * backslash (<code>\</code>) before the percent (<code>%</code>) character.
372 * Although rarely used, this tag type allows the parser to recognise these escaped tags in addition to the common server tag itself.
373 * <p>
374 * <dl>
375 * <dt>Properties:</dt>
376 * <dd>
377 * <table class="bordered" style="margin: 15px" cellspacing="0">
378 * <tr><th>Property<th>Value
379 * <tr><td>{@link #getDescription() Description}<td>escaped common server tag
380 * <tr><td>{@link #getStartDelimiter() StartDelimiter}<td><code>&lt;\%</code>
381 * <tr><td>{@link #getClosingDelimiter() ClosingDelimiter}<td><code>%&gt;</code>
382 * <tr><td>{@link #isServerTag() IsServerTag}<td><code>true</code>
383 * <tr><td>{@link #getNamePrefix() NamePrefix}<td><code>\%</code>
384 * <tr><td>{@link #getCorrespondingEndTagType() CorrespondingEndTagType}<td><code>null</code>
385 * <tr><td>{@link #hasAttributes() HasAttributes}<td><code>false</code>
386 * <tr><td>{@link #isNameAfterPrefixRequired() IsNameAfterPrefixRequired}<td><code>false</code>
387 * </table>
388 * <dt>Example:</dt>
389 * <dd><code>&lt;\%@ include file="header.html" %&gt;</code></dd>
390 * </dl>
391 */
392 public static final StartTagType SERVER_COMMON_ESCAPED=StartTagTypeServerCommonEscaped.INSTANCE;
393
394 /**
395 * The tag type given to a common server comment tag
396 * (<code>&lt;%---<var> &#46;&#46;&#46; </var>--%&gt;</code>).
397 * <p>
398 * Some of the platforms that support the {@linkplain #SERVER_COMMON common server tag}, such as JSP, also support a server based comment tag
399 * that allow nested server tags.
400 * <p>
401 * <dl>
402 * <dt>Properties:</dt>
403 * <dd>
404 * <table class="bordered" style="margin: 15px" cellspacing="0">
405 * <tr><th>Property<th>Value
406 * <tr><td>{@link #getDescription() Description}<td>common server comment tag
407 * <tr><td>{@link #getStartDelimiter() StartDelimiter}<td><code>&lt;%--</code>
408 * <tr><td>{@link #getClosingDelimiter() ClosingDelimiter}<td><code>--%&gt;</code>
409 * <tr><td>{@link #isServerTag() IsServerTag}<td><code>true</code>
410 * <tr><td>{@link #getNamePrefix() NamePrefix}<td><code>%--</code>
411 * <tr><td>{@link #getCorrespondingEndTagType() CorrespondingEndTagType}<td><code>null</code>
412 * <tr><td>{@link #hasAttributes() HasAttributes}<td><code>false</code>
413 * <tr><td>{@link #isNameAfterPrefixRequired() IsNameAfterPrefixRequired}<td><code>false</code>
414 * </table>
415 * <dt>Example:</dt>
416 * <dd><code>&lt;%-- this server side comment contains a <%="nested"%> server tag --%&gt;</code></dd>
417 * </dl>
418 */
419 public static final StartTagType SERVER_COMMON_COMMENT=StartTagTypeServerCommonComment.INSTANCE;
420
421 /**
422 * Constructs a new <code>StartTagType</code> object with the specified properties.
423 * <br />(<a href="TagType.html#ImplementationAssistance">implementation assistance</a> method)
424 * <p>
425 * As <code>StartTagType</code> is an abstract class, this constructor is only called from sub-class constructors.
426 *
427 * @param description a {@linkplain #getDescription() description} of the new start tag type useful for debugging purposes.
428 * @param startDelimiter the {@linkplain #getStartDelimiter() start delimiter} of the new start tag type.
429 * @param closingDelimiter the {@linkplain #getClosingDelimiter() closing delimiter} of the new start tag type.
430 * @param correspondingEndTagType the {@linkplain #getCorrespondingEndTagType() corresponding end tag type} of the new start tag type.
431 * @param isServerTag indicates whether the new start tag type is a {@linkplain #isServerTag() server tag}.
432 * @param hasAttributes indicates whether the new start tag type {@linkplain #hasAttributes() has attributes}.
433 * @param isNameAfterPrefixRequired indicates whether a {@linkplain #isNameAfterPrefixRequired() name is required after the prefix}.
434 */
435 protected StartTagType(final String description, final String startDelimiter, final String closingDelimiter, final EndTagType correspondingEndTagType, final boolean isServerTag, final boolean hasAttributes, final boolean isNameAfterPrefixRequired) {
436 super(description,startDelimiter.toLowerCase(),closingDelimiter,isServerTag,START_DELIMITER_PREFIX);
437 if (!getStartDelimiter().startsWith(START_DELIMITER_PREFIX)) throw new IllegalArgumentException("startDelimiter of a start tag must start with \""+START_DELIMITER_PREFIX+'"');
438 this.correspondingEndTagType=correspondingEndTagType;
439 this.hasAttributes=hasAttributes;
440 this.isNameAfterPrefixRequired=isNameAfterPrefixRequired;
441 }
442
443 /**
444 * Returns the {@linkplain EndTagType type} of {@linkplain EndTag end tag} required to pair with a
445 * {@linkplain StartTag start tag} of this type to form an {@linkplain Element element}.
446 * <br />(<a href="TagType.html#Property">property</a> method)
447 * <p>
448 * This can be represented by the following expression that is always <code>true</code> given an arbitrary {@linkplain Element element}
449 * that has an end tag:
450 * <p>
451 * <code>element.</code>{@link Element#getStartTag() getStartTag()}<code>.</code>{@link StartTag#getStartTagType() getStartTagType()}<code>.</code>{@link #getCorrespondingEndTagType()}<code>==element.</code>{@link Element#getEndTag() getEndTag()}<code>.</code>{@link EndTag#getEndTagType() getEndTagType()}
452 * <p>
453 * <dl>
454 * <dt>Standard Tag Type Values:</dt>
455 * <dd>
456 * <table class="bordered" style="margin: 15px" cellspacing="0">
457 * <tr><th>Start Tag Type<th>Corresponding End Tag Type
458 * <tr><td>{@link StartTagType#UNREGISTERED}<td><code>null</code>
459 * <tr><td>{@link StartTagType#NORMAL}<td>{@link EndTagType#NORMAL}
460 * <tr><td>{@link StartTagType#COMMENT}<td><code>null</code>
461 * <tr><td>{@link StartTagType#XML_DECLARATION}<td><code>null</code>
462 * <tr><td>{@link StartTagType#XML_PROCESSING_INSTRUCTION}<td><code>null</code>
463 * <tr><td>{@link StartTagType#DOCTYPE_DECLARATION}<td><code>null</code>
464 * <tr><td>{@link StartTagType#MARKUP_DECLARATION}<td><code>null</code>
465 * <tr><td>{@link StartTagType#CDATA_SECTION}<td><code>null</code>
466 * <tr><td>{@link StartTagType#SERVER_COMMON}<td><code>null</code>
467 * <tr><td>{@link StartTagType#SERVER_COMMON_ESCAPED}<td><code>null</code>
468 * <tr><td>{@link StartTagType#SERVER_COMMON_COMMENT}<td><code>null</code>
469 * </table>
470 * </dl>
471 * <dl>
472 * <dt>Extended Tag Type Values:</dt>
473 * <dd>
474 * <table class="bordered" style="margin: 15px" cellspacing="0">
475 * <tr><th>Start Tag Type<th>Corresponding End Tag Type
476 * <tr><td>{@link MicrosoftConditionalCommentTagTypes#DOWNLEVEL_HIDDEN_IF}<td><code>null</code>
477 * <tr><td>{@link MicrosoftConditionalCommentTagTypes#DOWNLEVEL_HIDDEN_ENDIF}<td><code>null</code>
478 * <tr><td>{@link MicrosoftConditionalCommentTagTypes#DOWNLEVEL_REVEALED_IF}<td><code>null</code>
479 * <tr><td>{@link MicrosoftConditionalCommentTagTypes#DOWNLEVEL_REVEALED_ENDIF}<td><code>null</code>
480 * <tr><td>{@link MicrosoftConditionalCommentTagTypes#DOWNLEVEL_REVEALED_VALIDATING_IF}<td><code>null</code>
481 * <tr><td>{@link MicrosoftConditionalCommentTagTypes#DOWNLEVEL_REVEALED_VALIDATING_ENDIF}<td><code>null</code>
482 * <tr><td>{@link MicrosoftConditionalCommentTagTypes#DOWNLEVEL_REVEALED_VALIDATING_SIMPLIFIED_IF}<td><code>null</code>
483 * <tr><td>{@link PHPTagTypes#PHP_SCRIPT}<td>{@link EndTagType#NORMAL}
484 * <tr><td>{@link PHPTagTypes#PHP_SHORT}<td><code>null</code>
485 * <tr><td>{@link PHPTagTypes#PHP_STANDARD}<td><code>null</code>
486 * <tr><td>{@link MasonTagTypes#MASON_COMPONENT_CALL}<td><code>null</code>
487 * <tr><td>{@link MasonTagTypes#MASON_COMPONENT_CALLED_WITH_CONTENT}<td>{@link MasonTagTypes#MASON_COMPONENT_CALLED_WITH_CONTENT_END}
488 * <tr><td>{@link MasonTagTypes#MASON_NAMED_BLOCK}<td>{@link MasonTagTypes#MASON_NAMED_BLOCK_END}
489 * </table>
490 * </dl>
491 *
492 * @return the {@linkplain EndTagType type} of {@linkplain EndTag end tag} required to pair with a {@linkplain StartTag start tag} of this type to form an {@link Element}.
493 * @see EndTagType#getCorrespondingStartTagType()
494 */
495 public final EndTagType getCorrespondingEndTagType() {
496 return correspondingEndTagType;
497 }
498
499 /**
500 * Indicates whether a start tag of this type contains {@linkplain Attributes attributes}.
501 * <br />(<a href="TagType.html#Property">property</a> method)
502 * <p>
503 * The attributes start at the end of the {@linkplain Tag#getName() name} and continue until the
504 * {@linkplain #getClosingDelimiter() closing delimiter} is encountered. If the character sequence representing the
505 * closing delimiter occurs within a quoted attribute value it is not recognised as the end of the tag.
506 * <p>
507 * The {@link #atEndOfAttributes(Source, int pos, boolean isClosingSlashIgnored)} method can be overridden to provide more control
508 * over where the attributes end.
509 * <p>
510 * <dl>
511 * <dt>Standard Tag Type Values:</dt>
512 * <dd>
513 * <table class="bordered" style="margin: 15px" cellspacing="0">
514 * <tr><th>Start Tag Type<th>Has Attributes
515 * <tr><td>{@link StartTagType#UNREGISTERED}<td><code>false</code>
516 * <tr><td>{@link StartTagType#NORMAL}<td><code>true</code>
517 * <tr><td>{@link StartTagType#COMMENT}<td><code>false</code>
518 * <tr><td>{@link StartTagType#XML_DECLARATION}<td><code>true</code>
519 * <tr><td>{@link StartTagType#XML_PROCESSING_INSTRUCTION}<td><code>false</code>
520 * <tr><td>{@link StartTagType#DOCTYPE_DECLARATION}<td><code>false</code>
521 * <tr><td>{@link StartTagType#MARKUP_DECLARATION}<td><code>false</code>
522 * <tr><td>{@link StartTagType#CDATA_SECTION}<td><code>false</code>
523 * <tr><td>{@link StartTagType#SERVER_COMMON}<td><code>false</code>
524 * <tr><td>{@link StartTagType#SERVER_COMMON_ESCAPED}<td><code>false</code>
525 * <tr><td>{@link StartTagType#SERVER_COMMON_COMMENT}<td><code>false</code>
526 * </table>
527 * </dl>
528 * <dl>
529 * <dt>Extended Tag Type Values:</dt>
530 * <dd>
531 * <table class="bordered" style="margin: 15px" cellspacing="0">
532 * <tr><th>Start Tag Type<th>Has Attributes
533 * <tr><td>{@link MicrosoftConditionalCommentTagTypes#DOWNLEVEL_HIDDEN_IF}<td><code>false</code>
534 * <tr><td>{@link MicrosoftConditionalCommentTagTypes#DOWNLEVEL_HIDDEN_ENDIF}<td><code>false</code>
535 * <tr><td>{@link MicrosoftConditionalCommentTagTypes#DOWNLEVEL_REVEALED_IF}<td><code>false</code>
536 * <tr><td>{@link MicrosoftConditionalCommentTagTypes#DOWNLEVEL_REVEALED_ENDIF}<td><code>false</code>
537 * <tr><td>{@link MicrosoftConditionalCommentTagTypes#DOWNLEVEL_REVEALED_VALIDATING_IF}<td><code>false</code>
538 * <tr><td>{@link MicrosoftConditionalCommentTagTypes#DOWNLEVEL_REVEALED_VALIDATING_ENDIF}<td><code>false</code>
539 * <tr><td>{@link MicrosoftConditionalCommentTagTypes#DOWNLEVEL_REVEALED_VALIDATING_SIMPLIFIED_IF}<td><code>false</code>
540 * <tr><td>{@link PHPTagTypes#PHP_SCRIPT}<td><code>true</code>
541 * <tr><td>{@link PHPTagTypes#PHP_SHORT}<td><code>false</code>
542 * <tr><td>{@link PHPTagTypes#PHP_STANDARD}<td><code>false</code>
543 * <tr><td>{@link MasonTagTypes#MASON_COMPONENT_CALL}<td><code>false</code>
544 * <tr><td>{@link MasonTagTypes#MASON_COMPONENT_CALLED_WITH_CONTENT}<td><code>false</code>
545 * <tr><td>{@link MasonTagTypes#MASON_NAMED_BLOCK}<td><code>false</code>
546 * </table>
547 * </dl>
548 *
549 * @return <code>true</code> if a start tag of this type contains {@linkplain Attributes attributes}, otherwise <code>false</code>.
550 */
551 public final boolean hasAttributes() {
552 return hasAttributes;
553 }
554
555 /**
556 * Indicates whether a valid {@linkplain Tag#isXMLName(CharSequence) XML tag name} is required directly after the {@linkplain #getNamePrefix() prefix}.
557 * <br />(<a href="TagType.html#Property">property</a> method)
558 * <p>
559 * If this property is <code>true</code>, the {@linkplain Tag#getName() name} of the tag consists of the
560 * {@linkplain #getNamePrefix() prefix} followed by an {@linkplain Tag#isXMLName(CharSequence) XML tag name}.
561 * <p>
562 * If this property is <code>false</code>, the {@linkplain Tag#getName() name} of the tag consists of only the
563 * {@linkplain #getNamePrefix() prefix}.
564 * <p>
565 * <dl>
566 * <dt>Standard Tag Type Values:</dt>
567 * <dd>
568 * <table class="bordered" style="margin: 15px" cellspacing="0">
569 * <tr><th>Start Tag Type<th>Name After Prefix Required
570 * <tr><td>{@link StartTagType#UNREGISTERED}<td><code>false</code>
571 * <tr><td>{@link StartTagType#NORMAL}<td><code>true</code>
572 * <tr><td>{@link StartTagType#COMMENT}<td><code>false</code>
573 * <tr><td>{@link StartTagType#XML_DECLARATION}<td><code>false</code>
574 * <tr><td>{@link StartTagType#XML_PROCESSING_INSTRUCTION}<td><code>true</code>
575 * <tr><td>{@link StartTagType#DOCTYPE_DECLARATION}<td><code>false</code>
576 * <tr><td>{@link StartTagType#MARKUP_DECLARATION}<td><code>true</code>
577 * <tr><td>{@link StartTagType#CDATA_SECTION}<td><code>false</code>
578 * <tr><td>{@link StartTagType#SERVER_COMMON}<td><code>false</code>
579 * <tr><td>{@link StartTagType#SERVER_COMMON_ESCAPED}<td><code>false</code>
580 * <tr><td>{@link StartTagType#SERVER_COMMON_COMMENT}<td><code>false</code>
581 * </table>
582 * </dl>
583 * <dl>
584 * <dt>Extended Tag Type Values:</dt>
585 * <dd>
586 * <table class="bordered" style="margin: 15px" cellspacing="0">
587 * <tr><th>Start Tag Type<th>Name After Prefix Required
588 * <tr><td>{@link MicrosoftConditionalCommentTagTypes#DOWNLEVEL_HIDDEN_IF}<td><code>false</code>
589 * <tr><td>{@link MicrosoftConditionalCommentTagTypes#DOWNLEVEL_HIDDEN_ENDIF}<td><code>false</code>
590 * <tr><td>{@link MicrosoftConditionalCommentTagTypes#DOWNLEVEL_REVEALED_IF}<td><code>false</code>
591 * <tr><td>{@link MicrosoftConditionalCommentTagTypes#DOWNLEVEL_REVEALED_ENDIF}<td><code>false</code>
592 * <tr><td>{@link MicrosoftConditionalCommentTagTypes#DOWNLEVEL_REVEALED_VALIDATING_IF}<td><code>false</code>
593 * <tr><td>{@link MicrosoftConditionalCommentTagTypes#DOWNLEVEL_REVEALED_VALIDATING_ENDIF}<td><code>false</code>
594 * <tr><td>{@link MicrosoftConditionalCommentTagTypes#DOWNLEVEL_REVEALED_VALIDATING_SIMPLIFIED_IF}<td><code>false</code>
595 * <tr><td>{@link PHPTagTypes#PHP_SCRIPT}<td><code>false</code>
596 * <tr><td>{@link PHPTagTypes#PHP_SHORT}<td><code>false</code>
597 * <tr><td>{@link PHPTagTypes#PHP_STANDARD}<td><code>false</code>
598 * <tr><td>{@link MasonTagTypes#MASON_COMPONENT_CALL}<td><code>false</code>
599 * <tr><td>{@link MasonTagTypes#MASON_COMPONENT_CALLED_WITH_CONTENT}<td><code>false</code>
600 * <tr><td>{@link MasonTagTypes#MASON_NAMED_BLOCK}<td><code>true</code>
601 * </table>
602 * </dl>
603 *
604 * @return <code>true</code> if a valid {@linkplain Tag#isXMLName(CharSequence) XML tag name} is required directly after the {@linkplain #getNamePrefix() prefix}, otherwise <code>false</code>.
605 */
606 public final boolean isNameAfterPrefixRequired() {
607 return isNameAfterPrefixRequired;
608 }
609
610 /**
611 * Indicates whether the specified source document position is at the end of a tag's {@linkplain Attributes attributes}.
612 * <br />(<a href="TagType.html#DefaultImplementation">default implementation</a> method)
613 * <p>
614 * This method is called internally while parsing {@linkplain Attributes attributes} to detect where they should end.
615 * <p>
616 * It can be assumed that the specified position is not inside a quoted attribute value.
617 * <p>
618 * The default implementation simply compares the {@linkplain ParseText parse text} at the specified
619 * position with the {@linkplain #getClosingDelimiter() closing delimiter}, and is equivalent to:<br />
620 * <code>source.</code>{@link Source#getParseText() getParseText()}<code>.containsAt(</code>{@link #getClosingDelimiter() getClosingDelimiter()}<code>,pos)</code>
621 * <p>
622 * The <code>isClosingSlashIgnored</code> parameter is only relevant in the {@link #NORMAL} start tag type,
623 * which makes use of it to cater for the '<code>/</code>' character that can occur before the
624 * {@linkplain #getClosingDelimiter() closing delimiter} in {@linkplain StartTag#isEmptyElementTag() empty-element tags}.
625 * It's value is always <code>false</code> when passed to other start tag types.
626 *
627 * @param source the {@link Source} document.
628 * @param pos the character position in the source document.
629 * @param isClosingSlashIgnored indicates whether the {@linkplain StartTag#getName() name} of the {@linkplain StartTag start tag} being tested is incompatible with an {@linkplain StartTag#isEmptyElementTag() empty-element tag}.
630 * @return <code>true</code> if the specified source document position is at the end of a tag's {@linkplain Attributes attributes}, otherwise <code>false</code>.
631 */
632 public boolean atEndOfAttributes(final Source source, final int pos, final boolean isClosingSlashIgnored) {
633 return source.getParseText().containsAt(getClosingDelimiter(),pos);
634 }
635
636 /**
637 * Internal method for the construction of a {@link StartTag} object if this type.
638 * <br />(<a href="TagType.html#ImplementationAssistance">implementation assistance</a> method)
639 * <p>
640 * Intended for use from within the {@link #constructTagAt(Source,int) constructTagAt(Source, int pos)} method.
641 *
642 * @param source the {@link Source} document.
643 * @param begin the character position in the source document where the tag {@linkplain Segment#getBegin() begins}.
644 * @param end the character position in the source document where the tag {@linkplain Segment#getEnd() ends}.
645 * @param name the {@linkplain Tag#getName() name} of the tag.
646 * @param attributes the {@linkplain StartTag#getAttributes() attributes} of the tag.
647 * @return the new {@link StartTag} object.
648 */
649 protected final StartTag constructStartTag(final Source source, final int begin, final int end, final String name, final Attributes attributes) {
650 return new StartTag(source,begin,end,this,name,attributes);
651 }
652
653 /**
654 * Internal method for the parsing of {@link Attributes}.
655 * <br />(<a href="TagType.html#ImplementationAssistance">implementation assistance</a> method)
656 * <p>
657 * Intended for use from within the {@link #constructTagAt(Source,int) constructTagAt(Source, int pos)} method.
658 * <p>
659 * The returned {@link Attributes} segment begins at <code>startTagBegin+1+tagName.length()</code>,
660 * and ends straight after the last attribute found before the tag's {@linkplain #getClosingDelimiter() closing delimiter}.
661 * <p>
662 * Only returns <code>null</code> if the segment contains a major syntactical error
663 * or more than the {@linkplain Attributes#getDefaultMaxErrorCount() default maximum} number of
664 * minor syntactical errors.
665 *
666 * @param source the {@link Source} document.
667 * @param startTagBegin the position in the source document at which the start tag is to begin.
668 * @param tagName the {@linkplain StartTag#getName() name} of the start tag to be constructed.
669 * @return the {@link Attributes} of the start tag to be constructed, or <code>null</code> if too many errors occur while parsing.
670 */
671 protected final Attributes parseAttributes(final Source source, final int startTagBegin, final String tagName) {
672 return Attributes.construct(source,startTagBegin,this,tagName);
673 }
674 }
675

   
Visit the aagtl Website