mirror of
https://github.com/mamoe/mirai.git
synced 2025-01-25 15:40:28 +08:00
Support line markers for CommandDeclaration
This commit is contained in:
parent
9351128f38
commit
dee84791f1
@ -128,13 +128,11 @@ object MyCompositeCommand : CompositeCommand(
|
||||
) {
|
||||
// 会自动创建一个 ID 为 "org.example.example-plugin:command.manage" 的权限.
|
||||
|
||||
// [参数智能解析]
|
||||
//
|
||||
// 在控制台执行 "/manage <群号>.<群员> <持续时间>",
|
||||
// 或在聊天群内发送 "/manage <@一个群员> <持续时间>",
|
||||
// 或在聊天群内发送 "/manage <目标群员的群名> <持续时间>",
|
||||
// 或在聊天群内发送 "/manage <目标群员的账号> <持续时间>"
|
||||
// 时调用这个函数
|
||||
@SubCommand
|
||||
suspend fun CommandSender.mute(target: Member, duration: Int) { // 通过 /manage mute <target> <duration> 调用
|
||||
sendMessage("/manage mute 被调用了, 参数为: $target, $duration")
|
||||
|
@ -0,0 +1,14 @@
|
||||
package org.example.myplugin
|
||||
|
||||
import net.mamoe.mirai.console.command.CommandSender
|
||||
import net.mamoe.mirai.console.command.SimpleCommand
|
||||
|
||||
object MySimpleCommand000 : SimpleCommand(
|
||||
MyPluginMain, "foo",
|
||||
description = "示例指令"
|
||||
) {
|
||||
@Handler
|
||||
suspend fun CommandSender.handle(int: Int, str: String) {
|
||||
|
||||
}
|
||||
}
|
@ -0,0 +1,40 @@
|
||||
package net.mamoe.mirai.console.intellij.line.marker
|
||||
|
||||
import com.intellij.codeHighlighting.Pass
|
||||
import com.intellij.codeInsight.daemon.LineMarkerInfo
|
||||
import com.intellij.codeInsight.daemon.LineMarkerProvider
|
||||
import com.intellij.openapi.actionSystem.AnAction
|
||||
import com.intellij.openapi.editor.markup.GutterIconRenderer
|
||||
import com.intellij.psi.PsiElement
|
||||
import net.mamoe.mirai.console.intellij.Icons
|
||||
import net.mamoe.mirai.console.intellij.resolve.isSimpleCommandHandlerOrCompositeCommandSubCommand
|
||||
import org.jetbrains.kotlin.psi.KtNamedFunction
|
||||
|
||||
class CommandDeclarationLineMarkerProvider : LineMarkerProvider {
|
||||
override fun getLineMarkerInfo(element: PsiElement): LineMarkerInfo<*>? {
|
||||
if (element !is KtNamedFunction) return null
|
||||
if (!element.isSimpleCommandHandlerOrCompositeCommandSubCommand()) return null
|
||||
return Info(getElementForLineMark(element.funKeyword ?: element.identifyingElement ?: element))
|
||||
}
|
||||
|
||||
@Suppress("DEPRECATION")
|
||||
class Info(
|
||||
callElement: PsiElement,
|
||||
) : LineMarkerInfo<PsiElement>(
|
||||
callElement,
|
||||
callElement.textRange,
|
||||
Icons.CommandDeclaration,
|
||||
Pass.LINE_MARKERS,
|
||||
{
|
||||
"子指令定义"
|
||||
},
|
||||
null,
|
||||
GutterIconRenderer.Alignment.RIGHT
|
||||
) {
|
||||
override fun createGutterRenderer(): GutterIconRenderer? {
|
||||
return object : LineMarkerInfo.LineMarkerGutterIconRenderer<PsiElement>(this) {
|
||||
override fun getClickAction(): AnAction? = null
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@ -5,12 +5,10 @@ import com.intellij.codeInsight.daemon.LineMarkerInfo
|
||||
import com.intellij.codeInsight.daemon.LineMarkerProvider
|
||||
import com.intellij.openapi.actionSystem.AnAction
|
||||
import com.intellij.openapi.editor.markup.GutterIconRenderer
|
||||
import com.intellij.openapi.progress.ProgressManager
|
||||
import com.intellij.psi.PsiElement
|
||||
import com.intellij.psi.PsiJavaCodeReferenceCodeFragment
|
||||
import com.intellij.util.castSafelyTo
|
||||
import net.mamoe.mirai.console.intellij.Icons
|
||||
import net.mamoe.mirai.console.intellij.Plugin_FQ_NAME
|
||||
import org.jetbrains.kotlin.idea.core.util.getLineNumber
|
||||
import org.jetbrains.kotlin.nj2k.postProcessing.resolve
|
||||
import org.jetbrains.kotlin.psi.KtClass
|
||||
import org.jetbrains.kotlin.psi.KtConstructor
|
||||
@ -19,50 +17,13 @@ import org.jetbrains.kotlin.psi.KtReferenceExpression
|
||||
|
||||
class PluginMainLineMarkerProvider : LineMarkerProvider {
|
||||
override fun getLineMarkerInfo(element: PsiElement): LineMarkerInfo<*>? {
|
||||
return null
|
||||
}
|
||||
|
||||
override fun collectSlowLineMarkers(
|
||||
elements: MutableList<out PsiElement>,
|
||||
result: MutableCollection<in LineMarkerInfo<*>>,
|
||||
) {
|
||||
val markedLineNumbers = HashSet<Int>()
|
||||
|
||||
for (element in elements) {
|
||||
ProgressManager.checkCanceled()
|
||||
|
||||
|
||||
val containingFile = element.containingFile
|
||||
if (containingFile is PsiJavaCodeReferenceCodeFragment) {
|
||||
continue
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
when {
|
||||
element is KtReferenceExpression // constructor call
|
||||
-> {
|
||||
val objectDeclaration =
|
||||
element.parents.filterIsInstance<KtObjectDeclaration>().firstOrNull() ?: continue
|
||||
|
||||
val resolved = element.resolve() as? KtConstructor<*> ?: continue
|
||||
|
||||
val kotlinPluginClass = resolved.parent as? KtClass ?: continue
|
||||
|
||||
if (kotlinPluginClass.allSuperNames.none { it == Plugin_FQ_NAME }) continue
|
||||
|
||||
val lineNumber = objectDeclaration.getLineNumber()
|
||||
if (lineNumber in markedLineNumbers) continue
|
||||
|
||||
markedLineNumbers += lineNumber
|
||||
result += Info(getElementForLineMark(objectDeclaration))
|
||||
}
|
||||
}
|
||||
|
||||
// if (!element.hasBridgeCalls()) continue
|
||||
|
||||
}
|
||||
if (element !is KtReferenceExpression) return null
|
||||
val objectDeclaration =
|
||||
element.parents.filterIsInstance<KtObjectDeclaration>().firstOrNull() ?: return null
|
||||
val kotlinPluginClass =
|
||||
element.resolve().castSafelyTo<KtConstructor<*>>()?.parent?.castSafelyTo<KtClass>() ?: return null
|
||||
if (kotlinPluginClass.allSuperNames.none { it == Plugin_FQ_NAME }) return null
|
||||
return Info(getElementForLineMark(objectDeclaration))
|
||||
}
|
||||
|
||||
@Suppress("DEPRECATION")
|
||||
|
@ -49,4 +49,10 @@ internal fun getElementForLineMark(callElement: PsiElement): PsiElement =
|
||||
// a fallback,
|
||||
//but who knows what to reference in KtArrayAccessExpression ?
|
||||
generateSequence(callElement, { it.firstChild }).last()
|
||||
}
|
||||
}
|
||||
|
||||
internal val KtAnnotationEntry.annotationClass: KtClass?
|
||||
get() = calleeExpression?.constructorReferenceExpression?.resolve()?.findParent<KtClass>()
|
||||
|
||||
internal fun KtAnnotated.hasAnnotation(fqName: FqName): Boolean =
|
||||
this.annotationEntries.any { it.annotationClass?.getKotlinFqName() == fqName }
|
@ -0,0 +1,30 @@
|
||||
/*
|
||||
* Copyright 2020 Mamoe Technologies and contributors.
|
||||
*
|
||||
* 此源代码的使用受 GNU AFFERO GENERAL PUBLIC LICENSE version 3 许可证的约束, 可以在以下链接找到该许可证.
|
||||
* Use of this source code is governed by the GNU AGPLv3 license that can be found through the following link.
|
||||
*
|
||||
* https://github.com/mamoe/mirai/blob/master/LICENSE
|
||||
*/
|
||||
|
||||
package net.mamoe.mirai.console.intellij.resolve
|
||||
|
||||
import net.mamoe.mirai.console.intellij.line.marker.hasAnnotation
|
||||
import org.jetbrains.kotlin.name.FqName
|
||||
import org.jetbrains.kotlin.psi.KtNamedFunction
|
||||
|
||||
val COMPOSITE_COMMAND_SUB_COMMAND_FQ_NAME = FqName("net.mamoe.mirai.console.command.CompositeCommand.SubCommand")
|
||||
val SIMPLE_COMMAND_HANDLER_COMMAND_FQ_NAME = FqName("net.mamoe.mirai.console.command.SimpleCommand.Handler")
|
||||
|
||||
/**
|
||||
* For CompositeCommand.SubCommand
|
||||
*/
|
||||
fun KtNamedFunction.isCompositeCommandSubCommand(): Boolean = this.hasAnnotation(COMPOSITE_COMMAND_SUB_COMMAND_FQ_NAME)
|
||||
|
||||
/**
|
||||
* SimpleCommand.Handler
|
||||
*/
|
||||
fun KtNamedFunction.isSimpleCommandHandler(): Boolean = this.hasAnnotation(SIMPLE_COMMAND_HANDLER_COMMAND_FQ_NAME)
|
||||
|
||||
fun KtNamedFunction.isSimpleCommandHandlerOrCompositeCommandSubCommand(): Boolean =
|
||||
this.isSimpleCommandHandler() || this.isCompositeCommandSubCommand()
|
@ -17,6 +17,10 @@
|
||||
implementationClass="net.mamoe.mirai.console.intellij.line.marker.PluginMainLineMarkerProvider"/>
|
||||
<codeInsight.lineMarkerProvider language="kotlin"
|
||||
implementationClass="net.mamoe.mirai.console.intellij.line.marker.PluginMainLineMarkerProvider"/>
|
||||
<codeInsight.lineMarkerProvider language="JAVA"
|
||||
implementationClass="net.mamoe.mirai.console.intellij.line.marker.CommandDeclarationLineMarkerProvider"/>
|
||||
<codeInsight.lineMarkerProvider language="kotlin"
|
||||
implementationClass="net.mamoe.mirai.console.intellij.line.marker.CommandDeclarationLineMarkerProvider"/>
|
||||
</extensions>
|
||||
|
||||
<extensions defaultExtensionNs="org.jetbrains.kotlin">
|
||||
|
Loading…
Reference in New Issue
Block a user