KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > eclipse > jdt > internal > ui > text > javadoc > JavaDoc2HTMLTextReader


1 /*******************************************************************************
2  * Copyright (c) 2000, 2006 IBM Corporation and others.
3  * All rights reserved. This program and the accompanying materials
4  * are made available under the terms of the Eclipse Public License v1.0
5  * which accompanies this distribution, and is available at
6  * http://www.eclipse.org/legal/epl-v10.html
7  *
8  * Contributors:
9  * IBM Corporation - initial API and implementation
10  * Brock Janiczak (brockj_eclipse@ihug.com.au) - https://bugs.eclipse.org/bugs/show_bug.cgi?id=20644
11  * Brock Janiczak (brockj_eclipse@ihug.com.au) - https://bugs.eclipse.org/bugs/show_bug.cgi?id=83607
12  *******************************************************************************/

13 package org.eclipse.jdt.internal.ui.text.javadoc;
14
15 import java.io.IOException JavaDoc;
16 import java.io.Reader JavaDoc;
17 import java.util.ArrayList JavaDoc;
18 import java.util.Iterator JavaDoc;
19 import java.util.List JavaDoc;
20
21 import org.eclipse.jface.internal.text.html.HTMLPrinter;
22 import org.eclipse.jface.internal.text.html.SubstitutionTextReader;
23
24 import org.eclipse.jdt.core.dom.TagElement;
25
26
27 /**
28  * Processes JavaDoc tags.
29  */

