I have a hard time understanding `Column`, `Row`, ...
# compose
r
I have a hard time understanding
Column
,
Row
,
modifier=
and
Gravity
Do anyone have reasonable (sane) explanation on how I can achieve following tricky thing (see picture). Here's the code where this layout is built, I want the "5 Center End me!" to be centered vertically (up-down) (as shown), but I can't find any reasonable way to do it in dev03, this was achievable in dev02...
Copy code
@Composable
fun CardGravityTest()
{
    Card(
            modifier = Spacing(all = 4.dp),
            color = Color.LightGray,
            shape = RoundedCornerShape(
                    5.dp
            )
    ){
        Column {
            Row {
                Surface(color = Color.Red,
                        modifier = Spacing(all = 4.dp)) {
                    Text(text = "1 XX")
                }
                Column(modifier = Flexible(1f) wraps Expanded wraps Spacing(4.dp)){
                    Surface(color = Color.Green){
                        Text(text="2 Flexible wraps Expanded(1f) wraps Spacing(4.dp) x x xx xxx xxxx x xx xxx x xxx")
                    }
                    Surface(color = Color.Magenta){
                        Text(text = "3 Second line xxxxx xxx xx xxxxx xxxx")
                    }
                }
                Column() {
                    Surface(color = Color.DarkGray) {
                        Text(text = "4 Column: OK High on top!")
                    }

                    Surface(color = Color.Yellow,
                            modifier = Gravity.End){
                        Text(text = "5 Center End me!",
                                modifier = Gravity.End)
                    }
                }
            }

            Divider()

            Row (modifier = Spacing(top = 4.dp)){
                Column (modifier = Flexible(1f) wraps Expanded){
                    Surface(color = Color.Blue, modifier = Gravity.Start) {
                        Text(text = "6 Row spacing top, Column Flexible(1f) wraps Expanded, Surface gravity start")
                    }
                }
                Column(modifier = Flexible(1f) wraps Expanded){
                    Surface(color = Color.Cyan, modifier = Gravity.End) {
                        Text(text = "7 Column Flexible wraps Expanded, Surface gravity end, " +
                                "paragraphstyle TextAlign.end ", paragraphStyle = ParagraphStyle(textAlign = TextAlign.End))
                    }
                }
            }

            Row {
                Surface(modifier = Spacing(all = 4.dp), color = Color.White) {
                    Text(text = "8 on Row")
                }
                Surface(modifier = Spacing(all = 4.dp), color = Color.Green)
                {
                    Text(text = "9 on Row")
                }
                Column(modifier = Gravity.Center wraps Flexible(1f)){
                    Surface(color = Color.Red) {
                        Text(text = "10 col center flex, line 1")
                    }
                    Surface(color = Color.DarkGray)
                    {
                        Text(text = "11 line 2 xxxxxx")
                    }
                }
                Column(modifier = Gravity.Center wraps Expanded) {
                    Surface(color = Color.Magenta, modifier = Gravity.End) {
                        Text(text = "12 col cnt mod end")
                    }
                }
            }


        }
    }
}
m
I took a look at your code. The layout problem here is that the height of the Row is not known when asking the Column that contains 4 and 5 to do its layout. Because you want Row to wrap the Column horizontally. But what if the Column containing 4 and 5 was taller than the one containing 2 and 3? You would have to relayout the Column containing 2 and 3. Anyways, the solution is to wrap the Row in a MaxIntrinsicHeight component. This will prelayout the Row, such that its final height will be known when laying out the Columns. (note that MaxIntrinsicHeight will soon be exposed as a modifier). Then you need to add an ExpandedHeight modifier to the Column containing 4 and 5 to make sure it fills the available space of the Row. Then you can add
Gravity.End wraps Align.CenterVertically
modifier to the Surface of 5. This will make sure the Text is centered vertically in the remaining space after 4.
I am pretty sure you could not achieve the centering of 5 in dev02 either, I'd be interested to know how if otherwise 🙂
Regarding your code, make sure that you only use Gravity modifiers on direct children of Row/Column. Otherwise they do nothing if you put them on a child of Surface for example. We are currently investigating if we can avoid this. Otherwise linting will hopefully help but it's not yet here
🙏 1
👍 1
Also to make achieve the screenshot I had to do small other modifications. For example, you are making the Column of 2 Expanded. This will fill the height of the entire screen, making the further two Rows not make it inside the screen. Let me know if you have further questions 🙂
r
The screenshot is taken from an emulator, here the the column is not stretched to the bottom... ...but anyhow, I'll take your suggestions into consideration and change the code. Thanx for responding. I really miss a good documentation on layots (rows, columns and gravity, what is possible and not).
@Mihai Popa Thanx for advices, have followed what you have suggested, and ended with a much more cleaner setup. But I ran into trouble with 5. when I tried to add
modifier=Gravity.End wraps Align.CenterVertically
. It redlines
CenterVertically
, is this dev04 ?, or do I miss a dependency ? Code below is the upper part (above
Divider()
) justified to the suggestions you have.
Copy code
fun CardGravityTest2()
{
    Card(
            modifier = Spacing(all = 4.dp),
            color = Color.LightGray,
            shape = RoundedCornerShape(
                    size = 5.dp
            )
    ){
        Column {

            MaxIntrinsicHeight {
                Row {
                    Surface(
                            color = Color.Red,
                            modifier = Spacing(all = 4.dp)
                    ) {
                        Text(text = "1 Surface")
                    }

                    Column(
                            modifier = Flexible(
                                    flex = 1f
                            ) wraps Spacing(
                                    all = 4.dp
                            )
                    ) {
                        Surface(
                                color = Color.Green
                        ) {
                            Text(text = "2 Column mod Flexible wraps Spacing," +
                                    "Surface no mod ")
                        }
                        Surface(
                                color = Color.Magenta
                        ){
                            Text(text = "3 Surface no mod ")
                        }
                    }

                    Column (modifier = ExpandedHeight) {
                        Surface(
                                modifier = Gravity.End,
                                color = Color.DarkGray
                        ){
                            Text(text = "4. Col no mod, Srf Gr.end")
                        }
                        Surface(
                                modifier = Gravity.End wraps Align.CenterVertically,
                                color = Color.Yellow
                        ){
                            Text(text = "5. Srf Gr. end, Center vert ? ")
                        }
                    }
                }
            }

        }
    }
}
(Tried to add a screenshot, it seems to have disappeared... sorry about that)
m
Oh yes, indeed CenterVertically is not in dev03 😞
For the moment, a workaround would be to wrap in a
Container
:
Copy code
Container(Gravity.End wraps ExpandedHeight) {
                                    Surface(color = Color.Yellow){
                                        Text(text = "5 Center End me!")
                                    }
                                }
r
You were right about dev02 (I actually rechecked my code, I knew 🤔 I hav fought about this and found a solution, and actually ended in wrapping near like you did here, but then in dev02 ). I'll try this as you suggests. Thank you for good advices!!