flexbox는 모던 웹을 위해 제안된 기존 layout보다 더 세련된 방식의 니즈에 부합하기 위한 CSS3의 새로운 layout방식.
요소 사이즈가 불명확 / 동적 변화시에도 유연한 레이아웃 가능.
단, flexbox는 비교적 최신 스펙이기 때문에 벤더 프리픽스를 이용해야할 수 있다. IE계열에서 Flexbox를 사용하기 위해서는 flexibility.js이용 시 편리. (브라우저별 지원여부)
Flexbox 사용
Flexbox 레이아웃은 flex item
이라 불리는 복수의 자식 요소,
이들을 내포하는 flex-container
부모 요소로 구성
사용법1. flexbox를 사용하기 위해서 HTML 부모 요소의 display 속성에 flex를 지정
부모 요소가 inline 요소인 경우 inline-flex을 지정
.flex-container {
display: flex;
}
.flex-container {
display: inline-flex;
}
flex 또는 inline-flex는 부모 요소에 반드시 지정해야하는 유일한 속성,자식 요소는 자동적으로 flex item이 된다.
flex-direction 속성은 flex 컨테이너의 주축(main axis) 방향을 설정
flex-direction: row;
: 좌에서 우로(ltr) 수평 배치된다. flex-direction 속성의 기본값.flex-container {
flex-direction: row;
}
flex-direction: row-reverse;
: 우에서 좌로(rtl) 수평 배치
.flex-container {
flex-direction: row-reverse;
}
flex-direction: column;
: 위에서 아래로 수직 배치
.flex-container {
flex-direction: column;
}
flex-direction: column-reverse;
: 아래에서 위로 수직 배치
.flex-container {
flex-direction: column-reverse;
}
flex-wrap 속성은 flex 컨테이너의 복수 flex item을 1행으로 또는 복수행으로 배치. flex-wrap 속성은 flex 컨테이너의 width보다 flex item들의 width의 합계가 더 큰 경우 , 한줄로 표현할 것인지, 여러줄로 표현할 것인지를 지정
flex-wrap: nowrap;
: flex item을 개행하지 않고 1행에 배치한다. flex-wrap 속성의 기본값.
.flex-container {
flex-wrap: nowrap;
}
하지만 flex item들의 width의 합계가 flex 컨테이너의 width보다 큰 경우 flex 컨테이너를 넘치게 된다. 이때 overflow: auto;
를 지정하면 가로 스크롤이 생기며 컨테이너를 넘치지 않는다.
flex-wrap: wrap;
: flex item들의 width의 합계가 flex 컨테이너의 width보다 큰 경우, flex item을 복수행에 배치. 기본적으로 좌에서 우로, 위에서 아래로 배치
.flex-container {
flex-wrap: wrap;
}
flex-wrap: wrap;
: lex-wrap: wrap;과 동일하나 아래에서 위로 배치
.flex-container {
flex-wrap: wrap-reverse;
}
flex-flow 속성은 flex-direction 속성과 flex-wrap 속성을 설정하기 위한 shorthand . 기본값은 row nowrap.
.flex-container {
flex-flow: <flex-direction> || <flex-wrap>;
}
flex container의 main axis를 기준으로 flex item을 수평 정렬.
justify-content: flex-start;
: main start(좌측)를 기준으로 정렬. justify-content 속성의 기본값.
.flex-container {
justify-content: flex-start;
}
justify-content: flex-end;
: main end(우측)를 기준으로 정렬
.flex-container {
justify-content: flex-end;
}
justify-content: center;
: flex container의 중앙에 정렬
.flex-container {
justify-content: center;
}
justify-content: space-between;
: 첫번째와 마지막 flex item은 좌우 측면에 정렬되고 나머지와 균등한 간격으로 정렬
.flex-container {
justify-content: space-between;
}
justify-content: space-around;
: 모든 flex item은 균등한 간격으로 정렬
.flex-container {
justify-content: space-around;
}
flex item을 flex container의 수직 방향(cross axis)으로 정렬,align-items 속성은 모든 flex item에 적용된다.
align-items: stretch;
: 모든 flex item은 flex container의 높이(cross start에서 cross end까지의 높이)에 꽉찬 높이를 갖는다. align-items 속성의 기본값.
.flex-container {
align-items: stretch;
}
align-items: flex-start;
: 모든 flex item은 flex container의 cross start 기준으로 정렬.
.flex-container {
align-items: flex-start;
}
align-items: flex-end;
: 모든 flex item은 flex container의 cross end 기준으로 정렬.
.flex-container {
align-items: flex-end;
}
align-items: center;
: 모든 flex item은 flex container의 cross axis의 중앙에 정렬.
.flex-container {
align-items: center;
}
align-items: baseline;
: 모든 flex item은 flex container의 baseline을 기준으로 정렬
.flex-container {
align-items: baseline;
}
flex container의 axis를 기준으로 flex item을 수직정렬.
justify-content 속성은 flex container의 main axis를 기준으로 flex item을 수평 정렬하는것임.
align-content: stretch;
: 모든 flex item은 flex item의 행 이후에 균등하게 분배된 공간에 정렬되어 배치, align-content 속성의 기본값
.flex-container {
align-content: stretch;
}
align-content: flex-start;
: 모든 flex item은 flex container의 cross start 기준으로 stack 정렬.
.flex-container {
align-content: flex-start;
}
align-content: flex-end;
: 모든 flex item은 flex container의 cross end 기준으로 stack 정렬.
.flex-container {
align-content: flex-end;
}
align-content: flex-end;
: 모든 flex item은 flex container의 cross axis의 중앙에 stack 정렬.
.flex-container {
align-content: center;
}
align-content: space-between;
: 첫번째 flex item의 행은 flex container의 상단에 마지막 flex item의 행은 flex container의 하단에 배치되며 나머지 행은 균등 분할된 공간에 배치 정렬
.flex-container {
align-content: space-between;
}
align-content: space-around;
: 모든 flex item은 균등 분할된 공간 내에 배치 정렬
.flex-container {
align-content: space-around;
}
float, clear, vertical-align 속성은 flex item에 영향을 주지 않는다.
flex item의 배치 순서를 지정.
HTML 코드를 변경하지 않고 order 속성값을 지정하는 것으로 간단히 재배치할 수 있다.
기본 배치 순서는 flex container에 추가된 순서, 기본값은 0.
.flex-item {
order: 정수값;
}
flex item의 너비에 대한 확대 인자(flex grow factor)를 지정 . 기본값은 0이고 음수값은 무효
.flex-item {
flex-grow: 양의 정수값;
}
모든 flex item이 동일한 flex-grow 속성값을 가지면 모든 flex item은 동일한 너비
두번째 flex item의 flex-grow 속성값을 3으로 지정하면 다른 flex item보다 더 넓은 너비
flex item의 너비에 대한 축소 인자(flex shrink factor)를 지정. 기본값은 1이고 음수값은 무효. 0을 지정하면 축소가 해제되어 원래의 너비를 유지.
.flex-item {
flex-shrink: 양의 정수값;
}
기본적으로 모든 flex item은 축소된 상태로 지정(기본값 1)하고 두번째 flex item만 축소를 해제(flex-shrink: 0;)하면 원래의 너비를 유지
flex item의 너비 기본값을 px, % 등의 단위로 지정,기본값은 auto.
.flex-item {
flex-basis: auto | <width>;
}
flex-grow, flex-shrink, flex-basis 속성의 shorthand이다. 기본값은 0 1 auto, (W3C에서는 이 속성을 사용하는 것 보다 개별적으로 기술하는 것을 추천)
.flex-item {
flex: none | auto | [ <flex-grow> <flex-shrink>? || <flex-basis> ];
}
align-items 속성(flex container속성으로 flex item을 flex container의 수직 방향(cross axis)으로 정렬) 보다 우선하여 개발 flexx item을 정렬할 수 있다. (기본값은 auto)
.flex-item {
align-self: auto | flex-start | flex-end | center | baseline | stretch;
}
flexbox playground
: flexbox 레이아웃(property값)을 조작하며 렌더결과를 확인할 수 있다.
정렬 대상 요소(텍스트 또는 링크 등의 inline 레벨 요소 또는 inline-block 레벨 요소)의 부모 요소에 text-align: center;를 지정
.container {
text-align: center;
}
정렬 대상 요소에 너비를 명시적으로 지정하고 margin-right와 margin-left 프로퍼티에 auto를 지정.
정렬 대상 요소에 너비를 명시적으로 지정하지 않으면 너비는 full width가 되므로 중앙 정렬이 필요없다.
.item {
width: 200px;
margin: 20px auto;
}
복수의 block 요소는 기본적으로 수직 정렬된다. 이것을 수평정렬하기 위해서는 정렬 대상 block 요소를 inline-block 요소로 변경한 후 부모 요소에 text-align: center;를 지정
정렬 대상 요소에 width를 지정하지 않으면 콘텐츠에 너비에 맞추어 너비가 결정되므로 명시적으로 너비를 지정
.container {
text-align: center;
}
.item {
width: 150px;
display: inline-block;
}
flexbox를 사용할 수도 있다. 정렬 대상의 부모 요소에 아래의 룰셋을 선언.
.flex-center {
display: flex;
justify-content: center;
}
Single line
정렬 대상의 부모 요소에 padding-top과 padding-bottom 프로퍼티값을 동일하게 적용
.container {
padding: 50px;
}
.container {
height: 100px;
line-height: 100px;
}
Multiple lines
여러 줄의 텍스트의 경우, padding-top과 padding-bottom 프로퍼티값을 동일하게 적용하는 방법도 가능
또 다른 방법으로 vertical-align 프로퍼티를 사용한 방법도 가능( table 속성을 사용하여야 한다.)
.parent {
display: table;
height: 100px;
}
.child {
display: table-cell;
vertical-align: middle;
}
Flexbox
vertical-align 프로퍼티를 사용하는 방법은 table 프로퍼티를 사용하여야 하므로 번거로울 수 있다. 좀 더 간단한 방법은 flexbox를 사용하는 것. (지원하지 않는 브라우저 아니면 사용하는 것 추천)
.container {
display: flex;
justify-content: center;
flex-direction: column;
height: 400px;
}
.parent {
position: relative;
}
.child {
position: absolute;
top: 50%;
height: 100px;
/*요소의 높이(100px)의 반 만큼 위로 이동*/
margin-top: -50px;
}
.parent {
position: relative;
}
.child {
position: absolute;
top: 50%;
/*요소의 높이의 반(50%) 만큼 위로 이동*/
transform: translateY(-50%);
}
.parent {
display: flex;
/*위에서 아래로 수직 배치*/
flex-direction: column;
/*중앙정렬*/
justify-content: center;
}
요소의 너비와 높이가 고정되어 있는 경우, 요소의 너비와 높이가 불확정 상태의 경우 모두 사용 가능한 방법.
.parent {
position: relative;
}
.child {
position: absolute;
top: 50%;
left: 50%;
/*요소의 높이/너비의 반(50%)만큼 위/왼쪽으로 이동*/
transform: translate(-50%, -50%);
}
flexbox이용 시
.parent {
display: flex;
justify-content: center;
align-items: center;
}
컨테이너 요소로 img 요소를 래핑하면 img 요소 아래에 의도하지 않은 여분의 공간이 패딩.
image 요소는 inline 요소이며, image 요소는 텍스트로 취급된다.
텍스트요소는 렌더링할 시 타이포그래피라는 나름의 방식이 존재하며,
이미지 요소 또한 이 방식을 따른다.
이 방법을 해결하려면,
(1) image 요소를 블록 요소로 전환하면 더 이상 텍스트로 취급되지 않는다.
(2) inline 요소에 사용할 수 있는 vertical-align 프로퍼티를 사용(블록요소로 전환 불가능한경우). vertical-align 프로퍼티의 기본값은 baseline인데 이를 변경하여 이미지 표시 위치를 조정