AnnotationTypeWriterImpl.java revision 2571:10fc81ac75b4
1/*
2 * Copyright (c) 2003, 2014, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation.  Oracle designates this
8 * particular file as subject to the "Classpath" exception as provided
9 * by Oracle in the LICENSE file that accompanied this code.
10 *
11 * This code is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
14 * version 2 for more details (a copy is included in the LICENSE file that
15 * accompanied this code).
16 *
17 * You should have received a copy of the GNU General Public License version
18 * 2 along with this work; if not, write to the Free Software Foundation,
19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20 *
21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
22 * or visit www.oracle.com if you need additional information or have any
23 * questions.
24 */
25
26package com.sun.tools.doclets.formats.html;
27
28import java.io.IOException;
29
30import com.sun.javadoc.*;
31import com.sun.tools.doclets.formats.html.markup.*;
32import com.sun.tools.doclets.internal.toolkit.*;
33import com.sun.tools.doclets.internal.toolkit.builders.*;
34import com.sun.tools.doclets.internal.toolkit.util.*;
35
36/**
37 * Generate the Class Information Page.
38 *
39 *  <p><b>This is NOT part of any supported API.
40 *  If you write code that depends on this, you do so at your own risk.
41 *  This code and its internal interfaces are subject to change or
42 *  deletion without notice.</b>
43 *
44 * @see com.sun.javadoc.ClassDoc
45 * @see java.util.Collections
46 * @see java.util.List
47 * @see java.util.ArrayList
48 * @see java.util.HashMap
49 *
50 * @author Atul M Dambalkar
51 * @author Robert Field
52 * @author Bhavesh Patel (Modified)
53 */
54public class AnnotationTypeWriterImpl extends SubWriterHolderWriter
55        implements AnnotationTypeWriter {
56
57    protected AnnotationTypeDoc annotationType;
58
59    protected Type prev;
60
61    protected Type next;
62
63    /**
64     * @param annotationType the annotation type being documented.
65     * @param prevType the previous class that was documented.
66     * @param nextType the next class being documented.
67     */
68    public AnnotationTypeWriterImpl(ConfigurationImpl configuration,
69            AnnotationTypeDoc annotationType, Type prevType, Type nextType)
70            throws Exception {
71        super(configuration, DocPath.forClass(annotationType));
72        this.annotationType = annotationType;
73        configuration.currentcd = annotationType.asClassDoc();
74        this.prev = prevType;
75        this.next = nextType;
76    }
77
78    /**
79     * Get this package link.
80     *
81     * @return a content tree for the package link
82     */
83    protected Content getNavLinkPackage() {
84        Content linkContent = getHyperLink(DocPaths.PACKAGE_SUMMARY,
85                packageLabel);
86        Content li = HtmlTree.LI(linkContent);
87        return li;
88    }
89
90    /**
91     * Get the class link.
92     *
93     * @return a content tree for the class link
94     */
95    protected Content getNavLinkClass() {
96        Content li = HtmlTree.LI(HtmlStyle.navBarCell1Rev, classLabel);
97        return li;
98    }
99
100    /**
101     * Get the class use link.
102     *
103     * @return a content tree for the class use link
104     */
105    protected Content getNavLinkClassUse() {
106        Content linkContent = getHyperLink(DocPaths.CLASS_USE.resolve(filename), useLabel);
107        Content li = HtmlTree.LI(linkContent);
108        return li;
109    }
110
111    /**
112     * Get link to previous class.
113     *
114     * @return a content tree for the previous class link
115     */
116    public Content getNavLinkPrevious() {
117        Content li;
118        if (prev != null) {
119            Content prevLink = getLink(new LinkInfoImpl(configuration,
120                    LinkInfoImpl.Kind.CLASS, prev.asClassDoc())
121                    .label(prevclassLabel).strong(true));
122            li = HtmlTree.LI(prevLink);
123        }
124        else
125            li = HtmlTree.LI(prevclassLabel);
126        return li;
127    }
128
129    /**
130     * Get link to next class.
131     *
132     * @return a content tree for the next class link
133     */
134    public Content getNavLinkNext() {
135        Content li;
136        if (next != null) {
137            Content nextLink = getLink(new LinkInfoImpl(configuration,
138                    LinkInfoImpl.Kind.CLASS, next.asClassDoc())
139                    .label(nextclassLabel).strong(true));
140            li = HtmlTree.LI(nextLink);
141        }
142        else
143            li = HtmlTree.LI(nextclassLabel);
144        return li;
145    }
146
147    /**
148     * {@inheritDoc}
149     */
150    public Content getHeader(String header) {
151        String pkgname = (annotationType.containingPackage() != null)?
152            annotationType.containingPackage().name(): "";
153        String clname = annotationType.name();
154        Content bodyTree = getBody(true, getWindowTitle(clname));
155        addTop(bodyTree);
156        addNavLinks(true, bodyTree);
157        bodyTree.addContent(HtmlConstants.START_OF_CLASS_DATA);
158        HtmlTree div = new HtmlTree(HtmlTag.DIV);
159        div.addStyle(HtmlStyle.header);
160        if (pkgname.length() > 0) {
161            Content pkgNameContent = new StringContent(pkgname);
162            Content pkgNameDiv = HtmlTree.DIV(HtmlStyle.subTitle, pkgNameContent);
163            div.addContent(pkgNameDiv);
164        }
165        LinkInfoImpl linkInfo = new LinkInfoImpl(configuration,
166                LinkInfoImpl.Kind.CLASS_HEADER, annotationType);
167        Content headerContent = new StringContent(header);
168        Content heading = HtmlTree.HEADING(HtmlConstants.CLASS_PAGE_HEADING, true,
169                HtmlStyle.title, headerContent);
170        heading.addContent(getTypeParameterLinks(linkInfo));
171        div.addContent(heading);
172        bodyTree.addContent(div);
173        return bodyTree;
174    }
175
176    /**
177     * {@inheritDoc}
178     */
179    public Content getAnnotationContentHeader() {
180        return getContentHeader();
181    }
182
183    /**
184     * {@inheritDoc}
185     */
186    public void addFooter(Content contentTree) {
187        contentTree.addContent(HtmlConstants.END_OF_CLASS_DATA);
188        addNavLinks(false, contentTree);
189        addBottom(contentTree);
190    }
191
192    /**
193     * {@inheritDoc}
194     */
195    public void printDocument(Content contentTree) throws IOException {
196        printHtmlDocument(configuration.metakeywords.getMetaKeywords(annotationType),
197                true, contentTree);
198    }
199
200    /**
201     * {@inheritDoc}
202     */
203    public Content getAnnotationInfoTreeHeader() {
204        return getMemberTreeHeader();
205    }
206
207    /**
208     * {@inheritDoc}
209     */
210    public Content getAnnotationInfo(Content annotationInfoTree) {
211        return getMemberTree(HtmlStyle.description, annotationInfoTree);
212    }
213
214    /**
215     * {@inheritDoc}
216     */
217    public void addAnnotationTypeSignature(String modifiers, Content annotationInfoTree) {
218        annotationInfoTree.addContent(new HtmlTree(HtmlTag.BR));
219        Content pre = new HtmlTree(HtmlTag.PRE);
220        addAnnotationInfo(annotationType, pre);
221        pre.addContent(modifiers);
222        LinkInfoImpl linkInfo = new LinkInfoImpl(configuration,
223                LinkInfoImpl.Kind.CLASS_SIGNATURE, annotationType);
224        Content annotationName = new StringContent(annotationType.name());
225        Content parameterLinks = getTypeParameterLinks(linkInfo);
226        if (configuration.linksource) {
227            addSrcLink(annotationType, annotationName, pre);
228            pre.addContent(parameterLinks);
229        } else {
230            Content span = HtmlTree.SPAN(HtmlStyle.memberNameLabel, annotationName);
231            span.addContent(parameterLinks);
232            pre.addContent(span);
233        }
234        annotationInfoTree.addContent(pre);
235    }
236
237    /**
238     * {@inheritDoc}
239     */
240    public void addAnnotationTypeDescription(Content annotationInfoTree) {
241        if(!configuration.nocomment) {
242            if (annotationType.inlineTags().length > 0) {
243                addInlineComment(annotationType, annotationInfoTree);
244            }
245        }
246    }
247
248    /**
249     * {@inheritDoc}
250     */
251    public void addAnnotationTypeTagInfo(Content annotationInfoTree) {
252        if(!configuration.nocomment) {
253            addTagsInfo(annotationType, annotationInfoTree);
254        }
255    }
256
257    /**
258     * {@inheritDoc}
259     */
260    public void addAnnotationTypeDeprecationInfo(Content annotationInfoTree) {
261        Content hr = new HtmlTree(HtmlTag.HR);
262        annotationInfoTree.addContent(hr);
263        Tag[] deprs = annotationType.tags("deprecated");
264        if (utils.isDeprecated(annotationType)) {
265            Content deprLabel = HtmlTree.SPAN(HtmlStyle.deprecatedLabel, deprecatedPhrase);
266            Content div = HtmlTree.DIV(HtmlStyle.block, deprLabel);
267            if (deprs.length > 0) {
268                Tag[] commentTags = deprs[0].inlineTags();
269                if (commentTags.length > 0) {
270                    div.addContent(getSpace());
271                    addInlineDeprecatedComment(annotationType, deprs[0], div);
272                }
273            }
274            annotationInfoTree.addContent(div);
275        }
276    }
277
278    /**
279     * {@inheritDoc}
280     */
281    protected Content getNavLinkTree() {
282        Content treeLinkContent = getHyperLink(DocPaths.PACKAGE_TREE,
283                treeLabel, "", "");
284        Content li = HtmlTree.LI(treeLinkContent);
285        return li;
286    }
287
288    /**
289     * Add summary details to the navigation bar.
290     *
291     * @param subDiv the content tree to which the summary detail links will be added
292     */
293    protected void addSummaryDetailLinks(Content subDiv) {
294        try {
295            Content div = HtmlTree.DIV(getNavSummaryLinks());
296            div.addContent(getNavDetailLinks());
297            subDiv.addContent(div);
298        } catch (Exception e) {
299            e.printStackTrace();
300            throw new DocletAbortException(e);
301        }
302    }
303
304    /**
305     * Get summary links for navigation bar.
306     *
307     * @return the content tree for the navigation summary links
308     */
309    protected Content getNavSummaryLinks() throws Exception {
310        Content li = HtmlTree.LI(summaryLabel);
311        li.addContent(getSpace());
312        Content ulNav = HtmlTree.UL(HtmlStyle.subNavList, li);
313        MemberSummaryBuilder memberSummaryBuilder = (MemberSummaryBuilder)
314                configuration.getBuilderFactory().getMemberSummaryBuilder(this);
315        Content liNavField = new HtmlTree(HtmlTag.LI);
316        addNavSummaryLink(memberSummaryBuilder,
317                "doclet.navField",
318                VisibleMemberMap.ANNOTATION_TYPE_FIELDS, liNavField);
319        addNavGap(liNavField);
320        ulNav.addContent(liNavField);
321        Content liNavReq = new HtmlTree(HtmlTag.LI);
322        addNavSummaryLink(memberSummaryBuilder,
323                "doclet.navAnnotationTypeRequiredMember",
324                VisibleMemberMap.ANNOTATION_TYPE_MEMBER_REQUIRED, liNavReq);
325        addNavGap(liNavReq);
326        ulNav.addContent(liNavReq);
327        Content liNavOpt = new HtmlTree(HtmlTag.LI);
328        addNavSummaryLink(memberSummaryBuilder,
329                "doclet.navAnnotationTypeOptionalMember",
330                VisibleMemberMap.ANNOTATION_TYPE_MEMBER_OPTIONAL, liNavOpt);
331        ulNav.addContent(liNavOpt);
332        return ulNav;
333    }
334
335    /**
336     * Add the navigation summary link.
337     *
338     * @param builder builder for the member to be documented
339     * @param label the label for the navigation
340     * @param type type to be documented
341     * @param liNav the content tree to which the navigation summary link will be added
342     */
343    protected void addNavSummaryLink(MemberSummaryBuilder builder,
344            String label, int type, Content liNav) {
345        AbstractMemberWriter writer = ((AbstractMemberWriter) builder.
346                getMemberSummaryWriter(type));
347        if (writer == null) {
348            liNav.addContent(getResource(label));
349        } else {
350            liNav.addContent(writer.getNavSummaryLink(null,
351                    ! builder.getVisibleMemberMap(type).noVisibleMembers()));
352        }
353    }
354
355    /**
356     * Get detail links for the navigation bar.
357     *
358     * @return the content tree for the detail links
359     */
360    protected Content getNavDetailLinks() throws Exception {
361        Content li = HtmlTree.LI(detailLabel);
362        li.addContent(getSpace());
363        Content ulNav = HtmlTree.UL(HtmlStyle.subNavList, li);
364        MemberSummaryBuilder memberSummaryBuilder = (MemberSummaryBuilder)
365                configuration.getBuilderFactory().getMemberSummaryBuilder(this);
366        AbstractMemberWriter writerField =
367                ((AbstractMemberWriter) memberSummaryBuilder.
368                getMemberSummaryWriter(VisibleMemberMap.ANNOTATION_TYPE_FIELDS));
369        AbstractMemberWriter writerOptional =
370                ((AbstractMemberWriter) memberSummaryBuilder.
371                getMemberSummaryWriter(VisibleMemberMap.ANNOTATION_TYPE_MEMBER_OPTIONAL));
372        AbstractMemberWriter writerRequired =
373                ((AbstractMemberWriter) memberSummaryBuilder.
374                getMemberSummaryWriter(VisibleMemberMap.ANNOTATION_TYPE_MEMBER_REQUIRED));
375        Content liNavField = new HtmlTree(HtmlTag.LI);
376        if (writerField != null){
377            writerField.addNavDetailLink(annotationType.fields().length > 0, liNavField);
378        } else {
379            liNavField.addContent(getResource("doclet.navField"));
380        }
381        addNavGap(liNavField);
382        ulNav.addContent(liNavField);
383        if (writerOptional != null){
384            Content liNavOpt = new HtmlTree(HtmlTag.LI);
385            writerOptional.addNavDetailLink(annotationType.elements().length > 0, liNavOpt);
386            ulNav.addContent(liNavOpt);
387        } else if (writerRequired != null){
388            Content liNavReq = new HtmlTree(HtmlTag.LI);
389            writerRequired.addNavDetailLink(annotationType.elements().length > 0, liNavReq);
390            ulNav.addContent(liNavReq);
391        } else {
392            Content liNav = HtmlTree.LI(getResource("doclet.navAnnotationTypeMember"));
393            ulNav.addContent(liNav);
394        }
395        return ulNav;
396    }
397
398    /**
399     * Add gap between navigation bar elements.
400     *
401     * @param liNav the content tree to which the gap will be added
402     */
403    protected void addNavGap(Content liNav) {
404        liNav.addContent(getSpace());
405        liNav.addContent("|");
406        liNav.addContent(getSpace());
407    }
408
409    /**
410     * {@inheritDoc}
411     */
412    public AnnotationTypeDoc getAnnotationTypeDoc() {
413        return annotationType;
414    }
415}
416