如何在 Android 项目中使用 Kotlin 工作表

Mar*_*ius 5 android kotlin kotlin-script

我想在我的 Android 项目中使用Kotlin 工作表,以便添加如下代码草稿:

草稿.ws.kts

package com.example.app

val a = 1 + 1
a
Run Code Online (Sandbox Code Playgroud)

工作表本身正在工作:

val a: Int
2
Run Code Online (Sandbox Code Playgroud)

但是构建我的 Android 应用程序失败并显示以下输出:

> Task :appicals:compileDebugKotlin FAILED
e: org.jetbrains.kotlin.util.KotlinFrontEndException: Front-end Internal error: Failed to analyze declaration Draft_ws
File being compiled: (1,43) in /Users/me/secretproject/app/src/main/java/com/example/app/draft.ws.kts
The root cause org.jetbrains.kotlin.resolve.lazy.NoDescriptorForDeclarationException was thrown at: org.jetbrains.kotlin.resolve.lazy.BasicAbsentDescriptorHandler.diagnoseDescriptorNotFound(AbsentDescriptorHandler.kt:18)
    at org.jetbrains.kotlin.resolve.ExceptionWrappingKtVisitorVoid.visitDeclaration(ExceptionWrappingKtVisitorVoid.kt:43)
    at org.jetbrains.kotlin.psi.KtVisitorVoid.visitDeclaration(KtVisitorVoid.java:453)
    at org.jetbrains.kotlin.psi.KtVisitorVoid.visitDeclaration(KtVisitorVoid.java:21)
    at org.jetbrains.kotlin.psi.KtVisitor.visitScript(KtVisitor.java:78)
    at org.jetbrains.kotlin.psi.KtVisitorVoid.visitScript(KtVisitorVoid.java:73)
    at org.jetbrains.kotlin.psi.KtVisitorVoid.visitScript(KtVisitorVoid.java:519)
    at org.jetbrains.kotlin.psi.KtVisitorVoid.visitScript(KtVisitorVoid.java:21)
    at org.jetbrains.kotlin.psi.KtScript.accept(KtScript.java:69)
    at org.jetbrains.kotlin.psi.KtElementImplStub.accept(KtElementImplStub.java:59)
    at org.jetbrains.kotlin.resolve.LazyTopDownAnalyzer$analyzeDeclarations$1.registerDeclarations(LazyTopDownAnalyzer.kt:78)
    at org.jetbrains.kotlin.resolve.LazyTopDownAnalyzer$analyzeDeclarations$1.visitKtFile(LazyTopDownAnalyzer.kt:96)
    at org.jetbrains.kotlin.psi.KtVisitorVoid.visitKtFile(KtVisitorVoid.java:513)
    at org.jetbrains.kotlin.psi.KtVisitorVoid.visitKtFile(KtVisitorVoid.java:21)
    at org.jetbrains.kotlin.psi.KtFile.accept(KtFile.kt:242)
    at org.jetbrains.kotlin.psi.KtFile.accept(KtFile.kt:229)
    at org.jetbrains.kotlin.resolve.ExceptionWrappingKtVisitorVoid.visitElement(ExceptionWrappingKtVisitorVoid.kt:27)
    at org.jetbrains.kotlin.com.intellij.psi.PsiElementVisitor.visitFile(PsiElementVisitor.java:34)
    at org.jetbrains.kotlin.psi.KtVisitor.visitKtFile(KtVisitor.java:73)
    at org.jetbrains.kotlin.psi.KtVisitorVoid.visitKtFile(KtVisitorVoid.java:69)
    at org.jetbrains.kotlin.psi.KtVisitorVoid.visitKtFile(KtVisitorVoid.java:513)
    at org.jetbrains.kotlin.psi.KtVisitorVoid.visitKtFile(KtVisitorVoid.java:21)
    at org.jetbrains.kotlin.psi.KtFile.accept(KtFile.kt:242)
    at org.jetbrains.kotlin.psi.KtFile.accept(KtFile.kt:229)
    at org.jetbrains.kotlin.resolve.LazyTopDownAnalyzer.analyzeDeclarations(LazyTopDownAnalyzer.kt:201)
    at org.jetbrains.kotlin.resolve.LazyTopDownAnalyzer.analyzeDeclarations$default(LazyTopDownAnalyzer.kt:60)
    at org.jetbrains.kotlin.cli.jvm.compiler.TopDownAnalyzerFacadeForJVM.analyzeFilesWithJavaIntegration(TopDownAnalyzerFacadeForJVM.kt:112)
    at org.jetbrains.kotlin.cli.jvm.compiler.TopDownAnalyzerFacadeForJVM.analyzeFilesWithJavaIntegration$default(TopDownAnalyzerFacadeForJVM.kt:82)
    at org.jetbrains.kotlin.cli.jvm.compiler.KotlinToJVMBytecodeCompiler$analyze$1.invoke(KotlinToJVMBytecodeCompiler.kt:554)
    at org.jetbrains.kotlin.cli.jvm.compiler.KotlinToJVMBytecodeCompiler$analyze$1.invoke(KotlinToJVMBytecodeCompiler.kt:81)
    at org.jetbrains.kotlin.cli.common.messages.AnalyzerWithCompilerReport.analyzeAndReport(AnalyzerWithCompilerReport.kt:107)
    at org.jetbrains.kotlin.cli.jvm.compiler.KotlinToJVMBytecodeCompiler.analyze(KotlinToJVMBytecodeCompiler.kt:545)
    at org.jetbrains.kotlin.cli.jvm.compiler.KotlinToJVMBytecodeCompiler.compileModules$cli(KotlinToJVMBytecodeCompiler.kt:176)
    at org.jetbrains.kotlin.cli.jvm.K2JVMCompiler.doExecute(K2JVMCompiler.kt:163)
    at org.jetbrains.kotlin.cli.jvm.K2JVMCompiler.doExecute(K2JVMCompiler.kt:51)
    at org.jetbrains.kotlin.cli.common.CLICompiler.execImpl(CLICompiler.kt:85)
    at org.jetbrains.kotlin.cli.common.CLICompiler.execImpl(CLICompiler.kt:43)
    at org.jetbrains.kotlin.cli.common.CLITool.exec(CLITool.kt:104)
    at org.jetbrains.kotlin.incremental.IncrementalJvmCompilerRunner.runCompiler(IncrementalJvmCompilerRunner.kt:349)
    at org.jetbrains.kotlin.incremental.IncrementalJvmCompilerRunner.runCompiler(IncrementalJvmCompilerRunner.kt:105)
    at org.jetbrains.kotlin.incremental.IncrementalCompilerRunner.compileIncrementally(IncrementalCompilerRunner.kt:237)
    at org.jetbrains.kotlin.incremental.IncrementalCompilerRunner.access$compileIncrementally(IncrementalCompilerRunner.kt:37)
    at org.jetbrains.kotlin.incremental.IncrementalCompilerRunner$compile$2.invoke(IncrementalCompilerRunner.kt:79)
    at org.jetbrains.kotlin.incremental.IncrementalCompilerRunner.compile(IncrementalCompilerRunner.kt:91)
    at org.jetbrains.kotlin.daemon.CompileServiceImplBase.execIncrementalCompiler(CompileServiceImpl.kt:606)
    at org.jetbrains.kotlin.daemon.CompileServiceImplBase.access$execIncrementalCompiler(CompileServiceImpl.kt:99)
    at org.jetbrains.kotlin.daemon.CompileServiceImpl.compile(CompileServiceImpl.kt:1645)
    at sun.reflect.GeneratedMethodAccessor182.invoke(Unknown Source)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:498)
    at sun.rmi.server.UnicastServerRef.dispatch(UnicastServerRef.java:357)
    at sun.rmi.transport.Transport$1.run(Transport.java:200)
    at sun.rmi.transport.Transport$1.run(Transport.java:197)
    at java.security.AccessController.doPrivileged(Native Method)
    at sun.rmi.transport.Transport.serviceCall(Transport.java:196)
    at sun.rmi.transport.tcp.TCPTransport.handleMessages(TCPTransport.java:573)
    at sun.rmi.transport.tcp.TCPTransport$ConnectionHandler.run0(TCPTransport.java:834)
    at sun.rmi.transport.tcp.TCPTransport$ConnectionHandler.lambda$run$0(TCPTransport.java:688)
    at java.security.AccessController.doPrivileged(Native Method)
    at sun.rmi.transport.tcp.TCPTransport$ConnectionHandler.run(TCPTransport.java:687)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624)
    at java.lang.Thread.run(Thread.java:748)
