diff --git a/idea/idea-core/src/org/jetbrains/kotlin/idea/core/overrideImplement/DescriptorClassMember.kt b/idea/idea-core/src/org/jetbrains/kotlin/idea/core/overrideImplement/DescriptorClassMember.kt index 9aa36e5e48f54..1890e13fd6f27 100644 --- a/idea/idea-core/src/org/jetbrains/kotlin/idea/core/overrideImplement/DescriptorClassMember.kt +++ b/idea/idea-core/src/org/jetbrains/kotlin/idea/core/overrideImplement/DescriptorClassMember.kt @@ -36,58 +36,38 @@ import org.jetbrains.kotlin.renderer.DescriptorRenderer import org.jetbrains.kotlin.renderer.DescriptorRendererModifier import org.jetbrains.kotlin.renderer.NameShortness import org.jetbrains.kotlin.renderer.render -import org.jetbrains.kotlin.resolve.DescriptorUtils +import org.jetbrains.kotlin.resolve.descriptorUtil.fqNameSafe import javax.swing.Icon -public class DescriptorClassMember(private val myPsiElement: PsiElement, public val descriptor: DeclarationDescriptor) : MemberChooserObjectBase(DescriptorClassMember.getText(descriptor), DescriptorClassMember.getIcon(myPsiElement, descriptor)), ClassMemberWithElement { +public class DescriptorClassMember( + private val psiElement: PsiElement, + public val descriptor: DeclarationDescriptor +) : MemberChooserObjectBase(DescriptorClassMember.getText(descriptor), DescriptorClassMember.getIcon(psiElement, descriptor)), ClassMemberWithElement { override fun getParentNodeDelegate(): MemberChooserObject { - val parent = descriptor.containingDeclaration - var declaration: PsiElement? - if (myPsiElement is JetDeclaration) { - // kotlin - declaration = PsiTreeUtil.getStubOrPsiParentOfType(myPsiElement, javaClass()) - if (declaration == null) { - declaration = PsiTreeUtil.getStubOrPsiParentOfType(myPsiElement, javaClass()) - } - } - else { - // java or bytecode - declaration = (myPsiElement as PsiMember).containingClass - } - assert(parent != null) { "$NO_PARENT_FOR$descriptor" } - assert(declaration != null) { "$NO_PARENT_FOR$myPsiElement" } + val parent = descriptor.containingDeclaration ?: error("No parent for $descriptor") - if (declaration is JetFile) { - return PsiElementMemberChooserObject(declaration, declaration.name) + val declaration = if (psiElement is JetDeclaration) { // kotlin + PsiTreeUtil.getStubOrPsiParentOfType(psiElement, javaClass()) + ?: PsiTreeUtil.getStubOrPsiParentOfType(psiElement, javaClass()) } + else { // java or compiled + (psiElement as PsiMember).containingClass + } ?: error("No parent for $psiElement") - return DescriptorClassMember(declaration!!, parent!!) + return when (declaration) { + is JetFile -> PsiElementMemberChooserObject(declaration, declaration.name) + else -> DescriptorClassMember(declaration, parent) + } } - override fun equals(other: Any?): Boolean { - if (this === other) return true - if (other == null || javaClass != other.javaClass) return false - - val that = other as DescriptorClassMember + override fun equals(other: Any?) = this === other || other is DescriptorClassMember && descriptor == other.descriptor - if (descriptor != that.descriptor) return false - - return true - } - - override fun hashCode(): Int { - return descriptor.hashCode() - } + override fun hashCode() = descriptor.hashCode() - override fun getElement(): PsiElement { - return myPsiElement - } + override fun getElement() = psiElement companion object { - - public val NO_PARENT_FOR: String = "No parent for " - private val MEMBER_RENDERER = DescriptorRenderer.withOptions { withDefinedIn = false modifiers = emptySet() @@ -96,30 +76,29 @@ public class DescriptorClassMember(private val myPsiElement: PsiElement, public } private fun getText(descriptor: DeclarationDescriptor): String { - if (descriptor is ClassDescriptor) { - return DescriptorUtils.getFqNameSafe(descriptor).render() - } - else { - return MEMBER_RENDERER.render(descriptor) - } + return if (descriptor is ClassDescriptor) + descriptor.fqNameSafe.render() + else + MEMBER_RENDERER.render(descriptor) } - private fun getIcon(element: PsiElement, declarationDescriptor: DeclarationDescriptor): Icon { + private fun getIcon(element: PsiElement, descriptor: DeclarationDescriptor): Icon { if (element.isValid) { val isClass = element is PsiClass || element is JetClass val flags = if (isClass) 0 else Iconable.ICON_FLAG_VISIBILITY if (element is JetDeclaration) { // kotlin declaration // visibility and abstraction better detect by a descriptor - return JetDescriptorIconProvider.getIcon(declarationDescriptor, element, flags) + return JetDescriptorIconProvider.getIcon(descriptor, element, flags) } else { // it is better to show java icons for java code return element.getIcon(flags) } } - - return JetDescriptorIconProvider.getIcon(declarationDescriptor, element, 0) + else { + return JetDescriptorIconProvider.getIcon(descriptor, element, 0) + } } } } diff --git a/idea/idea-core/src/org/jetbrains/kotlin/idea/core/overrideImplement/ImplementMethodsHandler.kt b/idea/idea-core/src/org/jetbrains/kotlin/idea/core/overrideImplement/ImplementMethodsHandler.kt index c432d42016013..a368f1e6d2935 100644 --- a/idea/idea-core/src/org/jetbrains/kotlin/idea/core/overrideImplement/ImplementMethodsHandler.kt +++ b/idea/idea-core/src/org/jetbrains/kotlin/idea/core/overrideImplement/ImplementMethodsHandler.kt @@ -20,34 +20,19 @@ import com.intellij.codeInsight.intention.IntentionAction import com.intellij.openapi.editor.Editor import com.intellij.openapi.project.Project import com.intellij.psi.PsiFile -import org.jetbrains.kotlin.descriptors.CallableMemberDescriptor import org.jetbrains.kotlin.descriptors.ClassDescriptor import org.jetbrains.kotlin.idea.JetBundle -import org.jetbrains.kotlin.idea.core.overrideImplement.OverrideImplementMethodsHandler import org.jetbrains.kotlin.resolve.OverrideResolver public class ImplementMethodsHandler : OverrideImplementMethodsHandler(), IntentionAction { - override fun collectMethodsToGenerate(descriptor: ClassDescriptor): Set { - return OverrideResolver.getMissingImplementations(descriptor) - } + override fun collectMethodsToGenerate(descriptor: ClassDescriptor) = OverrideResolver.getMissingImplementations(descriptor) - override fun getChooserTitle(): String { - return "Implement Members" - } + override fun getChooserTitle() = "Implement Members" - override fun getNoMethodsFoundHint(): String { - return "No methods to implement have been found" - } + override fun getNoMethodsFoundHint() = "No methods to implement have been found" - override fun getText(): String { - return JetBundle.message("implement.members") - } + override fun getText() = JetBundle.message("implement.members") + override fun getFamilyName() = JetBundle.message("implement.members") - override fun getFamilyName(): String { - return JetBundle.message("implement.members") - } - - override fun isAvailable(project: Project, editor: Editor, file: PsiFile): Boolean { - return isValidFor(editor, file) - } + override fun isAvailable(project: Project, editor: Editor, file: PsiFile) = isValidFor(editor, file) } diff --git a/idea/idea-core/src/org/jetbrains/kotlin/idea/core/overrideImplement/OverrideImplementMethodsHandler.kt b/idea/idea-core/src/org/jetbrains/kotlin/idea/core/overrideImplement/OverrideImplementMethodsHandler.kt index f4f684d612e14..6a4cf8040c79f 100644 --- a/idea/idea-core/src/org/jetbrains/kotlin/idea/core/overrideImplement/OverrideImplementMethodsHandler.kt +++ b/idea/idea-core/src/org/jetbrains/kotlin/idea/core/overrideImplement/OverrideImplementMethodsHandler.kt @@ -30,7 +30,6 @@ import org.jetbrains.kotlin.builtins.KotlinBuiltIns import org.jetbrains.kotlin.descriptors.* import org.jetbrains.kotlin.idea.caches.resolve.resolveToDescriptor import org.jetbrains.kotlin.idea.codeInsight.DescriptorToSourceUtilsIde -import org.jetbrains.kotlin.idea.core.overrideImplement.DescriptorClassMember import org.jetbrains.kotlin.idea.quickfix.moveCaretIntoGeneratedElement import org.jetbrains.kotlin.idea.util.IdeDescriptorRenderers import org.jetbrains.kotlin.idea.util.ShortenReferences @@ -43,30 +42,25 @@ import java.util.ArrayList public abstract class OverrideImplementMethodsHandler : LanguageCodeInsightActionHandler { public fun collectMethodsToGenerate(classOrObject: JetClassOrObject): Set { - val descriptor = classOrObject.resolveToDescriptor() - if (descriptor is ClassDescriptor) { - return collectMethodsToGenerate(descriptor) - } - return emptySet() + val descriptor = classOrObject.resolveToDescriptor() as? ClassDescriptor ?: return emptySet() + return collectMethodsToGenerate(descriptor) } protected abstract fun collectMethodsToGenerate(descriptor: ClassDescriptor): Set private fun showOverrideImplementChooser(project: Project, members: Array): MemberChooser? { val chooser = MemberChooser(members, true, true, project) - chooser.setTitle(getChooserTitle()) + chooser.title = getChooserTitle() chooser.show() - if (chooser.getExitCode() != DialogWrapper.OK_EXIT_CODE) return null + if (chooser.exitCode != DialogWrapper.OK_EXIT_CODE) return null return chooser } protected abstract fun getChooserTitle(): String override fun isValidFor(editor: Editor, file: PsiFile): Boolean { - if (file !is JetFile) { - return false - } - val elementAtCaret = file.findElementAt(editor.getCaretModel().getOffset()) + if (file !is JetFile) return false + val elementAtCaret = file.findElementAt(editor.caretModel.offset) val classOrObject = elementAtCaret?.getNonStrictParentOfType() return classOrObject != null } @@ -74,7 +68,7 @@ public abstract class OverrideImplementMethodsHandler : LanguageCodeInsightActio protected abstract fun getNoMethodsFoundHint(): String public fun invoke(project: Project, editor: Editor, file: PsiFile, implementAll: Boolean) { - val elementAtCaret = file.findElementAt(editor.getCaretModel().getOffset()) + val elementAtCaret = file.findElementAt(editor.caretModel.offset) val classOrObject = elementAtCaret?.getNonStrictParentOfType()!! val missingImplementations = collectMethodsToGenerate(classOrObject) @@ -82,22 +76,17 @@ public abstract class OverrideImplementMethodsHandler : LanguageCodeInsightActio HintManager.getInstance().showErrorHint(editor, getNoMethodsFoundHint()) return } + val members = membersFromDescriptors(file as JetFile, missingImplementations) - val selectedElements: List? - if (implementAll) { - selectedElements = members + val selectedElements: List = if (implementAll) { + members } else { - val chooser = showOverrideImplementChooser(project, members.toTypedArray()) - - if (chooser == null) { - return - } - - selectedElements = chooser.getSelectedElements() - if (selectedElements == null || selectedElements.isEmpty()) return + val chooser = showOverrideImplementChooser(project, members.toTypedArray()) ?: return + chooser.selectedElements ?: return } + if (selectedElements.isEmpty()) return PsiDocumentManager.getInstance(project).commitAllDocuments() @@ -119,18 +108,17 @@ public abstract class OverrideImplementMethodsHandler : LanguageCodeInsightActio typeNormalizer = IdeDescriptorRenderers.APPROXIMATE_FLEXIBLE_TYPES } - private val LOG = Logger.getInstance(javaClass().getCanonicalName()) + private val LOG = Logger.getInstance(javaClass().canonicalName) public fun membersFromDescriptors(file: JetFile, missingImplementations: Iterable): List { val members = ArrayList() for (memberDescriptor in missingImplementations) { - val declaration = DescriptorToSourceUtilsIde.getAnyDeclaration(file.getProject(), memberDescriptor) + val declaration = DescriptorToSourceUtilsIde.getAnyDeclaration(file.project, memberDescriptor) if (declaration == null) { - LOG.error("Can not find declaration for descriptor " + memberDescriptor) + LOG.error("Can not find declaration for descriptor $memberDescriptor") } else { - val member = DescriptorClassMember(declaration, memberDescriptor) - members.add(member) + members.add(DescriptorClassMember(declaration, memberDescriptor)) } } return members @@ -140,9 +128,7 @@ public abstract class OverrideImplementMethodsHandler : LanguageCodeInsightActio runWriteAction { val body = classOrObject.getOrCreateBody() - var afterAnchor = findInsertAfterAnchor(editor, body) - - if (afterAnchor == null) return@runWriteAction + var afterAnchor = findInsertAfterAnchor(editor, body) ?: return@runWriteAction var firstGenerated: PsiElement? = null @@ -162,12 +148,12 @@ public abstract class OverrideImplementMethodsHandler : LanguageCodeInsightActio if (firstGenerated == null) return@runWriteAction - val project = classOrObject.getProject() + val project = classOrObject.project val pointer = SmartPointerManager.getInstance(project).createSmartPsiElementPointer(firstGenerated) - PsiDocumentManager.getInstance(project).doPostponedOperationsAndUnblockDocument(editor.getDocument()) + PsiDocumentManager.getInstance(project).doPostponedOperationsAndUnblockDocument(editor.document) - val element = pointer.getElement() + val element = pointer.element if (element != null) { moveCaretIntoGeneratedElement(editor, element) } @@ -176,19 +162,18 @@ public abstract class OverrideImplementMethodsHandler : LanguageCodeInsightActio } private fun findInsertAfterAnchor(editor: Editor, body: JetClassBody): PsiElement? { - val afterAnchor = body.getLBrace() - if (afterAnchor == null) return null + val afterAnchor = body.lBrace ?: return null - val offset = editor.getCaretModel().getOffset() - val offsetCursorElement = PsiTreeUtil.findFirstParent(body.getContainingFile().findElementAt(offset)) { - it.getParent() == body + val offset = editor.caretModel.offset + val offsetCursorElement = PsiTreeUtil.findFirstParent(body.containingFile.findElementAt(offset)) { + it.parent == body } if (offsetCursorElement is PsiWhiteSpace) { return removeAfterOffset(offset, offsetCursorElement) } - if (offsetCursorElement != null && offsetCursorElement != body.getRBrace()) { + if (offsetCursorElement != null && offsetCursorElement != body.rBrace) { return offsetCursorElement } @@ -196,23 +181,23 @@ public abstract class OverrideImplementMethodsHandler : LanguageCodeInsightActio } private fun removeAfterOffset(offset: Int, whiteSpace: PsiWhiteSpace): PsiElement { - val spaceNode = whiteSpace.getNode() - if (spaceNode.getTextRange().contains(offset)) { - var beforeWhiteSpaceText = spaceNode.getText().substring(0, offset - spaceNode.getStartOffset()) + val spaceNode = whiteSpace.node + if (spaceNode.textRange.contains(offset)) { + var beforeWhiteSpaceText = spaceNode.text.substring(0, offset - spaceNode.startOffset) if (!StringUtil.containsLineBreak(beforeWhiteSpaceText)) { // Prevent insertion on same line beforeWhiteSpaceText += "\n" } - val factory = JetPsiFactory(whiteSpace.getProject()) + val factory = JetPsiFactory(whiteSpace.project) - val insertAfter = whiteSpace.getPrevSibling() + val insertAfter = whiteSpace.prevSibling whiteSpace.delete() val beforeSpace = factory.createWhiteSpace(beforeWhiteSpaceText) - insertAfter.getParent().addAfter(beforeSpace, insertAfter) + insertAfter.parent.addAfter(beforeSpace, insertAfter) - return insertAfter.getNextSibling() + return insertAfter.nextSibling } return whiteSpace @@ -234,38 +219,38 @@ public abstract class OverrideImplementMethodsHandler : LanguageCodeInsightActio } private fun overrideProperty(classOrObject: JetClassOrObject, descriptor: PropertyDescriptor): JetElement { - val newDescriptor = descriptor.copy(descriptor.getContainingDeclaration(), Modality.OPEN, descriptor.getVisibility(), - descriptor.getKind(), /* copyOverrides = */ true) as PropertyDescriptor + val newDescriptor = descriptor.copy(descriptor.containingDeclaration, Modality.OPEN, descriptor.visibility, + descriptor.kind, /* copyOverrides = */ true) as PropertyDescriptor newDescriptor.addOverriddenDescriptor(descriptor) val body = StringBuilder() body.append("\nget()") body.append(" = ") body.append(generateUnsupportedOrSuperCall(classOrObject, descriptor)) - if (descriptor.isVar()) { + if (descriptor.isVar) { body.append("\nset(value) {}") } - return JetPsiFactory(classOrObject.getProject()).createProperty(OVERRIDE_RENDERER.render(newDescriptor) + body) + return JetPsiFactory(classOrObject.project).createProperty(OVERRIDE_RENDERER.render(newDescriptor) + body) } private fun overrideFunction(classOrObject: JetClassOrObject, descriptor: FunctionDescriptor): JetNamedFunction { - val newDescriptor = descriptor.copy(descriptor.getContainingDeclaration(), Modality.OPEN, descriptor.getVisibility(), - descriptor.getKind(), /* copyOverrides = */ true) + val newDescriptor = descriptor.copy(descriptor.containingDeclaration, Modality.OPEN, descriptor.visibility, + descriptor.kind, /* copyOverrides = */ true) newDescriptor.addOverriddenDescriptor(descriptor) - val returnType = descriptor.getReturnType() + val returnType = descriptor.returnType val returnsNotUnit = returnType != null && !KotlinBuiltIns.isUnit(returnType) - val isAbstract = descriptor.getModality() == Modality.ABSTRACT + val isAbstract = descriptor.modality == Modality.ABSTRACT val delegation = generateUnsupportedOrSuperCall(classOrObject, descriptor) val body = "{" + (if (returnsNotUnit && !isAbstract) "return " else "") + delegation + "}" - return JetPsiFactory(classOrObject.getProject()).createFunction(OVERRIDE_RENDERER.render(newDescriptor) + body) + return JetPsiFactory(classOrObject.project).createFunction(OVERRIDE_RENDERER.render(newDescriptor) + body) } private fun generateUnsupportedOrSuperCall(classOrObject: JetClassOrObject, descriptor: CallableMemberDescriptor): String { - val isAbstract = descriptor.getModality() == Modality.ABSTRACT + val isAbstract = descriptor.modality == Modality.ABSTRACT if (isAbstract) { return "throw UnsupportedOperationException()" } @@ -273,14 +258,14 @@ public abstract class OverrideImplementMethodsHandler : LanguageCodeInsightActio val builder = StringBuilder() builder.append("super") if (classOrObject.getDelegationSpecifiers().size() > 1) { - builder.append("<").append(descriptor.getContainingDeclaration().escapedName()).append(">") + builder.append("<").append(descriptor.containingDeclaration.escapedName()).append(">") } builder.append(".").append(descriptor.escapedName()) if (descriptor is FunctionDescriptor) { - val paramTexts = descriptor.getValueParameters().map { + val paramTexts = descriptor.valueParameters.map { val renderedName = it.escapedName() - if (it.getVarargElementType() != null) "*$renderedName" else renderedName + if (it.varargElementType != null) "*$renderedName" else renderedName } paramTexts.joinTo(builder, prefix="(", postfix=")") } @@ -289,6 +274,6 @@ public abstract class OverrideImplementMethodsHandler : LanguageCodeInsightActio } } - private fun DeclarationDescriptor.escapedName() = getName().render() + private fun DeclarationDescriptor.escapedName() = name.render() } } diff --git a/idea/idea-core/src/org/jetbrains/kotlin/idea/core/overrideImplement/OverrideMethodsHandler.kt b/idea/idea-core/src/org/jetbrains/kotlin/idea/core/overrideImplement/OverrideMethodsHandler.kt index 19c3abeb65e8a..cef375214e715 100644 --- a/idea/idea-core/src/org/jetbrains/kotlin/idea/core/overrideImplement/OverrideMethodsHandler.kt +++ b/idea/idea-core/src/org/jetbrains/kotlin/idea/core/overrideImplement/OverrideMethodsHandler.kt @@ -23,8 +23,6 @@ import org.jetbrains.kotlin.resolve.OverrideResolver import org.jetbrains.kotlin.resolve.OverridingUtil import org.jetbrains.kotlin.resolve.OverridingUtil.OverrideCompatibilityInfo.Result.OVERRIDABLE import org.jetbrains.kotlin.resolve.calls.callResolverUtil.isOrOverridesSynthesized -import java.util.HashSet -import java.util.LinkedHashSet public class OverrideMethodsHandler : OverrideImplementMethodsHandler() { override fun collectMethodsToGenerate(descriptor: ClassDescriptor): Set { @@ -36,29 +34,20 @@ public class OverrideMethodsHandler : OverrideImplementMethodsHandler() { } } } - val result = HashSet() - for (superMethod in superMethods) { - if (superMethod.modality.isOverridable) { - if (!isOrOverridesSynthesized(superMethod)) { - result.add(superMethod) - } - } - } - return result + + return superMethods + .filter { it.modality.isOverridable && !isOrOverridesSynthesized(it) } + .toSet() } private fun collectSuperMethods(classDescriptor: ClassDescriptor): MutableSet { - val inheritedFunctions = LinkedHashSet() - for (supertype in classDescriptor.typeConstructor.supertypes) { - for (descriptor in supertype.memberScope.getAllDescriptors()) { - if (descriptor is CallableMemberDescriptor) { - inheritedFunctions.add(descriptor) - } - } - } + val inheritedFunctionsSet = classDescriptor.typeConstructor.supertypes + .flatMap { it.memberScope.getAllDescriptors() } + .filterIsInstance() + .toSet() // Only those actually inherited - val filteredMembers = OverrideResolver.filterOutOverridden(inheritedFunctions) + val filteredMembers = OverrideResolver.filterOutOverridden(inheritedFunctionsSet) // Group members with "the same" signature val factoredMembers = LinkedHashMultimap.create() @@ -76,11 +65,7 @@ public class OverrideMethodsHandler : OverrideImplementMethodsHandler() { return factoredMembers.keySet() } - override fun getChooserTitle(): String { - return "Override Members" - } + override fun getChooserTitle() = "Override Members" - override fun getNoMethodsFoundHint(): String { - return "No methods to override have been found" - } + override fun getNoMethodsFoundHint() = "No methods to override have been found" }