I’m trying to show a horizontal box divided into multiple equals parts containing different colours. How can I use the specified integer to divide the box, then use the list of specified colours to colour the sections in?
Expected result
Current reuslt
class MainActivity : ComponentActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContent {
NestedScrollingTheme {
Surface(
modifier = Modifier.fillMaxSize(),
color = MaterialTheme.colorScheme.background
) {
MyScreen()
}
}
}
}
}
@Composable
fun MyReusableScaffold(scaffoldTitle: String, scaffoldFab: @Composable () -> Unit,
scaffoldContent: @Composable (contentPadding: PaddingValues) -> Unit) {
val scrollBehavior = TopAppBarDefaults.exitUntilCollapsedScrollBehavior()
Scaffold(
modifier = Modifier.nestedScroll(scrollBehavior.nestedScrollConnection),
topBar = {
LargeTopAppBar(
title = { Text(text = scaffoldTitle) },
scrollBehavior = scrollBehavior
)
},
floatingActionButton = { scaffoldFab },
content = { contentPadding -> scaffoldContent(contentPadding = contentPadding) }
)
}
@Composable
fun ReusableRow(rowItems: Array<RowItems>) {
val scrollState = rememberScrollState()
Row(modifier = Modifier
.height(300.dp)
.horizontalScroll(state = scrollState),
verticalAlignment = Alignment.CenterVertically) {
rowItems.forEach { rowItem ->
MyInfoCard(cardTitle = rowItem.rowItemTitle, cardSubtitle = rowItem.rowItemDesc)
}
}
}
@Composable
fun <T> ReusableLazyColumn(
header: @Composable () -> Unit,
lazyColumnItems: Array<T>,
lazyColumnItemLayout: @Composable Any.(item: T) -> Unit,
onClickLazyColumnItem: (T) -> Unit
) {
val listState = rememberLazyListState()
Box(modifier = Modifier.fillMaxSize()) {
LazyColumn(
state = listState,
contentPadding = PaddingValues(top = 0.dp, bottom = 80.dp)
) {
item { header.invoke() }
item { Spacer(modifier = Modifier.height(24.dp)) }
items(lazyColumnItems) { itemC ->
Row(modifier = Modifier
.fillMaxWidth()
.clickable {
onClickLazyColumnItem(itemC)
}) {
lazyColumnItemLayout(itemC)
}
Divider(color = MaterialTheme.colorScheme.onSurface.copy(alpha = 0.2f))
}
}
ButtonScrollToTopList(listState = listState)
}
}
@Composable
fun MyScreen() {
MyReusableScaffold(
scaffoldTitle = "Demo",
scaffoldFab = { /*TODO*/ },
scaffoldContent = {
MyScreenContent(contentPadding = it)
}
)
}
@Composable
fun MyScreenContent(
modifier: Modifier = Modifier,
contentPadding: PaddingValues = PaddingValues()
) {
val rowItems = arrayOf(
RowItems.ItemRowNeapolitan,
RowItems.ItemRowSpumoni
)
val columnItems = arrayOf(
ColumnItems.ItemPetitFour,
...
ColumnItems.ItemUpsideDownCake
)
Box(modifier = modifier
.fillMaxSize()
.padding(contentPadding)
) {
Column(content = {
ReusableLazyColumn(
header = { ReusableRow(rowItems) },
lazyColumnItems = columnItems,
lazyColumnItemLayout = {
Row { ... }
},
onClickLazyColumnItem = { listenerColumnItems }
)
}
)
}
}
enum class RowItems(val rowItemTitle: String, val rowItemDesc: String,
val barSectionCount: Int, val barSectionColors: List<Any>) {
ItemRowNeapolitan("Neapolitan ice cream",
"vanilla, chocolate, and strawberry",
3,
listOf(0xFFFBFFFE, 0xFF774B3B, 0xFFEFAD89)
),
ItemRowSpumoni("Spumoni ice cream",
"vanilla, pistachio, and strawberry",
3,
listOf(0xFFFBFFFE, 0xFF93C572, 0xFFEFAD89)
)
}
enum class ColumnItems(val columnItemTitle: String) {
ItemPetitFour("Petit Four"),
...
ItemUpsideDownCake("Upside Down Cake")
}
val listenerColumnItems: (ColumnItems) -> Unit = {...}
@Composable
fun MyInfoCard(
cardTitle: String,
cardSubtitle: String,
// boxSections: Int,
// boxSectionColours: Array<Any>
) {
OutlinedCard(modifier = Modifier
.height(350.dp)
.padding(16.dp),
shape = RoundedCornerShape(size = 16.dp),
) {
Column() {
Box(
modifier = Modifier
.background(???)
.fillMaxWidth()
.height(30.dp)
)
Text(text = cardTitle)
Text(text = cardSubtitle)
}
}
}
val listenerRowItems: (RowItems) -> Unit = { item ->
when (item) {
RowItems.ItemRowCheetah -> TODO()
...
RowItems.ItemRowSonoma -> TODO()
}
}
enum class ColumnItems(val columnItemTitle: String) {
ItemPetitFour("Petit Four"),
...
ItemUpsideDownCake("Upside Down Cake")
}
val listenerColumnItems: (ColumnItems) -> Unit = { item ->
when (item) {
ColumnItems.ItemPetitFour -> TODO()
...
ColumnItems.ItemUpsideDownCake -> TODO()
}
}
(Typing this on a phone, so some stuff might be wrong, will factcheck later <3)
a simple composable like:
@Composable
fun Stackoverflow() {
val listOfColors = listOf(Color.Gray, Color.Black, Color.Red)
Row {
listOfColors.forEach {
Box(modifier = Modifier.height(50.dp).weight(1f).background(it))
}
}
}
should do the job (the .weight(1f)
makes sure all of the boxes take the same amount of space)
This can also be done as as Modifier that draws multi-colored background
fun Modifier.multiColorBackground(
colors: List<Color>
) = this.then(
Modifier.drawBehind {
if (colors.isNotEmpty()) {
val colorCount = colors.size
val width = size.width / colorCount
colors.forEachIndexed { index, color ->
drawRect(
color = color,
topLeft = Offset(index * width, 0f),
size = Size(width, size.height)
)
}
}
}
)
Result
Demo
@Preview
@Composable
fun ColorTest() {
Column(
modifier = Modifier
.background(Color.Black)
.padding(top=20.dp)
.fillMaxSize()
) {
Box(
modifier = Modifier
.fillMaxWidth()
.height(60.dp)
.multiColorBackground(listOf(Color.White, Brown400, Pink400))
)
}
}