Selector (WIP)

This commit is contained in:
2024-06-18 23:23:55 +02:00
parent f7a1725029
commit 755c3de295
4 changed files with 59 additions and 36 deletions

View File

@@ -1,6 +1,7 @@
import androidx.compose.animation.AnimatedVisibility
import androidx.compose.foundation.Image
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.Row
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.material3.Button
import androidx.compose.material3.MaterialTheme
@@ -14,24 +15,28 @@ import org.jetbrains.compose.resources.ExperimentalResourceApi
import org.jetbrains.compose.resources.painterResource
import org.jetbrains.compose.ui.tooling.preview.Preview
import ui.DrawItem
import ui.Selector
import yaep.composeapp.generated.resources.Res
import yaep.composeapp.generated.resources.compose_multiplatform
@OptIn(ExperimentalResourceApi::class)
@Composable
@Preview
fun App() {
fun App(modifier: Modifier = Modifier) {
val size = 6
val options = remember { Animals.items.shuffled().take(size) }
var selectedItem by remember { mutableStateOf<Item<Animals>?>(Item(options.random())) }
// var selectedItem by remember { mutableStateOf<Item<Animals>?>(null) }
// Selector(
// category = Animals,
// options = Animals.items.map { Item(it) },
// selectedItem = selectedItem,
// onSelectItem = { selectedItem = it }
// )
DrawItem(selectedItem!!)
Column(modifier = modifier) {
Row {
val options = remember { Animals.items.shuffled().take(size) }
for (option in options) {
var selectedItem by remember { mutableStateOf<Item<Animals>?>(Item(option)) }
Selector(
category = Animals,
options = Animals.items.map { Item(it) },
selectedItem = selectedItem,
onSelectItem = { selectedItem = it },
modifier = Modifier.weight(1f)
)
}
}
}
}

View File

@@ -1,9 +1,11 @@
package ui
import androidx.compose.foundation.Canvas
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.clickable
import androidx.compose.foundation.layout.aspectRatio
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.foundation.lazy.grid.GridCells
import androidx.compose.foundation.lazy.grid.LazyHorizontalGrid
import androidx.compose.material3.OutlinedCard
import androidx.compose.runtime.Composable
import androidx.compose.runtime.getValue
@@ -11,16 +13,11 @@ import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.remember
import androidx.compose.runtime.setValue
import androidx.compose.ui.Modifier
import androidx.compose.ui.draw.drawWithContent
import androidx.compose.ui.geometry.Offset
import androidx.compose.ui.geometry.Size
import androidx.compose.ui.graphics.nativeCanvas
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.text.TextStyle
import androidx.compose.ui.text.drawText
import androidx.compose.ui.text.rememberTextMeasurer
import androidx.compose.ui.unit.TextUnit
import androidx.compose.ui.unit.dp
import androidx.compose.ui.unit.sp
import domain.Animals
import domain.Item
import domain.ItemClass
@@ -34,13 +31,22 @@ fun <C : ItemClass<C>> Selector(
category: ItemClassCompanion<C>,
options: List<Item<C>>,
selectedItem: Item<C>?,
onSelectItem: (Item<C>) -> Unit
onSelectItem: (Item<C>?) -> Unit
) {
if (selectedItem != null) {
DrawItem(selectedItem)
DrawItem(item = selectedItem, modifier = modifier.clickable { onSelectItem(null) })
} else {
OutlinedCard(modifier = modifier.aspectRatio(1f)) {
LazyHorizontalGrid(rows = GridCells.Fixed(3)) {
for (option in options) {
item {
DrawItem(
item = option,
modifier = Modifier.clickable { onSelectItem(option) }
)
}
}
}
}
}
}
@@ -48,7 +54,6 @@ fun <C : ItemClass<C>> Selector(
@Composable
fun <C : ItemClass<C>> DrawItem(item: Item<C>, modifier: Modifier = Modifier) {
OutlinedCard(modifier = modifier.aspectRatio(1f)) {
var textSize by remember { mutableStateOf(12.sp) }
val emoji = item.symbol
val textMeasurer = rememberTextMeasurer()
@@ -56,20 +61,27 @@ fun <C : ItemClass<C>> DrawItem(item: Item<C>, modifier: Modifier = Modifier) {
Canvas(
modifier = Modifier.fillMaxSize(1f),
onDraw = {
drawRect(Color.Red, size = size)
val textSize = textMeasurer.measure(text = emoji)
val fontSize = min(
val minTextSizeDimension = min(
textSize.size.width,
textSize.size.height
)
val fontSizeBase = minTextSizeDimension * min(
size.width / textSize.size.width,
size.height / textSize.size.height
).toSp()
)
val fontSize = (0.9f * fontSizeBase).toDp().toSp()
val offset = Offset(
x = size.width / 2 - textSize.size.width * fontSizeBase / (2f * minTextSizeDimension),
y = size.height / 2 - textSize.size.height * fontSizeBase / (2f * minTextSizeDimension)
)
drawText(
textMeasurer = textMeasurer,
text = emoji,
style = TextStyle(fontSize = fontSize),
topLeft = Offset(
x = size.width / 2 - 100f - (textSize.size.width / 2),
y = size.height / 2 - (textSize.size.height / 2)
)
topLeft = offset
)
}
)