Completion of parameter name+type works for val/var parameters
This commit is contained in:
+18
-18
@@ -263,13 +263,14 @@ class BasicCompletionSession(configuration: CompletionSessionConfiguration,
|
||||
resultSet: CompletionResultSet)
|
||||
: CompletionSessionBase(configuration, parameters, resultSet) {
|
||||
|
||||
public enum class CompletionKind {
|
||||
KEYWORDS_ONLY,
|
||||
NAMED_ARGUMENTS_ONLY,
|
||||
ALL,
|
||||
TYPES,
|
||||
ANNOTATION_TYPES,
|
||||
ANNOTATION_TYPES_OR_PARAMETER_NAME
|
||||
public enum class CompletionKind(val classKindFilter: ((ClassKind) -> Boolean)?) {
|
||||
KEYWORDS_ONLY(classKindFilter = null),
|
||||
NAMED_ARGUMENTS_ONLY(classKindFilter = null),
|
||||
ALL(classKindFilter = { it != ClassKind.ENUM_ENTRY }),
|
||||
TYPES(classKindFilter = { it != ClassKind.ENUM_ENTRY }),
|
||||
ANNOTATION_TYPES(classKindFilter = { it == ClassKind.ANNOTATION_CLASS }),
|
||||
ANNOTATION_TYPES_OR_PARAMETER_NAME(classKindFilter = { it == ClassKind.ANNOTATION_CLASS }),
|
||||
PARAMETER_NAME(classKindFilter = null)
|
||||
}
|
||||
|
||||
public val completionKind: CompletionKind = calcCompletionKind()
|
||||
@@ -284,12 +285,12 @@ class BasicCompletionSession(configuration: CompletionSessionConfiguration,
|
||||
CompletionKind.ALL ->
|
||||
DescriptorKindFilter(DescriptorKindFilter.ALL_KINDS_MASK)
|
||||
|
||||
CompletionKind.NAMED_ARGUMENTS_ONLY, CompletionKind.KEYWORDS_ONLY ->
|
||||
CompletionKind.NAMED_ARGUMENTS_ONLY, CompletionKind.KEYWORDS_ONLY, CompletionKind.PARAMETER_NAME ->
|
||||
null
|
||||
}
|
||||
|
||||
private val parameterNameAndTypeCompletion = if (completionKind == CompletionKind.ANNOTATION_TYPES_OR_PARAMETER_NAME)
|
||||
ParameterNameAndTypeCompletion(collector, lookupElementFactory, prefixMatcher)
|
||||
private val parameterNameAndTypeCompletion = if (completionKind == CompletionKind.PARAMETER_NAME || completionKind == CompletionKind.ANNOTATION_TYPES_OR_PARAMETER_NAME)
|
||||
ParameterNameAndTypeCompletion(collector, lookupElementFactory, prefixMatcher, resolutionFacade)
|
||||
else
|
||||
null
|
||||
|
||||
@@ -299,7 +300,11 @@ class BasicCompletionSession(configuration: CompletionSessionConfiguration,
|
||||
}
|
||||
|
||||
if (reference == null) {
|
||||
return CompletionKind.KEYWORDS_ONLY
|
||||
val parameter = position.getParent() as? JetParameter
|
||||
return if (parameter != null && position == parameter.getNameIdentifier())
|
||||
CompletionKind.PARAMETER_NAME
|
||||
else
|
||||
CompletionKind.KEYWORDS_ONLY
|
||||
}
|
||||
|
||||
val annotationEntry = position.getStrictParentOfType<JetAnnotationEntry>()
|
||||
@@ -333,7 +338,7 @@ class BasicCompletionSession(configuration: CompletionSessionConfiguration,
|
||||
if (completionKind != CompletionKind.NAMED_ARGUMENTS_ONLY) {
|
||||
collector.addDescriptorElements(referenceVariants, suppressAutoInsertion = false)
|
||||
|
||||
parameterNameAndTypeCompletion?.addFromImports(reference!!.expression, bindingContext, { isVisibleDescriptor(it) })
|
||||
parameterNameAndTypeCompletion?.addFromImports(position, bindingContext, { isVisibleDescriptor(it) })
|
||||
|
||||
val keywordsPrefix = prefix.substringBefore('@') // if there is '@' in the prefix - use shorter prefix to not loose 'this' etc
|
||||
KeywordCompletion.complete(expression ?: parameters.getPosition(), keywordsPrefix) { lookupElement ->
|
||||
@@ -402,12 +407,7 @@ class BasicCompletionSession(configuration: CompletionSessionConfiguration,
|
||||
flushToResultSet()
|
||||
|
||||
if (shouldRunTopLevelCompletion()) {
|
||||
addAllClasses {
|
||||
if (completionKind != CompletionKind.ANNOTATION_TYPES && completionKind != CompletionKind.ANNOTATION_TYPES_OR_PARAMETER_NAME)
|
||||
it != ClassKind.ENUM_ENTRY
|
||||
else
|
||||
it == ClassKind.ANNOTATION_CLASS
|
||||
}
|
||||
completionKind.classKindFilter?.let { addAllClasses(it) }
|
||||
|
||||
if (completionKind == CompletionKind.ALL) {
|
||||
collector.addDescriptorElements(getTopLevelCallables(), suppressAutoInsertion = true)
|
||||
|
||||
+33
-4
@@ -23,29 +23,37 @@ import com.intellij.codeInsight.lookup.LookupElement
|
||||
import com.intellij.codeInsight.lookup.LookupElementDecorator
|
||||
import com.intellij.codeInsight.lookup.LookupElementPresentation
|
||||
import com.intellij.psi.PsiClass
|
||||
import com.intellij.psi.PsiElement
|
||||
import com.intellij.psi.codeStyle.CodeStyleSettingsManager
|
||||
import org.jetbrains.kotlin.descriptors.ClassDescriptorWithResolutionScopes
|
||||
import org.jetbrains.kotlin.descriptors.ClassifierDescriptor
|
||||
import org.jetbrains.kotlin.descriptors.DeclarationDescriptor
|
||||
import org.jetbrains.kotlin.idea.caches.resolve.ResolutionFacade
|
||||
import org.jetbrains.kotlin.idea.core.KotlinIndicesHelper
|
||||
import org.jetbrains.kotlin.idea.core.formatter.JetCodeStyleSettings
|
||||
import org.jetbrains.kotlin.idea.core.refactoring.EmptyValidator
|
||||
import org.jetbrains.kotlin.idea.core.refactoring.JetNameSuggester
|
||||
import org.jetbrains.kotlin.psi.JetSimpleNameExpression
|
||||
import org.jetbrains.kotlin.psi.JetClassOrObject
|
||||
import org.jetbrains.kotlin.psi.JetExpression
|
||||
import org.jetbrains.kotlin.psi.JetFile
|
||||
import org.jetbrains.kotlin.psi.psiUtil.parentsWithSelf
|
||||
import org.jetbrains.kotlin.resolve.BindingContext
|
||||
import org.jetbrains.kotlin.resolve.scopes.DescriptorKindFilter
|
||||
import org.jetbrains.kotlin.resolve.scopes.JetScope
|
||||
import org.jetbrains.kotlin.resolve.scopes.getDescriptorsFiltered
|
||||
|
||||
class ParameterNameAndTypeCompletion(
|
||||
private val collector: LookupElementsCollector,
|
||||
private val lookupElementFactory: LookupElementFactory,
|
||||
private val prefixMatcher: PrefixMatcher
|
||||
private val prefixMatcher: PrefixMatcher,
|
||||
private val resolutionFacade: ResolutionFacade
|
||||
) {
|
||||
private val modifiedPrefixMatcher = prefixMatcher.cloneWithPrefix(prefixMatcher.getPrefix().capitalize())
|
||||
|
||||
public fun addFromImports(nameExpression: JetSimpleNameExpression, bindingContext: BindingContext, visibilityFilter: (DeclarationDescriptor) -> Boolean) {
|
||||
public fun addFromImports(context: PsiElement, bindingContext: BindingContext, visibilityFilter: (DeclarationDescriptor) -> Boolean) {
|
||||
if (prefixMatcher.getPrefix().isEmpty()) return
|
||||
|
||||
val resolutionScope = bindingContext[BindingContext.RESOLUTION_SCOPE, nameExpression] ?: return
|
||||
val resolutionScope = context.getResolutionScope(bindingContext)
|
||||
val classifiers = resolutionScope.getDescriptorsFiltered(DescriptorKindFilter.NON_SINGLETON_CLASSIFIERS, modifiedPrefixMatcher.asNameFilter())
|
||||
|
||||
for (classifier in classifiers) {
|
||||
@@ -55,6 +63,27 @@ class ParameterNameAndTypeCompletion(
|
||||
}
|
||||
}
|
||||
|
||||
private fun PsiElement.getResolutionScope(bindingContext: BindingContext): JetScope {
|
||||
for (parent in parentsWithSelf) {
|
||||
if (parent is JetExpression) {
|
||||
val scope = bindingContext[BindingContext.RESOLUTION_SCOPE, parent]
|
||||
if (scope != null) return scope
|
||||
}
|
||||
|
||||
if (parent is JetClassOrObject) {
|
||||
val classDescriptor = bindingContext[BindingContext.CLASS, parent] as? ClassDescriptorWithResolutionScopes
|
||||
if (classDescriptor != null) {
|
||||
return classDescriptor.getScopeForMemberDeclarationResolution()
|
||||
}
|
||||
}
|
||||
|
||||
if (parent is JetFile) {
|
||||
return resolutionFacade.getFileTopLevelScope(parent)
|
||||
}
|
||||
}
|
||||
error("Not in JetFile")
|
||||
}
|
||||
|
||||
public fun addAll(parameters: CompletionParameters, indicesHelper: KotlinIndicesHelper) {
|
||||
if (prefixMatcher.getPrefix().isEmpty()) return
|
||||
|
||||
|
||||
+11
@@ -0,0 +1,11 @@
|
||||
package pack
|
||||
|
||||
class FooBar
|
||||
|
||||
class Boo
|
||||
|
||||
class C(val b<caret>)
|
||||
|
||||
// EXIST: { lookupString: "bar", itemText: "bar: FooBar", tailText: " (pack)" }
|
||||
// EXIST: { lookupString: "fooBar", itemText: "fooBar: FooBar", tailText: " (pack)" }
|
||||
// EXIST: { lookupString: "boo", itemText: "boo: Boo", tailText: " (pack)" }
|
||||
+11
@@ -0,0 +1,11 @@
|
||||
package pack
|
||||
|
||||
class FooBar
|
||||
|
||||
class C(private var b<caret>) {
|
||||
class Boo
|
||||
}
|
||||
|
||||
// EXIST: { lookupString: "bar", itemText: "bar: FooBar", tailText: " (pack)" }
|
||||
// EXIST: { lookupString: "fooBar", itemText: "fooBar: FooBar", tailText: " (pack)" }
|
||||
// EXIST: { lookupString: "boo", itemText: "boo: Boo", tailText: " (pack.C)" }
|
||||
+12
@@ -1427,6 +1427,18 @@ public class JSBasicCompletionTestGenerated extends AbstractJSBasicCompletionTes
|
||||
String fileName = JetTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/parameterNameAndType/Simple.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("ValParameter.kt")
|
||||
public void testValParameter() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/parameterNameAndType/ValParameter.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("VarParameter.kt")
|
||||
public void testVarParameter() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/parameterNameAndType/VarParameter.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
}
|
||||
|
||||
@TestMetadata("idea/idea-completion/testData/basic/common/shadowing")
|
||||
|
||||
+12
@@ -1427,6 +1427,18 @@ public class JvmBasicCompletionTestGenerated extends AbstractJvmBasicCompletionT
|
||||
String fileName = JetTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/parameterNameAndType/Simple.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("ValParameter.kt")
|
||||
public void testValParameter() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/parameterNameAndType/ValParameter.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("VarParameter.kt")
|
||||
public void testVarParameter() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/parameterNameAndType/VarParameter.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
}
|
||||
|
||||
@TestMetadata("idea/idea-completion/testData/basic/common/shadowing")
|
||||
|
||||
Reference in New Issue
Block a user