Caused by: org.jetbrains.kotlin.resolve.lazy.NoDescriptorForDeclarationException: Descriptor wasn't found for declaration SCRIPT
    at org.jetbrains.kotlin.resolve.lazy.BasicAbsentDescriptorHandler.diagnoseDescriptorNotFound(AbsentDescriptorHandler.kt:18)
    at org.jetbrains.kotlin.resolve.lazy.BasicAbsentDescriptorHandler.diagnoseDescriptorNotFound(AbsentDescriptorHandler.kt:17)
    at org.jetbrains.kotlin.resolve.lazy.LazyDeclarationResolver.findClassDescriptor(LazyDeclarationResolver.kt:88)
    at org.jetbrains.kotlin.resolve.lazy.LazyDeclarationResolver.getScriptDescriptor(LazyDeclarationResolver.kt:65)
    at org.jetbrains.kotlin.resolve.LazyTopDownAnalyzer$analyzeDeclarations$1.visitScript(LazyTopDownAnalyzer.kt:89)
    at org.jetbrains.kotlin.psi.KtVisitorVoid.visitScript(KtVisitorVoid.java:519)
    at org.jetbrains.kotlin.psi.KtVisitorVoid.visitScript(KtVisitorVoid.java:21)
    at org.jetbrains.kotlin.psi.KtScript.accept(KtScript.java:69)
    at org.jetbrains.kotlin.psi.KtElementImplStub.accept(KtElementImplStub.java:59)
    at org.jetbrains.kotlin.resolve.ExceptionWrappingKtVisitorVoid.visitDeclaration(ExceptionWrappingKtVisitorVoid.kt:32)
    ... 61 more
