PackageFrameWriter.java revision 3233:b5d08bc0d224
1/*
2 * Copyright (c) 1998, 2016, 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 jdk.javadoc.internal.doclets.formats.html;
27
28import java.io.*;
29import java.util.*;
30
31import javax.lang.model.element.PackageElement;
32import javax.lang.model.element.TypeElement;
33
34import jdk.javadoc.internal.doclets.formats.html.markup.HtmlConstants;
35import jdk.javadoc.internal.doclets.formats.html.markup.HtmlStyle;
36import jdk.javadoc.internal.doclets.formats.html.markup.HtmlTag;
37import jdk.javadoc.internal.doclets.formats.html.markup.HtmlTree;
38import jdk.javadoc.internal.doclets.formats.html.markup.StringContent;
39import jdk.javadoc.internal.doclets.toolkit.Configuration;
40import jdk.javadoc.internal.doclets.toolkit.Content;
41import jdk.javadoc.internal.doclets.toolkit.util.DocPath;
42import jdk.javadoc.internal.doclets.toolkit.util.DocPaths;
43import jdk.javadoc.internal.doclets.toolkit.util.DocletAbortException;
44
45
46/**
47 * Class to generate file for each package contents in the left-hand bottom
48 * frame. This will list all the Class Kinds in the package. A click on any
49 * class-kind will update the right-hand frame with the clicked class-kind page.
50 *
51 *  <p><b>This is NOT part of any supported API.
52 *  If you write code that depends on this, you do so at your own risk.
53 *  This code and its internal interfaces are subject to change or
54 *  deletion without notice.</b>
55 *
56 * @author Atul M Dambalkar
57 * @author Bhavesh Patel (Modified)
58 */
59public class PackageFrameWriter extends HtmlDocletWriter {
60
61    /**
62     * The package being documented.
63     */
64    private PackageElement packageElement;
65
66    /**
67     * The classes to be documented.  Use this to filter out classes
68     * that will not be documented.
69     */
70    private SortedSet<TypeElement> documentedClasses;
71
72    /**
73     * Constructor to construct PackageFrameWriter object and to generate
74     * "package-frame.html" file in the respective package directory.
75     * For example for package "java.lang" this will generate file
76     * "package-frame.html" file in the "java/lang" directory. It will also
77     * create "java/lang" directory in the current or the destination directory
78     * if it doesn't exist.
79     *
80     * @param configuration the configuration of the doclet.
81     * @param packageElement PackageElement under consideration.
82     */
83    public PackageFrameWriter(ConfigurationImpl configuration, PackageElement packageElement)
84            throws IOException {
85        super(configuration, DocPath.forPackage(packageElement).resolve(DocPaths.PACKAGE_FRAME));
86        this.packageElement = packageElement;
87        if (utils.getSpecifiedPackages().isEmpty()) {
88            documentedClasses = new TreeSet<>(utils.makeGeneralPurposeComparator());
89            documentedClasses.addAll(configuration.root.getIncludedClasses());
90        }
91    }
92
93    /**
94     * Generate a package summary page for the left-hand bottom frame. Construct
95     * the PackageFrameWriter object and then uses it generate the file.
96     *
97     * @param configuration the current configuration of the doclet.
98     * @param packageElement The package for which "pacakge-frame.html" is to be generated.
99     */
100    public static void generate(ConfigurationImpl configuration, PackageElement packageElement) {
101        PackageFrameWriter packgen;
102        try {
103            packgen = new PackageFrameWriter(configuration, packageElement);
104            String pkgName = configuration.utils.getPackageName(packageElement);
105            HtmlTree body = packgen.getBody(false, packgen.getWindowTitle(pkgName));
106            Content pkgNameContent = new StringContent(pkgName);
107            HtmlTree htmlTree = (configuration.allowTag(HtmlTag.MAIN))
108                    ? HtmlTree.MAIN()
109                    : body;
110            Content heading = HtmlTree.HEADING(HtmlConstants.TITLE_HEADING, HtmlStyle.bar,
111                    packgen.getTargetPackageLink(packageElement, "classFrame", pkgNameContent));
112            htmlTree.addContent(heading);
113            HtmlTree div = new HtmlTree(HtmlTag.DIV);
114            div.addStyle(HtmlStyle.indexContainer);
115            packgen.addClassListing(div);
116            htmlTree.addContent(div);
117            if (configuration.allowTag(HtmlTag.MAIN)) {
118                body.addContent(htmlTree);
119            }
120            packgen.printHtmlDocument(
121                    configuration.metakeywords.getMetaKeywords(packageElement), false, body);
122            packgen.close();
123        } catch (IOException exc) {
124            configuration.standardmessage.error(
125                    "doclet.exception_encountered",
126                    exc.toString(), DocPaths.PACKAGE_FRAME.getPath());
127            throw new DocletAbortException(exc);
128        }
129    }
130
131    /**
132     * Add class listing for all the classes in this package. Divide class
133     * listing as per the class kind and generate separate listing for
134     * Classes, Interfaces, Exceptions and Errors.
135     *
136     * @param contentTree the content tree to which the listing will be added
137     */
138    protected void addClassListing(HtmlTree contentTree) {
139        Configuration config = configuration;
140        if (utils.isIncluded(packageElement)) {
141            addClassKindListing(utils.getInterfaces(packageElement),
142                getResource("doclet.Interfaces"), contentTree);
143            addClassKindListing(utils.getOrdinaryClasses(packageElement),
144                getResource("doclet.Classes"), contentTree);
145            addClassKindListing(utils.getEnums(packageElement),
146                getResource("doclet.Enums"), contentTree);
147            addClassKindListing(utils.getExceptions(packageElement),
148                getResource("doclet.Exceptions"), contentTree);
149            addClassKindListing(utils.getErrors(packageElement),
150                getResource("doclet.Errors"), contentTree);
151            addClassKindListing(utils.getAnnotationTypes(packageElement),
152                getResource("doclet.AnnotationTypes"), contentTree);
153        } else {
154            addClassKindListing(config.typeElementCatalog.interfaces(packageElement),
155                getResource("doclet.Interfaces"), contentTree);
156            addClassKindListing(config.typeElementCatalog.ordinaryClasses(packageElement),
157                getResource("doclet.Classes"), contentTree);
158            addClassKindListing(config.typeElementCatalog.enums(packageElement),
159                getResource("doclet.Enums"), contentTree);
160            addClassKindListing(config.typeElementCatalog.exceptions(packageElement),
161                getResource("doclet.Exceptions"), contentTree);
162            addClassKindListing(config.typeElementCatalog.errors(packageElement),
163                getResource("doclet.Errors"), contentTree);
164            addClassKindListing(config.typeElementCatalog.annotationTypes(packageElement),
165                getResource("doclet.AnnotationTypes"), contentTree);
166        }
167    }
168
169    /**
170     * Add specific class kind listing. Also add label to the listing.
171     *
172     * @param arr Array of specific class kinds, namely Class or Interface or Exception or Error
173     * @param labelContent content tree of the label to be added
174     * @param contentTree the content tree to which the class kind listing will be added
175     */
176    protected void addClassKindListing(Iterable<TypeElement> list, Content labelContent,
177            HtmlTree contentTree) {
178        SortedSet<TypeElement> tset = utils.filterOutPrivateClasses(list, configuration.javafx);
179        if(!tset.isEmpty()) {
180            boolean printedHeader = false;
181            HtmlTree htmlTree = (configuration.allowTag(HtmlTag.SECTION))
182                    ? HtmlTree.SECTION()
183                    : contentTree;
184            HtmlTree ul = new HtmlTree(HtmlTag.UL);
185            ul.setTitle(labelContent);
186            for (TypeElement typeElement : tset) {
187                if (documentedClasses != null && !documentedClasses.contains(typeElement)) {
188                    continue;
189                }
190                if (!utils.isCoreClass(typeElement) || !configuration.isGeneratedDoc(typeElement)) {
191                    continue;
192                }
193                if (!printedHeader) {
194                    Content heading = HtmlTree.HEADING(HtmlConstants.CONTENT_HEADING,
195                                                       true, labelContent);
196                    htmlTree.addContent(heading);
197                    printedHeader = true;
198                }
199                Content arr_i_name = new StringContent(utils.getSimpleName(typeElement));
200                if (utils.isInterface(typeElement))
201                    arr_i_name = HtmlTree.SPAN(HtmlStyle.interfaceName, arr_i_name);
202                Content link = getLink(new LinkInfoImpl(configuration,
203                                                        LinkInfoImpl.Kind.PACKAGE_FRAME, typeElement).label(arr_i_name).target("classFrame"));
204                Content li = HtmlTree.LI(link);
205                ul.addContent(li);
206            }
207            htmlTree.addContent(ul);
208            if (configuration.allowTag(HtmlTag.SECTION)) {
209                contentTree.addContent(htmlTree);
210            }
211        }
212    }
213}
214