YetAnotherConfigLib

YetAnotherConfigLib

34M Downloads

Add kotlin DSL for list options

solonovamax opened this issue ยท 4 comments

commented

Currently, there is no kotlin DSL for list options.

Here is a very quick implementation I made of that (in my implementation I had to use reflection to grab the groupKey, but that's only bc I don't have access to your private api)

// OptionRegistrar (API.kt)
interface OptionRegistrar {
    fun <T> registerList(id: String, @BuilderInference block: ListOptionDsl<T>.() -> Unit): ListOption<T>

    fun <T> registeringList(id: String? = null, @BuilderInference block: ListOptionDsl<T>.() -> Unit): RegisterableActionDelegateProvider<ListOptionDsl<T>, ListOption<T>>
}

// API.kt
interface ListOptionDsl<T> : ListOption.Builder<T>, Buildable<ListOption<T>> {
    val optionKey: String
    val optionId: String
    val thisOption: CompletableFuture<ListOption<T>>

    fun OptionDescription.Builder.addDefaultText(lines: Int? = null) = addDefaultText("$optionKey.description", lines)
}

// OptionRegistrarImpl (Impl.kt)
class OptionRegistratImpl {
    override fun <T> registerList(id: String, @BuilderInference block: ListOptionDsl<T>.() -> Unit) = register(id, ListOptionDslImpl<T>(id, groupKey).apply(block).build())

    override fun <T> registeringList(id: String? = null, @BuilderInference block: ListOptionDsl<T>.() -> Unit) = RegisterableActionDelegateProvider(this::registerList, block, id)
}

// Impl.kt
class ListOptionDslImpl<T>(
    override val optionId: String,
    groupKey: String,
    private val builder: ListOption.Builder<T> = ListOption.createBuilder(),
) : ListOptionDsl<T>, ListOption.Builder<T> by builder {
    override val optionKey = "$groupKey.option.$optionId"

    override val thisOption = CompletableFuture<ListOption<T>>()
    override val built = thisOption

    init {
        builder.name(Text.translatable(optionKey))
    }

    override fun OptionDescription.Builder.addDefaultText(lines: Int?) = addDefaultText(prefix = "$optionKey.description", lines = lines)

    override fun build(): ListOption<T> = builder.build().also { thisOption.complete(it) }
}

// Extensions.kt
fun <T : Any> ListOption.Builder<T>.binding(property: KMutableProperty0<List<T>>, default: List<T>) {
    binding(default, { property.get() }, { property.set(it) })
}
commented

nvm, they need to be added as a group, not an option, so all that code there is useless.

however, the issue still applies.

commented

nvm part two, it does work, but it can only be used on rootOptions.

also there's some weird generics issue with the builder inference, so just remove it lol nvm, the issue has to do with using lambdas. idfk what it is.

commented

The issue is that a lot of the block versions of things like name get interpreted at the wrong level, use the brace versions in nested blocks. Could you share how you got the list working with Kotlin DSL?

commented

The issue is that a lot of the block versions of things like name get interpreted at the wrong level, use the brace versions in nested blocks. Could you share how you got the list working with Kotlin DSL?

You can take a look at what I did here:
https://github.com/solonovamax/BeaconOverhaulReloaded/blob/c5c97efdb707313cb47332ea7d557ad52e5d5d80/src/main/kotlin/gay/solonovamax/beaconsoverhaul/config/ConfigManager.kt#L47-L203

all of the extensions I wrote for yacl can be found here:
https://github.com/solonovamax/BeaconOverhaulReloaded/blob/c5c97efdb707313cb47332ea7d557ad52e5d5d80/src/main/kotlin/gay/solonovamax/beaconsoverhaul/util/YetAnotherConfigLibUtil.kt

(I do want to note though, that if you happen to go looking for the language files, they are all datagened from here through a rather jank system)