Run Code Online (Sandbox Code Playgroud)

依赖是 implementation "org.jetbrains.kotlin:kotlin-script-runtime:1.3.70"

Sla*_*Cow 1

编辑(2021-04-11):这是一个丑陋的拼凑,没有权利存在。请阅读我更闪亮、更新、更好的答案。

\n

不确定这是否算一个很好的答案,因为它不仅仅完全修复它,但它的要点是......更改文件扩展名。只需在末尾添加下划线或其他内容即可。

\n

OMFSM 我花了长时间试图找到一种合适的方法来做到这一点。然后尝试一百万种不同的拼凑。我以前甚至没有遇到过这个问题(老实说,我什至不知道工作表的存在),它看起来像是一个好主意。

\n

有几种方法可以使这变得更容易,但每当您想要构建时仍然需要人工干预(或者您可以将它们保留,直到您再次需要它们)。

\n

就我个人而言,我刚刚创建了几个批处理文件(尽管它们每个都只有一个命令),它们重命名所有 .kts 文件(然后将它们重命名回来)并创建了一些方便的快捷方式。我正在运行 Windows,并且 bash 脚本绝对不在我的技能范围内,所以我确信这也可以在 *nix 上完成。

\n

将它们全部重命名,这样它们就不会尝试被编译:

\n
forfiles /S /M *.ws.kts /C "cmd /c ren @file @fname.kts_"\n
Run Code Online (Sandbox Code Playgroud)\n