30 public class JavaDoc2HTMLTextReader extends SubstitutionTextReader {
31
32
33     static private class Pair {
34         String JavaDoc fTag;
35         String JavaDoc fContent;
36
37         Pair(String JavaDoc tag, String JavaDoc content) {
38             fTag= tag;
39             fContent= content;
40         }
41     }
42
43     private List JavaDoc fParameters;
44     private String JavaDoc fReturn;
45     private List JavaDoc fExceptions;
46     private List JavaDoc fAuthors;
47     private List JavaDoc fSees;
48     private List JavaDoc fSince;
49     private List JavaDoc fRest; // list of Pair objects
50

51     public JavaDoc2HTMLTextReader(Reader JavaDoc reader) {
52         super(reader);
53         setSkipWhitespace(false);
54     }
55
56     private int getTag(StringBuffer JavaDoc buffer) throws IOException JavaDoc {
57         int c= nextChar();
58         while (c == '.' || c != -1 && Character.isLetter((char) c)) {
59             buffer.append((char) c);
60             c= nextChar();
61         }
62         return c;
63     }
64
65     private int getContent(StringBuffer JavaDoc buffer, char stopChar) throws IOException JavaDoc {
66         int c= nextChar();
67         while (c != -1 && c != stopChar) {
68             buffer.append((char) c);
69             c= nextChar();
70         }
71         return c;
72     }
73
74     private int getContentUntilNextTag(StringBuffer JavaDoc buffer) throws IOException JavaDoc {
75         int c= nextChar();
76         boolean blockStartRead= false;
77         while (c != -1) {
78             if (c == '@') {
79                 int index= buffer.length();
80                 while (--index >= 0 && Character.isWhitespace(buffer.charAt(index))) {
81                     switch (buffer.charAt(index)) {
82                     case '\n':
83                     case '\r':
84                         return c;
85                     }
86                     if (index <= 0) {
87                         return c;
88                     }
89                 }
90             }
91             if (blockStartRead) {
92                 buffer.append(processBlockTag());
93                 blockStartRead= false;
94             } else {
95                 buffer.append((char) c);
96             }
97
98             c= nextChar();
99             blockStartRead= c == '{';
100         }
101         return c;
102     }
103
104     private String JavaDoc substituteQualification(String JavaDoc qualification) {
105         String JavaDoc result= qualification.replace('#', '.');
106         if (result.startsWith(".")) { //$NON-NLS-1$
107
result= result.substring(1);
108         }
109         return result;
110     }
111
112     private void printDefinitions(StringBuffer JavaDoc buffer, List JavaDoc list, boolean firstword) {
113         Iterator JavaDoc e= list.iterator();
114         while (e.hasNext()) {
115             String JavaDoc s= (String JavaDoc) e.next();
116             buffer.append("<dd>"); //$NON-NLS-1$
117
if (!firstword)
118                 buffer.append(s);
119             else {
120                 buffer.append("<b>"); //$NON-NLS-1$
121

122                 int i= getParamEndOffset(s);
123                 if (i <= s.length()) {
124                     buffer.append(HTMLPrinter.convertToHTMLContent(s.substring(0, i)));
125                     buffer.append("</b>"); //$NON-NLS-1$
126
buffer.append(s.substring(i));
127                 } else {
128                     buffer.append("</b>"); //$NON-NLS-1$
129
}
130             }
131             buffer.append("</dd>"); //$NON-NLS-1$
132
}
133     }
134
135     private int getParamEndOffset(String JavaDoc s) {
136         int i= 0;
137         final int length= s.length();
138         // \s*
139
while (i < length && Character.isWhitespace(s.charAt(i)))
140             ++i;
141         if (i < length && s.charAt(i) == '<') {
142             // generic type parameter
143
// read <\s*\w*\s*>
144
while (i < length && Character.isWhitespace(s.charAt(i)))
145                 ++i;
146             while (i < length && Character.isJavaIdentifierPart(s.charAt(i)))
147                 ++i;
148             while (i < length && s.charAt(i) != '>')
149                 ++i;
150         } else {
151             // simply read an identifier
152
while (i < length && Character.isJavaIdentifierPart(s.charAt(i)))
153                 ++i;
154         }
155
156         return i;
157     }
158
159     private void print(StringBuffer JavaDoc buffer, String JavaDoc tag, List JavaDoc elements, boolean firstword) {
160         if ( !elements.isEmpty()) {
161             buffer.append("<dt>"); //$NON-NLS-1$
162
buffer.append(tag);
163             buffer.append("</dt>"); //$NON-NLS-1$
164
printDefinitions(buffer, elements, firstword);
165         }
166     }
167
168     private void print(StringBuffer JavaDoc buffer, String JavaDoc tag, String JavaDoc content) {
169         if (content != null) {
170             buffer.append("<dt>"); //$NON-NLS-1$
171
buffer.append(tag);
172             buffer.append("</dt>"); //$NON-NLS-1$
173
buffer.append("<dd>"); //$NON-NLS-1$
174
buffer.append(content);
175             buffer.append("</dd>"); //$NON-NLS-1$
176
}
177     }
178
179     private void printRest(StringBuffer JavaDoc buffer) {
180         if ( !fRest.isEmpty()) {
181             Iterator JavaDoc e= fRest.iterator();
182             while (e.hasNext()) {
183                 Pair p= (Pair) e.next();
184                 buffer.append("<dt>"); //$NON-NLS-1$
185
if (p.fTag != null)
186                     buffer.append(p.fTag);
187                 buffer.append("</dt>"); //$NON-NLS-1$
188
buffer.append("<dd>"); //$NON-NLS-1$
189
if (p.fContent != null)
190                     buffer.append(p.fContent);
191                 buffer.append("</dd>"); //$NON-NLS-1$
192
}
193         }
194     }
195
196     private String JavaDoc printSimpleTag() {
197         StringBuffer JavaDoc buffer= new StringBuffer JavaDoc();
198         buffer.append("<dl>"); //$NON-NLS-1$
199
print(buffer, JavaDocMessages.JavaDoc2HTMLTextReader_see_section, fSees, false);
200         print(buffer, JavaDocMessages.JavaDoc2HTMLTextReader_parameters_section, fParameters, true);
201         print(buffer, JavaDocMessages.JavaDoc2HTMLTextReader_returns_section, fReturn);
202         print(buffer, JavaDocMessages.JavaDoc2HTMLTextReader_throws_section, fExceptions, false);
203         print(buffer, JavaDocMessages.JavaDoc2HTMLTextReader_author_section, fAuthors, false);
204         print(buffer, JavaDocMessages.JavaDoc2HTMLTextReader_since_section, fSince, false);
205         printRest(buffer);
206         buffer.append("</dl>"); //$NON-NLS-1$
207

208         return buffer.toString();
209     }
210
211     private void handleTag(String JavaDoc tag, String JavaDoc tagContent) {
212
213         tagContent= tagContent.trim();
214
215         if (TagElement.TAG_PARAM.equals(tag))
216             fParameters.add(tagContent);
217         else if (TagElement.TAG_RETURN.equals(tag))
218             fReturn= tagContent;
219         else if (TagElement.TAG_EXCEPTION.equals(tag))
220             fExceptions.add(tagContent);
221         else if (TagElement.TAG_THROWS.equals(tag))
222             fExceptions.add(tagContent);
223         else if (TagElement.TAG_AUTHOR.equals(tag))
224             fAuthors.add(substituteQualification(tagContent));
225         else if (TagElement.TAG_SEE.equals(tag))
226             fSees.add(substituteQualification(tagContent));
227         else if (TagElement.TAG_SINCE.equals(tag))
228             fSince.add(substituteQualification(tagContent));
229         else if (tagContent != null)
230             fRest.add(new Pair(tag, tagContent));
231     }
232
233     /*
234      * A '@' has been read. Process a javadoc tag
235      */

236     private String JavaDoc processSimpleTag() throws IOException JavaDoc {
237
238         fParameters= new ArrayList JavaDoc();
239         fExceptions= new ArrayList JavaDoc();
240         fAuthors= new ArrayList JavaDoc();
241         fSees= new ArrayList JavaDoc();
242         fSince= new ArrayList JavaDoc();
243         fRest= new ArrayList JavaDoc();
244
245         StringBuffer JavaDoc buffer= new StringBuffer JavaDoc();
246         int c= '@';
247         while (c != -1) {
248
249             buffer.setLength(0);
250             buffer.append((char) c);
251             c= getTag(buffer);
252             String JavaDoc tag= buffer.toString();
253
254             buffer.setLength(0);
255             if (c != -1) {
256                 c= getContentUntilNextTag(buffer);
257             }
258
259             handleTag(tag, buffer.toString());
260         }
261
262         return printSimpleTag();
263     }
264
265     private String JavaDoc printBlockTag(String JavaDoc tag, String JavaDoc tagContent) {
266
267         if (TagElement.TAG_LINK.equals(tag) || TagElement.TAG_LINKPLAIN.equals(tag)) {
268
269             char[] contentChars= tagContent.toCharArray();
270             boolean inParentheses= false;
271             int labelStart= 0;
272
273             for (int i= 0; i < contentChars.length; i++) {
274                 char nextChar= contentChars[i];
275
276                 // tagContent always has a leading space
277
if (i == 0 && Character.isWhitespace(nextChar)) {
278                     labelStart= 1;
279                     continue;
280                 }
281
282                 if (nextChar == '(') {
283                     inParentheses= true;
284                     continue;
285                 }
286
287                 if (nextChar == ')') {
288                     inParentheses= false;
289                     continue;
290                 }
291
292                 // Stop at first whitespace that is not in parentheses
293
if (!inParentheses && Character.isWhitespace(nextChar)) {
294                     labelStart= i+1;
295                     break;
296                 }
297             }
298             if (TagElement.TAG_LINK.equals(tag))
299                 return "<code>" + substituteQualification(tagContent.substring(labelStart)) + "</code>"; //$NON-NLS-1$//$NON-NLS-2$
300
else
301                 return substituteQualification(tagContent.substring(labelStart));
302             
303         } else if (TagElement.TAG_LITERAL.equals(tag)) {
304             return printLiteral(tagContent);
305             
306         } else if (TagElement.TAG_CODE.equals(tag)) {
307             return "<code>" + printLiteral(tagContent) + "</code>"; //$NON-NLS-1$//$NON-NLS-2$
308
}
309
310         // If something went wrong at least replace the {} with the content
311
return substituteQualification(tagContent);
312     }
313
314     private String JavaDoc printLiteral(String JavaDoc tagContent) {
315         int contentStart= 0;
316         for (int i= 0; i < tagContent.length(); i++) {
317             if (! Character.isWhitespace(tagContent.charAt(i))) {
318                 contentStart= i;
319                 break;
320             }
321         }
322         return HTMLPrinter.convertToHTMLContent(tagContent.substring(contentStart));
323     }
324
325     /*
326      * A '{' has been read. Process a block tag
327      */

328     private String JavaDoc processBlockTag() throws IOException JavaDoc {
329
330         int c= nextChar();
331
332         if (c != '@') {
333             StringBuffer JavaDoc buffer= new StringBuffer JavaDoc();
334             buffer.append('{');
335             buffer.append((char) c);
336             return buffer.toString();
337         }
338
339         StringBuffer JavaDoc buffer= new StringBuffer JavaDoc();
340         if (c != -1) {
341
342             buffer.setLength(0);
343             buffer.append((char) c);
344
345             c= getTag(buffer);
346             String JavaDoc tag= buffer.toString();
347
348             buffer.setLength(0);
349             if (c != -1 && c != '}') {
350                 buffer.append((char) c);
351                 c= getContent(buffer, '}');
352             }
353
354             return printBlockTag(tag, buffer.toString());
355         }
356
357         return null;
358     }
359
360     /*
361      * @see SubstitutionTextReaderr#computeSubstitution(int)
362      */

363     protected String JavaDoc computeSubstitution(int c) throws IOException JavaDoc {
364         if (c == '@' && fWasWhiteSpace)
365             return processSimpleTag();
366
367         if (c == '{')
368             return processBlockTag();
369
370         return null;
371     }
372 }
373
Popular Tags