diff --git a/idea/src/org/jetbrains/kotlin/idea/completion/KotlinCompletionContributor.kt b/idea/src/org/jetbrains/kotlin/idea/completion/KotlinCompletionContributor.kt index 3708fcf4f72..6297792b225 100644 --- a/idea/src/org/jetbrains/kotlin/idea/completion/KotlinCompletionContributor.kt +++ b/idea/src/org/jetbrains/kotlin/idea/completion/KotlinCompletionContributor.kt @@ -50,7 +50,9 @@ public class KotlinCompletionContributor : CompletionContributor() { private val AFTER_NUMBER_LITERAL = psiElement().afterLeafSkipping(psiElement().withText(""), psiElement().withElementType(elementType().oneOf(JetTokens.FLOAT_LITERAL, JetTokens.INTEGER_LITERAL))) private val AFTER_INTEGER_LITERAL_AND_DOT = psiElement().afterLeafSkipping(psiElement().withText("."), psiElement().withElementType(elementType().oneOf(JetTokens.INTEGER_LITERAL))) - private val DEFAULT_DUMMY_IDENTIFIER = CompletionUtilCore.DUMMY_IDENTIFIER_TRIMMED + "$" // add '$' to ignore context after the caret + companion object { + public val DEFAULT_DUMMY_IDENTIFIER: String = CompletionUtilCore.DUMMY_IDENTIFIER_TRIMMED + "$" // add '$' to ignore context after the caret + } init { val provider = object : CompletionProvider() { diff --git a/idea/src/org/jetbrains/kotlin/idea/kdoc/KDocCompletionContributor.kt b/idea/src/org/jetbrains/kotlin/idea/kdoc/KDocCompletionContributor.kt index 4469499b900..5a075dcd44b 100644 --- a/idea/src/org/jetbrains/kotlin/idea/kdoc/KDocCompletionContributor.kt +++ b/idea/src/org/jetbrains/kotlin/idea/kdoc/KDocCompletionContributor.kt @@ -16,31 +16,27 @@ package org.jetbrains.kotlin.idea.kdoc -import com.intellij.codeInsight.completion.CompletionContributor -import com.intellij.codeInsight.completion.CompletionType +import com.intellij.codeInsight.completion.* +import com.intellij.codeInsight.lookup.LookupElement +import com.intellij.codeInsight.lookup.LookupElementBuilder +import com.intellij.codeInsight.lookup.LookupElementDecorator import com.intellij.patterns.PlatformPatterns.psiElement -import org.jetbrains.kotlin.kdoc.psi.impl.KDocName -import com.intellij.codeInsight.completion.CompletionProvider -import com.intellij.codeInsight.completion.CompletionParameters +import com.intellij.patterns.StandardPatterns import com.intellij.util.ProcessingContext -import com.intellij.codeInsight.completion.CompletionResultSet -import org.jetbrains.kotlin.resolve.BindingContext -import org.jetbrains.kotlin.kdoc.parser.KDocKnownTag -import org.jetbrains.kotlin.idea.caches.resolve.analyze -import org.jetbrains.kotlin.kdoc.psi.impl.KDocLink -import org.jetbrains.kotlin.psi.psiUtil.getStrictParentOfType -import org.jetbrains.kotlin.psi.psiUtil.getParentOfType import org.jetbrains.kotlin.descriptors.DeclarationDescriptor import org.jetbrains.kotlin.idea.caches.resolve.KotlinCacheService -import org.jetbrains.kotlin.resolve.lazy.KotlinCodeAnalyzer -import org.jetbrains.kotlin.idea.completion.LookupElementFactory +import org.jetbrains.kotlin.idea.caches.resolve.analyze import org.jetbrains.kotlin.idea.caches.resolve.getResolutionFacade -import com.intellij.codeInsight.lookup.LookupElementDecorator -import com.intellij.codeInsight.lookup.LookupElement -import com.intellij.codeInsight.completion.InsertionContext +import org.jetbrains.kotlin.idea.completion.KotlinCompletionContributor +import org.jetbrains.kotlin.idea.completion.LookupElementFactory import org.jetbrains.kotlin.kdoc.lexer.KDocTokens -import com.intellij.codeInsight.lookup.LookupElementBuilder -import com.intellij.patterns.StandardPatterns +import org.jetbrains.kotlin.kdoc.parser.KDocKnownTag +import org.jetbrains.kotlin.kdoc.psi.impl.KDocLink +import org.jetbrains.kotlin.kdoc.psi.impl.KDocName +import org.jetbrains.kotlin.psi.psiUtil.getParentOfType +import org.jetbrains.kotlin.psi.psiUtil.getStrictParentOfType +import org.jetbrains.kotlin.resolve.BindingContext +import org.jetbrains.kotlin.resolve.lazy.KotlinCodeAnalyzer class KDocCompletionContributor(): CompletionContributor() { init { @@ -51,6 +47,9 @@ class KDocCompletionContributor(): CompletionContributor() { psiElement().afterLeaf( StandardPatterns.or(psiElement(KDocTokens.LEADING_ASTERISK), psiElement(KDocTokens.START))), KDocTagCompletionProvider) + + extend(CompletionType.BASIC, + psiElement(KDocTokens.TAG_NAME), KDocTagCompletionProvider) } } @@ -103,9 +102,14 @@ object KDocNameCompletionProvider: CompletionProvider() { } object KDocTagCompletionProvider: CompletionProvider() { - override fun addCompletions(parameters: CompletionParameters?, context: ProcessingContext, result: CompletionResultSet) { + override fun addCompletions(parameters: CompletionParameters, context: ProcessingContext, result: CompletionResultSet) { + val prefix = if (parameters.getPosition().getNode().getElementType() == KDocTokens.TAG_NAME) + parameters.getPosition().getText().removeSuffix(KotlinCompletionContributor.DEFAULT_DUMMY_IDENTIFIER) + else + null + val resultWithPrefix = if (prefix != null) result.withPrefixMatcher(prefix) else result KDocKnownTag.values().forEach { - result.addElement(LookupElementBuilder.create("@" + it.name().toLowerCase())) + resultWithPrefix.addElement(LookupElementBuilder.create("@" + it.name().toLowerCase())) } } } diff --git a/idea/testData/kdoc/completion/TagNameAfterAt.kt b/idea/testData/kdoc/completion/TagNameAfterAt.kt new file mode 100644 index 00000000000..43932e1c5fb --- /dev/null +++ b/idea/testData/kdoc/completion/TagNameAfterAt.kt @@ -0,0 +1,8 @@ +/** + * @ + */ +fun f(x: Int): Int { +} + +// EXIST: @param +// EXIST: @return diff --git a/idea/testData/kdoc/completion/TagNameMiddle.kt b/idea/testData/kdoc/completion/TagNameMiddle.kt new file mode 100644 index 00000000000..b95978fad53 --- /dev/null +++ b/idea/testData/kdoc/completion/TagNameMiddle.kt @@ -0,0 +1,8 @@ +/** + * @r + */ +fun f(x: Int): Int { +} + +// ABSENT: @param +// EXIST: @return \ No newline at end of file diff --git a/idea/tests/org/jetbrains/kotlin/idea/kdoc/KDocCompletionTestGenerated.java b/idea/tests/org/jetbrains/kotlin/idea/kdoc/KDocCompletionTestGenerated.java index d84edf11e54..e26168dbd79 100644 --- a/idea/tests/org/jetbrains/kotlin/idea/kdoc/KDocCompletionTestGenerated.java +++ b/idea/tests/org/jetbrains/kotlin/idea/kdoc/KDocCompletionTestGenerated.java @@ -17,10 +17,9 @@ package org.jetbrains.kotlin.idea.kdoc; import com.intellij.testFramework.TestDataPath; -import org.jetbrains.kotlin.test.InnerTestClasses; +import org.jetbrains.kotlin.completion.AbstractJvmBasicCompletionTest; import org.jetbrains.kotlin.test.JUnit3RunnerWithInners; import org.jetbrains.kotlin.test.JetTestUtils; -import org.jetbrains.kotlin.completion.AbstractJvmBasicCompletionTest; import org.jetbrains.kotlin.test.TestMetadata; import org.junit.runner.RunWith; @@ -61,6 +60,18 @@ public class KDocCompletionTestGenerated extends AbstractJvmBasicCompletionTest doTest(fileName); } + @TestMetadata("TagNameAfterAt.kt") + public void testTagNameAfterAt() throws Exception { + String fileName = JetTestUtils.navigationMetadata("idea/testData/kdoc/completion/TagNameAfterAt.kt"); + doTest(fileName); + } + + @TestMetadata("TagNameMiddle.kt") + public void testTagNameMiddle() throws Exception { + String fileName = JetTestUtils.navigationMetadata("idea/testData/kdoc/completion/TagNameMiddle.kt"); + doTest(fileName); + } + @TestMetadata("TagNameStart.kt") public void testTagNameStart() throws Exception { String fileName = JetTestUtils.navigationMetadata("idea/testData/kdoc/completion/TagNameStart.kt");