[Kotlin] Bring back module names in expect/actual popup

Also rework UI logic in the popup — show symbol names only if symbols from the same module are shown, otherwise show only module names

^KTIJ-27115 Verification Pending

GitOrigin-RevId: e8b465ac0a321b1c6f44b9a855303bb311045f48
This commit is contained in:
Artem Daugel-Dauge
2023-10-24 14:51:46 +00:00
committed by intellij-monorepo-bot
parent 1f7e4d459e
commit 227c9f5651
43 changed files with 173 additions and 185 deletions
@@ -6,7 +6,6 @@ import com.intellij.openapi.roots.OrderRootType
import com.intellij.openapi.roots.libraries.Library
import com.intellij.openapi.vfs.VirtualFile
import com.intellij.psi.search.GlobalSearchScope
import org.jetbrains.kotlin.analyzer.LibraryModuleSourceInfoBase
import org.jetbrains.kotlin.analyzer.ModuleInfo
import org.jetbrains.kotlin.idea.base.projectStructure.KotlinBaseProjectStructureBundle
import org.jetbrains.kotlin.idea.base.projectStructure.LibraryInfoCache
@@ -17,7 +16,7 @@ import org.jetbrains.kotlin.platform.TargetPlatform
import org.jetbrains.kotlin.resolve.PlatformDependentAnalyzerServices
data class LibrarySourceInfo(override val project: Project, val library: Library, override val binariesModuleInfo: BinaryModuleInfo) :
IdeaModuleInfo, SourceForBinaryModuleInfo, LibraryModuleSourceInfoBase {
IdeaModuleInfo, SourceForBinaryModuleInfo {
override val name: Name = Name.special("<sources for library ${library.name}>")
@@ -2,8 +2,10 @@
package org.jetbrains.kotlin.idea.codeInsight.lineMarkers.shared
import com.intellij.codeInsight.navigation.impl.PsiTargetPresentationRenderer
import com.intellij.icons.AllIcons
import com.intellij.openapi.application.runReadAction
import com.intellij.openapi.editor.Document
import com.intellij.openapi.roots.libraries.Library
import com.intellij.psi.PsiDocumentManager
import com.intellij.psi.PsiElement
import com.intellij.psi.SmartPsiElementPointer
@@ -13,8 +15,15 @@ import com.intellij.psi.util.parentOfType
import com.intellij.refactoring.suggested.createSmartPointer
import com.intellij.util.concurrency.annotations.RequiresBackgroundThread
import org.jetbrains.annotations.ApiStatus
import org.jetbrains.annotations.Nls
import org.jetbrains.kotlin.analysis.api.analyze
import org.jetbrains.kotlin.analysis.api.symbols.KtDeclarationSymbol
import org.jetbrains.kotlin.analyzer.ModuleInfo
import org.jetbrains.kotlin.idea.base.facet.isHMPPEnabled
import org.jetbrains.kotlin.idea.base.projectStructure.moduleInfo
import org.jetbrains.kotlin.idea.base.projectStructure.moduleInfo.LibraryInfo
import org.jetbrains.kotlin.idea.base.projectStructure.moduleInfo.LibrarySourceInfo
import org.jetbrains.kotlin.idea.base.projectStructure.moduleInfo.ModuleSourceInfo
import org.jetbrains.kotlin.idea.stubindex.*
import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.psi.*
@@ -22,6 +31,7 @@ import org.jetbrains.kotlin.psi.psiUtil.containingClass
import org.jetbrains.kotlin.psi.psiUtil.containingClassOrObject
import org.jetbrains.kotlin.psi.psiUtil.hasActualModifier
import org.jetbrains.kotlin.psi.psiUtil.hasExpectModifier
import javax.swing.Icon
val KtNamedDeclaration.expectOrActualAnchor: PsiElement
@ApiStatus.Internal
@@ -119,10 +129,59 @@ fun KtNamedDeclaration.areMarkersForbidden(
return false
}
class ActualExpectedPsiElementCellRenderer : PsiTargetPresentationRenderer<PsiElement>() {
override fun getContainerText(element: PsiElement): String = ""
private class ActualExpectedPsiElementCellRenderer(private val onlyModuleNames: Boolean) : PsiTargetPresentationRenderer<PsiElement>() {
override fun getContainerText(element: PsiElement): String? = if (onlyModuleNames) null else element.moduleName()
override fun getIcon(element: PsiElement): Icon = when (element.moduleInfo) {
is LibrarySourceInfo, is LibraryInfo -> AllIcons.Nodes.PpLibFolder
else -> AllIcons.Nodes.Module
}
override fun getElementText(element: PsiElement): String = if (onlyModuleNames) element.moduleName() else super.getElementText(element)
@Nls
private fun PsiElement.moduleName() = moduleInfo.nameForTooltip()
}
@Nls
@Suppress("HardCodedStringLiteral")
fun ModuleInfo.nameForTooltip(): String {
when (this) {
/* For hmpp modules, prefer the module name, if present */
is ModuleSourceInfo -> takeIf { module.isHMPPEnabled }?.module?.name?.let { return it }
/* For libraries, we're trying to show artifact variant name */
is LibrarySourceInfo -> library.extractVariantName()?.let { return it }
is LibraryInfo -> library.extractVariantName()?.let { return it }
}
stableName?.asStringStripSpecialMarkers()?.let { return it }
// We want to represent actual descriptors, so let's represent them by platform
return platform.componentPlatforms.joinToString(", ", "{", "}") { it.platformName }
}
/*
Supported formats:
<groupId>:<artifactId>:<variant>:<version>
<groupId>:<artifactId>-<variant>:<version>
*/
private fun Library.extractVariantName(): String? {
val split = name.orEmpty().split(":")
if (split.size != 3 && split.size != 4) {
return null
}
return when (split.size) {
3 -> split[1].substringAfterLast('-')
4 -> split[2]
else -> null
}
}
private fun Collection<KtDeclaration>.hasUniqueModuleNames() = distinctBy { it.moduleInfo.nameForTooltip() }.size == size
@ApiStatus.Internal
fun buildNavigateToActualDeclarationsPopup(element: PsiElement?, allNavigatableActualDeclarations: KtDeclaration.() -> Collection<KtDeclaration>): NavigationPopupDescriptor? {
return element?.markerDeclaration?.let {
@@ -133,7 +192,7 @@ fun buildNavigateToActualDeclarationsPopup(element: PsiElement?, allNavigatableA
navigatableActualDeclarations,
KotlinLineMarkersSharedBundle.message("highlighter.title.choose.actual.for", name),
KotlinLineMarkersSharedBundle.message("highlighter.title.actuals.for", name),
ActualExpectedPsiElementCellRenderer()
ActualExpectedPsiElementCellRenderer(onlyModuleNames = navigatableActualDeclarations.hasUniqueModuleNames())
)
}
}
@@ -148,7 +207,7 @@ fun buildNavigateToExpectedDeclarationsPopup(element: PsiElement?, allNavigatabl
navigatableExpectedDeclarations,
KotlinLineMarkersSharedBundle.message("highlighter.title.choose.expected.for", name),
KotlinLineMarkersSharedBundle.message("highlighter.title.expected.for", name),
ActualExpectedPsiElementCellRenderer()
ActualExpectedPsiElementCellRenderer(onlyModuleNames = navigatableExpectedDeclarations.hasUniqueModuleNames())
)
}
}
@@ -1,18 +1,18 @@
// Copyright 2000-2023 JetBrains s.r.o. and contributors. Use of this source code is governed by the Apache 2.0 license.
package sample
expect class <!LINE_MARKER("descr='Has actuals in js, jvm modules'")!>Sample<!>() {
fun <!LINE_MARKER("descr='Has actuals in js, jvm modules'")!>checkMe<!>(): Int
expect class <!LINE_MARKER("descr='Has actuals in js, jvm modules'; targets=[(text=jvm; icon=nodes/Module.svg); (text=js; icon=nodes/Module.svg)]")!>Sample<!>() {
fun <!LINE_MARKER("descr='Has actuals in js, jvm modules'; targets=[(text=jvm; icon=nodes/Module.svg); (text=js; icon=nodes/Module.svg)]")!>checkMe<!>(): Int
}
expect object <!LINE_MARKER("descr='Has actuals in js, jvm modules'")!>Platform<!> {
val <!LINE_MARKER("descr='Has actuals in js, jvm modules'")!>name<!>: String
expect object <!LINE_MARKER("descr='Has actuals in js, jvm modules'; targets=[(text=jvm; icon=nodes/Module.svg); (text=js; icon=nodes/Module.svg)]")!>Platform<!> {
val <!LINE_MARKER("descr='Has actuals in js, jvm modules'; targets=[(text=jvm; icon=nodes/Module.svg); (text=js; icon=nodes/Module.svg)]")!>name<!>: String
}
fun hello(): String = "Hello from ${Platform.name}"
expect fun <!LINE_MARKER("descr='Has actuals in js, jvm modules'")!>foo<!>()
expect fun <!LINE_MARKER("descr='Has actuals in js, jvm modules'; targets=[(text=jvm; icon=nodes/Module.svg); (text=js; icon=nodes/Module.svg)]")!>foo<!>()
expect annotation class <!LINE_MARKER("descr='Has actuals in js, jvm modules'")!>Preview<!>()
expect annotation class <!LINE_MARKER("descr='Has actuals in js, jvm modules'; targets=[(text=jvm; icon=nodes/Module.svg); (text=js; icon=nodes/Module.svg)]")!>Preview<!>()
expect object <!LINE_MARKER("descr='Has actuals in js, jvm modules'")!>SomeObject<!>()
expect object <!LINE_MARKER("descr='Has actuals in js, jvm modules'; targets=[(text=jvm; icon=nodes/Module.svg); (text=js; icon=nodes/Module.svg)]")!>SomeObject<!>()
@@ -1,70 +1,21 @@
// Copyright 2000-2023 JetBrains s.r.o. and contributors. Use of this source code is governed by the Apache 2.0 license.
package org.jetbrains.kotlin.idea.highlighter.markers
import com.intellij.openapi.roots.libraries.Library
import org.jetbrains.annotations.ApiStatus
import org.jetbrains.kotlin.analyzer.moduleInfo
import org.jetbrains.kotlin.descriptors.DeclarationDescriptor
import org.jetbrains.kotlin.descriptors.MemberDescriptor
import org.jetbrains.kotlin.descriptors.ModuleDescriptor
import org.jetbrains.kotlin.idea.base.facet.isHMPPEnabled
import org.jetbrains.kotlin.idea.base.projectStructure.moduleInfo.LibraryInfo
import org.jetbrains.kotlin.idea.base.projectStructure.moduleInfo.LibrarySourceInfo
import org.jetbrains.kotlin.idea.base.projectStructure.moduleInfo.ModuleSourceInfo
import org.jetbrains.kotlin.idea.codeInsight.lineMarkers.shared.nameForTooltip
import org.jetbrains.kotlin.resolve.descriptorUtil.module
@ApiStatus.Internal
fun getModulesStringForExpectActualMarkerTooltip(
descriptors: List<DeclarationDescriptor>
): String? {
if (descriptors.isEmpty()) return null
val isExpectDescriptors = descriptors.all { it is MemberDescriptor && it.isExpect }
fun ModuleDescriptor.nameForTooltip(): String {
when (val moduleInfo = moduleInfo) {
/* For hmpp modules, prefer the module name, if present */
is ModuleSourceInfo -> moduleInfo.takeIf { it.module.isHMPPEnabled }?.module?.name?.let { return it }
/* For libraries we're trying to show artifact variant name */
is LibrarySourceInfo -> moduleInfo.library.extractVariantName()?.let { return it }
is LibraryInfo -> moduleInfo.library.extractVariantName()?.let { return it }
}
stableName?.asStringStripSpecialMarkers()?.let { return it }
/* Handle non-hmpp modes where no stableName might be present: */
// There is no 'easy' way to figure out the exact common module in this case
if (isExpectDescriptors) return "?common?"
// We want to represent actual descriptors, so let's represent them by platform
this.platform?.componentPlatforms?.joinToString(", ", "{", "}") { it.platformName }?.let { return it }
// We did our best, what can you do, this is life for you!
return "N/A"
}
return when (descriptors.size) {
1 -> descriptors.single().module.nameForTooltip()
else -> descriptors.joinToString(", ", "[", "]") { it.module.nameForTooltip() }
0 -> null
1 -> descriptors.single().moduleNameForTooltip()
else -> descriptors.joinToString(", ", "[", "]") { it.moduleNameForTooltip() }
}
}
/*
Supported formats:
<groupId>:<artifactId>:<variant>:<version>
<groupId>:<artifactId>-<variant>:<version>
*/
private fun Library.extractVariantName(): String? {
val split = name.orEmpty().split(":")
if (split.size != 3 && split.size != 4) {
return null
}
return when (split.size) {
3 -> split[1].substringAfterLast('-')
4 -> split[2]
else -> null
}
}
private fun DeclarationDescriptor.moduleNameForTooltip() = module.moduleInfo?.nameForTooltip() ?: "N/A"
@@ -5,6 +5,7 @@ package org.jetbrains.kotlin.idea.codeMetaInfo.renderConfigurations
import com.intellij.lang.annotation.HighlightSeverity
import org.jetbrains.kotlin.codeMetaInfo.model.CodeMetaInfo
import org.jetbrains.kotlin.codeMetaInfo.renderConfigurations.AbstractCodeMetaInfoRenderConfiguration
import org.jetbrains.kotlin.idea.codeInsight.lineMarkers.shared.TestableLineMarkerNavigator
import org.jetbrains.kotlin.idea.codeMetaInfo.models.HighlightingCodeMetaInfo
import org.jetbrains.kotlin.idea.codeMetaInfo.models.LineMarkerCodeMetaInfo
@@ -21,12 +22,33 @@ open class LineMarkerConfiguration(var renderDescription: Boolean = true) : Abst
if (!renderParams) return ""
val params = mutableListOf<String>()
val lineMarker = lineMarkerCodeMetaInfo.lineMarker
if (renderDescription) {
lineMarkerCodeMetaInfo.lineMarker.lineMarkerTooltip?.apply {
lineMarker.lineMarkerTooltip?.apply {
params.add("descr='${sanitizeLineMarkerTooltip(this)}'")
}
}
(lineMarker.navigationHandler as? TestableLineMarkerNavigator)?.getTargetsPopupDescriptor(lineMarker.element)?.let { navigator ->
val targets = navigator.targets.map { target ->
val presentation = navigator.renderer.getPresentation(target)
buildString {
append("(text=")
append(presentation.presentableText)
append("; ")
append(presentation.containerText?.let { "container=$it; " } ?: "")
append("icon=")
append(presentation.icon.toString())
append(")")
}
}
if (targets.size > 1) {
params.add(targets.joinToString(prefix = "targets=[", postfix = "]", separator = "; "))
}
}
params.add(getAdditionalParams(lineMarkerCodeMetaInfo))
val paramsString = params.filter { it.isNotEmpty() }.joinToString("; ")
@@ -1,7 +1,7 @@
package test
expect class <!LINE_MARKER("descr='Has actuals in [project.producer.jsMain, project.producer.jvmMain] modules'")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.producer.jsMain, project.producer.jvmMain] modules'")!>commonApi<!>()
expect class <!LINE_MARKER("descr='Has actuals in [project.producer.jsMain, project.producer.jvmMain] modules'; targets=[(text=project.producer.jsMain; icon=nodes/Module.svg); (text=project.producer.jvmMain; icon=nodes/Module.svg)]")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.producer.jsMain, project.producer.jvmMain] modules'; targets=[(text=project.producer.jsMain; icon=nodes/Module.svg); (text=project.producer.jvmMain; icon=nodes/Module.svg)]")!>commonApi<!>()
}
fun produceCommonMainExpect(): CommonMainExpect = null!!
@@ -1,7 +1,7 @@
package test
expect class <!LINE_MARKER("descr='Has actuals in [project.producer.jsMain, project.producer.jvmMain] modules'")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.producer.jsMain, project.producer.jvmMain] modules'")!>commonApi<!>()
expect class <!LINE_MARKER("descr='Has actuals in [project.producer.jsMain, project.producer.jvmMain] modules'; targets=[(text=project.producer.jsMain; icon=nodes/Module.svg); (text=project.producer.jvmMain; icon=nodes/Module.svg)]")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.producer.jsMain, project.producer.jvmMain] modules'; targets=[(text=project.producer.jsMain; icon=nodes/Module.svg); (text=project.producer.jvmMain; icon=nodes/Module.svg)]")!>commonApi<!>()
}
fun produceCommonMainExpect(): CommonMainExpect = null!!
@@ -1,8 +1,8 @@
package com.example.lib
expect object <!LINE_MARKER("descr='Has actuals in [iosarm64, jvm, linuxx64] modules'")!>Lib<!> {
expect object <!LINE_MARKER("descr='Has actuals in [iosarm64, jvm, linuxx64] modules'; targets=[(text=iosarm64; icon=nodes/ppLibFolder.svg); (text=jvm; icon=nodes/ppLibFolder.svg); (text=linuxx64; icon=nodes/ppLibFolder.svg)]")!>Lib<!> {
fun <!LINE_MARKER("descr='Has actuals in [iosarm64, jvm, linuxx64] modules'")!>foo<!>(): Int
fun <!LINE_MARKER("descr='Has actuals in [iosarm64, jvm, linuxx64] modules'; targets=[(text=iosarm64; icon=nodes/ppLibFolder.svg); (text=jvm; icon=nodes/ppLibFolder.svg); (text=linuxx64; icon=nodes/ppLibFolder.svg)]")!>foo<!>(): Int
}
expect fun <!LINE_MARKER("descr='Has actuals in [iosarm64, jvm, linuxx64] modules'")!>topLevelFun<!>()
expect fun <!LINE_MARKER("descr='Has actuals in [iosarm64, jvm, linuxx64] modules'; targets=[(text=iosarm64; icon=nodes/ppLibFolder.svg); (text=jvm; icon=nodes/ppLibFolder.svg); (text=linuxx64; icon=nodes/ppLibFolder.svg)]")!>topLevelFun<!>()
@@ -5,4 +5,5 @@ actual object <!LINE_MARKER("descr='Has expects in commonMain module'")!>Lib<!>
actual fun <!LINE_MARKER("descr='Has expects in commonMain module'")!>foo<!>(): Int = 42
}
expect val <!LINE_MARKER("descr='Has actuals in [iosarm64, linuxx64] modules'")!>topLevelVal<!>: String
expect val <!LINE_MARKER("descr='Has actuals in [iosarm64, linuxx64] modules'; targets=[(text=iosarm64; icon=nodes/ppLibFolder.svg); (text=linuxx64; icon=nodes/ppLibFolder.svg)]")!>topLevelVal<!>: String
M
@@ -1,7 +1,7 @@
package kmmApplication
expect class <!LINE_MARKER("descr='Has actuals in [project.iosMain, project.main] modules'")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.iosMain, project.main] modules'")!>commonMainApi<!>()
expect class <!LINE_MARKER("descr='Has actuals in [project.iosMain, project.main] modules'; targets=[(text=project.iosMain; icon=nodes/Module.svg); (text=project.main; icon=nodes/Module.svg)]")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.iosMain, project.main] modules'; targets=[(text=project.iosMain; icon=nodes/Module.svg); (text=project.main; icon=nodes/Module.svg)]")!>commonMainApi<!>()
}
fun consumeCommonMainExpect(e: CommonMainExpect?) { }
@@ -1,7 +1,7 @@
package kmmApplication
expect class <!LINE_MARKER("descr='Has actuals in [project.jvmMain, project.iosMain] modules'")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.jvmMain, project.iosMain] modules'")!>commonMainApi<!>()
expect class <!LINE_MARKER("descr='Has actuals in [project.jvmMain, project.iosMain] modules'; targets=[(text=project.jvmMain; icon=nodes/Module.svg); (text=project.iosMain; icon=nodes/Module.svg)]")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.jvmMain, project.iosMain] modules'; targets=[(text=project.jvmMain; icon=nodes/Module.svg); (text=project.iosMain; icon=nodes/Module.svg)]")!>commonMainApi<!>()
}
fun consumeCommonMainExpect(e: CommonMainExpect?) { }
@@ -1,7 +1,7 @@
package kmmApplication
expect class <!LINE_MARKER("descr='Has actuals in [project.iosMain, project.main] modules'")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.iosMain, project.main] modules'")!>commonMainApi<!>()
expect class <!LINE_MARKER("descr='Has actuals in [project.iosMain, project.main] modules'; targets=[(text=project.iosMain; icon=nodes/Module.svg); (text=project.main; icon=nodes/Module.svg)]")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.iosMain, project.main] modules'; targets=[(text=project.iosMain; icon=nodes/Module.svg); (text=project.main; icon=nodes/Module.svg)]")!>commonMainApi<!>()
}
fun consumeCommonMainExpect(e: CommonMainExpect?) { }
@@ -1,7 +1,7 @@
package kmmApplication
expect class <!LINE_MARKER("descr='Has actuals in [project.jvmMain, project.iosMain] modules'")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.jvmMain, project.iosMain] modules'")!>commonMainApi<!>()
expect class <!LINE_MARKER("descr='Has actuals in [project.jvmMain, project.iosMain] modules'; targets=[(text=project.jvmMain; icon=nodes/Module.svg); (text=project.iosMain; icon=nodes/Module.svg)]")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.jvmMain, project.iosMain] modules'; targets=[(text=project.jvmMain; icon=nodes/Module.svg); (text=project.iosMain; icon=nodes/Module.svg)]")!>commonMainApi<!>()
}
fun consumeCommonMainExpect(e: CommonMainExpect?) { }
@@ -1,7 +1,7 @@
package test
expect class <!LINE_MARKER("descr='Has actuals in [project.kmmLib.iosMain, project.kmmLib.main] modules'")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.kmmLib.iosMain, project.kmmLib.main] modules'")!>commonApi<!>()
expect class <!LINE_MARKER("descr='Has actuals in [project.kmmLib.iosMain, project.kmmLib.main] modules'; targets=[(text=project.kmmLib.iosMain; icon=nodes/Module.svg); (text=project.kmmLib.main; icon=nodes/Module.svg)]")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.kmmLib.iosMain, project.kmmLib.main] modules'; targets=[(text=project.kmmLib.iosMain; icon=nodes/Module.svg); (text=project.kmmLib.main; icon=nodes/Module.svg)]")!>commonApi<!>()
}
fun produceCommonMainExpect(): CommonMainExpect = null!!
@@ -1,7 +1,7 @@
package test
expect class <!LINE_MARKER("descr='Has actuals in [project.kmmLib.iosMain, project.kmmLib.main] modules'")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.kmmLib.iosMain, project.kmmLib.main] modules'")!>commonApi<!>()
expect class <!LINE_MARKER("descr='Has actuals in [project.kmmLib.iosMain, project.kmmLib.main] modules'; targets=[(text=project.kmmLib.iosMain; icon=nodes/Module.svg); (text=project.kmmLib.main; icon=nodes/Module.svg)]")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.kmmLib.iosMain, project.kmmLib.main] modules'; targets=[(text=project.kmmLib.iosMain; icon=nodes/Module.svg); (text=project.kmmLib.main; icon=nodes/Module.svg)]")!>commonApi<!>()
}
fun produceCommonMainExpect(): CommonMainExpect = null!!
@@ -1,7 +1,7 @@
package test
expect class <!LINE_MARKER("descr='Has actuals in [project.kmmLib.jvmMain, project.kmmLib.iosMain] modules'")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.kmmLib.jvmMain, project.kmmLib.iosMain] modules'")!>commonApi<!>()
expect class <!LINE_MARKER("descr='Has actuals in [project.kmmLib.jvmMain, project.kmmLib.iosMain] modules'; targets=[(text=project.kmmLib.jvmMain; icon=nodes/Module.svg); (text=project.kmmLib.iosMain; icon=nodes/Module.svg)]")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.kmmLib.jvmMain, project.kmmLib.iosMain] modules'; targets=[(text=project.kmmLib.jvmMain; icon=nodes/Module.svg); (text=project.kmmLib.iosMain; icon=nodes/Module.svg)]")!>commonApi<!>()
}
fun produceCommonMainExpect(): CommonMainExpect = null!!
@@ -1,7 +1,7 @@
package test
expect class <!LINE_MARKER("descr='Has actuals in [project.kmmLib.jvmMain, project.kmmLib.iosMain] modules'")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.kmmLib.jvmMain, project.kmmLib.iosMain] modules'")!>commonApi<!>()
expect class <!LINE_MARKER("descr='Has actuals in [project.kmmLib.jvmMain, project.kmmLib.iosMain] modules'; targets=[(text=project.kmmLib.jvmMain; icon=nodes/Module.svg); (text=project.kmmLib.iosMain; icon=nodes/Module.svg)]")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.kmmLib.jvmMain, project.kmmLib.iosMain] modules'; targets=[(text=project.kmmLib.jvmMain; icon=nodes/Module.svg); (text=project.kmmLib.iosMain; icon=nodes/Module.svg)]")!>commonApi<!>()
}
fun produceCommonMainExpect(): CommonMainExpect = null!!
@@ -1,7 +1,7 @@
package test
expect class <!LINE_MARKER("descr='Has actuals in [project.kmmLib.jvmMain, project.kmmLib.iosMain] modules'")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.kmmLib.jvmMain, project.kmmLib.iosMain] modules'")!>commonApi<!>()
expect class <!LINE_MARKER("descr='Has actuals in [project.kmmLib.jvmMain, project.kmmLib.iosMain] modules'; targets=[(text=project.kmmLib.jvmMain; icon=nodes/Module.svg); (text=project.kmmLib.iosMain; icon=nodes/Module.svg)]")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.kmmLib.jvmMain, project.kmmLib.iosMain] modules'; targets=[(text=project.kmmLib.jvmMain; icon=nodes/Module.svg); (text=project.kmmLib.iosMain; icon=nodes/Module.svg)]")!>commonApi<!>()
}
fun produceCommonMainExpect(): CommonMainExpect = null!!
@@ -1,7 +1,7 @@
package test
expect class <!LINE_MARKER("descr='Has actuals in [project.kmmLib.jvmMain, project.kmmLib.iosMain] modules'")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.kmmLib.jvmMain, project.kmmLib.iosMain] modules'")!>commonApi<!>()
expect class <!LINE_MARKER("descr='Has actuals in [project.kmmLib.jvmMain, project.kmmLib.iosMain] modules'; targets=[(text=project.kmmLib.jvmMain; icon=nodes/Module.svg); (text=project.kmmLib.iosMain; icon=nodes/Module.svg)]")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.kmmLib.jvmMain, project.kmmLib.iosMain] modules'; targets=[(text=project.kmmLib.jvmMain; icon=nodes/Module.svg); (text=project.kmmLib.iosMain; icon=nodes/Module.svg)]")!>commonApi<!>()
}
fun produceCommonMainExpect(): CommonMainExpect = null!!
@@ -1,7 +1,7 @@
package test
expect class <!LINE_MARKER("descr='Has actuals in [project.kmmLib.jvmMain, project.kmmLib.iosMain] modules'")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.kmmLib.jvmMain, project.kmmLib.iosMain] modules'")!>commonApi<!>()
expect class <!LINE_MARKER("descr='Has actuals in [project.kmmLib.jvmMain, project.kmmLib.iosMain] modules'; targets=[(text=project.kmmLib.jvmMain; icon=nodes/Module.svg); (text=project.kmmLib.iosMain; icon=nodes/Module.svg)]")!>CommonMainExpect<!> {
fun <!LINE_MARKER("descr='Has actuals in [project.kmmLib.jvmMain, project.kmmLib.iosMain] modules'; targets=[(text=project.kmmLib.jvmMain; icon=nodes/Module.svg); (text=project.kmmLib.iosMain; icon=nodes/Module.svg)]")!>commonApi<!>()
}
fun produceCommonMainExpect(): CommonMainExpect = null!!
@@ -1,11 +1 @@
actual class <!LINE_MARKER("descr='Has expects in common module'")!>WithConstructor<!> actual constructor(actual val x: Int, actual val s: String)
/*
LINEMARKER: Has declaration in common module
TARGETS:
common.kt
expect class <1>WithConstructor(x: Int, s: String) {
val <3>x: Int
val <2>s: String
*/
actual class <!LINE_MARKER("descr='Has expects in common module'; targets=[(text=WithConstructor; container=common; icon=nodes/Module.svg); (text=x; container=common; icon=nodes/Module.svg); (text=s; container=common; icon=nodes/Module.svg)]")!>WithConstructor<!> actual constructor(actual val x: Int, actual val s: String)
@@ -1,10 +1,3 @@
package test
actual enum class <!LINE_MARKER("descr='Has expects in common module'")!>Enum<!> { A, B, C }
/*
LINEMARKER: Has declaration in common module
TARGETS:
common.kt
expect enum class <4>Enum { <1>A, <2>B, <3>C }
*/
actual enum class <!LINE_MARKER("descr='Has expects in common module'; targets=[(text=Enum; container=common; icon=nodes/Module.svg); (text=A; container=common; icon=nodes/Module.svg); (text=B; container=common; icon=nodes/Module.svg); (text=C; container=common; icon=nodes/Module.svg)]")!>Enum<!> { A, B, C }
@@ -1,10 +1,3 @@
package test
expect enum class <!LINE_MARKER("descr='Has actuals in jvm module'")!>Enum<!> { A, B, C, D }
/*
LINEMARKER: Has actuals in JVM
TARGETS:
jvm.kt
actual enum class <5>Enum { <1>A, <2>B, <3>C, <4>D }
*/
expect enum class <!LINE_MARKER("descr='Has actuals in jvm module'; targets=[(text=Enum; container=jvm; icon=nodes/Module.svg); (text=A; container=jvm; icon=nodes/Module.svg); (text=B; container=jvm; icon=nodes/Module.svg); (text=C; container=jvm; icon=nodes/Module.svg); (text=D; container=jvm; icon=nodes/Module.svg)]")!>Enum<!> { A, B, C, D }
@@ -1,17 +1,5 @@
package test
expect enum class <!LINE_MARKER("descr='Has actuals in jvm module'")!>Enum<!> {
<!LINE_MARKER("descr='Has actuals in jvm module'")!>A<!>, B, C, D
<!LINE_MARKER("descr='Has actuals in jvm module'; targets=[(text=A; container=jvm; icon=nodes/Module.svg); (text=B; container=jvm; icon=nodes/Module.svg); (text=C; container=jvm; icon=nodes/Module.svg); (text=D; container=jvm; icon=nodes/Module.svg)]")!>A<!>, B, C, D
}
/*
LINEMARKER: Has actuals in JVM
TARGETS:
jvm.kt
actual enum class <1>Enum {
*//*
LINEMARKER: Has actuals in JVM
TARGETS:
jvm.kt
<1>A, <2>B, <3>C, <4>D
*/
@@ -1,6 +1,4 @@
// !CHECK_HIGHLIGHTING
expect annotation class Ann(
val x: Int, val y: String,
val z: Double, val b: Boolean
)
expect annotation class <!LINE_MARKER("descr='Has actuals in [jvm, js] modules'; targets=[(text=jvm; icon=nodes/Module.svg); (text=js; icon=nodes/Module.svg)]")!>Ann<!>(
val <!LINE_MARKER("descr='Has actuals in [jvm, js] modules'; targets=[(text=x; container=jvm; icon=nodes/Module.svg); (text=x; container=js; icon=nodes/Module.svg); (text=y; container=jvm; icon=nodes/Module.svg); (text=y; container=js; icon=nodes/Module.svg)]")!>x<!>: Int, val y: String,
val <!LINE_MARKER("descr='Has actuals in [jvm, js] modules'; targets=[(text=z; container=jvm; icon=nodes/Module.svg); (text=z; container=js; icon=nodes/Module.svg); (text=b; container=jvm; icon=nodes/Module.svg); (text=b; container=js; icon=nodes/Module.svg)]")!>z<!>: Double, val b: Boolean
)
@@ -1,4 +1,6 @@
MODULE common { platform=[JVM, JS, Native] }
MODULE jvm { platform=[JVM] }
MODULE js { platform=[JS] }
jvm -> common { kind=DEPENDS_ON }
jvm -> common { kind=DEPENDS_ON }
js -> common { kind=DEPENDS_ON }
@@ -0,0 +1,4 @@
actual annotation class <!LINE_MARKER("descr='Has expects in common module'")!>Ann<!>(
actual val <!LINE_MARKER("descr='Has expects in common module'; targets=[(text=x; container=common; icon=nodes/Module.svg); (text=y; container=common; icon=nodes/Module.svg)]")!>x<!>: Int, actual val y: String,
actual val <!LINE_MARKER("descr='Has expects in common module'; targets=[(text=z; container=common; icon=nodes/Module.svg); (text=b; container=common; icon=nodes/Module.svg)]")!>z<!>: Double, actual val b: Boolean
)
@@ -1,22 +1,4 @@
actual annotation class <!LINE_MARKER("descr='Has expects in common module'")!>Ann<!>(
actual val <!LINE_MARKER("descr='Has expects in common module'")!>x<!>: Int, actual val y: String,
actual val <!LINE_MARKER("descr='Has expects in common module'")!>z<!>: Double, actual val b: Boolean
actual val <!LINE_MARKER("descr='Has expects in common module'; targets=[(text=x; container=common; icon=nodes/Module.svg); (text=y; container=common; icon=nodes/Module.svg)]")!>x<!>: Int, actual val y: String,
actual val <!LINE_MARKER("descr='Has expects in common module'; targets=[(text=z; container=common; icon=nodes/Module.svg); (text=b; container=common; icon=nodes/Module.svg)]")!>z<!>: Double, actual val b: Boolean
)
/*
LINEMARKER: Has declaration in common module
TARGETS:
common.kt
expect annotation class <1>Ann(
*//*
LINEMARKER: Has declaration in common module
TARGETS:
common.kt
val <1>x: Int, val <2>y: String,
*//*
LINEMARKER: Has declaration in common module
TARGETS:
common.kt
val <2>z: Double, val <1>b: Boolean
*/
@@ -1,3 +1,3 @@
expect class <!LINE_MARKER("descr='Has actuals in jvm module'")!>Header<!> {
expect class <!LINE_MARKER("descr='Has actuals in [jvm, js] modules'; targets=[(text=jvm; icon=nodes/Module.svg); (text=js; icon=nodes/Module.svg)]")!>Header<!> {
}
@@ -1,4 +1,6 @@
MODULE common { platform=[JVM, JS, Native] }
MODULE jvm { platform=[JVM] }
MODULE js { platform=[JS] }
jvm -> common { kind=DEPENDS_ON }
jvm -> common { kind=DEPENDS_ON }
js -> common { kind=DEPENDS_ON }
@@ -0,0 +1,4 @@
// !CHECK_HIGHLIGHTING
actual typealias Header = String
@@ -1,4 +1,4 @@
expect class <!LINE_MARKER("descr='Has actuals in [native, jvmJs] modules'")!>Common<!> : Number {
expect class <!LINE_MARKER("descr='Has actuals in [native, jvmJs] modules'; targets=[(text=native; icon=nodes/Module.svg); (text=jvmJs; icon=nodes/Module.svg)]")!>Common<!> : Number {
override fun <!LINE_MARKER("descr='Press ... to navigate'")!>toDouble<!>(): Double
override fun <!LINE_MARKER("descr='Press ... to navigate'")!>toFloat<!>(): Float
override fun <!LINE_MARKER("descr='Press ... to navigate'")!>toLong<!>(): Long
@@ -4,8 +4,8 @@ package sample
// --------------------------------------------
expect interface <!LINE_MARKER("descr='Has actuals in [common-2-2, common-2-1] modules'"), LINE_MARKER("descr='Is subclassed by B (sample) Press ... to navigate'")!>A<!> {
fun <!LINE_MARKER("descr='Has actuals in [common-2-2, common-2-1] modules'")!>foo<!>()
expect interface <!LINE_MARKER("descr='Has actuals in [common-2-2, common-2-1] modules'; targets=[(text=common-2-2; icon=nodes/Module.svg); (text=common-2-1; icon=nodes/Module.svg)]"), LINE_MARKER("descr='Is subclassed by B (sample) Press ... to navigate'")!>A<!> {
fun <!LINE_MARKER("descr='Has actuals in [common-2-2, common-2-1] modules'; targets=[(text=common-2-2; icon=nodes/Module.svg); (text=common-2-1; icon=nodes/Module.svg)]")!>foo<!>()
}
fun take_A_common_1(x: A) {
@@ -1,5 +1,5 @@
package sample
expect class <!LINE_MARKER("descr='Has actuals in [left, right] modules'")!>A<!> {
fun <!LINE_MARKER("descr='Has actuals in [left, right] modules'")!>foo<!>(): Int
expect class <!LINE_MARKER("descr='Has actuals in [left, right] modules'; targets=[(text=left; icon=nodes/Module.svg); (text=right; icon=nodes/Module.svg)]")!>A<!> {
fun <!LINE_MARKER("descr='Has actuals in [left, right] modules'; targets=[(text=left; icon=nodes/Module.svg); (text=right; icon=nodes/Module.svg)]")!>foo<!>(): Int
}
@@ -1 +1 @@
expect class <!LINE_MARKER("descr='Has actuals in [a-js, a-jvm] modules'")!>A<!>
expect class <!LINE_MARKER("descr='Has actuals in [a-js, a-jvm] modules'; targets=[(text=a-js; icon=nodes/Module.svg); (text=a-jvm; icon=nodes/Module.svg)]")!>A<!>
@@ -1,3 +1,3 @@
package foo
expect class <!AMBIGUOUS_ACTUALS, LINE_MARKER("descr='Has actuals in [middle, bottom] modules'")!>A<!>
expect class <!AMBIGUOUS_ACTUALS, LINE_MARKER("descr='Has actuals in [middle, bottom] modules'; targets=[(text=middle; icon=nodes/Module.svg); (text=bottom; icon=nodes/Module.svg)]")!>A<!>
@@ -1,3 +1,3 @@
package foo
expect fun <!LINE_MARKER("descr='Has actuals in [middle, bottom] modules'")!>foo<!>(): Int
expect fun <!LINE_MARKER("descr='Has actuals in [middle, bottom] modules'; targets=[(text=middle; icon=nodes/Module.svg); (text=bottom; icon=nodes/Module.svg)]")!>foo<!>(): Int
@@ -1,3 +1,3 @@
expect class <!LINE_MARKER("descr='Has actuals in [iosX64, sharedLinux] modules'")!>ActualizedInSharedAndLeaf<!>
expect class <!LINE_MARKER("descr='Has actuals in [iosX64, sharedLinux] modules'; targets=[(text=iosX64; icon=nodes/Module.svg); (text=sharedLinux; icon=nodes/Module.svg)]")!>ActualizedInSharedAndLeaf<!>
expect class <!LINE_MARKER("descr='Has actuals in [linuxArm64, iosX64, linuxX64] modules'")!>ActualizedInLeaves<!>
expect class <!LINE_MARKER("descr='Has actuals in [linuxArm64, iosX64, linuxX64] modules'; targets=[(text=linuxArm64; icon=nodes/Module.svg); (text=iosX64; icon=nodes/Module.svg); (text=linuxX64; icon=nodes/Module.svg)]")!>ActualizedInLeaves<!>
@@ -1,6 +1,6 @@
package foo
expect class <!LINE_MARKER("descr='Has actuals in jvmAndJs module'")!>ExpectInCommonActualInMiddle<!>
expect class <!LINE_MARKER("descr='Has actuals in [jvm, js] modules'")!>ExpectInCommonActualInPlatforms<!>
expect class <!LINE_MARKER("descr='Has actuals in [jvm, js] modules'; targets=[(text=jvm; icon=nodes/Module.svg); (text=js; icon=nodes/Module.svg)]")!>ExpectInCommonActualInPlatforms<!>
expect class <!NO_ACTUAL_FOR_EXPECT, NO_ACTUAL_FOR_EXPECT!>ExpectInCommonWithoutActual<!>
@@ -3,4 +3,4 @@ package kotlin.jvm
annotation class JvmInline
@JvmInline
actual value class <!LINE_MARKER("descr='Has expects in common module'")!>VC<!>(val i: Int)
actual value class <!LINE_MARKER("descr='Has expects in common module'; targets=[(text=VC; container=common; icon=nodes/Module.svg); (text=i; container=common; icon=nodes/Module.svg)]")!>VC<!>(val i: Int)
@@ -2,7 +2,7 @@
package sample
actual data class <!LINE_MARKER("descr='Has expects in common module'")!>A<!>(actual val x: Int, actual val y: Double, val t: String) {
actual data class <!LINE_MARKER("descr='Has expects in common module'; targets=[(text=A; container=common; icon=nodes/Module.svg); (text=x; container=common; icon=nodes/Module.svg); (text=y; container=common; icon=nodes/Module.svg)]")!>A<!>(actual val x: Int, actual val y: Double, val t: String) {
actual fun <!LINE_MARKER("descr='Has expects in common module'")!>commonFun<!>() {}
fun platformFun() {}
@@ -1,11 +1,11 @@
package sample
expect class <!LINE_MARKER("descr='Has actuals in [jvm, js] modules'")!>Sample<!>() {
fun <!LINE_MARKER("descr='Has actuals in [jvm, js] modules'")!>checkMe<!>(): Int
expect class <!LINE_MARKER("descr='Has actuals in [jvm, js] modules'; targets=[(text=jvm; icon=nodes/Module.svg); (text=js; icon=nodes/Module.svg)]")!>Sample<!>() {
fun <!LINE_MARKER("descr='Has actuals in [jvm, js] modules'; targets=[(text=jvm; icon=nodes/Module.svg); (text=js; icon=nodes/Module.svg)]")!>checkMe<!>(): Int
}
expect object <!LINE_MARKER("descr='Has actuals in [jvm, js] modules'")!>Platform<!> {
val <!LINE_MARKER("descr='Has actuals in [jvm, js] modules'")!>name<!>: String
expect object <!LINE_MARKER("descr='Has actuals in [jvm, js] modules'; targets=[(text=jvm; icon=nodes/Module.svg); (text=js; icon=nodes/Module.svg)]")!>Platform<!> {
val <!LINE_MARKER("descr='Has actuals in [jvm, js] modules'; targets=[(text=jvm; icon=nodes/Module.svg); (text=js; icon=nodes/Module.svg)]")!>name<!>: String
}
fun hello(): String = "Hello from ${Platform.name}"
@@ -1,4 +1,4 @@
expect sealed class <!LINE_MARKER("descr='Has actuals in [platformAY, platformAX] modules'"), LINE_MARKER("descr='Is subclassed by CommonAImplTestClass CommonImplTestClass PlatformAXImplTestClass PlatformAYImplTestClass Press ... to navigate'")!>TestClass<!>()
expect sealed class <!LINE_MARKER("descr='Has actuals in [platformAY, platformAX] modules'; targets=[(text=platformAY; icon=nodes/Module.svg); (text=platformAX; icon=nodes/Module.svg)]"), LINE_MARKER("descr='Is subclassed by CommonAImplTestClass CommonImplTestClass PlatformAXImplTestClass PlatformAYImplTestClass Press ... to navigate'")!>TestClass<!>()
class CommonImplTestClass: TestClass()