mirror of
https://github.com/JakeWharton/mosaic.git
synced 2025-11-03 13:57:35 +08:00
Put nodes in charge of rendering themselves
This commit is contained in:
@ -4,10 +4,13 @@ import androidx.compose.runtime.AbstractApplier
|
||||
import com.facebook.yoga.YogaMeasureOutput
|
||||
import com.facebook.yoga.YogaNode
|
||||
import com.facebook.yoga.YogaNodeFactory
|
||||
import com.jakewharton.crossword.TextCanvas
|
||||
import com.jakewharton.crossword.visualCodePointCount
|
||||
|
||||
internal sealed class MosaicNode {
|
||||
val yoga: YogaNode = YogaNodeFactory.create()
|
||||
|
||||
abstract fun render(canvas: TextCanvas)
|
||||
}
|
||||
|
||||
internal class TextNode(initialValue: String = "") : MosaicNode() {
|
||||
@ -26,12 +29,30 @@ internal class TextNode(initialValue: String = "") : MosaicNode() {
|
||||
yoga.dirty()
|
||||
}
|
||||
|
||||
override fun render(canvas: TextCanvas) {
|
||||
value.split('\n').forEachIndexed { index, line ->
|
||||
canvas.write(index, 0, line)
|
||||
}
|
||||
}
|
||||
|
||||
override fun toString() = "Text($value)"
|
||||
}
|
||||
|
||||
internal class BoxNode : MosaicNode() {
|
||||
val children = mutableListOf<MosaicNode>()
|
||||
|
||||
override fun render(canvas: TextCanvas) {
|
||||
for (child in children) {
|
||||
val childYoga = child.yoga
|
||||
val left = childYoga.layoutX.toInt()
|
||||
val top = childYoga.layoutY.toInt()
|
||||
val right = left + childYoga.layoutWidth.toInt()
|
||||
val bottom = top + childYoga.layoutHeight.toInt()
|
||||
val clipped = canvas.clip(left, top, right, bottom)
|
||||
child.render(clipped)
|
||||
}
|
||||
}
|
||||
|
||||
override fun toString() = children.joinToString(prefix = "Box(", postfix = ")")
|
||||
}
|
||||
|
||||
|
||||
@ -7,24 +7,3 @@ internal fun MosaicNode.renderToString(): String {
|
||||
render(surface)
|
||||
return surface.toString()
|
||||
}
|
||||
|
||||
private fun MosaicNode.render(canvas: TextCanvas) {
|
||||
when (this) {
|
||||
is TextNode -> {
|
||||
value.split('\n').forEachIndexed { index, line ->
|
||||
canvas.write(index, 0, line)
|
||||
}
|
||||
}
|
||||
is BoxNode -> {
|
||||
for (child in children) {
|
||||
val childYoga = child.yoga
|
||||
val left = childYoga.layoutX.toInt()
|
||||
val top = childYoga.layoutY.toInt()
|
||||
val right = left + childYoga.layoutWidth.toInt()
|
||||
val bottom = top + childYoga.layoutHeight.toInt()
|
||||
val clipped = canvas.clip(left, top, right, bottom)
|
||||
child.render(clipped)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user