mirror of
https://github.com/yairm210/Unciv.git
synced 2025-07-05 07:49:17 +07:00
Console: autocomplete ALL THE THINGS!
This commit is contained in:
@ -10,24 +10,24 @@ import com.unciv.models.stats.Stat
|
|||||||
internal fun String.toCliInput() = this.lowercase().replace(" ","-")
|
internal fun String.toCliInput() = this.lowercase().replace(" ","-")
|
||||||
|
|
||||||
/** Returns the string to *add* to the existing command */
|
/** Returns the string to *add* to the existing command */
|
||||||
fun getAutocompleteString(lastWord:String, allOptions:Iterable<String>):String? {
|
fun getAutocompleteString(lastWord: String, allOptions: Collection<String>):String? {
|
||||||
val matchingOptions = allOptions.filter { it.toCliInput().startsWith(lastWord.toCliInput()) }
|
val matchingOptions = allOptions.filter { it.toCliInput().startsWith(lastWord.toCliInput()) }
|
||||||
if (matchingOptions.isEmpty()) return null
|
if (matchingOptions.isEmpty()) return null
|
||||||
if (matchingOptions.size == 1) return matchingOptions.first().removePrefix(lastWord)
|
if (matchingOptions.size == 1) return matchingOptions.first().drop(lastWord.length)
|
||||||
|
|
||||||
val firstOption = matchingOptions.first()
|
val firstOption = matchingOptions.first()
|
||||||
for ((index, char) in firstOption.withIndex()) {
|
for ((index, char) in firstOption.withIndex()) {
|
||||||
if (matchingOptions.any { it.lastIndex < index } ||
|
if (matchingOptions.any { it.lastIndex < index } ||
|
||||||
matchingOptions.any { it[index] != char })
|
matchingOptions.any { it[index] != char })
|
||||||
return firstOption.substring(0, index).removePrefix(lastWord)
|
return firstOption.substring(0, index).drop(lastWord.length)
|
||||||
}
|
}
|
||||||
return firstOption.removePrefix(lastWord)
|
return firstOption.drop(lastWord.length)
|
||||||
}
|
}
|
||||||
|
|
||||||
interface ConsoleCommand {
|
interface ConsoleCommand {
|
||||||
fun handle(console: DevConsolePopup, params: List<String>): DevConsoleResponse
|
fun handle(console: DevConsolePopup, params: List<String>): DevConsoleResponse
|
||||||
/** Returns the string to *add* to the existing command */
|
/** Returns the string to *add* to the existing command */
|
||||||
fun autocomplete(params: List<String>): String? = ""
|
fun autocomplete(console: DevConsolePopup, params: List<String>): String? = ""
|
||||||
}
|
}
|
||||||
|
|
||||||
class ConsoleHintException(val hint:String):Exception()
|
class ConsoleHintException(val hint:String):Exception()
|
||||||
@ -44,6 +44,36 @@ class ConsoleAction(val format: String, val action: (console: DevConsolePopup, p
|
|||||||
DevConsoleResponse.error(errorException.error)
|
DevConsoleResponse.error(errorException.error)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
override fun autocomplete(console: DevConsolePopup, params: List<String>): String? {
|
||||||
|
if (params.isEmpty()) return null
|
||||||
|
|
||||||
|
val formatParams = format.split(" ").drop(2).map {
|
||||||
|
it.removeSurrounding("<",">").removeSurrounding("[","]").removeSurrounding("\"")
|
||||||
|
}
|
||||||
|
if (formatParams.size < params.size) return null
|
||||||
|
val formatParam = formatParams[params.lastIndex]
|
||||||
|
|
||||||
|
val lastParam = params.last()
|
||||||
|
val options = when (formatParam) {
|
||||||
|
"civName" -> console.gameInfo.civilizations.map { it.civName }
|
||||||
|
"unitName" -> console.gameInfo.ruleset.units.keys
|
||||||
|
"promotionName" -> console.gameInfo.ruleset.unitPromotions.keys
|
||||||
|
"improvementName" -> console.gameInfo.ruleset.tileImprovements.keys
|
||||||
|
"featureName" -> console.gameInfo.ruleset.terrains.values.filter { it.type == TerrainType.TerrainFeature }.map { it.name }
|
||||||
|
"stat" -> Stat.names()
|
||||||
|
else -> listOf()
|
||||||
|
}
|
||||||
|
return getAutocompleteString(lastParam, options)
|
||||||
|
}
|
||||||
|
|
||||||
|
fun validateFormat(format: String, params:List<String>){
|
||||||
|
val allParams = format.split(" ")
|
||||||
|
val requiredParamsAmount = allParams.count { it.startsWith('<') }
|
||||||
|
val optionalParamsAmount = allParams.count { it.startsWith('[') }
|
||||||
|
if (params.size < requiredParamsAmount || params.size > requiredParamsAmount + optionalParamsAmount)
|
||||||
|
throw ConsoleHintException("Format: $format")
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
interface ConsoleCommandNode : ConsoleCommand {
|
interface ConsoleCommandNode : ConsoleCommand {
|
||||||
@ -57,10 +87,10 @@ interface ConsoleCommandNode : ConsoleCommand {
|
|||||||
return handler.handle(console, params.drop(1))
|
return handler.handle(console, params.drop(1))
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun autocomplete(params: List<String>): String? {
|
override fun autocomplete(console: DevConsolePopup, params: List<String>): String? {
|
||||||
if (params.isEmpty()) return null
|
if (params.isEmpty()) return null
|
||||||
val firstParam = params[0]
|
val firstParam = params[0]
|
||||||
if (firstParam in subcommands) return subcommands[firstParam]!!.autocomplete(params.drop(1))
|
if (firstParam in subcommands) return subcommands[firstParam]!!.autocomplete(console, params.drop(1))
|
||||||
return getAutocompleteString(firstParam, subcommands.keys)
|
return getAutocompleteString(firstParam, subcommands.keys)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -74,15 +104,6 @@ class ConsoleCommandRoot : ConsoleCommandNode {
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
fun validateFormat(format: String, params:List<String>){
|
|
||||||
val allParams = format.split(" ")
|
|
||||||
val requiredParamsAmount = allParams.count { it.startsWith('<') }
|
|
||||||
val optionalParamsAmount = allParams.count { it.startsWith('[') }
|
|
||||||
if (params.size < requiredParamsAmount || params.size > requiredParamsAmount + optionalParamsAmount)
|
|
||||||
throw ConsoleHintException("Format: $format")
|
|
||||||
}
|
|
||||||
|
|
||||||
class ConsoleUnitCommands : ConsoleCommandNode {
|
class ConsoleUnitCommands : ConsoleCommandNode {
|
||||||
override val subcommands = hashMapOf<String, ConsoleCommand>(
|
override val subcommands = hashMapOf<String, ConsoleCommand>(
|
||||||
|
|
||||||
@ -269,13 +290,4 @@ class ConsoleCivCommands : ConsoleCommandNode {
|
|||||||
DevConsoleResponse.OK
|
DevConsoleResponse.OK
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
|
|
||||||
override fun autocomplete(params: List<String>): String? {
|
|
||||||
if (params.isNotEmpty())
|
|
||||||
when (params[0]){
|
|
||||||
"addstat" -> if (params.size == 2)
|
|
||||||
return getAutocompleteString(params[1], Stat.names())
|
|
||||||
}
|
|
||||||
return super.autocomplete(params)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
@ -85,7 +85,9 @@ class DevConsolePopup(val screen: WorldScreen) : Popup(screen) {
|
|||||||
|
|
||||||
private fun getAutocomplete(): String {
|
private fun getAutocomplete(): String {
|
||||||
val params = getParams(textField.text)
|
val params = getParams(textField.text)
|
||||||
return commandRoot.autocomplete(params) ?: ""
|
val result = commandRoot.autocomplete(this, params)
|
||||||
|
if (result.isNullOrEmpty()) return ""
|
||||||
|
return "$result "
|
||||||
}
|
}
|
||||||
|
|
||||||
internal fun getCivByName(name: String) = gameInfo.civilizations.firstOrNull { it.civName.toCliInput() == name.toCliInput() }
|
internal fun getCivByName(name: String) = gameInfo.civilizations.firstOrNull { it.civName.toCliInput() == name.toCliInput() }
|
||||||
|
Reference in New Issue
Block a user