KT-12124 No code completion for a java property in a specific position

#KT-12124 Fixed
This commit is contained in:
Valentin Kipyatkov
2016-05-11 19:48:55 +03:00
parent f6c8ac70fc
commit 97ad0d5c86
2 changed files with 26 additions and 2 deletions
@@ -23,6 +23,7 @@ import org.jetbrains.kotlin.resolve.BindingContext
import org.jetbrains.kotlin.resolve.calls.smartcasts.DataFlowInfo
import org.jetbrains.kotlin.resolve.calls.smartcasts.SmartCastManager
import org.jetbrains.kotlin.resolve.scopes.receivers.ReceiverValue
import org.jetbrains.kotlin.types.Flexibility
import org.jetbrains.kotlin.types.KotlinType
import org.jetbrains.kotlin.types.checker.KotlinTypeChecker
@@ -58,8 +59,31 @@ fun SmartCastManager.getSmartCastVariantsWithLessSpecificExcluded(
containingDeclarationOrModule: DeclarationDescriptor,
dataFlowInfo: DataFlowInfo
): List<KotlinType> {
val variants = getSmartCastVariants(receiverToCast, bindingContext, containingDeclarationOrModule, dataFlowInfo).distinct()
val variants = getSmartCastVariants(receiverToCast, bindingContext, containingDeclarationOrModule, dataFlowInfo)
return variants.filter { type ->
variants.none { another -> another !== type && KotlinTypeChecker.DEFAULT.isSubtypeOf(another, type) }
variants.all { another -> another === type || chooseMoreSpecific(type, another).let { it == null || it === type } }
}
}
private fun chooseMoreSpecific(type1: KotlinType, type2: KotlinType): KotlinType? {
val type1IsSubtype = KotlinTypeChecker.DEFAULT.isSubtypeOf(type1, type2)
val type2IsSubtype = KotlinTypeChecker.DEFAULT.isSubtypeOf(type2, type1)
when {
type1IsSubtype && !type2IsSubtype -> return type1
type2IsSubtype && !type1IsSubtype -> return type2
!type1IsSubtype && !type2IsSubtype -> return null
else -> { // type1IsSubtype && type2IsSubtype
val flexibility1 = type1.getCapability(Flexibility::class.java)
val flexibility2 = type2.getCapability(Flexibility::class.java)
when {
flexibility1 != null && flexibility2 == null -> return type2
flexibility2 != null && flexibility1 == null -> return type1
else -> return null //TODO?
}
}
}
}