본문 바로가기

FrontEnd

[번역] CSS 레이아웃과 블록 서식 맥락 이해하기

반응형
블록 서식 맥락(Block Formatting Context)이라는 말을 들어보셨나요?
부끄럽게도 저는 얼마 전에 처음 들어봤습니다.
의외로 CSS 레이아웃에서 굉장히 중요한 역할을 하는 개념입니다.
블록 서식 맥락을 생성하는 방법과 CSS 레이아웃에서 블록 서식 맥락이 왜 중요한지 알아봅니다.
 
아래 글의 번역입니다.
 

Understanding CSS Layout And The Block Formatting Context — Smashing Magazine

You might never have heard the phrase 'Block Formatting Context', but if you have used CSS for layout you probably already know what it does. In this article I’ll explain the existing ways to create a Block Formatting Context, why it is important in CSS

www.smashingmagazine.com

TL;DR

  • BFC를 사용하면, 플로팅된 요소가 블록 내부에에 포함되게 할 수 있다.
  • BFC를 사용하면, 마진 겹침을 예방할 수 있다
  • BFC를 사용하면, 텍스트가 플로팅된 요소를 감싸지 않도록 할 수 있다.

블록 서식 맥락(Block Formatting Context;BFC)가 뭔가요?

https://developer.mozilla.org/ko/docs/Web/Guide/CSS/Block_formatting_context

블록 서식 맥락(block format context)은 웹 페이지를 렌더링하는 시각적 CSS의 일부로서,
블록 박스의 레이아웃이 발생하는 지점과 플로팅 요소의 상호작용 범위를 결정하는 범위입니다.
BFC(Block Formatting Context)가 작동하는 방식은 간단한 float 예제를 통해 이해하기 가장 쉽습니다.
아래 예제에는 왼쪽으로 떠 있는 이미지와 일부 텍스트가 포함된 상자가 있습니다.
 
충분한 양의 텍스트가 있으면
해당 텍스트가 플로팅된 이미지를 감싸고
테두리(border)가 전체를 둘러쌉니다.
<div class="outer">
  <div class="float">I am a floated element.</div>
  I am text inside the outer box.
</div>
<style>
    .outer {
          border: 5px dotted rgb(214,129,137);
          border-radius: 5px;
          width: 450px;
          padding: 10px;
          margin-bottom: 40px;
        }

    .float {
      padding: 10px;
      border: 5px solid rgba(214,129,137,.4);
      border-radius: 5px;
      background-color: rgba(233,78,119,.4);
      color: #fff;
      float: left;
      width: 200px;
      margin: 0 20px 0 0;
    }
</style>

텍스트는 플로팅된 요소를 둘러쌉니다.

일부 텍스트를 제거하면
텍스트가 이미지를 둘러싸기에 충분하지 않고,

플로팅된 이미지가 문서 흐름에서 제거되기 때문에
테두리가 이미지가 아닌 내부의 텍스트만을 둘러싸게 됩니다.

텍스트가 충분하지 않으면 테두리가 플로팅된 요소를 둘러싸지 않습니다.

이는 플로팅된 요소의 너비는 동일하게 유지되기 때문입니다.

플로팅된 요소의 공간을 위해 줄어든 것은 각 라인의 높이(텍스트 한 줄을 포함한 박스)입니다.
이것이 배경과 테두리가 플로트 뒤에 있는 것처럼 보이는 이유입니다.

 

일반적으로 이 레이아웃 문제를 해결하는 두 가지 방법이 있습니다.
하나는 텍스트와 이미지 아래에 요소를 삽입하고 clearfix hack을 사용하는 것입니다.
다른 방법은 overflow 속성을 사용하는 것입니다.
.outer {
      overflow: auto;
    }
overflow: auto를 사용하면 상자에 float가 포함됩니다. (큰 미리보기)
 

오버플로가 이런 방식으로 작동하는 이유는

overflow의 초기값인 visible 이외의 다른 값을 사용하면 블록 서식 맥락이 생성되고,

BFC의 기능 중 하나가 부동 요소를 포함하는 것이기 때문입니다.


BFC는 레이아웃 내의 미니 레이아웃 입니다.

BFC는 페이지 내부의 미니 레이아웃처럼 생각할 수 있습니다.
요소가 BFC를 생성하면 모든 것이 그 안에 포함됩니다.
우리가 본 것처럼 부동 요소는 더 이상 상자 바닥에서 튀어나오지 않습니다.
BFC는 또한 다른 유용한 동작을 유발합니다.

BFC는 마진 겹침을 방지합니다.

마진 겹침의 이해는 과소평가된 또 다른 CSS 기술입니다.
이 다음 예제에는 배경색이 회색인 div가 있습니다.

이 div에는 내부에 두 개의 p가 있습니다.

외부 div 요소에는 40px의 margin-bottom이 있습니다.

p에는 20px의 위쪽 및 아래쪽 마진도 있습니다.

<style>
.outer {
    background-color: #ccc;
    margin: 0 0 40px 0;
}

p {
  padding: 0;
  margin: 20px 0 20px 0;
  background-color: rgb(233,78,119);
  color: #fff;
}


</style>

p 요소의 여백과 외부 div의 여백 사이에 아무 것도 없기 때문에
두 요소의 마진이 겹쳐 단락이 상자의 위쪽과 아래쪽과 같은 높이가 됩니다.

단락 위와 아래에 회색이 표시되지 않습니다.

마진이 겹쳐 상자의 위쪽과 아래쪽이 회색으로 표시되지 않습니다.

그러나 상자를 BFC로 만든 뒤,

p와 마진을 포함하면, 더 이상 마진 겹침이 발생하지 않습니다.

