[FIR IDE] Make KtFakeLightClass independent

This commit is contained in:
Igor Yakovlev
2021-01-27 21:33:24 +03:00
parent c1cdf273a6
commit 2812034896
4 changed files with 48 additions and 40 deletions
@@ -6,14 +6,16 @@
package org.jetbrains.kotlin.idea.asJava
import com.intellij.psi.*
import com.intellij.psi.impl.InheritanceImplUtil
import org.jetbrains.kotlin.asJava.*
import org.jetbrains.kotlin.asJava.classes.KtLightClass
import org.jetbrains.kotlin.idea.caches.lightClasses.KtFakeLightClass
import org.jetbrains.kotlin.idea.caches.lightClasses.KtFakeLightMethod
import org.jetbrains.kotlin.psi.*
class LightClassProviderFirImpl : LightClassProvider {
override fun getLightFieldForCompanionObject(companionObject: KtClassOrObject): PsiField? {
return null
}
override fun getLightFieldForCompanionObject(companionObject: KtClassOrObject): PsiField? =
LightClassUtil.getLightFieldForCompanionObject(companionObject)
override fun getLightClassMethods(function: KtFunction): List<PsiMethod> =
LightClassUtil.getLightClassMethods(function)
@@ -25,7 +27,7 @@ class LightClassProviderFirImpl : LightClassProvider {
LightClassUtil.getLightClassPropertyMethods(property).allDeclarations
override fun toLightClassWithBuiltinMapping(classOrObject: KtClassOrObject): PsiClass? =
null
classOrObject.toLightClassWithBuiltinMapping()
override fun toLightMethods(psiElement: PsiElement): List<PsiMethod> =
psiElement.toLightMethods()
@@ -36,23 +38,20 @@ class LightClassProviderFirImpl : LightClassProvider {
override fun toLightElements(ktElement: KtElement): List<PsiNamedElement> =
ktElement.toLightElements()
override fun createKtFakeLightClass(kotlinOrigin: KtClassOrObject): PsiClass? {
return null
}
override fun createKtFakeLightClass(kotlinOrigin: KtClassOrObject): PsiClass? =
KtFakeLightClass(kotlinOrigin)
override fun getRepresentativeLightMethod(psiElement: PsiElement): PsiMethod? {
return null
}
override fun getRepresentativeLightMethod(psiElement: PsiElement): PsiMethod? =
psiElement.getRepresentativeLightMethod()
override fun isKtFakeLightClass(psiClass: PsiClass): Boolean {
return false
}
override fun isKtFakeLightClass(psiClass: PsiClass): Boolean =
psiClass is KtFakeLightClass
override fun isKtLightClassForDecompiledDeclaration(psiClass: PsiClass): Boolean {
return false
}
override fun isKtLightClassForDecompiledDeclaration(psiClass: PsiClass): Boolean = false //TODO
override fun createKtFakeLightMethod(ktDeclaration: KtNamedDeclaration): PsiMethod? {
return null
}
override fun createKtFakeLightMethod(ktDeclaration: KtNamedDeclaration): PsiMethod? =
KtFakeLightMethod.get(ktDeclaration)
override fun isFakeLightClassInheritor(ktFakeLightClass: KtFakeLightClass, baseClass: PsiClass, checkDeep: Boolean): Boolean =
InheritanceImplUtil.isInheritor(ktFakeLightClass, baseClass, checkDeep)
}
@@ -9,6 +9,7 @@ import com.intellij.openapi.components.ServiceManager
import com.intellij.openapi.project.Project
import com.intellij.psi.*
import org.jetbrains.kotlin.asJava.classes.KtLightClass
import org.jetbrains.kotlin.idea.caches.lightClasses.KtFakeLightClass
import org.jetbrains.kotlin.psi.*
interface LightClassProvider {
@@ -39,6 +40,8 @@ interface LightClassProvider {
fun createKtFakeLightMethod(ktDeclaration: KtNamedDeclaration): PsiMethod?
fun isFakeLightClassInheritor(ktFakeLightClass: KtFakeLightClass, baseClass: PsiClass, checkDeep: Boolean): Boolean
companion object {
fun getInstance(project: Project): LightClassProvider {
@@ -83,5 +86,8 @@ interface LightClassProvider {
fun PsiElement.providedGetRepresentativeLightMethod(): PsiMethod? =
getInstance(project).getRepresentativeLightMethod(this)
fun KtFakeLightClass.isFakeLightClassInheritor(baseClass: PsiClass, checkDeep: Boolean): Boolean =
getInstance(project).isFakeLightClassInheritor(this, baseClass, checkDeep)
}
}
@@ -12,17 +12,14 @@ import com.intellij.psi.impl.PsiClassImplUtil
import com.intellij.psi.impl.light.AbstractLightClass
import com.intellij.psi.impl.light.LightMethod
import com.intellij.util.IncorrectOperationException
import org.jetbrains.kotlin.asJava.ImpreciseResolveResult
import org.jetbrains.kotlin.asJava.classes.KtLightClass
import org.jetbrains.kotlin.asJava.classes.LightClassInheritanceHelper
import org.jetbrains.kotlin.asJava.elements.KtLightElement
import org.jetbrains.kotlin.idea.KotlinLanguage
import org.jetbrains.kotlin.idea.caches.resolve.resolveToDescriptorIfAny
import org.jetbrains.kotlin.idea.asJava.LightClassProvider.Companion.isFakeLightClassInheritor
import org.jetbrains.kotlin.load.java.structure.LightClassOriginKind
import org.jetbrains.kotlin.psi.KtClassOrObject
import org.jetbrains.kotlin.psi.KtNamedDeclaration
import org.jetbrains.kotlin.psi.psiUtil.containingClassOrObject
import org.jetbrains.kotlin.resolve.DescriptorUtils
import javax.swing.Icon
// Used as a placeholder when actual light class does not exist (expect-classes, for example)
@@ -48,23 +45,8 @@ class KtFakeLightClass(override val kotlinOrigin: KtClassOrObject) :
override fun getContainingFile() = kotlinOrigin.containingFile
override fun getUseScope() = kotlinOrigin.useScope
override fun isInheritor(baseClass: PsiClass, checkDeep: Boolean): Boolean {
if (manager.areElementsEquivalent(baseClass, this)) return false
LightClassInheritanceHelper.getService(project).isInheritor(this, baseClass, checkDeep).ifSure { return it }
val baseKtClass = (baseClass as? KtLightClass)?.kotlinOrigin ?: return false
val baseDescriptor = baseKtClass.resolveToDescriptorIfAny() ?: return false
val thisDescriptor = kotlinOrigin.resolveToDescriptorIfAny() ?: return false
val thisFqName = DescriptorUtils.getFqName(thisDescriptor).asString()
val baseFqName = DescriptorUtils.getFqName(baseDescriptor).asString()
if (thisFqName == baseFqName) return false
return if (checkDeep)
DescriptorUtils.isSubclass(thisDescriptor, baseDescriptor)
else
DescriptorUtils.isDirectSubclass(thisDescriptor, baseDescriptor)
}
override fun isInheritor(baseClass: PsiClass, checkDeep: Boolean): Boolean =
isFakeLightClassInheritor(baseClass, checkDeep)
override fun isEquivalentTo(another: PsiElement?): Boolean = PsiClassImplUtil.isClassEquivalentTo(this, another)
}
@@ -8,10 +8,13 @@ package org.jetbrains.kotlin.idea.asJava
import com.intellij.psi.*
import org.jetbrains.kotlin.asJava.*
import org.jetbrains.kotlin.asJava.classes.KtLightClass
import org.jetbrains.kotlin.asJava.classes.LightClassInheritanceHelper
import org.jetbrains.kotlin.idea.caches.lightClasses.KtFakeLightClass
import org.jetbrains.kotlin.idea.caches.lightClasses.KtFakeLightMethod
import org.jetbrains.kotlin.idea.caches.lightClasses.KtLightClassForDecompiledDeclaration
import org.jetbrains.kotlin.idea.caches.resolve.resolveToDescriptorIfAny
import org.jetbrains.kotlin.psi.*
import org.jetbrains.kotlin.resolve.DescriptorUtils
class LightClassProviderImpl : LightClassProvider {
override fun getLightFieldForCompanionObject(companionObject: KtClassOrObject): PsiField? =
@@ -52,4 +55,22 @@ class LightClassProviderImpl : LightClassProvider {
override fun createKtFakeLightMethod(ktDeclaration: KtNamedDeclaration): PsiMethod? =
KtFakeLightMethod.get(ktDeclaration)
override fun isFakeLightClassInheritor(ktFakeLightClass: KtFakeLightClass, baseClass: PsiClass, checkDeep: Boolean): Boolean {
if (ktFakeLightClass.manager.areElementsEquivalent(baseClass, ktFakeLightClass)) return false
LightClassInheritanceHelper.getService(ktFakeLightClass.project).isInheritor(ktFakeLightClass, baseClass, checkDeep).ifSure { return it }
val baseKtClass = (baseClass as? KtLightClass)?.kotlinOrigin ?: return false
val baseDescriptor = baseKtClass.resolveToDescriptorIfAny() ?: return false
val thisDescriptor = ktFakeLightClass.kotlinOrigin.resolveToDescriptorIfAny() ?: return false
val thisFqName = DescriptorUtils.getFqName(thisDescriptor).asString()
val baseFqName = DescriptorUtils.getFqName(baseDescriptor).asString()
if (thisFqName == baseFqName) return false
return if (checkDeep)
DescriptorUtils.isSubclass(thisDescriptor, baseDescriptor)
else
DescriptorUtils.isDirectSubclass(thisDescriptor, baseDescriptor)
}
}