简体   繁体   中英

Android compose Modifier width unexpected behaviour inside scrollable/lazy row

I am building a basic layout which diplays a horizontally scrollable row with cards. The cards are a column component with a couple dividers in the middle:

@Composable
fun TestCard(
  name: String
) {
  Column(
    modifier = Modifier
      .background(MaterialTheme.colors.surface)
      .padding(12.dp),
    horizontalAlignment = Alignment.Start
  ) {
    Text(text = name, style = Typography.h4.bold.black)
    Spacer(modifier = Modifier.height(8.dp))
    Divider(color = Color.Black) //DOES NOT APPEAR IN ROW
    Spacer(modifier = Modifier.height(8.dp))
    Divider(modifier = Modifier.fillMaxWidth(), color = Color.Black) //DOES NOT APPEAR IN ROW
    Spacer(modifier = Modifier.height(8.dp))
    Text(text = "Other text", style = Typography.h4.bold.black)
  }
}

I also have a scrollable row that contains a list of these cards:

@Composable
fun TestComponent() {

  val scrollState = rememberScrollState()
  val names = listOf("Martha", "Erik","Steve","Roy","Pete")

  Column(
    modifier = Modifier
      .fillMaxWidth()
      .background(MaterialTheme.colors.primary),
    horizontalAlignment = Alignment.Start
  ) {
    Row(Modifier.horizontalScroll(scrollState), horizontalArrangement = Arrangement.spacedBy(16.dp)) {
      names.forEach { name ->
        TestCard(name)
      }
    }
  }
}

When I display the card on its own, I can see both dividers. When I display the row containing cards the dividers don't appear, because their width is set to 0 (I can verify with LayoutInspector the dividers are there). Visual representation:

例子

I know I can create a state variable for width that would be updated inside the Modifier.onSizeChanged but I am sure there must be a reason for this to happen and a better solution.

The Divider has inside a fillMaxWidth() modifier, but as you check in the doc :

If the incoming maximum width is Constraints.Infinity this modifier will have no effect.

It happens because of the horizontalScroll .
You have to specify the width for the Divider s and the Spacer s.

A workaround is to apply width(IntrinsicSize.Max) to the Column in the TestCard . In this way the Constraints have a Constraints.fixedWidth(width) :

@Composable
fun TestCard(
    name: String
) {
    Column(
        modifier = Modifier
            .width(IntrinsicSize.Max)
            .background(androidx.compose.material.MaterialTheme.colors.surface)
            .padding(12.dp),
        horizontalAlignment = Alignment.Start
    ) {
        Text(text = name,)
        Spacer(modifier = Modifier.height(8.dp).fillMaxWidth())
        Divider(color = Color.Black, modifier = Modifier.fillMaxWidth()) 
        Spacer(modifier = Modifier.height(8.dp).fillMaxWidth())
        Divider(modifier = Modifier.fillMaxWidth(), color = Color.Black) 
        Spacer(modifier = Modifier.height(8.dp).fillMaxWidth())
        Text(text = "Other text" )
    }

} 

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM