Overrides completion on typing member name too

#KT-9431 Fixed
This commit is contained in:
Valentin Kipyatkov
2015-10-02 22:17:50 +03:00
parent fd6244ac51
commit c5fdd649ab
12 changed files with 123 additions and 11 deletions
@@ -28,7 +28,6 @@ import com.intellij.psi.JavaPsiFacade
import com.intellij.psi.search.GlobalSearchScope
import com.intellij.psi.util.PsiTreeUtil
import com.intellij.util.ProcessingContext
import org.jetbrains.kotlin.builtins.KotlinBuiltIns
import org.jetbrains.kotlin.descriptors.ClassDescriptor
import org.jetbrains.kotlin.descriptors.ClassKind
import org.jetbrains.kotlin.descriptors.ClassifierDescriptor
@@ -27,6 +27,7 @@ import com.intellij.psi.filters.*
import com.intellij.psi.filters.position.LeftNeighbour
import com.intellij.psi.filters.position.PositionElementFilter
import com.intellij.psi.tree.IElementType
import com.intellij.psi.tree.TokenSet
import org.jetbrains.kotlin.idea.completion.handlers.KotlinFunctionInsertHandler
import org.jetbrains.kotlin.idea.completion.handlers.KotlinKeywordInsertHandler
import org.jetbrains.kotlin.lexer.JetKeywordToken
@@ -51,6 +52,8 @@ object KeywordCompletion {
FILE_KEYWORD to ":"
)
private val KEYWORDS_TO_IGNORE_PREFIX = TokenSet.create(OVERRIDE_KEYWORD /* it's needed to complete overrides that should be work by member name too */)
public fun complete(position: PsiElement, prefix: String, consumer: (LookupElement) -> Unit) {
if (!GENERAL_FILTER.isAcceptable(position, position)) return
@@ -70,15 +73,18 @@ object KeywordCompletion {
}
}
if (keyword.startsWith(prefix)/* use simple matching by prefix, not prefix matcher from completion*/ && parserFilter(keywordToken)) {
val element = LookupElementBuilder.create(KeywordLookupObject(), keyword)
.bold()
.withInsertHandler(if (keywordToken !in FUNCTION_KEYWORDS)
KotlinKeywordInsertHandler
else
KotlinFunctionInsertHandler.Normal(inputTypeArguments = false, inputValueArguments = false))
consumer(element)
}
// we use simple matching by prefix, not prefix matcher from completion
if (!keyword.startsWith(prefix) && keywordToken !in KEYWORDS_TO_IGNORE_PREFIX) continue
if (!parserFilter(keywordToken)) continue
val element = LookupElementBuilder.create(KeywordLookupObject(), keyword)
.bold()
.withInsertHandler(if (keywordToken !in FUNCTION_KEYWORDS)
KotlinKeywordInsertHandler
else
KotlinFunctionInsertHandler.Normal(inputTypeArguments = false, inputValueArguments = false))
consumer(element)
}
}
@@ -87,7 +87,7 @@ class OverridesCompletion(
lookupElement = object : LookupElementDecorator<LookupElement>(lookupElement) {
override fun getLookupString() = "override"
override fun getAllLookupStrings() = setOf(lookupString)
override fun getAllLookupStrings() = setOf(lookupString, delegate.lookupString)
override fun renderElement(presentation: LookupElementPresentation) {
super.renderElement(presentation)
@@ -0,0 +1,19 @@
interface I {
fun foo()
val someVal: Int
var someVar: Int
}
class Base1 {
protected open fun bar(){}
open val fromBase: String = ""
}
open class Base2 : Base1() {
}
class A(some<caret>) : Base2(), I
// EXIST: { itemText: "override val someVal: Int", tailText: null, typeText: "I" }
// EXIST: { itemText: "override var someVar: Int", tailText: null, typeText: "I" }
// NOTHING_ELSE
@@ -0,0 +1,22 @@
interface I {
fun someFun()
val someVal: Int
var someVar: Int
}
class Base1 {
protected open fun bar(){}
}
open class Base2 : Base1() {
}
class A : Base2(), I {
so<caret>
}
// ABSENT: { itemText: "override" }
// ABSENT: { itemText: "override fun bar() {...}" }
// EXIST: { itemText: "override fun someFun() {...}", lookupString: "override", allLookupStrings: "override, someFun", tailText: null, typeText: "I" }
// EXIST: { itemText: "override val someVal: Int", lookupString: "override", allLookupStrings: "override, someVal", tailText: null, typeText: "I" }
// EXIST: { itemText: "override var someVar: Int", lookupString: "override", allLookupStrings: "override, someVar", tailText: null, typeText: "I" }
@@ -0,0 +1,5 @@
class A {
equ<caret>
}
// ELEMENT_TEXT: "override operator fun equals(other: Any?): Boolean {...}"
@@ -0,0 +1,7 @@
class A {
override fun equals(other: Any?): Boolean {
<caret><selection>return super.equals(other)</selection>
}
}
// ELEMENT_TEXT: "override operator fun equals(other: Any?): Boolean {...}"
@@ -0,0 +1,8 @@
interface I {
var someVar: java.io.File?
}
class A(som<caret>) : I {
}
// ELEMENT_TEXT: "override var someVar: File?"
@@ -0,0 +1,10 @@
import java.io.File
interface I {
var someVar: java.io.File?
}
class A(override var someVar: File?<caret>) : I {
}
// ELEMENT_TEXT: "override var someVar: File?"
@@ -1605,11 +1605,23 @@ public class JSBasicCompletionTestGenerated extends AbstractJSBasicCompletionTes
doTest(fileName);
}
@TestMetadata("InConstructorParameters2.kt")
public void testInConstructorParameters2() throws Exception {
String fileName = JetTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/override/InConstructorParameters2.kt");
doTest(fileName);
}
@TestMetadata("Simple.kt")
public void testSimple() throws Exception {
String fileName = JetTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/override/Simple.kt");
doTest(fileName);
}
@TestMetadata("TypeFunctionName.kt")
public void testTypeFunctionName() throws Exception {
String fileName = JetTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/override/TypeFunctionName.kt");
doTest(fileName);
}
}
@TestMetadata("idea/idea-completion/testData/basic/common/parameterNameAndType")
@@ -1605,11 +1605,23 @@ public class JvmBasicCompletionTestGenerated extends AbstractJvmBasicCompletionT
doTest(fileName);
}
@TestMetadata("InConstructorParameters2.kt")
public void testInConstructorParameters2() throws Exception {
String fileName = JetTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/override/InConstructorParameters2.kt");
doTest(fileName);
}
@TestMetadata("Simple.kt")
public void testSimple() throws Exception {
String fileName = JetTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/override/Simple.kt");
doTest(fileName);
}
@TestMetadata("TypeFunctionName.kt")
public void testTypeFunctionName() throws Exception {
String fileName = JetTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/override/TypeFunctionName.kt");
doTest(fileName);
}
}
@TestMetadata("idea/idea-completion/testData/basic/common/parameterNameAndType")
@@ -406,6 +406,18 @@ public class BasicCompletionHandlerTestGenerated extends AbstractBasicCompletion
doTest(fileName);
}
@TestMetadata("TypeFunctionName.kt")
public void testTypeFunctionName() throws Exception {
String fileName = JetTestUtils.navigationMetadata("idea/idea-completion/testData/handlers/basic/override/TypeFunctionName.kt");
doTest(fileName);
}
@TestMetadata("TypeNameInConstructorParameter.kt")
public void testTypeNameInConstructorParameter() throws Exception {
String fileName = JetTestUtils.navigationMetadata("idea/idea-completion/testData/handlers/basic/override/TypeNameInConstructorParameter.kt");
doTest(fileName);
}
@TestMetadata("ValInConstructorParameter.kt")
public void testValInConstructorParameter() throws Exception {
String fileName = JetTestUtils.navigationMetadata("idea/idea-completion/testData/handlers/basic/override/ValInConstructorParameter.kt");