package components import ValueChangeEvent import kotlinx.css.* import kotlinx.html.classes import kotlinx.html.js.onClickFunction import kotlinx.serialization.json.buildJsonObject import react.* import react.dom.attrs import schema.ConfigSchema import styled.* external interface JsonObjectProps: Props { var schema: ConfigSchema var name: String var data: kotlinx.serialization.json.JsonObject? var id: String var handleChange: (event: ValueChangeEvent) -> Unit var level: Int } data class JsonObjectState( var data: kotlinx.serialization.json.JsonObject?, var showChildren: Boolean = true, ): State class JsonObject(props: JsonObjectProps): RComponent() { init { this.state = JsonObjectState( data = props.data, ) } override fun RBuilder.render() { styledDiv { css { if (props.name != "") { borderColor = hsl((props.level * 40) % 256, 100, 15) +Styles.objectContainer } } if (props.name != "") { styledDiv { css { +Styles.objectHeader } styledI { attrs { classes = if (state.showChildren) { setOf("ri-arrow-down-s-line", "ri-xl") } else { setOf("ri-arrow-right-s-line", "ri-xl") } onClickFunction = { setState { showChildren = !showChildren } } } } styledLabel { css { textTransform = TextTransform.capitalize } +props.name } styledDiv { css { width = 24.px } } } } styledDiv { css { if (!state.showChildren) display = Display.none } descriptionBlock(props.schema.description) for (property in props.schema.children!!) { jsonSchema( schema = property.value, name = property.key, data = state.data?.get(property.key), id = property.key, handleChange = ::handleChange, level = props.level + 1, ) } } } } fun handleChange(event: ValueChangeEvent) { state.data = buildJsonObject { if (state.data != null) for (entry in state.data!!) { put(entry.key, entry.value) } put(event.id, event.value) } props.handleChange(ValueChangeEvent(props.id, state.data!!)) } } fun RBuilder.jsonObject(schema: ConfigSchema, name: String, data: kotlinx.serialization.json.JsonObject?, id: String, handleChange: (event: ValueChangeEvent) -> Unit, level: Int) { child(JsonObject::class) { attrs { this.schema = schema this.name = name this.data = data this.id = id this.handleChange = handleChange this.level = level } } }