Implement TextFlowWithToneColors and use it in search results

This commit is contained in:
Marvin Elsen 2024-11-14 19:59:55 +01:00
parent 5baccc4b3f
commit 9096941d58
Signed by: marvinelsen
GPG Key ID: 820672408CC318C2
2 changed files with 62 additions and 15 deletions

View File

@ -2,8 +2,8 @@ package com.marvinelsen.willow.ui.cells
import com.marvinelsen.willow.config.Config import com.marvinelsen.willow.config.Config
import com.marvinelsen.willow.config.Pronunciation import com.marvinelsen.willow.config.Pronunciation
import com.marvinelsen.willow.config.Script
import com.marvinelsen.willow.domain.entities.DictionaryEntry import com.marvinelsen.willow.domain.entities.DictionaryEntry
import com.marvinelsen.willow.ui.components.TextFlowWithToneColors
import com.marvinelsen.willow.ui.util.createContextMenuForEntry import com.marvinelsen.willow.ui.util.createContextMenuForEntry
import javafx.application.HostServices import javafx.application.HostServices
import javafx.beans.binding.Bindings import javafx.beans.binding.Bindings
@ -39,8 +39,8 @@ private class EntryCell(
private val hostServices: HostServices, private val hostServices: HostServices,
) : ListCell<DictionaryEntry?>() { ) : ListCell<DictionaryEntry?>() {
private val labelHeadword by lazy { private val textFlowHeadword by lazy {
Label().apply { TextFlowWithToneColors(config).apply {
styleClass.add("headword") styleClass.add("headword")
styleProperty().bind( styleProperty().bind(
Bindings.concat( Bindings.concat(
@ -83,7 +83,7 @@ private class EntryCell(
} }
private val flowPane by lazy { private val flowPane by lazy {
FlowPane(labelHeadword, labelPronunciation).apply { FlowPane(textFlowHeadword, labelPronunciation).apply {
hgap = FLOW_PANE_HGAP hgap = FLOW_PANE_HGAP
rowValignment = VPos.BASELINE rowValignment = VPos.BASELINE
} }
@ -105,17 +105,8 @@ private class EntryCell(
graphic = null graphic = null
contextMenu = null contextMenu = null
} else { } else {
labelHeadword.textProperty().bind( textFlowHeadword.entry.value = entry
Bindings.createStringBinding(
{
when (config.script.value!!) {
Script.SIMPLIFIED -> entry.simplified
Script.TRADITIONAL -> entry.traditional
}
},
config.script
)
)
labelPronunciation.textProperty().bind( labelPronunciation.textProperty().bind(
Bindings.createStringBinding( Bindings.createStringBinding(
{ {
@ -144,6 +135,7 @@ private class EntryCell(
else -> error("No definition for entry") else -> error("No definition for entry")
} }
labelDefinition.text = definition labelDefinition.text = definition
contextMenu = createContextMenuForEntry(entry, resources, hostServices) contextMenu = createContextMenuForEntry(entry, resources, hostServices)

View File

@ -0,0 +1,55 @@
package com.marvinelsen.willow.ui.components
import com.marvinelsen.willow.config.Config
import com.marvinelsen.willow.config.Script
import com.marvinelsen.willow.domain.entities.DictionaryEntry
import javafx.beans.property.SimpleObjectProperty
import javafx.scene.paint.Color
import javafx.scene.text.Text
import javafx.scene.text.TextFlow
class TextFlowWithToneColors(private val config: Config) : TextFlow() {
init {
config.script.addListener { _, _, newValue ->
updateTextFlow(newValue)
}
}
val entry = SimpleObjectProperty<DictionaryEntry?>().apply {
addListener { _, _, _ ->
updateTextFlow(config.script.value)
}
}
private val invalidCharacterRegex = """[a-zA-Z0-9·\[\]{}()+]""".toRegex()
@Suppress("MagicNumber")
private fun updateTextFlow(script: Script) {
children.clear()
val headword = when (script) {
Script.SIMPLIFIED -> entry.value?.simplified
Script.TRADITIONAL -> entry.value?.traditional
} ?: return
var index = 0
for (char in headword) {
val text = Text(char.toString())
val color = if (invalidCharacterRegex.matches(char.toString())) {
Color.BLACK
} else {
when (entry.value?.tones?.getOrNull(index++)) {
1 -> Color.RED
2 -> Color.GREEN
3 -> Color.BLUE
4 -> Color.PURPLE
5 -> Color.DARKGRAY
else -> Color.BLACK
}
}
text.fill = color
children.add(text)
}
}
}