KT-22815: Render sections properly
This commit is contained in:
@@ -311,9 +311,7 @@ class KotlinQuickDocumentationProvider : AbstractDocumentationProvider() {
|
|||||||
var renderedHtml: String
|
var renderedHtml: String
|
||||||
|
|
||||||
|
|
||||||
//if (!quickNavigation) {
|
|
||||||
renderedHtml = "${DocumentationMarkup.DEFINITION_START}$declaration${DocumentationMarkup.DEFINITION_END}"
|
renderedHtml = "${DocumentationMarkup.DEFINITION_START}$declaration${DocumentationMarkup.DEFINITION_END}"
|
||||||
//}
|
|
||||||
|
|
||||||
val deprecationProvider = ktElement.getResolutionFacade().frontendService<DeprecationResolver>()
|
val deprecationProvider = ktElement.getResolutionFacade().frontendService<DeprecationResolver>()
|
||||||
renderedHtml += renderDeprecationInfo(declarationDescriptor, deprecationProvider)
|
renderedHtml += renderDeprecationInfo(declarationDescriptor, deprecationProvider)
|
||||||
@@ -322,13 +320,7 @@ class KotlinQuickDocumentationProvider : AbstractDocumentationProvider() {
|
|||||||
val comment = declarationDescriptor.findKDoc { DescriptorToSourceUtilsIde.getAnyDeclaration(ktElement.project, it) }
|
val comment = declarationDescriptor.findKDoc { DescriptorToSourceUtilsIde.getAnyDeclaration(ktElement.project, it) }
|
||||||
if (comment != null) {
|
if (comment != null) {
|
||||||
val renderedComment = KDocRenderer.renderKDoc(comment)
|
val renderedComment = KDocRenderer.renderKDoc(comment)
|
||||||
renderedHtml += "${DocumentationMarkup.CONTENT_START}$renderedComment${DocumentationMarkup.CONTENT_END}"
|
renderedHtml += "${DocumentationMarkup.CONTENT_START}$renderedComment"
|
||||||
// if (renderedComment.startsWith("<p>")) {
|
|
||||||
// renderedHtml += renderedComment
|
|
||||||
// }
|
|
||||||
// else {
|
|
||||||
// renderedHtml = "$renderedHtml<br/>$renderedComment"
|
|
||||||
// }
|
|
||||||
} else {
|
} else {
|
||||||
if (declarationDescriptor is CallableDescriptor) { // If we couldn't find KDoc, try to find javadoc in one of super's
|
if (declarationDescriptor is CallableDescriptor) { // If we couldn't find KDoc, try to find javadoc in one of super's
|
||||||
val psi = declarationDescriptor.findPsi() as? KtFunction
|
val psi = declarationDescriptor.findPsi() as? KtFunction
|
||||||
|
|||||||
@@ -17,6 +17,7 @@
|
|||||||
package org.jetbrains.kotlin.idea.kdoc
|
package org.jetbrains.kotlin.idea.kdoc
|
||||||
|
|
||||||
import com.intellij.codeInsight.documentation.DocumentationManagerUtil
|
import com.intellij.codeInsight.documentation.DocumentationManagerUtil
|
||||||
|
import com.intellij.lang.documentation.DocumentationMarkup.*
|
||||||
import com.intellij.psi.PsiElement
|
import com.intellij.psi.PsiElement
|
||||||
import org.intellij.markdown.IElementType
|
import org.intellij.markdown.IElementType
|
||||||
import org.intellij.markdown.MarkdownElementTypes
|
import org.intellij.markdown.MarkdownElementTypes
|
||||||
@@ -36,30 +37,35 @@ import org.jetbrains.kotlin.psi.psiUtil.getChildrenOfType
|
|||||||
|
|
||||||
object KDocRenderer {
|
object KDocRenderer {
|
||||||
fun renderKDoc(docComment: KDocTag): String {
|
fun renderKDoc(docComment: KDocTag): String {
|
||||||
val content = docComment.getContent()
|
return if (docComment is KDocSection) {
|
||||||
val result = StringBuilder()
|
renderKDocSection(docComment)
|
||||||
result.append(markdownToHtml(content, allowSingleParagraph = true))
|
} else {
|
||||||
if (docComment is KDocSection) {
|
markdownToHtml(docComment.getContent(), allowSingleParagraph = true)
|
||||||
result.append("\n")
|
|
||||||
renderTag(docComment.findTagByName("receiver"), "Receiver", result)
|
|
||||||
val paramTags = docComment.findTagsByName("param").filter { it.getSubjectName() != null }
|
|
||||||
renderTagList(paramTags, "Parameters", result)
|
|
||||||
|
|
||||||
renderTag(docComment.findTagByName("return"), "Returns", result)
|
|
||||||
|
|
||||||
val throwsTags = (docComment.findTagsByName("exception").union(docComment.findTagsByName("throws")))
|
|
||||||
.filter { it.getSubjectName() != null }
|
|
||||||
renderTagList(throwsTags, "Throws", result)
|
|
||||||
|
|
||||||
renderTag(docComment.findTagByName("author"), "Author", result)
|
|
||||||
renderTag(docComment.findTagByName("since"), "Since", result)
|
|
||||||
|
|
||||||
renderSeeAlso(docComment, result)
|
|
||||||
|
|
||||||
val sampleTags = docComment.findTagsByName("sample").filter { it.getSubjectLink() != null }
|
|
||||||
renderSamplesList(sampleTags, result)
|
|
||||||
}
|
}
|
||||||
return result.toString()
|
}
|
||||||
|
|
||||||
|
fun renderKDocSection(section: KDocSection): String = buildString {
|
||||||
|
append(markdownToHtml(section.getContent(), allowSingleParagraph = true))
|
||||||
|
append(CONTENT_END)
|
||||||
|
append(SECTIONS_START)
|
||||||
|
renderTag(section.findTagByName("receiver"), "Receiver", this)
|
||||||
|
val paramTags = section.findTagsByName("param").filter { it.getSubjectName() != null }
|
||||||
|
renderTagList(paramTags, "Parameters", this)
|
||||||
|
|
||||||
|
renderTag(section.findTagByName("return"), "Returns", this)
|
||||||
|
|
||||||
|
val throwsTags = (section.findTagsByName("exception").union(section.findTagsByName("throws")))
|
||||||
|
.filter { it.getSubjectName() != null }
|
||||||
|
renderTagList(throwsTags, "Throws", this)
|
||||||
|
|
||||||
|
renderTag(section.findTagByName("author"), "Author", this)
|
||||||
|
renderTag(section.findTagByName("since"), "Since", this)
|
||||||
|
|
||||||
|
renderSeeAlso(section, this)
|
||||||
|
|
||||||
|
val sampleTags = section.findTagsByName("sample").filter { it.getSubjectLink() != null }
|
||||||
|
renderSamplesList(sampleTags, this)
|
||||||
|
append(SECTIONS_END)
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun KDocLink.createHyperlink(to: StringBuilder) {
|
private fun KDocLink.createHyperlink(to: StringBuilder) {
|
||||||
@@ -89,25 +95,27 @@ object KDocRenderer {
|
|||||||
return lines.joinToString("\n") { it.drop(minIndent) }
|
return lines.joinToString("\n") { it.drop(minIndent) }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private fun StringBuilder.renderSection(title: String, content: StringBuilder.() -> Unit) {
|
||||||
|
append(SECTION_HEADER_START, title, SECTION_SEPARATOR)
|
||||||
|
content()
|
||||||
|
append(SECTION_END)
|
||||||
|
}
|
||||||
|
|
||||||
private fun renderSamplesList(sampleTags: List<KDocTag>, to: StringBuilder) {
|
private fun renderSamplesList(sampleTags: List<KDocTag>, to: StringBuilder) {
|
||||||
if (sampleTags.isEmpty()) return
|
if (sampleTags.isEmpty()) return
|
||||||
to.apply {
|
|
||||||
wrapTag("dl") {
|
to.renderSection("Samples") {
|
||||||
append("<dt><b>Samples:</b></dt>")
|
sampleTags.forEach {
|
||||||
sampleTags.forEach {
|
it.getSubjectLink()?.let { subjectLink ->
|
||||||
wrapTag("dd") {
|
append("<p>")
|
||||||
it.getSubjectLink()?.let { subjectLink ->
|
subjectLink.createHyperlink(to)
|
||||||
subjectLink.createHyperlink(to)
|
val target = subjectLink.getTargetElement()
|
||||||
val target = subjectLink.getTargetElement()
|
wrapTag("pre") {
|
||||||
wrapTag("pre") {
|
wrapTag("code") {
|
||||||
wrapTag("code") {
|
if (target == null)
|
||||||
if (target == null)
|
to.append("// Unresolved")
|
||||||
to.append("// Unresolved")
|
else {
|
||||||
else {
|
to.append(trimCommonIndent(target.extractExampleText()))
|
||||||
to.append(trimCommonIndent(target.extractExampleText()))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -119,40 +127,39 @@ object KDocRenderer {
|
|||||||
private fun renderSeeAlso(docComment: KDocSection, to: StringBuilder) {
|
private fun renderSeeAlso(docComment: KDocSection, to: StringBuilder) {
|
||||||
val seeTags = docComment.findTagsByName("see")
|
val seeTags = docComment.findTagsByName("see")
|
||||||
if (seeTags.isEmpty()) return
|
if (seeTags.isEmpty()) return
|
||||||
to.append("<DD><DL>")
|
|
||||||
to.append("<DT><b>").append("See Also:").append("</b>")
|
to.renderSection("See Also") {
|
||||||
to.append("<DD>")
|
seeTags.forEachIndexed { index, tag ->
|
||||||
seeTags.forEachIndexed { index, tag ->
|
val subjectName = tag.getSubjectName()
|
||||||
val subjectName = tag.getSubjectName()
|
if (subjectName != null) {
|
||||||
if (subjectName != null) {
|
DocumentationManagerUtil.createHyperlink(this, subjectName, subjectName, false)
|
||||||
DocumentationManagerUtil.createHyperlink(to, subjectName, subjectName, false)
|
}
|
||||||
}
|
else {
|
||||||
else {
|
append(tag.getContent())
|
||||||
to.append(tag.getContent())
|
}
|
||||||
}
|
if (index < seeTags.size - 1) {
|
||||||
if (index < seeTags.size - 1) {
|
append(", ")
|
||||||
to.append(", ")
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
to.append("</DD></DL></DD>")
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun renderTagList(tags: List<KDocTag>, title: String, to: StringBuilder) {
|
private fun renderTagList(tags: List<KDocTag>, title: String, to: StringBuilder) {
|
||||||
if (tags.isEmpty()) {
|
if (tags.isEmpty()) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
to.append("<dl><dt><b>$title:</b></dt>")
|
to.renderSection(title) {
|
||||||
tags.forEach {
|
tags.forEach {
|
||||||
to.append("<dd><code>${it.getSubjectName()}</code> - ${markdownToHtml(it.getContent().trimStart())}</dd>")
|
append("<p><code>${it.getSubjectName()}</code> - ${markdownToHtml(it.getContent().trimStart())}")
|
||||||
|
}
|
||||||
}
|
}
|
||||||
to.append("</dl>\n")
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun renderTag(tag: KDocTag?, title: String, to: StringBuilder) {
|
private fun renderTag(tag: KDocTag?, title: String, to: StringBuilder) {
|
||||||
if (tag != null) {
|
if (tag != null) {
|
||||||
to.append("<dl><dt><b>$title:</b></dt>")
|
to.renderSection(title) {
|
||||||
to.append("<dd>${markdownToHtml(tag.getContent())}</dd>")
|
markdownToHtml(tag.getContent())
|
||||||
to.append("</dl>\n")
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user