1 /* 2 * Copyright (c) 1997, 2018, 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 26 package jdk.javadoc.internal.doclets.formats.html; 27 28 import jdk.javadoc.internal.doclets.formats.html.markup.Table; 29 import jdk.javadoc.internal.doclets.formats.html.markup.TableHeader; 30 31 import java.util.*; 32 33 import javax.lang.model.element.ModuleElement; 34 import javax.lang.model.element.PackageElement; 35 import javax.lang.model.element.TypeElement; 36 37 import com.sun.source.doctree.DocTree; 38 import jdk.javadoc.internal.doclets.formats.html.markup.ContentBuilder; 39 import jdk.javadoc.internal.doclets.formats.html.markup.HtmlConstants; 40 import jdk.javadoc.internal.doclets.formats.html.markup.HtmlStyle; 41 import jdk.javadoc.internal.doclets.formats.html.markup.HtmlTag; 42 import jdk.javadoc.internal.doclets.formats.html.markup.HtmlTree; 43 import jdk.javadoc.internal.doclets.formats.html.markup.Navigation; 44 import jdk.javadoc.internal.doclets.formats.html.markup.Navigation.PageMode; 45 import jdk.javadoc.internal.doclets.formats.html.markup.StringContent; 46 import jdk.javadoc.internal.doclets.toolkit.Content; 47 import jdk.javadoc.internal.doclets.toolkit.PackageSummaryWriter; 48 import jdk.javadoc.internal.doclets.toolkit.util.CommentHelper; 49 import jdk.javadoc.internal.doclets.toolkit.util.DocFileIOException; 50 import jdk.javadoc.internal.doclets.toolkit.util.DocPaths; 51 52 /** 53 * Class to generate file for each package contents in the right-hand 54 * frame. This will list all the Class Kinds in the package. A click on any 55 * class-kind will update the frame with the clicked class-kind page. 56 * 57 * <p><b>This is NOT part of any supported API. 58 * If you write code that depends on this, you do so at your own risk. 59 * This code and its internal interfaces are subject to change or 60 * deletion without notice.</b> 61 * 62 * @author Atul M Dambalkar 63 * @author Bhavesh Patel (Modified) 64 */ 65 public class PackageWriterImpl extends HtmlDocletWriter 66 implements PackageSummaryWriter { 67 68 /** 69 * The package being documented. 70 */ 71 protected PackageElement packageElement; 72 73 /** 74 * The HTML tree for main tag. 75 */ 76 protected HtmlTree mainTree = HtmlTree.MAIN(); 77 78 /** 79 * The HTML tree for section tag. 80 */ 81 protected HtmlTree sectionTree = HtmlTree.SECTION(); 82 83 private final Navigation navBar; 84 85 /** 86 * Constructor to construct PackageWriter object and to generate 87 * "package-summary.html" file in the respective package directory. 88 * For example for package "java.lang" this will generate file 89 * "package-summary.html" file in the "java/lang" directory. It will also 90 * create "java/lang" directory in the current or the destination directory 91 * if it doesn't exist. 92 * 93 * @param configuration the configuration of the doclet. 94 * @param packageElement PackageElement under consideration. 95 */ PackageWriterImpl(HtmlConfiguration configuration, PackageElement packageElement)96 public PackageWriterImpl(HtmlConfiguration configuration, PackageElement packageElement) { 97 super(configuration, 98 configuration.docPaths.forPackage(packageElement) 99 .resolve(DocPaths.PACKAGE_SUMMARY)); 100 this.packageElement = packageElement; 101 this.navBar = new Navigation(packageElement, configuration, fixedNavDiv, PageMode.PACKAGE, path); 102 } 103 104 /** 105 * {@inheritDoc} 106 */ 107 @Override getPackageHeader(String heading)108 public Content getPackageHeader(String heading) { 109 HtmlTree bodyTree = getBody(true, getWindowTitle(utils.getPackageName(packageElement))); 110 HtmlTree htmlTree = (configuration.allowTag(HtmlTag.HEADER)) 111 ? HtmlTree.HEADER() 112 : bodyTree; 113 addTop(htmlTree); 114 Content linkContent = getModuleLink(utils.elementUtils.getModuleOf(packageElement), 115 contents.moduleLabel); 116 navBar.setNavLinkModule(linkContent); 117 navBar.setUserHeader(getUserHeaderFooter(true)); 118 htmlTree.addContent(navBar.getContent(true)); 119 if (configuration.allowTag(HtmlTag.HEADER)) { 120 bodyTree.addContent(htmlTree); 121 } 122 HtmlTree div = new HtmlTree(HtmlTag.DIV); 123 div.setStyle(HtmlStyle.header); 124 if (configuration.showModules) { 125 ModuleElement mdle = configuration.docEnv.getElementUtils().getModuleOf(packageElement); 126 Content classModuleLabel = HtmlTree.SPAN(HtmlStyle.moduleLabelInPackage, contents.moduleLabel); 127 Content moduleNameDiv = HtmlTree.DIV(HtmlStyle.subTitle, classModuleLabel); 128 moduleNameDiv.addContent(Contents.SPACE); 129 moduleNameDiv.addContent(getModuleLink(mdle, 130 new StringContent(mdle.getQualifiedName().toString()))); 131 div.addContent(moduleNameDiv); 132 } 133 Content annotationContent = new HtmlTree(HtmlTag.P); 134 addAnnotationInfo(packageElement, annotationContent); 135 div.addContent(annotationContent); 136 Content tHeading = HtmlTree.HEADING(HtmlConstants.TITLE_HEADING, true, 137 HtmlStyle.title, contents.packageLabel); 138 tHeading.addContent(Contents.SPACE); 139 Content packageHead = new StringContent(heading); 140 tHeading.addContent(packageHead); 141 div.addContent(tHeading); 142 if (configuration.allowTag(HtmlTag.MAIN)) { 143 mainTree.addContent(div); 144 } else { 145 bodyTree.addContent(div); 146 } 147 return bodyTree; 148 } 149 150 /** 151 * {@inheritDoc} 152 */ 153 @Override getContentHeader()154 public Content getContentHeader() { 155 HtmlTree div = new HtmlTree(HtmlTag.DIV); 156 div.setStyle(HtmlStyle.contentContainer); 157 return div; 158 } 159 160 /** 161 * Add the package deprecation information to the documentation tree. 162 * 163 * @param div the content tree to which the deprecation information will be added 164 */ addDeprecationInfo(Content div)165 public void addDeprecationInfo(Content div) { 166 List<? extends DocTree> deprs = utils.getBlockTags(packageElement, DocTree.Kind.DEPRECATED); 167 if (utils.isDeprecated(packageElement)) { 168 CommentHelper ch = utils.getCommentHelper(packageElement); 169 HtmlTree deprDiv = new HtmlTree(HtmlTag.DIV); 170 deprDiv.setStyle(HtmlStyle.deprecationBlock); 171 Content deprPhrase = HtmlTree.SPAN(HtmlStyle.deprecatedLabel, getDeprecatedPhrase(packageElement)); 172 deprDiv.addContent(deprPhrase); 173 if (!deprs.isEmpty()) { 174 List<? extends DocTree> commentTags = ch.getDescription(configuration, deprs.get(0)); 175 if (!commentTags.isEmpty()) { 176 addInlineDeprecatedComment(packageElement, deprs.get(0), deprDiv); 177 } 178 } 179 div.addContent(deprDiv); 180 } 181 } 182 183 /** 184 * {@inheritDoc} 185 */ 186 @Override getSummaryHeader()187 public Content getSummaryHeader() { 188 HtmlTree ul = new HtmlTree(HtmlTag.UL); 189 ul.setStyle(HtmlStyle.blockList); 190 return ul; 191 } 192 193 /** 194 * {@inheritDoc} 195 */ 196 @Override addInterfaceSummary(SortedSet<TypeElement> interfaces, Content summaryContentTree)197 public void addInterfaceSummary(SortedSet<TypeElement> interfaces, Content summaryContentTree) { 198 TableHeader tableHeader= new TableHeader(contents.interfaceLabel, contents.descriptionLabel); 199 addClassesSummary(interfaces, resources.interfaceSummary, resources.interfaceTableSummary, 200 tableHeader, summaryContentTree); 201 } 202 203 /** 204 * {@inheritDoc} 205 */ 206 @Override addClassSummary(SortedSet<TypeElement> classes, Content summaryContentTree)207 public void addClassSummary(SortedSet<TypeElement> classes, Content summaryContentTree) { 208 TableHeader tableHeader= new TableHeader(contents.classLabel, contents.descriptionLabel); 209 addClassesSummary(classes, resources.classSummary, resources.classTableSummary, 210 tableHeader, summaryContentTree); 211 } 212 213 /** 214 * {@inheritDoc} 215 */ 216 @Override addEnumSummary(SortedSet<TypeElement> enums, Content summaryContentTree)217 public void addEnumSummary(SortedSet<TypeElement> enums, Content summaryContentTree) { 218 TableHeader tableHeader= new TableHeader(contents.enum_, contents.descriptionLabel); 219 addClassesSummary(enums, resources.enumSummary, resources.enumTableSummary, 220 tableHeader, summaryContentTree); 221 } 222 223 /** 224 * {@inheritDoc} 225 */ 226 @Override addExceptionSummary(SortedSet<TypeElement> exceptions, Content summaryContentTree)227 public void addExceptionSummary(SortedSet<TypeElement> exceptions, Content summaryContentTree) { 228 TableHeader tableHeader= new TableHeader(contents.exception, contents.descriptionLabel); 229 addClassesSummary(exceptions, resources.exceptionSummary, resources.exceptionTableSummary, 230 tableHeader, summaryContentTree); 231 } 232 233 /** 234 * {@inheritDoc} 235 */ 236 @Override addErrorSummary(SortedSet<TypeElement> errors, Content summaryContentTree)237 public void addErrorSummary(SortedSet<TypeElement> errors, Content summaryContentTree) { 238 TableHeader tableHeader= new TableHeader(contents.error, contents.descriptionLabel); 239 addClassesSummary(errors, resources.errorSummary, resources.errorTableSummary, 240 tableHeader, summaryContentTree); 241 } 242 243 /** 244 * {@inheritDoc} 245 */ 246 @Override addAnnotationTypeSummary(SortedSet<TypeElement> annoTypes, Content summaryContentTree)247 public void addAnnotationTypeSummary(SortedSet<TypeElement> annoTypes, Content summaryContentTree) { 248 TableHeader tableHeader= new TableHeader(contents.annotationType, contents.descriptionLabel); 249 addClassesSummary(annoTypes, resources.annotationTypeSummary, resources.annotationTypeTableSummary, 250 tableHeader, summaryContentTree); 251 } 252 addClassesSummary(SortedSet<TypeElement> classes, String label, String tableSummary, TableHeader tableHeader, Content summaryContentTree)253 public void addClassesSummary(SortedSet<TypeElement> classes, String label, 254 String tableSummary, TableHeader tableHeader, Content summaryContentTree) { 255 if(!classes.isEmpty()) { 256 Table table = new Table(configuration.htmlVersion, HtmlStyle.typeSummary) 257 .setSummary(tableSummary) 258 .setCaption(getTableCaption(new StringContent(label))) 259 .setHeader(tableHeader) 260 .setColumnStyles(HtmlStyle.colFirst, HtmlStyle.colLast); 261 262 for (TypeElement klass : classes) { 263 if (!utils.isCoreClass(klass) || !configuration.isGeneratedDoc(klass)) { 264 continue; 265 } 266 Content classLink = getLink(new LinkInfoImpl( 267 configuration, LinkInfoImpl.Kind.PACKAGE, klass)); 268 ContentBuilder description = new ContentBuilder(); 269 if (utils.isDeprecated(klass)) { 270 description.addContent(getDeprecatedPhrase(klass)); 271 List<? extends DocTree> tags = utils.getDeprecatedTrees(klass); 272 if (!tags.isEmpty()) { 273 addSummaryDeprecatedComment(klass, tags.get(0), description); 274 } 275 } else { 276 addSummaryComment(klass, description); 277 } 278 table.addRow(classLink, description); 279 } 280 Content li = HtmlTree.LI(HtmlStyle.blockList, table.toContent()); 281 summaryContentTree.addContent(li); 282 } 283 } 284 285 /** 286 * {@inheritDoc} 287 */ 288 @Override addPackageDescription(Content packageContentTree)289 public void addPackageDescription(Content packageContentTree) { 290 if (!utils.getBody(packageElement).isEmpty()) { 291 Content tree = configuration.allowTag(HtmlTag.SECTION) ? sectionTree : packageContentTree; 292 tree.addContent(links.createAnchor(SectionName.PACKAGE_DESCRIPTION)); 293 addDeprecationInfo(tree); 294 addInlineComment(packageElement, tree); 295 } 296 } 297 298 /** 299 * {@inheritDoc} 300 */ 301 @Override addPackageTags(Content packageContentTree)302 public void addPackageTags(Content packageContentTree) { 303 Content htmlTree = (configuration.allowTag(HtmlTag.SECTION)) 304 ? sectionTree 305 : packageContentTree; 306 addTagsInfo(packageElement, htmlTree); 307 if (configuration.allowTag(HtmlTag.SECTION)) { 308 packageContentTree.addContent(sectionTree); 309 } 310 } 311 312 /** 313 * {@inheritDoc} 314 */ 315 @Override addPackageContent(Content contentTree, Content packageContentTree)316 public void addPackageContent(Content contentTree, Content packageContentTree) { 317 if (configuration.allowTag(HtmlTag.MAIN)) { 318 mainTree.addContent(packageContentTree); 319 contentTree.addContent(mainTree); 320 } else { 321 contentTree.addContent(packageContentTree); 322 } 323 } 324 325 /** 326 * {@inheritDoc} 327 */ 328 @Override addPackageFooter(Content contentTree)329 public void addPackageFooter(Content contentTree) { 330 Content htmlTree = (configuration.allowTag(HtmlTag.FOOTER)) 331 ? HtmlTree.FOOTER() 332 : contentTree; 333 navBar.setUserFooter(getUserHeaderFooter(false)); 334 htmlTree.addContent(navBar.getContent(false)); 335 addBottom(htmlTree); 336 if (configuration.allowTag(HtmlTag.FOOTER)) { 337 contentTree.addContent(htmlTree); 338 } 339 } 340 341 /** 342 * {@inheritDoc} 343 */ 344 @Override printDocument(Content contentTree)345 public void printDocument(Content contentTree) throws DocFileIOException { 346 printHtmlDocument(configuration.metakeywords.getMetaKeywords(packageElement), 347 true, contentTree); 348 } 349 } 350