diff --git a/idea/src/org/jetbrains/jet/plugin/completion/JetCompletionContributor.java b/idea/src/org/jetbrains/jet/plugin/completion/JetCompletionContributor.java index fa8ca6c567e..b2e53c42847 100644 --- a/idea/src/org/jetbrains/jet/plugin/completion/JetCompletionContributor.java +++ b/idea/src/org/jetbrains/jet/plugin/completion/JetCompletionContributor.java @@ -21,9 +21,11 @@ import com.intellij.openapi.progress.ProcessCanceledException; import com.intellij.patterns.PlatformPatterns; import com.intellij.psi.PsiElement; import com.intellij.psi.PsiReference; +import com.intellij.psi.tree.IElementType; import com.intellij.util.ProcessingContext; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; +import org.jetbrains.jet.JetNodeTypes; import org.jetbrains.jet.lang.psi.JetFile; import org.jetbrains.jet.plugin.references.JetSimpleNameReference; @@ -93,8 +95,10 @@ public class JetCompletionContributor extends CompletionContributor { @Override public void beforeCompletion(@NotNull CompletionInitializationContext context) { - if (context.getCompletionType() == CompletionType.BASIC && context.getFile() instanceof JetFile) { - PsiElement position = context.getFile().findElementAt(Math.max(0, context.getStartOffset() - 1)); + if (context.getFile() instanceof JetFile) { + int offset = context.getStartOffset(); + + PsiElement position = context.getFile().findElementAt(Math.max(0, offset - 1)); if (JetPackagesContributor.ACTIVATION_PATTERN.accepts(position)) { context.setDummyIdentifier(JetPackagesContributor.DUMMY_IDENTIFIER); @@ -102,6 +106,21 @@ public class JetCompletionContributor extends CompletionContributor { else if (JetExtensionReceiverTypeContributor.ACTIVATION_PATTERN.accepts(position)) { context.setDummyIdentifier(JetExtensionReceiverTypeContributor.DUMMY_IDENTIFIER); } + + if (!context.getEditor().getSelectionModel().hasSelection()) { + PsiReference reference = context.getFile().findReferenceAt(offset); + if (reference != null) { + PsiElement atElement = context.getFile().findElementAt(offset); + assert atElement != null : String.format("Element is not expected to be null: %d in file %s", + offset, context.getFile().getText()); + + IElementType parentElementType = atElement.getParent().getNode().getElementType(); + + if (!(reference instanceof JetSimpleNameReference) || parentElementType == JetNodeTypes.OPERATION_REFERENCE) { + context.setReplacementOffset(offset); + } + } + } } } } diff --git a/idea/testData/completion/handlers/TabInsertAtTheFileEnd.kt b/idea/testData/completion/handlers/TabInsertAtTheFileEnd.kt new file mode 100644 index 00000000000..d7dc9f1c0f5 --- /dev/null +++ b/idea/testData/completion/handlers/TabInsertAtTheFileEnd.kt @@ -0,0 +1,2 @@ +val vvvvv = 112 +val a = vv \ No newline at end of file diff --git a/idea/testData/completion/handlers/TabInsertAtTheFileEnd.kt.after b/idea/testData/completion/handlers/TabInsertAtTheFileEnd.kt.after new file mode 100644 index 00000000000..9fe24525f71 --- /dev/null +++ b/idea/testData/completion/handlers/TabInsertAtTheFileEnd.kt.after @@ -0,0 +1,2 @@ +val vvvvv = 112 +val a = vvvvv \ No newline at end of file diff --git a/idea/testData/completion/handlers/TabInsertBeforeBraces.kt b/idea/testData/completion/handlers/TabInsertBeforeBraces.kt new file mode 100644 index 00000000000..e22d9ac5892 --- /dev/null +++ b/idea/testData/completion/handlers/TabInsertBeforeBraces.kt @@ -0,0 +1,4 @@ +fun test() { + val vvvvv = 12 + vv{} +} \ No newline at end of file diff --git a/idea/testData/completion/handlers/TabInsertBeforeBraces.kt.after b/idea/testData/completion/handlers/TabInsertBeforeBraces.kt.after new file mode 100644 index 00000000000..a1617924641 --- /dev/null +++ b/idea/testData/completion/handlers/TabInsertBeforeBraces.kt.after @@ -0,0 +1,4 @@ +fun test() { + val vvvvv = 12 + vvvvv{} +} \ No newline at end of file diff --git a/idea/testData/completion/handlers/TabInsertBeforeBrackets.kt b/idea/testData/completion/handlers/TabInsertBeforeBrackets.kt new file mode 100644 index 00000000000..05b0b72c477 --- /dev/null +++ b/idea/testData/completion/handlers/TabInsertBeforeBrackets.kt @@ -0,0 +1,4 @@ +fun test() { + val vvvvv = 12 + vv[] +} \ No newline at end of file diff --git a/idea/testData/completion/handlers/TabInsertBeforeBrackets.kt.after b/idea/testData/completion/handlers/TabInsertBeforeBrackets.kt.after new file mode 100644 index 00000000000..0419c0ca814 --- /dev/null +++ b/idea/testData/completion/handlers/TabInsertBeforeBrackets.kt.after @@ -0,0 +1,4 @@ +fun test() { + val vvvvv = 12 + vvvvv[] +} \ No newline at end of file diff --git a/idea/testData/completion/handlers/TabInsertBeforeOperator.kt b/idea/testData/completion/handlers/TabInsertBeforeOperator.kt new file mode 100644 index 00000000000..3d9525ab4b0 --- /dev/null +++ b/idea/testData/completion/handlers/TabInsertBeforeOperator.kt @@ -0,0 +1,4 @@ +fun test() { + val vvvvv = 12 + vv+12 +} \ No newline at end of file diff --git a/idea/testData/completion/handlers/TabInsertBeforeOperator.kt.after b/idea/testData/completion/handlers/TabInsertBeforeOperator.kt.after new file mode 100644 index 00000000000..d7a65e67f95 --- /dev/null +++ b/idea/testData/completion/handlers/TabInsertBeforeOperator.kt.after @@ -0,0 +1,4 @@ +fun test() { + val vvvvv = 12 + vvvvv+12 +} \ No newline at end of file diff --git a/idea/testData/completion/handlers/TabInsertBeforeParentheses.kt b/idea/testData/completion/handlers/TabInsertBeforeParentheses.kt new file mode 100644 index 00000000000..5ca53d1b660 --- /dev/null +++ b/idea/testData/completion/handlers/TabInsertBeforeParentheses.kt @@ -0,0 +1,4 @@ +fun test() { + val vvvvv = 12 + vv() +} \ No newline at end of file diff --git a/idea/testData/completion/handlers/TabInsertBeforeParentheses.kt.after b/idea/testData/completion/handlers/TabInsertBeforeParentheses.kt.after new file mode 100644 index 00000000000..e05aecaa9bf --- /dev/null +++ b/idea/testData/completion/handlers/TabInsertBeforeParentheses.kt.after @@ -0,0 +1,4 @@ +fun test() { + val vvvvv = 12 + vvvvv() +} \ No newline at end of file diff --git a/idea/testData/completion/handlers/TabInsertInSimpleName.kt b/idea/testData/completion/handlers/TabInsertInSimpleName.kt new file mode 100644 index 00000000000..071c0098ff2 --- /dev/null +++ b/idea/testData/completion/handlers/TabInsertInSimpleName.kt @@ -0,0 +1,4 @@ +fun test() { + val vvvvv = 12 + vvvme +} \ No newline at end of file diff --git a/idea/testData/completion/handlers/TabInsertInSimpleName.kt.after b/idea/testData/completion/handlers/TabInsertInSimpleName.kt.after new file mode 100644 index 00000000000..4c089cff02a --- /dev/null +++ b/idea/testData/completion/handlers/TabInsertInSimpleName.kt.after @@ -0,0 +1,4 @@ +fun test() { + val vvvvv = 12 + vvvvv +} \ No newline at end of file diff --git a/idea/testData/completion/handlers/TabInsertInsideBraces.kt b/idea/testData/completion/handlers/TabInsertInsideBraces.kt new file mode 100644 index 00000000000..7f8f66939aa --- /dev/null +++ b/idea/testData/completion/handlers/TabInsertInsideBraces.kt @@ -0,0 +1,6 @@ +fun foo(f: (Int) -> Unit) = 12 + +fun test() { + val vvvvv = 12 + foo {vv} +} \ No newline at end of file diff --git a/idea/testData/completion/handlers/TabInsertInsideBraces.kt.after b/idea/testData/completion/handlers/TabInsertInsideBraces.kt.after new file mode 100644 index 00000000000..9a075a83aea --- /dev/null +++ b/idea/testData/completion/handlers/TabInsertInsideBraces.kt.after @@ -0,0 +1,6 @@ +fun foo(f: (Int) -> Unit) = 12 + +fun test() { + val vvvvv = 12 + foo {vvvvv} +} \ No newline at end of file diff --git a/idea/testData/completion/handlers/TabInsertInsideBrackets.kt b/idea/testData/completion/handlers/TabInsertInsideBrackets.kt new file mode 100644 index 00000000000..68cfc1d90b8 --- /dev/null +++ b/idea/testData/completion/handlers/TabInsertInsideBrackets.kt @@ -0,0 +1,5 @@ +fun test() { + val vvvvv = 12 + val foo = array(1, 2, 3) + foo[vv] +} \ No newline at end of file diff --git a/idea/testData/completion/handlers/TabInsertInsideBrackets.kt.after b/idea/testData/completion/handlers/TabInsertInsideBrackets.kt.after new file mode 100644 index 00000000000..6f590e64161 --- /dev/null +++ b/idea/testData/completion/handlers/TabInsertInsideBrackets.kt.after @@ -0,0 +1,5 @@ +fun test() { + val vvvvv = 12 + val foo = array(1, 2, 3) + foo[vvvvv] +} \ No newline at end of file diff --git a/idea/testData/completion/handlers/TabInsertInsideEmptyParentheses.kt b/idea/testData/completion/handlers/TabInsertInsideEmptyParentheses.kt new file mode 100644 index 00000000000..8f03387b87b --- /dev/null +++ b/idea/testData/completion/handlers/TabInsertInsideEmptyParentheses.kt @@ -0,0 +1,7 @@ +fun foo(a: Int) { +} + +fun test() { + val vvvvv = 12 + foo() +} \ No newline at end of file diff --git a/idea/testData/completion/handlers/TabInsertInsideEmptyParentheses.kt.after b/idea/testData/completion/handlers/TabInsertInsideEmptyParentheses.kt.after new file mode 100644 index 00000000000..f0cc2e11e77 --- /dev/null +++ b/idea/testData/completion/handlers/TabInsertInsideEmptyParentheses.kt.after @@ -0,0 +1,7 @@ +fun foo(a: Int) { +} + +fun test() { + val vvvvv = 12 + foo(vvvvv) +} \ No newline at end of file diff --git a/idea/testData/completion/handlers/TabInsertInsideParentheses.kt b/idea/testData/completion/handlers/TabInsertInsideParentheses.kt new file mode 100644 index 00000000000..e001f8ecd93 --- /dev/null +++ b/idea/testData/completion/handlers/TabInsertInsideParentheses.kt @@ -0,0 +1,7 @@ +fun foo(a: Int) { +} + +fun test() { + val vvvvv = 12 + foo(vv) +} \ No newline at end of file diff --git a/idea/testData/completion/handlers/TabInsertInsideParentheses.kt.after b/idea/testData/completion/handlers/TabInsertInsideParentheses.kt.after new file mode 100644 index 00000000000..f0cc2e11e77 --- /dev/null +++ b/idea/testData/completion/handlers/TabInsertInsideParentheses.kt.after @@ -0,0 +1,7 @@ +fun foo(a: Int) { +} + +fun test() { + val vvvvv = 12 + foo(vvvvv) +} \ No newline at end of file diff --git a/idea/tests/org/jetbrains/jet/completion/handlers/CompletionHandlerTest.kt b/idea/tests/org/jetbrains/jet/completion/handlers/CompletionHandlerTest.kt index 2e2585068ad..70f318ae0d1 100644 --- a/idea/tests/org/jetbrains/jet/completion/handlers/CompletionHandlerTest.kt +++ b/idea/tests/org/jetbrains/jet/completion/handlers/CompletionHandlerTest.kt @@ -70,6 +70,26 @@ public class CompletionHandlerTest() : JetLightCodeInsightFixtureTestCase() { fun testForceParenthesisForTabChar() = doTest(CompletionType.BASIC, 0, "some", null, '\t') + fun testTabInsertAtTheFileEnd() = doTest(CompletionType.BASIC, 0, "vvvvv", null, '\t') + + fun testTabInsertBeforeBraces() = doTest(CompletionType.BASIC, 0, "vvvvv", null, '\t') + + fun testTabInsertBeforeBrackets() = doTest(CompletionType.BASIC, 0, "vvvvv", null, '\t') + + fun testTabInsertBeforeOperator() = doTest(CompletionType.BASIC, 0, "vvvvv", null, '\t') + + fun testTabInsertBeforeParentheses() = doTest(CompletionType.BASIC, 0, "vvvvv", null, '\t') + + fun testTabInsertInsideBraces() = doTest(CompletionType.BASIC, 0, "vvvvv", null, '\t') + + fun testTabInsertInsideBrackets() = doTest(CompletionType.BASIC, 0, "vvvvv", null, '\t') + + fun testTabInsertInsideEmptyParentheses() = doTest(CompletionType.BASIC, 0, "vvvvv", null, '\t') + + fun testTabInsertInsideParentheses() = doTest(CompletionType.BASIC, 0, "vvvvv", null, '\t') + + fun testTabInsertInSimpleName() = doTest(CompletionType.BASIC, 0, "vvvvv", null, '\t') + var fixture by Delegates.notNull() protected override fun setUp() {