개요
Flutter에서 하나의 위젯을 배치하는 것은 굉장히 쉽다.
오버라이드된 `build` 메소드의 `return`에 위젯 클래스를 반환해주면 위젯을 쉽게 렌더링할 수 있다. (물론 그 과정은 굉장히 추상적이고 복잡하겠지만...)
"그렇다면 여러 개의 위젯을 배치하고 싶을 때는 어떻게 해야하지?"
`return` 에는 하나의 위젯만 반환시킬 수 있고, 반환 타입마저도 `List<Widget>`이 아니라서 여러 개의 위젯을 반환하는 것은 사실상 불가능하다.
"그럼 뭐 불가능하다는거야 뭐야?"
불가능했다면 Flutter는 이 세상에 나오지 못햇을 것이다... 당연히 가능하며, 이를 도와주는 것은 Multichild-Layout Widget들이다.
Multichild-Layout Widget에는 `Row`, `Column`, `Stack`과 같은 위젯들이 존재하며, 이번에 볼 것은 그 중 가장 많이 사용되는 `Row`와 `Column`이다.
Row
Row란?
먼저 `Row`부터 보자.
행과 열, `Row`는 그 중 행을 뜻한다.
행과 열이라고 하면 헷갈릴 수 있어 단번에 알아듣기 쉽게 설명하면, Row는 가로 배치를 도와주는 위젯이다.
정말 말 그대로 핸드폰 화면의 가로축 방향으로 위젯을 진열해준다.
사용 예시
아래와 같이 `children` 프로퍼티에 위젯 리스트를 넣어주면, 가로로 진열이 된다. ▼
Row(
children: [
Container(
width: 100,
height: 100,
color: Colors.blue,
),
Container(
width: 100,
height: 100,
color: Colors.red,
),
],
),
이렇게 두 사각형이 가로로 진열된 것을 볼 수 있다. ▼
Row 위젯의 프로퍼티들
Row 위젯의 프로퍼티는 생각보다 많지 않다.
많지 않은데 그 중에서도 `children`, `mainAxisAlignment`, `crossAxisAlignment` 정도만 사용한다.
하나씩 보도록 하자.
children
앞의 예시에서 사용된 프로퍼티로 `List<Widget>`을 받는다.
다른 프로퍼티들과는 다르게 `required`, 즉 필수 프로퍼티로 받아서 꼭 넣어줘야한다.
어떤 위젯도 들어갈 수 있지만, 만약에 내부에 들어간 위젯의 크기가 커지면 오버플로우가 나게 된다. ▼
mainAxisAlignment와 crossAxisAlignment
AxisAlignment
AxisAlignment는 축 정렬이란 뜻이기에, mainAxisAlignment는 주 축 정렬, crossAxisAlignment는 교차 축 정렬로 생각하면 쉽다.
Row의 mainAxis는 가로다.
그렇기에 `mainAxisAlignment`는 가로 축 정렬을 의미하고 `crossAxisAlignment`는 세로 축 정렬을 의미한다.
각각 `MainAxisAlignment`와 `CrossAxisAlignment` enum을 받는다.
`MainAxisAlignment`에는 `center`, `end`, `spaceAround`, `spaceBetween`, `spaceEvenly`, `start`가 있다. ▼
`CrossAxisAlignment`에는 `center`, `end`, `start`, `stretch`, `baseline`이 있다. ▼
이에 대한 설명은 아래에서 하겠다. Column에도 적용되는 이야기이기 때문이다.
이 두 값에 아무것도 넣지 않는다면 기본으로 `MainAxisAlignment`에는 `MainAxisAlignment.start`가, `CrossAxisAlignment`에는 `CrossAxisAlignment.center`가 들어가게 된다.
Column
Column이란?
행과 열, `Column`은 그 중 열을 뜻한다.
행과 열이라고 하면 헷갈릴 수 있어 단번에 알아듣기 쉽게 설명하면, Column은 세로 배치를 도와주는 위젯이다.
정말 말 그대로 핸드폰 화면의 세로축 방향으로 위젯을 진열해준다.
사용 예시
아래와 같이 `children` 프로퍼티에 위젯 리스트를 넣어주면, 세로로 진열이 된다. ▼
Column(
children: [
Container(
width: 100,
height: 100,
color: Colors.blue,
),
Container(
width: 100,
height: 100,
color: Colors.red,
),
],
),
이렇게 두 사각형이 세로로 진열된 것을 볼 수 있다. ▼
Column 위젯의 프로퍼티들
`Column`위젯의 프로퍼티는 `Row`와 동일하다.
Row와 마찬가지로 `children`, `mainAxisAlignment`, `crossAxisAlignment` 정도만 사용한다.
children
앞의 예시에서 사용된 프로퍼티로 `List<Widget>`을 받는다.
다른 프로퍼티들과는 다르게 `required`, 즉 필수 프로퍼티로 받아서 꼭 넣어줘야한다.
어떤 위젯도 들어갈 수 있지만, 만약에 내부에 들어간 위젯의 크기가 커지면 오버플로우가 나게 된다. ▼
mainAxisAlignment와 crossAxisAlignment
AxisAlignment
AxisAlignment는 축 정렬이란 뜻이기에, mainAxisAlignment는 주 축 정렬, crossAxisAlignment는 교차 축 정렬로 생각하면 쉽다.
Column의 mainAxis는 세로다.
그렇기에 `mainAxisAlignment`는 가로 축 정렬을 의미하고 `crossAxisAlignment`는 세로 축 정렬을 의미한다.
각각 `MainAxisAlignment`와 `CrossAxisAlignment` enum을 받는다.
`MainAxisAlignment`에는 `center`, `end`, `spaceAround`, `spaceBetween`, `spaceEvenly`, `start`가 있다. ▼
`CrossAxisAlignment`에는 `center`, `end`, `start`, `stretch`, `baseline`이 있다. ▼
Row와 Column의 MainAxisAlignment와 CrossAxisAlignment
Row와 Column 모두 MainAxisAlignment와 CrossAxisAlignment를 가진다.
하지만 같은 enum이라고 해도 Row냐 Column이냐에 따라 그 동작이 조금씩 바뀐다.
가장 핵심적으로 바뀌는 것은 가로와 세로이다.
Row기준 MainAxis는 가로이고, Column기준 MainAxis는 세로이기에 같은 MainAxisAlignment라고 해도 적용되는 축이 다르다.
축이 바뀌는 부분 말고는 적용되는 원리는 같기에 어떤 축인지만 알면 나머지는 쉽게 적용시킬 수 있다.
MainAxisAlignment
start, end, center
Column의 MainAxisAlignment.start, center, end는 아래와 같다.
그리고 Row의 MainAxisAlignment.start, center, end는 아래와 같다.
start, center, end는 이름 그대로 동작하기에 뜻만 알고 사용하면 된다.
spaceAround, spaceBetween, spaceEvenly
이 셋은 start, center, end와는 다르게 그 이름으로 뜻을 유추하기가 어렵다.
Around? Between? Evenly? 이 중에서 Evenly만 그나마 유추할 법 한데, 그럼 나머지는 어떤 차이가 있는지가 또 의문이 든다.
이 셋이 동작하는 것을 정리하면 아래의 그림과 같다. ▼
가장 먼저 spaceBetween, 앞과 뒤에 공백 없이 사이에 동일한 간격으로 공백(그림의 흰색 부분)을 넣어준다.
spaceEvenly는 앞과 뒤에도 동일한 간격으로 공백을 넣어준다.
spaceAround는 앞과 뒤에 공백을 넣어주긴 하나, 위젯들 사이에 들어가는 공백의 절반만큼만 공백이 들어간다.
crossAxisAlignment
start, center, end
셋 다 높이나 너비가 같으면 차이가 보이지 않기에 너비와 높이를 조정했다.
`Column`의 `CrossAxisAlignment.start`, `center`, `end`는 아래와 같다. ▼
`Row`의 `CrossAxisAlignment.start`, `center`, `end`는 아래와 같다. ▼
`start`, `center`, `end`는 이름 그대로 동작하기에 뜻만 알고 사용하면 된다.
stretch
CrossAxisAlignment.stretch는 아래와 같이 동작한다. ▼
빈 부분을 채워서 정렬해준다.
baseline
`baseline`은 `baseline`이 의미하는 바 자체를 모르면 조금 생소할 수 있다.
`baseline`은 텍스트의 밑부분을 말한다.
그렇기에 `CrossAxisAlignment.baseline`은 텍스트의 밑단을 기준으로 정렬해준다.
폰트 크기가 다를 때 사용하면 굉장히 유용하다.
다만 `baseline`은 다른 정렬들과 조금 다른 점이 있는데, 바로 `textBaseLine`이라는 프로퍼티와 같이 써야한다는 것이다.
같이 사용하지 않으면 아래와 같은 에러가 발생하게 된다. ▼
textBaseLine 프로퍼티는 `TextBaseLine.alphbetic`과 `TextBaseLine.ideographic`의 두 enum을 받을 수 있다.
`TextBaseLine.alphbetic`은 알파벳을 기준으로 삼고,
`TextBaseLine.ideographic`은 텍스트 영역의 아래를 기준으로 삼는다. ▼
마치며
이렇게 정렬까지 Row와 Column에 대해서 알아보았다.
여러 위젯을 담는 Multichild-Layout Widget의 가장 기본으로 이후에 굉장히 많이 사용하게 되는 기본적인 위젯이다.
Row와 Column말고도 다른 위젯들도 많지만 가장 기본이 되는 위젯이라고 생각하면 좋다.
'Develop > Flutter' 카테고리의 다른 글
[Flutter][Widget] CustomPaint로 나만의 위젯 만들기 (2) | 2024.04.08 |
---|---|
[Flutter] 패키지 사용법 (0) | 2024.04.01 |
[Flutter][Widget] Container 위젯 그리고 Container의 크기 설정 (0) | 2024.03.20 |
[Flutter][Widget] Text 위젯 (0) | 2024.03.19 |
[Flutter][Widget] Step Indicator 구현 (0) | 2024.02.29 |