마진 뒤에 있는 컨테이너의 회색 배경을 볼 수 있습니다.

<style>
.outer {
    background-color: #ccc;
    margin: 0 0 40px 0;
    overflow: auto;
}
</style>

BFC 내에서는 마진이 겹치지 않습니다.

다시 한 번 BFC는 그 안에 무언가를 포함하는 작업을 수행하고 있으며,
상자 밖으로 빠져나와 튀어나오는 것을 막습니다.

BFC는 콘텐츠가 플로팅된 요소를 감싸는 것을 막습니다.

플로트를 사용하는 컬럼 타입 레이아웃이 작동하는 방식이므로
BFC의 이러한 동작에도 익숙할 것입니다.
항목이 BFC를 생성하는 경우 해당 항목은 플로팅된 요소를 래핑하지 않습니다.

다음 예제에는 다음과 같은 마크업이 있습니다.

<div class="outer">
      <div class="float">I am a floated element.</div>
      <div class="text">I am text</div>
</div>

float 클래스가 있는 항목은 왼쪽으로 플로팅되므로
뒤에 오는 div의 텍스트가 float 주위를 둘러쌉니다.

텍스트가 플로팅된 요소를 둘러쌉니다.

텍스트를 래핑하는 div를 BFC로 만들어 래핑 동작을 방지할 수 있습니다.
<style>
.text{
  overflow: auto;
}
</style>

텍스트가 포함된 div는 이제 BFC이므로&nbsp;텍스트가 플로팅된 요소를 감싸지 않습니다.

이것은 기본적으로 여러 열이 있는 부동 레이아웃을 만들 수 있는 방법입니다.
항목을 플로팅하면 해당 항목에 대한 BFC도 생성되므로
오른쪽 항목이 왼쪽 항목보다 큰 경우 열이 서로를 감싸지 않습니다.

무엇이 BFC를 만드나요?

overflow를 사용하여 BFC를 만드는 것 외에도

일부 다른 CSS 속성 또한 BFC를 만듭니다.
우리가 본 것처럼 플로팅 요소는 BFC를 생성합니다.

따라서 플로팅된 요소는 그 안에 모든 것을 포함합니다.

  • 요소에 position: absolute 또는 position: fixed를 사용합니다.
  • 요소에 display: inline-block, display: table-cell 또는 display: table-caption을 사용합니다.
    • table-cell 및 table-captions는 HTML 요소의 기본값입니다.
    • 예를 들어 데이터 테이블이 있는 경우 각 셀은 BFC를 생성합니다.
  • 여러 열 레이아웃의 열을 확장하는 데 사용되는 column-span: all 사용.
  • Flex 및 Grid 아이템은 각각 Flex 서식 컨텍스트 및 Grid 서식 컨텍스트로 설명된다는 점을 제외하면 BFC와 유사한 항목을 만듭니다.
    • 이것은 각각이 참여하고 있는 레이아웃의 타입을 반영합니다.
      • 블록 서식 컨텍스트는 항목이 블록 레이아웃에 참여하고 있음을 나타내냅니다.
      • Flex 서식 컨텍스트는 항목이 Flex 레이아웃에 참여하고 있음을 의미합니다.
    • 실제로 결과는 동일하며 플로팅된 요소는 내부에 포함되고, 마진은 겹치지 않습니다.

BFC 를 만드는 새로운 방법

BFC를 생성하기 위해 overflow 또는 다른 방법을 사용하는 데는 두 가지 문제가 있습니다.
  1. overflow를 사용하는 방법은 BFC를 생성하고 플로트를 포함하지만 특정 시나리오에서는 원치 않는 스크롤바가 나타나거나 그림자가 잘리는 것을 발견할 수 있습니다.
    • 이는 overflow 속성이 overflow 상황에서 무엇을 해야 하는지 브라우저에 알릴 수 있도록 설계되었기 때문입니다.
    • 브라우저는 사용자가 지시한 대로 정확히 수행하고 있습니다!
  2. 다른 개발자에게 혼란을 줄 수 있습니다.(overflow를 사용한 이유가 BFC를 만들기 위함임을 알아야 합니다.)
    • overflow : auto 또는 scroll로 설정한 이유는 뭔가요?
    • 원래 개발자의 의도는 무엇인가요? 이 컴포넌트에 스크롤바가 필요했을까요?
유용한 것은 그렇지 않으면 비활성이어서 다른 동작을 유발하지 않고
미니 레이아웃을 생성하는 BFC를 생성하는 방법과 내부에서 안전하게 일어날 수 있는 기능입니다.
이 방법을 사용하면 예기치 않은 문제가 발생하지 않으며 개발자가 의도한 바를 명확하게 파악할 수 있습니다.
CSS Working Group은 이것이 매우 편리할 수 있다고 생각했고,
우리는 display 속성의 새로운 값인 flow-root를 갖게 되었습니다.

이 문서에서 설명한, 새 BFC를 만드는 것이 유리한 모든 상황에서 display: flow-root를 사용합시다.

  • 즉, float를 포함하거나
  • 마진 겹침을 방지하거나
  • float를 래핑하는 아이템을 방지할 수 있습니다.


 


 

Browser support for display: flow-root

Can I Use display: flow-root

현재 약 95%의 사용자가 사용하는 브라우저가 해당 기능을 지원하고 있습니다.

Can I Use display: flow-root

 

Can I use... Support tables for HTML5, CSS3, etc

 

caniuse.com

 
우리는 이제 BFC가 무엇인지 알았으며,
마진 겹침과 블록 내 float요소를 포함하기 위해
overflow 방법, 혹은 다른 방법들을 활용할 수 있다는 것을 알게 되었습니다.
 
 



 

반응형