Create from usage: Support generation of nested Java classes from usages in Kotlin code
This commit is contained in:
+49
-11
@@ -74,6 +74,10 @@ import com.intellij.psi.codeStyle.JavaCodeStyleManager
|
||||
import com.intellij.psi.PsiModifier
|
||||
import com.intellij.psi.PsiField
|
||||
import com.intellij.psi.PsiMember
|
||||
import org.jetbrains.kotlin.idea.caches.resolve.getJavaClassDescriptor
|
||||
import com.intellij.psi.PsiNamedElement
|
||||
import com.intellij.psi.PsiMethodCallExpression
|
||||
import com.intellij.psi.PsiExpressionStatement
|
||||
import org.jetbrains.kotlin.resolve.scopes.ChainedScope
|
||||
import org.jetbrains.kotlin.resolve.scopes.WritableScopeImpl
|
||||
import org.jetbrains.kotlin.resolve.scopes.RedeclarationHandler
|
||||
@@ -135,7 +139,7 @@ class CallableBuilderConfiguration(
|
||||
|
||||
trait CallablePlacement {
|
||||
class WithReceiver(val receiverTypeCandidate: TypeCandidate): CallablePlacement
|
||||
class NoReceiver(val containingElement: JetElement): CallablePlacement
|
||||
class NoReceiver(val containingElement: PsiElement): CallablePlacement
|
||||
}
|
||||
|
||||
class CallableBuilder(val config: CallableBuilderConfiguration) {
|
||||
@@ -231,8 +235,14 @@ class CallableBuilder(val config: CallableBuilderConfiguration) {
|
||||
val placement = placement
|
||||
when {
|
||||
placement is CallablePlacement.NoReceiver -> {
|
||||
containingElement = placement.containingElement
|
||||
receiverClassDescriptor = (containingElement as? JetClassOrObject)?.let { currentFileContext[BindingContext.CLASS, it] }
|
||||
containingElement = placement.containingElement as? JetElement ?: config.currentFile
|
||||
receiverClassDescriptor = with (placement.containingElement) {
|
||||
when (this) {
|
||||
is JetClassOrObject -> currentFileContext[BindingContext.CLASS, this]
|
||||
is PsiClass -> getJavaClassDescriptor()
|
||||
else -> null
|
||||
}
|
||||
}
|
||||
}
|
||||
placement is CallablePlacement.WithReceiver -> {
|
||||
receiverClassDescriptor =
|
||||
@@ -558,8 +568,9 @@ class CallableBuilder(val config: CallableBuilderConfiguration) {
|
||||
}
|
||||
|
||||
private fun setupTypeReferencesForShortening(declaration: JetNamedDeclaration,
|
||||
typeRefsToShorten: MutableList<JetElement>,
|
||||
parameterTypeExpressions: List<TypeExpression>) {
|
||||
parameterTypeExpressions: List<TypeExpression>): List<JetElement> {
|
||||
val typeRefsToShorten = ArrayList<JetElement>()
|
||||
|
||||
if (config.isExtension) {
|
||||
val receiverTypeRef = JetPsiFactory(declaration).createType(receiverTypeCandidate!!.theType.renderLong(typeParameterNameMap))
|
||||
replaceWithLongerName(receiverTypeRef, receiverTypeCandidate.theType)
|
||||
@@ -604,6 +615,8 @@ class CallableBuilder(val config: CallableBuilderConfiguration) {
|
||||
parameterIndicesToShorten.stream()
|
||||
.map { expandedValueParameters[it].getTypeReference() }
|
||||
.filterNotNullTo(typeRefsToShorten)
|
||||
|
||||
return typeRefsToShorten
|
||||
}
|
||||
|
||||
private fun setupFunctionBody(func: JetNamedFunction) {
|
||||
@@ -768,19 +781,31 @@ class CallableBuilder(val config: CallableBuilderConfiguration) {
|
||||
|
||||
val newJavaMember: PsiMember = when (declaration) {
|
||||
is JetNamedFunction -> {
|
||||
val method = createJavaMethod(declaration, targetClass)
|
||||
method.getModifierList().setModifierProperty(PsiModifier.FINAL, false)
|
||||
method
|
||||
createJavaMethod(declaration, targetClass)
|
||||
}
|
||||
is JetProperty -> {
|
||||
createJavaField(declaration, targetClass)
|
||||
}
|
||||
is JetClass -> {
|
||||
createJavaClass(declaration, targetClass)
|
||||
}
|
||||
else -> return false
|
||||
}
|
||||
|
||||
val modifierList = newJavaMember.getModifierList()
|
||||
if (newJavaMember is PsiMethod || newJavaMember is PsiClass) {
|
||||
modifierList.setModifierProperty(PsiModifier.FINAL, false)
|
||||
}
|
||||
|
||||
declaration.delete()
|
||||
|
||||
newJavaMember.getModifierList().setModifierProperty(PsiModifier.STATIC, callableInfo.receiverTypeInfo.classObjectRequired)
|
||||
val needStatic = when (callableInfo) {
|
||||
is ConstructorInfo -> with(callableInfo.classInfo) {
|
||||
!inner && kind != ClassKind.ENUM_ENTRY && kind != ClassKind.ENUM_CLASS
|
||||
}
|
||||
else -> callableInfo.receiverTypeInfo.classObjectRequired
|
||||
}
|
||||
modifierList.setModifierProperty(PsiModifier.STATIC, needStatic)
|
||||
|
||||
JavaCodeStyleManager.getInstance(project).shortenClassReferences(newJavaMember);
|
||||
|
||||
@@ -790,6 +815,18 @@ class CallableBuilder(val config: CallableBuilderConfiguration) {
|
||||
when (newJavaMember) {
|
||||
is PsiMethod -> CreateFromUsageUtils.setupEditor(newJavaMember, targetEditor)
|
||||
is PsiField -> targetEditor.getCaretModel().moveToOffset(newJavaMember.getTextRange().getEndOffset() - 1)
|
||||
is PsiClass -> {
|
||||
val constructor = newJavaMember.getConstructors().firstOrNull()
|
||||
val superStatement = constructor?.getBody()?.getStatements()?.firstOrNull() as? PsiExpressionStatement
|
||||
val superCall = superStatement?.getExpression() as? PsiMethodCallExpression
|
||||
if (superCall != null) {
|
||||
val lParen = superCall.getArgumentList().getFirstChild()
|
||||
targetEditor.getCaretModel().moveToOffset(lParen.getTextRange().getEndOffset())
|
||||
}
|
||||
else {
|
||||
targetEditor.getCaretModel().moveToOffset(newJavaMember.getTextRange().getStartOffset())
|
||||
}
|
||||
}
|
||||
}
|
||||
targetEditor.getScrollingModel().scrollToCaret(ScrollType.RELATIVE)
|
||||
|
||||
@@ -895,9 +932,10 @@ class CallableBuilder(val config: CallableBuilderConfiguration) {
|
||||
}
|
||||
}
|
||||
|
||||
// change short type names to fully qualified ones (to be shortened below)
|
||||
val typeRefsToShorten = setupTypeReferencesForShortening(newDeclaration, parameterTypeExpressions)
|
||||
if (!transformToJavaMemberIfApplicable(newDeclaration)) {
|
||||
// change short type names to fully qualified ones (to be shortened below)
|
||||
setupTypeReferencesForShortening(newDeclaration, elementsToShorten, parameterTypeExpressions)
|
||||
elementsToShorten.addAll(typeRefsToShorten)
|
||||
setupEditor(newDeclaration)
|
||||
}
|
||||
|
||||
|
||||
+12
-2
@@ -39,9 +39,19 @@ import org.jetbrains.kotlin.psi.JetReferenceExpression
|
||||
import java.util.Arrays
|
||||
import org.jetbrains.kotlin.psi.JetDotQualifiedExpression
|
||||
import org.jetbrains.kotlin.psi.psiUtil.isDotReceiver
|
||||
import com.intellij.psi.PsiClass
|
||||
import com.intellij.psi.PsiElement
|
||||
|
||||
public object CreateClassFromReferenceExpressionActionFactory : JetIntentionActionsFactory() {
|
||||
override fun doCreateActions(diagnostic: Diagnostic): List<IntentionAction> {
|
||||
fun isEnum(element: PsiElement): Boolean {
|
||||
return when (element) {
|
||||
is JetClass -> element.isEnum()
|
||||
is PsiClass -> element.isEnum()
|
||||
else -> false
|
||||
}
|
||||
}
|
||||
|
||||
val refExpr = diagnostic.getPsiElement() as? JetSimpleNameExpression ?: return Collections.emptyList()
|
||||
if (refExpr.getNonStrictParentOfType<JetTypeReference>() != null) return Collections.emptyList()
|
||||
|
||||
@@ -77,7 +87,7 @@ public object CreateClassFromReferenceExpressionActionFactory : JetIntentionActi
|
||||
.filter {
|
||||
when (it) {
|
||||
ClassKind.ANNOTATION_CLASS -> inImport
|
||||
ClassKind.ENUM_ENTRY -> inImport && targetParent is JetClass && targetParent.isEnum()
|
||||
ClassKind.ENUM_ENTRY -> inImport && isEnum(targetParent)
|
||||
else -> true
|
||||
}
|
||||
}
|
||||
@@ -104,7 +114,7 @@ public object CreateClassFromReferenceExpressionActionFactory : JetIntentionActi
|
||||
.filter {
|
||||
filter(it) && when (it) {
|
||||
ClassKind.OBJECT -> true
|
||||
ClassKind.ENUM_ENTRY -> targetParent is JetClass && targetParent.isEnum()
|
||||
ClassKind.ENUM_ENTRY -> isEnum(targetParent)
|
||||
else -> false
|
||||
}
|
||||
}
|
||||
|
||||
+16
-2
@@ -42,6 +42,9 @@ import com.intellij.ide.util.DirectoryChooserUtil
|
||||
import java.util.HashMap
|
||||
import com.intellij.openapi.application.ApplicationManager
|
||||
import org.jetbrains.kotlin.idea.refactoring.canRefactor
|
||||
import com.intellij.psi.PsiMember
|
||||
import com.intellij.psi.PsiClass
|
||||
import com.intellij.psi.PsiFile
|
||||
|
||||
enum class ClassKind(val keyword: String, val description: String) {
|
||||
PLAIN_CLASS: ClassKind("class", "class")
|
||||
@@ -70,6 +73,17 @@ public class CreateClassFromUsageFix(
|
||||
override fun getText(): String =
|
||||
JetBundle.message("create.0.from.usage", "${classInfo.kind.description} '${classInfo.name}'")
|
||||
|
||||
override fun isAvailable(project: Project, editor: Editor?, file: PsiFile?): Boolean {
|
||||
if (!super.isAvailable(project, editor, file)) return false
|
||||
with(classInfo) {
|
||||
if (targetParent is PsiClass) {
|
||||
if (kind == OBJECT || kind == ENUM_ENTRY) return false
|
||||
if (targetParent.isInterface() && inner) return false
|
||||
}
|
||||
}
|
||||
return true
|
||||
}
|
||||
|
||||
override fun invoke(project: Project, editor: Editor, file: JetFile) {
|
||||
fun createFileByPackage(psiPackage: PsiPackage): JetFile? {
|
||||
val directories = psiPackage.getDirectories().filter { it.canRefactor() }
|
||||
@@ -105,10 +119,10 @@ public class CreateClassFromUsageFix(
|
||||
with (classInfo) {
|
||||
val targetParent =
|
||||
when (targetParent) {
|
||||
is JetElement -> targetParent
|
||||
is JetElement, is PsiClass -> targetParent
|
||||
is PsiPackage -> createFileByPackage(targetParent)
|
||||
else -> throw AssertionError("Unexpected element: " + targetParent.getText())
|
||||
} as? JetElement ?: return
|
||||
} ?: return
|
||||
|
||||
val constructorInfo = ConstructorInfo(classInfo, expectedTypeInfo)
|
||||
val builder = CallableBuilderConfiguration(
|
||||
|
||||
+4
@@ -45,6 +45,8 @@ import org.jetbrains.kotlin.idea.quickfix.DelegatingIntentionAction
|
||||
import org.jetbrains.kotlin.idea.JetBundle
|
||||
import com.intellij.psi.PsiPackage
|
||||
import org.jetbrains.kotlin.idea.refactoring.canRefactor
|
||||
import com.intellij.psi.PsiClass
|
||||
import org.jetbrains.kotlin.descriptors.ClassKind as ClassDescriptorKind
|
||||
|
||||
private fun String.checkClassName(): Boolean = isNotEmpty() && Character.isUpperCase(first())
|
||||
|
||||
@@ -104,6 +106,8 @@ private fun JetExpression.getInheritableTypeInfo(
|
||||
return TypeInfo.ByType(type, Variance.OUT_VARIANCE).noSubstitutions() to { classKind ->
|
||||
when (classKind) {
|
||||
ClassKind.ENUM_ENTRY -> isEnum && containingDeclaration == DescriptorToSourceUtils.descriptorToDeclaration(descriptor)
|
||||
ClassKind.TRAIT -> containingDeclaration !is PsiClass
|
||||
|| (descriptor as? ClassDescriptor)?.getKind() == ClassDescriptorKind.TRAIT
|
||||
else -> canHaveSubtypes
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,37 @@
|
||||
/*
|
||||
* Copyright 2010-2015 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.jetbrains.kotlin.idea.refactoring
|
||||
|
||||
import com.intellij.psi.PsiReferenceList
|
||||
import com.intellij.psi.PsiReferenceList.Role
|
||||
import com.intellij.psi.PsiElementFactory
|
||||
import com.intellij.psi.PsiJavaCodeReferenceElement
|
||||
import org.jetbrains.kotlin.load.java.*
|
||||
|
||||
public fun PsiElementFactory.createReferenceListWithRole(
|
||||
references: Array<PsiJavaCodeReferenceElement>,
|
||||
role: Role
|
||||
): PsiReferenceList? {
|
||||
val filteredRefs = references.map { it.getCanonicalText() }.filter { it != JvmAbi.K_OBJECT.asString() }
|
||||
val refListText = if (filteredRefs.isNotEmpty()) filteredRefs.joinToString() else return null
|
||||
return when (role) {
|
||||
Role.THROWS_LIST -> createMethodFromText("void foo() throws $refListText {}", null).getThrowsList()
|
||||
Role.EXTENDS_LIST -> createClassFromText("class Foo extends $refListText {}", null).getInnerClasses()[0].getExtendsList()
|
||||
Role.IMPLEMENTS_LIST -> createClassFromText("class Foo implements $refListText {}", null).getInnerClasses()[0].getImplementsList()
|
||||
Role.EXTENDS_BOUNDS_LIST -> createTypeParameterFromText("T extends $refListText", null).getExtendsList()
|
||||
}
|
||||
}
|
||||
@@ -86,6 +86,14 @@ import com.intellij.util.VisibilityUtil
|
||||
import org.jetbrains.kotlin.descriptors.CallableMemberDescriptor
|
||||
import org.jetbrains.kotlin.descriptors.CallableMemberDescriptor.Kind
|
||||
import org.jetbrains.kotlin.resolve.OverridingUtil
|
||||
import org.jetbrains.kotlin.idea.caches.resolve.resolveToDescriptor
|
||||
import org.jetbrains.kotlin.descriptors.ClassDescriptor
|
||||
import org.jetbrains.kotlin.descriptors.ClassKind
|
||||
import com.intellij.psi.PsiReferenceList
|
||||
import com.intellij.psi.PsiTypeParameter
|
||||
import com.intellij.psi.PsiTypeParameterListOwner
|
||||
import com.intellij.psi.PsiNameIdentifierOwner
|
||||
import com.intellij.psi.PsiJavaCodeReferenceElement
|
||||
import com.intellij.lang.java.JavaLanguage
|
||||
import com.intellij.psi.PsiClass
|
||||
import com.intellij.codeInsight.daemon.impl.quickfix.CreateFromUsageUtils
|
||||
@@ -446,20 +454,19 @@ private fun copyModifierListItems(from: PsiModifierList, to: PsiModifierList, wi
|
||||
}
|
||||
}
|
||||
|
||||
public fun createJavaMethod(function: JetNamedFunction, targetClass: PsiClass): PsiMethod {
|
||||
val template = LightClassUtil.getLightClassMethod(function)
|
||||
?: throw AssertionError("Can't generate light method: ${JetPsiUtil.getElementTextWithContext(function)}")
|
||||
|
||||
val factory = PsiElementFactory.SERVICE.getInstance(template.getProject())
|
||||
val method = targetClass.add(factory.createMethod(template.getName(), template.getReturnType())) as PsiMethod
|
||||
|
||||
copyModifierListItems(template.getModifierList(), method.getModifierList())
|
||||
|
||||
val templateTypeParamList = template.getTypeParameterList()
|
||||
if (templateTypeParamList != null) {
|
||||
val targetTypeParamList = method.addAfter(factory.createTypeParameterList(), method.getModifierList()) as PsiTypeParameterList
|
||||
val newTypeParams = templateTypeParamList.getTypeParameters()
|
||||
.map { factory.createTypeParameter(it.getName(), it.getExtendsList().getReferencedTypes()) }
|
||||
private fun copyTypeParameters<T: PsiTypeParameterListOwner>(
|
||||
from: T,
|
||||
to: T,
|
||||
inserter: (T, PsiTypeParameterList) -> Unit
|
||||
) where T : PsiNameIdentifierOwner {
|
||||
val factory = PsiElementFactory.SERVICE.getInstance((from : PsiElement).getProject())
|
||||
val templateTypeParams = from.getTypeParameterList()?.getTypeParameters() ?: PsiTypeParameter.EMPTY_ARRAY
|
||||
if (templateTypeParams.isNotEmpty()) {
|
||||
inserter(to, factory.createTypeParameterList())
|
||||
val targetTypeParamList = to.getTypeParameterList()
|
||||
val newTypeParams = templateTypeParams.map {
|
||||
factory.createTypeParameter(it.getName(), it.getExtendsList().getReferencedTypes())
|
||||
}
|
||||
ChangeSignatureUtil.synchronizeList(
|
||||
targetTypeParamList,
|
||||
newTypeParams,
|
||||
@@ -467,6 +474,29 @@ public fun createJavaMethod(function: JetNamedFunction, targetClass: PsiClass):
|
||||
BooleanArray(newTypeParams.size())
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
public fun createJavaMethod(function: JetNamedFunction, targetClass: PsiClass): PsiMethod {
|
||||
val template = LightClassUtil.getLightClassMethod(function)
|
||||
?: throw AssertionError("Can't generate light method: ${JetPsiUtil.getElementTextWithContext(function)}")
|
||||
return createJavaMethod(template, targetClass)
|
||||
}
|
||||
|
||||
public fun createJavaMethod(template: PsiMethod, targetClass: PsiClass): PsiMethod {
|
||||
val factory = PsiElementFactory.SERVICE.getInstance(template.getProject())
|
||||
val methodToAdd = if (template.isConstructor()) {
|
||||
factory.createConstructor(template.getName())
|
||||
}
|
||||
else {
|
||||
factory.createMethod(template.getName(), template.getReturnType())
|
||||
}
|
||||
val method = targetClass.add(methodToAdd) as PsiMethod
|
||||
|
||||
copyModifierListItems(template.getModifierList(), method.getModifierList())
|
||||
|
||||
copyTypeParameters(template, method) { (method, typeParameterList) ->
|
||||
method.addAfter(typeParameterList, method.getModifierList())
|
||||
}
|
||||
|
||||
val targetParamList = method.getParameterList()
|
||||
val newParams = template.getParameterList().getParameters().map {
|
||||
@@ -484,7 +514,7 @@ public fun createJavaMethod(function: JetNamedFunction, targetClass: PsiClass):
|
||||
if (template.getModifierList().hasModifierProperty(PsiModifier.ABSTRACT) || targetClass.isInterface()) {
|
||||
method.getBody().delete()
|
||||
}
|
||||
else {
|
||||
else if (!template.isConstructor()) {
|
||||
CreateFromUsageUtils.setupMethodBody(method)
|
||||
}
|
||||
|
||||
@@ -509,3 +539,57 @@ fun createJavaField(property: JetProperty, targetClass: PsiClass): PsiField {
|
||||
|
||||
return field
|
||||
}
|
||||
|
||||
fun createJavaClass(klass: JetClass, targetClass: PsiClass): PsiMember {
|
||||
val kind = (klass.resolveToDescriptor() as ClassDescriptor).getKind()
|
||||
|
||||
val factory = PsiElementFactory.SERVICE.getInstance(klass.getProject())
|
||||
val javaClassToAdd = when (kind) {
|
||||
ClassKind.CLASS -> factory.createClass(klass.getName())
|
||||
ClassKind.TRAIT -> factory.createInterface(klass.getName())
|
||||
ClassKind.ANNOTATION_CLASS -> factory.createAnnotationType(klass.getName())
|
||||
ClassKind.ENUM_CLASS -> factory.createEnum(klass.getName())
|
||||
else -> throw AssertionError("Unexpected class kind: ${JetPsiUtil.getElementTextWithContext(klass)}")
|
||||
}
|
||||
val javaClass = targetClass.add(javaClassToAdd) as PsiClass
|
||||
|
||||
val template = LightClassUtil.getPsiClass(klass)
|
||||
?: throw AssertionError("Can't generate light class: ${JetPsiUtil.getElementTextWithContext(klass)}")
|
||||
|
||||
copyModifierListItems(template.getModifierList(), javaClass.getModifierList())
|
||||
if (template.isInterface()) {
|
||||
javaClass.getModifierList().setModifierProperty(PsiModifier.ABSTRACT, false)
|
||||
}
|
||||
|
||||
copyTypeParameters(template, javaClass) { (klass, typeParameterList) ->
|
||||
klass.addAfter(typeParameterList, klass.getNameIdentifier())
|
||||
}
|
||||
|
||||
val extendsList = factory.createReferenceListWithRole(
|
||||
template.getExtendsList()?.getReferenceElements() ?: PsiJavaCodeReferenceElement.EMPTY_ARRAY,
|
||||
PsiReferenceList.Role.EXTENDS_LIST
|
||||
)
|
||||
extendsList?.let { javaClass.getExtendsList()?.replace(it) }
|
||||
|
||||
val implementsList = factory.createReferenceListWithRole(
|
||||
template.getImplementsList()?.getReferenceElements() ?: PsiJavaCodeReferenceElement.EMPTY_ARRAY,
|
||||
PsiReferenceList.Role.IMPLEMENTS_LIST
|
||||
)
|
||||
implementsList?.let { javaClass.getImplementsList()?.replace(it) }
|
||||
|
||||
for (method in template.getMethods()) {
|
||||
val hasParams = method.getParameterList().getParametersCount() > 0
|
||||
val needSuperCall = !template.isEnum() &&
|
||||
(template.getSuperClass()?.getConstructors() ?: PsiMethod.EMPTY_ARRAY).all {
|
||||
it.getParameterList().getParametersCount() > 0
|
||||
}
|
||||
if (method.isConstructor() && !(hasParams || needSuperCall)) continue
|
||||
with(createJavaMethod(method, javaClass)) {
|
||||
if (isConstructor() && needSuperCall) {
|
||||
getBody().add(factory.createStatementFromText("super();", this))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return javaClass
|
||||
}
|
||||
|
||||
+6
@@ -0,0 +1,6 @@
|
||||
// "Create annotation 'foo'" "false"
|
||||
// ERROR: Unresolved reference: foo
|
||||
|
||||
J.<caret>foo(1, "2") fun test() {
|
||||
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class J {
|
||||
|
||||
}
|
||||
+8
@@ -0,0 +1,8 @@
|
||||
class J {
|
||||
|
||||
public static @interface foo {
|
||||
int i();
|
||||
|
||||
String s();
|
||||
}
|
||||
}
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
// "Create annotation 'foo'" "true"
|
||||
// ERROR: Unresolved reference: foo
|
||||
|
||||
J.foo(1, "2") fun test() {
|
||||
|
||||
}
|
||||
|
||||
+6
@@ -0,0 +1,6 @@
|
||||
// "Create annotation 'foo'" "true"
|
||||
// ERROR: Unresolved reference: foo
|
||||
|
||||
J.<caret>foo(1, "2") fun test() {
|
||||
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class J {
|
||||
|
||||
}
|
||||
+8
@@ -0,0 +1,8 @@
|
||||
class J {
|
||||
|
||||
public static @interface foo {
|
||||
int count();
|
||||
|
||||
String name();
|
||||
}
|
||||
}
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
// "Create annotation 'foo'" "true"
|
||||
// ERROR: Unresolved reference: foo
|
||||
|
||||
J.foo(count = 1, name = "2") fun test() {
|
||||
|
||||
}
|
||||
|
||||
+6
@@ -0,0 +1,6 @@
|
||||
// "Create annotation 'foo'" "true"
|
||||
// ERROR: Unresolved reference: foo
|
||||
|
||||
J.<caret>foo(count = 1, name = "2") fun test() {
|
||||
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class J {
|
||||
|
||||
}
|
||||
+8
@@ -0,0 +1,8 @@
|
||||
class J {
|
||||
|
||||
public static @interface bar {
|
||||
String s();
|
||||
|
||||
int i();
|
||||
}
|
||||
}
|
||||
+8
@@ -0,0 +1,8 @@
|
||||
// "Create annotation 'bar'" "true"
|
||||
// ERROR: Unresolved reference: foo
|
||||
// ERROR: Unresolved reference: bar
|
||||
|
||||
[foo(1, "2", J.bar("3", 4))] fun test() {
|
||||
|
||||
}
|
||||
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
// "Create annotation 'bar'" "true"
|
||||
// ERROR: Unresolved reference: foo
|
||||
// ERROR: Unresolved reference: bar
|
||||
|
||||
[foo(1, "2", J.<caret>bar("3", 4))] fun test() {
|
||||
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class J {
|
||||
|
||||
}
|
||||
+9
@@ -0,0 +1,9 @@
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
class J {
|
||||
|
||||
public static class Foo {
|
||||
public Foo(int abc, @NotNull A ghi, @NotNull String def) {
|
||||
}
|
||||
}
|
||||
}
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
class A(val n: Int)
|
||||
|
||||
fun test() = J.Foo(abc = 1, ghi = A(2), def = "s")
|
||||
|
||||
+6
@@ -0,0 +1,6 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
class A(val n: Int)
|
||||
|
||||
fun test() = J.<caret>Foo(abc = 1, ghi = A(2), def = "s")
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class J {
|
||||
|
||||
}
|
||||
+6
@@ -0,0 +1,6 @@
|
||||
// "Create class 'Foo'" "false"
|
||||
// ACTION: Create function 'Foo'
|
||||
// ACTION: Convert to block body
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
fun test(): A = <caret>Foo(2, "2")
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
final class A {
|
||||
|
||||
}
|
||||
+10
@@ -0,0 +1,10 @@
|
||||
class J<T> {
|
||||
public J(T n) {
|
||||
|
||||
}
|
||||
|
||||
public class Foo<U> {
|
||||
public Foo(U u) {
|
||||
}
|
||||
}
|
||||
}
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
fun test<U>(u: U) {
|
||||
val a = J(u).Foo(u)
|
||||
}
|
||||
|
||||
+6
@@ -0,0 +1,6 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
fun test<U>(u: U) {
|
||||
val a = J(u).<caret>Foo(u)
|
||||
}
|
||||
+5
@@ -0,0 +1,5 @@
|
||||
class J<T> {
|
||||
public J(T n) {
|
||||
|
||||
}
|
||||
}
|
||||
+4
@@ -0,0 +1,4 @@
|
||||
// "Create class 'Foo'" "false"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
fun test() = J.<caret>Foo(2, "2")
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class J {
|
||||
|
||||
}
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
class J {
|
||||
|
||||
public static class Foo {
|
||||
public Foo(int i) {
|
||||
}
|
||||
}
|
||||
}
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
fun test() {
|
||||
val a = J.Foo(2)
|
||||
}
|
||||
|
||||
+6
@@ -0,0 +1,6 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
fun test() {
|
||||
val a = J.<caret>Foo(2)
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class J {
|
||||
|
||||
}
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
class J {
|
||||
|
||||
public class Foo {
|
||||
public Foo(int i) {
|
||||
}
|
||||
}
|
||||
}
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
fun test() {
|
||||
val a = J().Foo(2)
|
||||
}
|
||||
|
||||
+3
-6
@@ -1,9 +1,6 @@
|
||||
// "Create class 'Foo'" "false"
|
||||
// ACTION: Create extension function 'Foo'
|
||||
// ACTION: Create function 'Foo'
|
||||
// ACTION: Convert to expression body
|
||||
// "Create class 'Foo'" "true"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
fun test(): Int {
|
||||
return A().<caret>Foo(1, "2")
|
||||
fun test() {
|
||||
val a = J().<caret>Foo(2)
|
||||
}
|
||||
+1
-1
@@ -1,3 +1,3 @@
|
||||
class A {
|
||||
class J {
|
||||
|
||||
}
|
||||
+10
@@ -0,0 +1,10 @@
|
||||
import kotlin.properties.ReadOnlyProperty;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
class J {
|
||||
|
||||
public static class Foo<T> implements ReadOnlyProperty<A<T>, B> {
|
||||
public Foo(T t, @NotNull String s) {
|
||||
}
|
||||
}
|
||||
}
|
||||
+10
@@ -0,0 +1,10 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// WITH_RUNTIME
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
open class B
|
||||
|
||||
class A<T>(val t: T) {
|
||||
val x: B by J.Foo(t, "")
|
||||
}
|
||||
|
||||
+9
@@ -0,0 +1,9 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// WITH_RUNTIME
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
open class B
|
||||
|
||||
class A<T>(val t: T) {
|
||||
val x: B by J.<caret>Foo(t, "")
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class J {
|
||||
|
||||
}
|
||||
+9
@@ -0,0 +1,9 @@
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
class J {
|
||||
|
||||
public static class Foo extends A {
|
||||
public Foo(int i, @NotNull String s) {
|
||||
}
|
||||
}
|
||||
}
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
open class A
|
||||
|
||||
fun test(): A = J.Foo(2, "2")
|
||||
|
||||
+6
@@ -0,0 +1,6 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
open class A
|
||||
|
||||
fun test(): A = J.<caret>Foo(2, "2")
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class J {
|
||||
|
||||
}
|
||||
+10
@@ -0,0 +1,10 @@
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
class J {
|
||||
|
||||
public static class Foo extends A {
|
||||
public Foo(int i, @NotNull String s) {
|
||||
super();
|
||||
}
|
||||
}
|
||||
}
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
open class A(val n: Int)
|
||||
|
||||
fun test(): A = J.Foo(2, "2")
|
||||
|
||||
+6
@@ -0,0 +1,6 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
open class A(val n: Int)
|
||||
|
||||
fun test(): A = J.<caret>Foo(2, "2")
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class J {
|
||||
|
||||
}
|
||||
+9
@@ -0,0 +1,9 @@
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
class J {
|
||||
|
||||
public static class Foo implements T {
|
||||
public Foo(int i, @NotNull String s) {
|
||||
}
|
||||
}
|
||||
}
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
trait T
|
||||
|
||||
fun test(): T = J.Foo(2, "2")
|
||||
|
||||
+6
@@ -0,0 +1,6 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
trait T
|
||||
|
||||
fun test(): T = J.<caret>Foo(2, "2")
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class J {
|
||||
|
||||
}
|
||||
+8
@@ -0,0 +1,8 @@
|
||||
class B<T> {
|
||||
final T t = null;
|
||||
|
||||
public static class Foo<U, V> {
|
||||
public Foo(U u, V v) {
|
||||
}
|
||||
}
|
||||
}
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
class A<T>(val b: B<T>) {
|
||||
fun test() = B.Foo<Int, String>(2, "2")
|
||||
}
|
||||
|
||||
+6
@@ -0,0 +1,6 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
class A<T>(val b: B<T>) {
|
||||
fun test() = B.<caret>Foo<Int, String>(2, "2")
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class B<T> {
|
||||
final T t = null;
|
||||
}
|
||||
+8
@@ -0,0 +1,8 @@
|
||||
class B<T> {
|
||||
final T t = null;
|
||||
|
||||
public class Foo<U, V> {
|
||||
public Foo(U u, V v) {
|
||||
}
|
||||
}
|
||||
}
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
class A<T>(val b: B<T>) {
|
||||
fun test() = b.Foo<Int, String>(2, "2")
|
||||
}
|
||||
|
||||
+6
@@ -0,0 +1,6 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
class A<T>(val b: B<T>) {
|
||||
fun test() = b.<caret>Foo<Int, String>(2, "2")
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class B<T> {
|
||||
final T t = null;
|
||||
}
|
||||
+8
@@ -0,0 +1,8 @@
|
||||
class B<T> {
|
||||
final T t = null;
|
||||
|
||||
public class Foo<U> {
|
||||
public Foo(int i, U u) {
|
||||
}
|
||||
}
|
||||
}
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
class A<T>(val b: B<T>) {
|
||||
fun test() = b.Foo<String>(2, "2")
|
||||
}
|
||||
|
||||
+6
@@ -0,0 +1,6 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
class A<T>(val b: B<T>) {
|
||||
fun test() = b.<caret>Foo<String>(2, "2")
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class B<T> {
|
||||
final T t = null;
|
||||
}
|
||||
+8
@@ -0,0 +1,8 @@
|
||||
class B<T> {
|
||||
final T t = null;
|
||||
|
||||
public class Foo<U, V, W> {
|
||||
public Foo(V v, W w) {
|
||||
}
|
||||
}
|
||||
}
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
class A<T>(val b: B<T>) {
|
||||
fun test() = b.Foo<T, Int, String>(2, "2")
|
||||
}
|
||||
|
||||
+6
@@ -0,0 +1,6 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
class A<T>(val b: B<T>) {
|
||||
fun test() = b.<caret>Foo<T, Int, String>(2, "2")
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class B<T> {
|
||||
final T t = null;
|
||||
}
|
||||
+8
@@ -0,0 +1,8 @@
|
||||
class B<T> {
|
||||
final T t = null;
|
||||
|
||||
public static class Foo<U> {
|
||||
public Foo(int i, U u) {
|
||||
}
|
||||
}
|
||||
}
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
class A<T>(val b: B<T>) {
|
||||
fun test() = B.Foo<String>(2, "2")
|
||||
}
|
||||
|
||||
+6
@@ -0,0 +1,6 @@
|
||||
// "Create class 'Foo'" "true"
|
||||
// ERROR: Unresolved reference: Foo
|
||||
|
||||
class A<T>(val b: B<T>) {
|
||||
fun test() = B.<caret>Foo<String>(2, "2")
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class B<T> {
|
||||
final T t = null;
|
||||
}
|
||||
+9
@@ -0,0 +1,9 @@
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
class J {
|
||||
|
||||
public static class A {
|
||||
public A(int i, @NotNull String s, @NotNull B B) {
|
||||
}
|
||||
}
|
||||
}
|
||||
+10
@@ -0,0 +1,10 @@
|
||||
// "Create class 'A'" "true"
|
||||
// ERROR: Unresolved reference: A
|
||||
class B {
|
||||
|
||||
}
|
||||
|
||||
class Foo: J.A(1, "2", B()) {
|
||||
|
||||
}
|
||||
|
||||
+9
@@ -0,0 +1,9 @@
|
||||
// "Create class 'A'" "true"
|
||||
// ERROR: Unresolved reference: A
|
||||
class B {
|
||||
|
||||
}
|
||||
|
||||
class Foo: J.<caret>A(1, "2", B()) {
|
||||
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class J {
|
||||
|
||||
}
|
||||
+9
@@ -0,0 +1,9 @@
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
class J {
|
||||
|
||||
public static class A {
|
||||
public A(int abc, @NotNull String ghi, @NotNull B def) {
|
||||
}
|
||||
}
|
||||
}
|
||||
+10
@@ -0,0 +1,10 @@
|
||||
// "Create class 'A'" "true"
|
||||
// ERROR: Unresolved reference: A
|
||||
class B {
|
||||
|
||||
}
|
||||
|
||||
class Foo: J.A(abc = 1, ghi = "2", def = B()) {
|
||||
|
||||
}
|
||||
|
||||
+9
@@ -0,0 +1,9 @@
|
||||
// "Create class 'A'" "true"
|
||||
// ERROR: Unresolved reference: A
|
||||
class B {
|
||||
|
||||
}
|
||||
|
||||
class Foo: J.<caret>A(abc = 1, ghi = "2", def = B()) {
|
||||
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class J {
|
||||
|
||||
}
|
||||
+5
@@ -0,0 +1,5 @@
|
||||
// "Create trait 'A'" "false"
|
||||
// ERROR: Unresolved reference: A
|
||||
class Foo: J.<caret>A {
|
||||
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class J {
|
||||
|
||||
}
|
||||
+5
@@ -0,0 +1,5 @@
|
||||
class J {
|
||||
|
||||
public static interface A {
|
||||
}
|
||||
}
|
||||
+6
@@ -0,0 +1,6 @@
|
||||
// "Create trait 'A'" "true"
|
||||
// ERROR: Unresolved reference: A
|
||||
class Foo: J.A {
|
||||
|
||||
}
|
||||
|
||||
+5
@@ -0,0 +1,5 @@
|
||||
// "Create trait 'A'" "true"
|
||||
// ERROR: Unresolved reference: A
|
||||
class Foo: J.<caret>A {
|
||||
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
class J {
|
||||
|
||||
}
|
||||
+5
@@ -0,0 +1,5 @@
|
||||
public class J {
|
||||
|
||||
public static @interface A {
|
||||
}
|
||||
}
|
||||
+8
@@ -0,0 +1,8 @@
|
||||
// "Create annotation 'A'" "true"
|
||||
// ERROR: Unresolved reference: A
|
||||
import J.A
|
||||
|
||||
class X {
|
||||
|
||||
}
|
||||
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
// "Create annotation 'A'" "true"
|
||||
// ERROR: Unresolved reference: A
|
||||
import J.<caret>A
|
||||
|
||||
class X {
|
||||
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
public class J {
|
||||
|
||||
}
|
||||
+8
@@ -0,0 +1,8 @@
|
||||
// "Create class 'A'" "false"
|
||||
// ERROR: Unresolved reference: A
|
||||
// ACTION: Create property 'A'
|
||||
import J.<caret>A
|
||||
|
||||
class X {
|
||||
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
public class J {
|
||||
|
||||
}
|
||||
+5
@@ -0,0 +1,5 @@
|
||||
public class J {
|
||||
|
||||
public static class A {
|
||||
}
|
||||
}
|
||||
+8
@@ -0,0 +1,8 @@
|
||||
// "Create class 'A'" "true"
|
||||
// ERROR: Unresolved reference: A
|
||||
import J.A
|
||||
|
||||
class X {
|
||||
|
||||
}
|
||||
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
// "Create class 'A'" "true"
|
||||
// ERROR: Unresolved reference: A
|
||||
import J.<caret>A
|
||||
|
||||
class X {
|
||||
|
||||
}
|
||||
+3
@@ -0,0 +1,3 @@
|
||||
public class J {
|
||||
|
||||
}
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user