并将它们转回有效的工作表:

\n
forfiles /S /M *.ws.kts_ /C "cmd /c ren @file @fname.kts"\n
Run Code Online (Sandbox Code Playgroud)\n

要使用其中之一制作批处理文件:

\n
    \n
  1. 打开记事本
  2. \n
  3. 将其中一行复制到其中。
  4. \n
  5. 转到File > Save,导航到保存项目的文件夹,并为其指定一个用双引号 (") 括起来以 .bat 结尾的文件名\n
      \n
    • 例如“disable_worksheets.bat”“enable_worksheets.bat”,但请确保包含双引号
    • \n
    \n
  6. \n
\n

现在,您只需在 Windows 资源管理器中找到该文件,然后双击它即可一次性禁用或启用它们。

\n

如果你愿意,你也可以在 Android Studio 中创建一个宏来以每种方式执行此操作,但据我所知,一次只能更改一个文件(尽管你可以设置键盘快捷键,所以如果你没有太多的话它也可以工作)许多工作表)。要使宏禁用工作表:

\n
    \n
  1. 在左侧的树视图中选择您的工作表文件
  2. \n
  3. 在菜单栏中,转到Edit > Macros并单击“开始宏录制
  4. \n
  5. 右键单击树视图中的工作表,然后在Refactor菜单下单击“重命名文件...
  6. \n
  7. 按键盘上的结束键
  8. \n
  9. 输入下划线_
  10. \n
  11. 回车键
  12. \n
  13. 在菜单栏中,转到Edit > Macros并单击“停止宏录制
  14. \n
  15. 为您的宏命名并单击“确定”
  16. \n
\n

对于重新启用它的人:

\n
    \n
  1. 在左侧的树视图中选择您的工作表文件
  2. \n
  3. 在菜单栏中,转到Edit > Macros并单击“开始宏录制
  4. \n
  5. 右键单击树视图中的工作表,然后在Refactor菜单下单击“重命名...
  6. \n
  7. 按键盘上的结束键
  8. \n
  9. 退格键
  10. \n
  11. 回车键
  12. \n
  13. 在菜单栏中,转到Edit > Macros并单击“停止宏录制
  14. \n
  15. 为您的宏命名并单击“确定”
  16. \n
\n

现在,您只需在树视图中选择一个文件,然后在菜单中转到Edit > Macros并单击您需要的文件。但为了更方便,您可以设置键盘快捷键。要做到这一点:

\n
    \n
  1. 在菜单栏中,转到File并单击“设置...
  2. \n
  3. 在左侧菜单中,单击“键盘映射
  4. \n
  5. 在编辑器的主窗格中,单击“ Macros ”旁边的\xe2\x96\xba以展开该部分
  6. \n
  7. 右键单击要为其设置快捷键的宏,然后单击“添加键盘快捷键
  8. \n
  9. 按您要使用的快捷键(例如Ctrl + 逗号)。如果您的快捷方式已使用这些键,它会向您发出警告,因此您可能必须使用几个修饰符(例如Ctrl + Shift + G)\n
      \n
    • 我发现有一些默认情况下是空的(至少在我的安装中)并且仅使用 Ctrl 作为修饰符,包括Ctrl + 逗号(,)、Ctrl + 分号(;) 和Ctrl + 反斜杠(\\)。
    • \n
    • 大多数小键盘键都没有使用,但显然它们不太方便。
    • \n
    \n
  10. \n
  11. 单击“确定”返回主设置窗口。
  12. \n
  13. 如果您想为其他宏设置快捷方式,只需重做步骤 4-6
  14. \n
  15. 单击设置窗口底部的“确定” 。
  16. \n
\n

完成这些设置后,您所要做的就是单击左侧树视图中的文件名,然后按键盘快捷键。

\n

希望这一切对某人有帮助!抱歉,如果这有点长,简洁也不符合我的技能。

\n