Implement invokeGlobal and eval

This commit is contained in:
DBotThePony 2024-12-16 20:17:55 +07:00
parent f82b48672e
commit ad120cccba
Signed by: DBot
GPG Key ID: DCC23B5715498507

View File

@ -18,6 +18,7 @@ import org.lwjgl.system.MemoryStack
import org.lwjgl.system.MemoryUtil
import ru.dbotthepony.kommons.gson.set
import ru.dbotthepony.kommons.util.Delegate
import ru.dbotthepony.kommons.util.KOptional
import ru.dbotthepony.kstarbound.Starbound
import ru.dbotthepony.kstarbound.defs.AssetPath
import ru.dbotthepony.kstarbound.json.InternedJsonElementAdapter
@ -213,6 +214,73 @@ class LuaThread private constructor(
return status
}
/**
* Returns boolean indicating whenever function exists
*/
inline fun invokeGlobal(name: String, arguments: LuaThread.() -> Int): Boolean {
val top = stackTop
try {
val type = loadGlobal(name)
if (type != LuaType.FUNCTION)
return false
val numArguments = arguments(this)
check(numArguments >= 0) { "Invalid amount of arguments provided to Lua function" }
call(numArguments)
return true
} finally {
setTop(top)
}
}
/**
* Returns empty [KOptional] if function does not exist
*/
inline fun <T> invokeGlobal(name: String, numResults: Int, arguments: LuaThread.() -> Int, results: LuaThread.(firstValue: Int) -> T): KOptional<T> {
require(numResults > 0) { "Invalid amount of results: $numResults" }
val top = stackTop
try {
val type = loadGlobal(name)
if (type != LuaType.FUNCTION)
return KOptional()
val numArguments = arguments(this)
call(numArguments, numResults)
return KOptional(results(this, top + 1))
} finally {
setTop(top)
}
}
inline fun <T> eval(chunk: String, name: String = "eval", numResults: Int, arguments: LuaThread.() -> Int, results: LuaThread.(firstValue: Int) -> T): T {
require(numResults > 0) { "Invalid amount of results: $numResults" }
val top = stackTop
try {
val numArguments = arguments(this)
load(chunk, name)
call(numArguments, numResults)
return results(this, top + 1)
} finally {
setTop(top)
}
}
inline fun <T> eval(chunk: String, name: String = "eval", arguments: LuaThread.() -> Int) {
val top = stackTop
try {
val numArguments = arguments(this)
load(chunk, name)
call(numArguments, 0)
} finally {
setTop(top)
}
}
private val attachedScripts = ArrayList<AssetPath>()
private var initCalled = false
@ -1122,7 +1190,7 @@ class LuaThread private constructor(
}
companion object {
private val LOGGER = LogManager.getLogger()
val LOGGER = LogManager.getLogger()
fun loadInternalScript(name: String): String {
return LuaThread::class.java.getResourceAsStream("/scripts/$name.lua")?.readAllBytes()?.toString(Charsets.UTF_8) ?: throw RuntimeException("/scripts/$name.lua is missing!")