CSS 셰이프 모듈 레벨 1

W3C 후보 권고안 초안,

이 문서에 대한 자세한 정보
이 버전:
https://www.w3.org/TR/2025/CRD-css-shapes-1-20250612/
최신 공개 버전:
https://www.w3.org/TR/css-shapes/
에디터스 드래프트:
https://drafts.csswg.org/css-shapes/
이전 버전:
히스토리:
https://www.w3.org/standards/history/css-shapes-1/
구현 보고서:
https://wpt.fyi/results/css/css-shapes
피드백:
CSSWG 이슈 저장소
에디터:
(Microsoft Corporation)
(Adobe)
Noam Rosenthal (Google)
이전 에디터:
Vincent Hardy
이 명세서에 대한 수정 제안:
GitHub 에디터
테스트 스위트:
https://wpt.fyi/results/css/css-shapes/

요약

CSS 셰이프는 CSS에서 사용할 기하학적 도형을 설명합니다. 레벨 1에서는 CSS 셰이프를 플로트에 적용할 수 있습니다. 플로트에 원형 셰이프를 적용하면 인라인 콘텐츠가 플로트의 경계 상자 대신 원형 셰이프를 따라 감싸집니다.

CSS는 구조화된 문서(HTML 및 XML 등)의 렌더링을 화면, 종이 등에서 기술하는 언어입니다.

이 문서의 상태

이 섹션은 이 문서가 공개된 시점의 상태를 설명합니다. 현재 W3C 공개 문서 목록과 이 기술 보고서의 최신 개정판은 W3C 표준 및 초안 색인 https://www.w3.org/TR/에서 확인할 수 있습니다.

이 문서는 CSS 워킹 그룹에 의해 후보 권고안 초안으로 권고안 트랙을 사용하여 공개되었습니다. 후보 권고안으로 공개되었다고 해서 W3C 및 회원사의 승인임을 의미하지는 않습니다. 후보 권고안 초안에는 워킹 그룹이 이후 후보 권고안 스냅샷에 포함할 계획인 이전 후보 권고안의 변경 사항이 통합되어 있습니다.

이 문서는 초안 문서로, 언제든지 업데이트, 교체 또는 다른 문서로 대체될 수 있습니다. 진행 중인 작업 이외의 용도로 이 문서를 인용하는 것은 부적절합니다.

피드백은 GitHub에 이슈를 등록하여 보내주시기 바랍니다(권장). 제목에 명세 코드 “css-shapes”를 포함하여 다음과 같이 작성해주세요: “[css-shapes] …코멘트 요약…”. 모든 이슈와 코멘트는 아카이브됩니다. 또는, 피드백은 (아카이브됨) 공개 메일링 리스트 www-style@w3.org로도 보낼 수 있습니다.

이 문서는 2023년 11월 3일 W3C 프로세스 문서에 따라 관리됩니다.

이 문서는 W3C 특허 정책 하에 운영되는 그룹에서 작성되었습니다. W3C는 해당 그룹의 결과물과 관련해 공개된 특허 공개 목록을 유지합니다; 해당 페이지에는 특허 공개 방법에 대한 안내도 포함되어 있습니다. 개인이 특정 특허가 필수 청구항을 포함한다고 실제로 알고 있는 경우, W3C 특허 정책 6절에 따라 정보를 공개해야 합니다.

1. 소개

이 섹션은 규범적이지 않습니다.

셰이프는 CSS 값으로 사용할 수 있는 임의의 기하학적 형태를 정의합니다. 이 명세서는 요소의 float area 기하를 제어하는 속성을 정의합니다. shape-outside 속성은 셰이프 값을 사용하여 플로트의 float area를 정의합니다.

참고: CSS Shapes의 향후 레벨에서는 플로트 이외의 요소에서도 셰이프를 사용할 수 있게 됩니다. 다른 CSS 모듈에서도 셰이프를 사용할 수 있으며, 예를 들어 CSS Masking [CSS-MASKING] 및 CSS Exclusions [CSS3-EXCLUSIONS]과 같이 사용할 수 있습니다.

참고: 사용자 에이전트가 CSS Shapes와 CSS Exclusions를 모두 구현한 경우, shape-outside 속성이 exclusion의 제외 영역을 정의합니다.

참고: CSS Shapes의 향후 레벨에서는 shape-inside 속성이 정의되어, 해당 요소 내에서 콘텐츠를 감싸는 셰이프를 지정할 수 있게 됩니다.

1.1. 모듈 상호작용

이 모듈은 [CSS2] 챕터 9에서 정의된 플로트 기능을 확장합니다.

1.2.

이 명세서는 CSS 속성 정의 규칙[CSS2]에서 따르며, 값 정의 문법[CSS-VALUES-3]에서 사용합니다. 이 명세서에서 정의되지 않은 값 타입은 CSS Values & Units [CSS-VALUES-3]에서 정의됩니다. 다른 CSS 모듈과의 조합으로 인해 이러한 값 타입의 정의가 확장될 수도 있습니다.

각 속성 정의에 명시된 값 이외에도, 이 명세서에서 정의된 모든 속성은 CSS-전역 키워드도 값으로 허용합니다. 가독성을 위해 별도로 반복하지 않았습니다.

1.3. 용어

감싸기

이 명세서에서는 감싸기라는 용어를 float area의 양 옆으로 콘텐츠가 흐르는 것을 의미합니다. 이는 [CSS2] 챕터 9에서 정의되어 있습니다. 콘텐츠는 왼쪽 플로트 박스의 오른쪽에서 감싸기가 되고, 오른쪽 플로트 박스의 왼쪽에서 감싸기가 됩니다. 이러한 감싸기의 결과로 플로트 옆에 있는 라인 박스는 float area와의 교차를 피하기 위해 필요에 따라 짧아집니다.

float area

플로트 요소 주위로 콘텐츠를 감싸기 위해 사용되는 영역입니다. 플로트 동작 규칙은 float area의 양쪽을 기준으로 콘텐츠 흐름을 결정합니다. 기본적으로 float area는 플로트 요소의 margin box입니다(이 값은 float areamargin-box 값으로 생성된 경우와 다를 수 있는데, 이때는 border-radius 곡률도 포함됩니다). 이 명세서의 shape-outsideshape-margin 속성을 사용하면 임의의 비직사각형 float area를 정의할 수 있습니다.

방향에 구애받지 않는 크기 박스의 방향에 구애받지 않는 크기는 박스의 대각선 길이를 sqrt(2)로 나눈 값과 같습니다.

참고: 이 방식은 박스의 크기 중 어느 한쪽(너비나 높이)이 특별히 우세하지 않고, 박스 크기의 백분율이 필요한 경우에 SVG 등에서 너비와 높이를 평균 내는 방법입니다. 정사각형 박스의 경우 너비와 높이가 동일하므로 이 값이 너비/높이와 같습니다.

2. 박스 모델 및 플로트 동작과의 관계

플로트 외부에 인라인 흐름 콘텐츠를 감싸기 하는 경계는 셰이프를 사용하여 정의할 수 있지만, 실제 박스 모델은 변경되지 않습니다. 요소에 마진, 테두리 또는 패딩이 지정되어 있다면, [CSS3BOX] 모듈에 따라 계산 및 렌더링됩니다. 또한 플로트의 위치 지정과 쌓임(stacking)은 셰이프로 float area를 정의해도 영향을 받지 않습니다.

셰이프를 이용해 float area를 정의하면, 셰이프는 플로트의 margin box로 잘려집니다. 즉, 셰이프는 float area를 줄일 수만 있고, 늘릴 수는 없습니다. 축소된 float area는 플로트의 영향을 받는 일부 라인 박스에 아무런 영향을 주지 않을 수 있습니다. 셰이프가 영역을 감싸지 않는 경우에도, 셰이프의 가장자리는 float area 정의에 사용됩니다.

셰이프로 정의된 float area는 모든 방향에서 일반 float area를 축소할 수 있지만, 그렇다고 해서 콘텐츠가 플로트의 양쪽을 감싸는 것은 아닙니다. shape-outside가 지정된 왼쪽 플로트는 여전히 오른쪽에서만 감싸기가 가능하며, 오른쪽 플로트는 왼쪽에서만 감싸기가 가능합니다.

다음 예제에서는 좌측 및 우측 플로트 img 요소가 shape-outside 속성을 사용하여 삼각형 셰이프를 지정합니다.

<img class="left" src="hand.svg"/>
<img class="right" src="hand.svg"/>
<p>
  Sometimes a web page’s text content appears to be
  funneling your attention towards a spot on the page
  to drive you to follow a particular link. Sometimes
  you don’t notice.
</p>

<style type="text/css">
  .left {
    shape-outside: polygon(0 0, 100% 100%, 0 100%);
    float: left;
    width: 40%;
    height: 12ex;
    transform: scaleX(-1);
  }

  .right {
    shape-outside: polygon(100% 0, 100% 100%, 0 100%);
    float: right;
    width: 40%;
    height: 12ex;
  }

  p {
    text-align: center;
  }
</style>

Using the shape-outside property with floats

셰이프는 플로트의 margin box로 잘려지므로, 위의 왼쪽 플로트에 이 셰이프를 추가해도 동일한 렌더링 결과가 나옵니다.

shape-outside: polygon(0 0, 500% 500%, 0 500%);

어떤 셰이프가 영역을 감싸지 않더라도, 해당 셰이프의 가장자리는 float area에 기여합니다.

이 inset 셰이프는 기준 박스의 중간 지점에 위치한 수직선이며, 이 중간선이 콘텐츠를 감싸는 float area의 가장자리로 사용됩니다.

shape-outside: inset(0% 50% 0% 50%);

inset 값들의 합이 너비보다 커질 경우, CSS Backgrounds 3 § 4.5 곡선 겹침 규칙에 따라 직사각형의 가장자리가 결정됩니다. 이 셰이프는 기준 박스의 왼쪽에서 25% 떨어진 수직 가장자리를 생성합니다.

shape-outside: inset(0% 150% 50% 0%);

셰이프가 수평선만 있을 경우, 이는 빈 float area가 되어 감싸기에 영향을 주지 않습니다. 이 예시에서는 shape-margin이 반드시 0px이어야 하며 (그렇지 않으면 선이 영역을 감싸게 됩니다).

shape-outside: inset(50% 0% 0% 50%);
shape-margin: 0px;

shape-outside 속성은 float area의 왼쪽과 오른쪽 모두에 열린 영역을 만들 수 있습니다. 이 경우에도 콘텐츠는 플로트 한쪽에서만 감싸기가 이루어집니다. 그림에서 셰이프는 파란색, 셰이프 외부의 콘텐츠 영역은 보라색으로 렌더링됩니다.

shape-outside: polygon(50px 0px, 100px 100px, 0px 100px);

wrapping around right side of a left-float float area

다음 스타일링은 플로트의 콘텐츠 영역보다 훨씬 작은 셰이프를 만들고, 플로트에 margin-top을 추가합니다. 그림에서 셰이프는 파란색, 셰이프 외부의 콘텐츠 영역은 보라색, 플로트 박스의 margin 영역은 노란색으로 렌더링됩니다. 인라인 콘텐츠는 셰이프만을 감싸기하고, 그 외에는 플로트 margin box 위에 겹쳐집니다.

.float-left {
  shape-outside: polygon(0% 50%, 50% 100%, 0 100%);
  float: left;
  width: 100px;
  height: 100px;
  margin-top: 20px;
}

Adding margin-top to a float with a small shape-outside

다음 그림은 이런 플로트 두 개가 나란히 쌓였을 때의 결과 예시를 보여줍니다. 플로트의 위치는 float area가 아닌 margin box를 기준으로 정렬된다는 점에 유의하세요.

Stacking two floats with a small shape-outside

3. 기본 셰이프

<basic-shape> 타입은 기본 셰이프 함수로 지정할 수 있습니다. 이 구문을 사용하여 셰이프를 정의할 때, reference box<basic-shape> 값을 사용하는 각 속성에 의해 정의됩니다. 셰이프의 좌표계는 reference box의 좌상단을 기준으로 하며, x축은 오른쪽으로, y축은 아래쪽으로 펼쳐집니다. 퍼센트로 표현된 모든 길이는 reference box의 실제 크기에서 계산됩니다.

3.1. 지원되는 셰이프

<basic-shape> 함수는 다음과 같습니다:

<inset()> = inset(
  <length-percentage>{1,4}
  [ round <'border-radius'> ]?
)

<xywh()> = xywh(
  <length-percentage>{2} <length-percentage [0,∞]>{2}
  [ round <'border-radius'> ]?
)

<rect()> = rect(
  [ <length-percentage> | auto ]{4}
  [ round <'border-radius'> ]?
)

<basic-shape-rect> = <inset()> | <rect()> | <xywh()>

<circle()> = circle(
  <radial-size>?
  [ at <position> ]?
)

<ellipse()> = ellipse(
  <radial-size>?
  [ at <position> ]?
)

<polygon()> = polygon(
  <'fill-rule'>? 
  [ round <length> ]? ,
  [<length-percentage> <length-percentage>]#
)

<path()> = path(
  <'fill-rule'>? ,
  <string>
)

<shape()> = shape(
  <'fill-rule'>?
  from <position>
  <shape-command>#
)
inset()
inset은 reference box의 각 가장자리로부터의 inset 값으로 사각형을 정의합니다.

네 개 미만의 <length-percentage> 값이 제공되면, 생략된 값은 margin 축약형과 동일한 방식으로 기본값이 지정됩니다: 두 번째 또는 세 번째 값이 생략된 경우 첫 번째 값으로, 네 번째 값이 생략된 경우 두 번째 값으로 처리됩니다.

네 개의 <length-percentage> 값은 각각 사각형의 위, 오른쪽, 아래, 왼쪽 가장자리 위치를 reference box의 해당 가장자리에서의 inset 값으로 정의합니다.

각 방향의 inset 합이 사용된 치수보다 크면 (예: 왼쪽과 오른쪽 inset이 각각 75%인 경우) CSS Backgrounds 3 § 4.5 곡선 겹침 규칙을 사용하여 inset 효과가 100%가 되도록 비례적으로 축소합니다.

예를 들어, inset(75% 0 50% 0)을 지정하면 위+아래 가장자리 합이 reference box의 높이의 125%가 됩니다. 이 값들은 합이 100%가 되도록 비례적으로 축소되어, inset(60% 0 40% 0)과 동일하게 됩니다.

선택적인 <'border-radius'> 인자는 border-radius 축약 구문을 사용하여 사각형 모서리를 둥글게 만듭니다.

테스트
xywh()
xywh는 reference box의 위와 왼쪽 가장자리로부터의 오프셋과 너비, 높이로 사각형을 정의합니다.

네 개의 <length-percentage> 값은 각각, reference box의 왼쪽에서의 inset, reference box의 위쪽에서의 inset, 사각형의 너비, 사각형의 높이를 의미합니다.

참고: 이 구문은 SVG의 viewBox 속성에서 영감을 받은 것입니다.

선택적인 <'border-radius'> 인자는 border-radius 축약 구문을 사용하여 사각형 모서리를 둥글게 만듭니다.

테스트
rect() =
rect는 reference box의 위와 왼쪽 가장자리로부터의 inset 값으로 사각형을 정의합니다.

네 개의 <length-percentage> 값은 각각 위, 오른쪽, 아래, 왼쪽 가장자리 위치를 첫 번째와 세 번째 값은 reference box의 위쪽에서, 두 번째와 네 번째 값은 reference box의 왼쪽에서의 inset 값으로 정의합니다.

auto 값은 박스의 해당 가장자리가 reference box의 해당 가장자리에 일치하게 하며, 첫 번째(위) 또는 네 번째(왼쪽) 값에서는 0%와, 두 번째(오른쪽) 또는 세 번째(아래) 값에서는 100%와 동일합니다.

두 번째(오른쪽)와 세 번째(아래) 값은 네 번째(왼쪽)와 두 번째(위) 값에 의해 바닥(floor) 처리됩니다.

예를 들어, rect(10px 0 0 20px)을 지정하면 아래쪽 가장자리가 위쪽 가장자리보다 높고, 오른쪽 가장자리가 왼쪽 가장자리보다 왼쪽에 위치하므로, 둘 다 교차하지 않도록 보정되어, rect(10px 20px 10px 20px)과 동일하게 처리됩니다.

참고: 이 구문은 rect() 함수(오직 clip 속성에서만 사용됨)와 비슷하지만, 완전히 동일하지는 않습니다.

선택적인 <'border-radius'> 인자는 border-radius 축약 구문을 사용하여 사각형 모서리를 둥글게 만듭니다.)

테스트
circle()
  • <radial-size> 인자는 원의 반지름을 정의합니다. gradient box를 참조하는 대신, 값은 reference box 기준으로 해석됩니다.

  • 두 개의 <length-percentage> 값은 유효하지 않습니다.

    <position> 인자는 원의 중심을 정의합니다. 별도로 지정하지 않으면, 생략 시 center가 기본값입니다.

테스트
ellipse()
  • <radial-size> 인자는 타원의 수평 및 수직 반지름을 정의합니다. gradient box를 참조하는 대신, 값은 reference box 기준으로 해석됩니다.

  • <position> 인자는 타원의 중심을 정의합니다. 별도로 지정하지 않으면, 생략 시 center가 기본값입니다.

테스트
polygon()
  • <'fill-rule'>은 내부를 결정할 때 사용하는 채우기 규칙을 지정합니다. 생략 시 nonzero가 기본값입니다.

  • 선택적으로 round 키워드 뒤에 <length>를 지정하면 다각형 꼭짓점마다 라운딩을 정의합니다. 이 길이는 각 꼭짓점을 기준으로 더 작은 각의 이등분선 위에 중심이 위치하고, 두 변과 접하는 원의 반지름입니다.

    rounding concave and convex polygon vertices
    오목/볼록 꼭짓점 모두 라운딩 처리된 다각형 예시.

    어떤 선분의 절반 이상을 라운딩하지 않도록, 각 꼭짓점의 라운딩은 개별적으로 클램프(clamp) 처리되어야 하며, 반지름은 각 꼭짓점 선분에서 tan(angle/2) segment / 2 중 더 작은 값보다 커질 수 없습니다.

    visualization of clamp formula
    이 다이어그램은 클램프 계산식의 의도를 보여줍니다.
  • <length-percentage> 쌍은 다각형의 꼭짓점을 지정하며, reference box의 왼쪽과 위쪽 가장자리로부터의 수평 및 수직 오프셋입니다.

UA는 마지막 꼭짓점과 첫 번째 꼭짓점을 연결하여 다각형을 닫아야 합니다.

테스트
path()
  • <'fill-rule'>은 내부를 결정할 때 사용하는 채우기 규칙을 지정합니다. 생략 시 nonzero가 기본값이며, 함수가 SVG 셰이프 등에서 fill-rule 속성이 의미가 있는 컨텍스트인 경우에는 생략 값이 해당 속성의 계산값을 사용합니다.

  • <string>SVG Path 데이터 문자열을 나타냅니다. Path 데이터 문자열이 SVG 1.1의 문법 및 파싱 규칙을 따르지 않거나, 문법을 따르더라도 빈 경로를 정의하는 경우, 전체 path()invalid가 됩니다.

    초기 위치는 path 문자열에서 첫 번째 “move to” 인자에 의해 정의됩니다. 초기 방향은 SVG 1.1을 따릅니다.

UA는 path를 암묵적으로 closepath 명령("z" 또는 "Z")으로 닫아야 하며, 문자열에 명시되어 있지 않더라도 닫힌 루프가 필요한 속성(예: shape-outsideclip-path)에서는 반드시 닫아야 합니다.

테스트
shape()
shape() 함수 참고.
테스트

    3.1.1. shape() 함수

    path() 함수는 SVG 경로 문법을 재사용하여 보다 전문화된 도형 함수보다 임의의 도형을 정의할 수 있게 해주지만, 경로를 하나의 문자열로 작성해야 하며 (예를 들어 var()로 경로를 부분적으로 구성하는 것과 호환되지 않음), SVG에서 유래한 여러 제한점도 함께 물려받게 됩니다. 예를 들어, 암묵적으로 px 단위만 허용하는 것 등이 있습니다.

    shape() 함수는 path()에서 사용하는 명령과 대략적으로 동등한 명령 집합을 사용하지만, 보다 표준적인 CSS 문법으로 작성하며, 추가 단위 및 수학 함수 등 전체 CSS 기능을 사용할 수 있습니다. shape()에서 사용되는 명령들은 렌더링 시 동적으로 경로 세그먼트로 변환됩니다. 예를 들어, 렌더된 clip-path를 계산할 때입니다.

    이런 점에서 shape()path()의 상위 집합입니다. path()는 쉽게 shape()로 변환할 수 있지만, shape()를 다시 path()나 SVG로 변환하려면 CSS 환경(예: 현재 CSS 사용자 정의 변수 값, em 단위의 현재 폰트 크기 등)에 대한 정보가 필요합니다.

    <'fill-rule'>path()에서 동일한 인자와 동일하게 해석됩니다.

    나머지 인자들은 함수가 나타내는 SVG 경로와 동일한 경로 데이터 명령의 목록을 정의합니다.

    from <coordinate-pair>는 첫 번째 shape-command의 시작점을 나타냅니다. 경로 데이터 명령 목록에 초기 절대 moveto를 추가합니다.

    일련의 <shape-command>들은 추가 경로 데이터 명령을 나타냅니다. 각 명령의 시작점은 이전 명령의 끝점입니다.

    <shape-command> = <move-command> | <line-command> | close |
                      <horizontal-line-command> | <vertical-line-command> |
                      <curve-command> | <smooth-command> | <arc-command>
    
    <move-command> = move <command-end-point>
    <line-command> = line <command-end-point>
    <horizontal-line-command> = hline
            [ to [ <length-percentage> | left | center | right | x-start | x-end ]
            | by <length-percentage> ]
    <vertical-line-command> = vline
            [ to [ <length-percentage> | top | center | bottom | y-start | y-end ]
            | by <length-percentage> ]
    <curve-command> = curve
            [ [ to <position> with <control-point> [ / <control-point> ]? ]
            | [ by <coordinate-pair> with <relative-control-point> [ / <relative-control-point> ]? ] ]
    <smooth-command> = smooth
            [ [ to <position> [ with <control-point> ]? ]
            | [ by <coordinate-pair> [ with <relative-control-point> ]? ] ]
    <arc-command> = arc <command-end-point>
                [ [ of <length-percentage>{1,2} ]
                  && <arc-sweep>? && <arc-size>? && [rotate <angle>]? ]
    
    <command-end-point> = [ to <position> | by <coordinate-pair> ]
    <control-point> = [ <position> | <relative-control-point> ]
    <relative-control-point> = <coordinate-pair> [ from [ start | end | origin ] ]?
    <coordinate-pair> = <length-percentage>{2}
    <arc-sweep> = cw | ccw
    <arc-size> = large | small
    
    <coordinate-pair> = <length-percentage>{2}
    좌표 쌍을 정의하며, 각각 지정된 기준점에서 오른쪽 및 아래쪽으로의 오프셋을 나타냅니다. 백분율은 reference box의 너비 또는 높이를 기준으로 각각 계산됩니다.
    <command-end-point> = [ to <position> | by <coordinate-pair> ]
    모든 명령은 "절대" 또는 "상대" 좌표로 지정할 수 있으며, by 또는 to 구성요소에 따라 결정됩니다. to는 해당 명령 내의 <coordinate-pair>들이 reference box의 좌상단 기준으로 상대적임을 나타내며, by<coordinate-pair>들이 명령의 시작점을 기준으로 상대적임을 나타냅니다.

    <relative-control-point>는 곡선 제어점에 대해 byto가 어떻게 해석되는지 정의하며, <horizontal-line-command><vertical-line-command>는 각각 수평 및 수직선에 대해 byto가 어떻게 해석되는지 정의합니다.

    to가 사용될 때, 좌표는 <position>으로도 지정할 수 있으며, <coordinate-pair> 대신 사용할 수 있습니다.

    참고: 두 경우 모두 <percentage> 값은 <coordinate-pair> 내에서 항상 reference box의 크기를 기준으로 계산됩니다.

    <move-command> = move <command-end-point>
    moveto 명령을 경로 데이터 명령 목록에 추가하며, 끝점은 <coordinate-pair>로 지정됩니다.

    이 명령은 아무 것도 그리지 않고, 다음 명령을 위해 "펜을 이동"만 합니다.

    참고: 이것은 close 명령을 위한 새로운 서브패스를 시작합니다.

    <line-command> = line <command-end-point>
    lineto 명령을 경로 데이터 명령 목록에 추가하며, 끝점은 <coordinate-pair>로 지정됩니다.

    이 명령은 시작점에서 끝점까지 직선을 그립니다.

    <horizontal-line-command> = hline [ to [ <length-percentage> | left | center | right | x-start | x-end ] | by <length-percentage> ]
    수평 lineto 명령을 경로 데이터 명령 목록에 추가합니다.

    이는 line 명령과 동일하며, <length-percentage><coordinate-pair>의 수평 성분으로 지정됩니다. <position>의 수평 성분을 <length-percentage> 대신 지정하면 (left, center, right, x-start, x-end), 해당 <position>까지 직선을 그리며, <position>의 수직 성분은 시작점과 동일하게 유지됩니다.

    <vertical-line-command> = vline [ to [ <length-percentage> | top | center | bottom | y-start | y-end ] | by <length-percentage> ]
    수직 lineto 명령을 경로 데이터 명령 목록에 추가합니다.

    이는 line 명령과 동일하며, <length-percentage><coordinate-pair>의 수직 성분으로 지정됩니다. <position>의 수직 성분을 지정하면 (top, center, bottom, y-start, y-end) <length-percentage> 대신 사용하면, 해당 <position>까지 직선을 그리며, <position>의 수평 성분은 시작점과 동일하게 유지됩니다.

    <curve-command> = curve [ [ to <position> with <control-point> [ / <control-point> ]? ] | [ by <coordinate-pair> with <relative-control-point> [ / <relative-control-point> ]? ] ]
    베지어 곡선 명령을 경로 데이터 명령 목록에 추가하며, 끝점은 <position> (to 키워드 뒤), 또는 <coordinate-pair> (by 키워드 뒤)로 지정됩니다.

    with 구성요소는 곡선의 제어점을 지정합니다: 하나의 <control-point> 또는 <relative-control-point>가 제공되면 이차 곡선을 지정하며, 두 개의 <control-point> 또는 <relative-control-point>이 제공되면 삼차 곡선을 지정합니다.

    <smooth-command> = smooth [ [ to <position> [with <control-point> ]? ] | [ by <coordinate-pair> [ with <relative-control-point> ]? ] ]
    부드러운 베지어 곡선 명령을 경로 데이터 명령 목록에 추가하며, 끝점은 <position> (to 키워드 뒤) 또는 <coordinate-pair> (by 키워드 뒤)로 지정됩니다. with 구성요소는 곡선의 제어점을 지정합니다: 생략되면 부드러운 이차 곡선을, 제공되면 부드러운 삼차 곡선을 지정합니다.

    참고: smooth 명령은 curve 명령과 동일하며, 첫 번째 제어점은 이전 곡선의 두 번째 제어점을 시작점을 중심으로 반사시킨 위치로 자동 지정합니다. 또는 이전 경로 데이터 명령이 곡선이 아니면 시작점이 됩니다. 이 방식은 이전 명령과 G1 연속성을 보장하여, 곡선이 이전 명령에서 부드럽게 이어지는 것처럼 보이게 하며, 갑작스러운 방향 변화를 방지합니다.

    <control-point> = [ <position> | <relative-control-point> ]
    이차 또는 삼차 베지어 곡선에 제어점을 제공합니다.
    <relative-control-point> = <coordinate-pair> [ from [ start | end | origin ] ]?
    이차 또는 삼차 베지어 곡선에 제어점을 제공합니다. from 키워드 뒤에 start, end, origin이 지정되면, 주어진 <coordinate-pair>는 각각 명령의 시작점, 명령의 끝점, reference box 기준으로 상대적입니다. 해당 구성요소가 제공되지 않으면 <coordinate-pair>는 세그먼트의 시작점을 기준으로 상대적입니다.
    <arc-command> = arc <command-end-point> [of <length-percentage>{1,2}] && <arc-sweep>? && <arc-size>? && rotate <angle>? ]
    타원 호 명령을 경로 데이터 명령 목록에 추가하며, 끝점은 <command-end-point>로 지정됩니다.

    of 구성요소는 호가 그려질 타원의 크기를 지정합니다. 첫 번째 <length-percentage>는 타원의 수평 반지름을, 두 번째는 수직 반지름을 나타냅니다. <coordinate-pair>와 마찬가지로, <percentage> 값은 reference box의 너비 또는 높이에 맞춰 계산됩니다.

    하나의 <length-percentage>만 제공되는 경우, 두 반지름 모두 해당 값이 사용됩니다. 이때 <percentage> 값은 direction-agnostic size를 기준으로 계산되며, reference box의 크기와 유사합니다 (circle() 함수 참고).

    SVG에서는 타원 반지름의 오류 처리가 있습니다:
    • 끝점이 시작점과 동일한 경우, 명령은 아무 것도 하지 않습니다.

    • 반지름 중 하나가 0이면, 명령은 끝점까지 <line-command>와 동일합니다.

    • 반지름 중 하나가 음수이면, 절대값이 사용됩니다.

    • 반지름이 회전된 <angle> 이후 시작점과 끝점을 모두 교차하도록 충분히 크지 않으면, 타원이 교차할 수 있을 때까지 균일하게 확대됩니다.

    지정된 반지름에 의해 묘사된 타원은 기본적으로 축에 정렬되어 있지만, <angle>을 지정하여 회전할 수 있습니다. rotate() 변환 함수와 비슷하게, 양수 각도는 시계 방향 회전을, 음수 각도는 반시계 방향 회전을 의미합니다. 생략 시 기본값은 0deg입니다.

    끝점, 반지름, 각도가 함께 주어지면, 보통 두 개의 타원과 각 타원에서 두 방향으로 그릴 수 있으므로 총 네 개의 호가 가능합니다. <arc-sweep><arc-size> 구성요소가 원하는 호를 지정합니다:

    • <arc-sweep>cw 또는 ccw일 수 있으며, 각각 중심에서 타원을 따라 시계 방향 또는 반시계 방향으로 그려지는 호를 지정합니다. 생략 시 기본값은 ccw입니다.

      참고: SVG arc 명령에서 cw는 sweep flag 값 1에, ccw는 값 0에 해당합니다.

    • <arc-size>large 또는 small일 수 있으며, 두 개의 가능 호 중 더 크거나 더 작은 호를 각각 선택합니다. 생략 시 기본값은 small입니다.

      참고: SVG arc 명령에서 large는 large flag 값 1에, small은 값 0에 해당합니다.

      참고: 시작점과 끝점이 타원의 정확히 반대쪽에 있을 경우, 두 개의 호 모두 크기가 같고, 타원도 하나뿐입니다. 이 경우 <arc-sweep>가 두 개의 호 중 어느 것을 선택할지 구분하며, <arc-size>는 영향이 없습니다.

    a depiction of four possible arcs given a start and end point
    시작점과 끝점에 대해 선택 가능한 두 개의 타원과 네 개의 호를 묘사한 그림
    close
    closepath 명령을 경로 데이터 명령 목록에 추가합니다.

    참고: 이는 line 명령과 유사하며, 끝점이 서브패스의 시작점으로 지정됩니다. 원시 shape를 지정할 때는 동일하지만, 경로에 테두리를 적용할 경우, close 명령의 끝점이 서브패스 시작점과 부드럽게 연결되어, 선의 연결과 끝부분의 렌더링 방식에 영향을 줍니다.

    3.1.1.1. shape()를 사용하여 반응형, 매개변수화된 말풍선 만들기
    shape() 함수는 확장형이 아닌 반응형 도형을 만들 수 있게 해줍니다. polygon() 도형도 반응형이지만, 복잡한 곡선이 아니라 단순한 둥근 모서리만 지원합니다.

    예시로, 다음과 같은 말풍선을 만들어 보겠습니다:

    A speech bubble shape

    이 도형을 clip-path로 사용하려면 path() 함수를 사용할 수 있습니다:

    .bubble { clip-path: path("m 5 0 H 95 Q 100 0 100 5 V 92 Q 100 97 95 97 H 70 l -2 3 l -2 -3 H 5 Q 0 97 0 92 V 5 Q 0 0 5 0") };
    

    이 경로는 쉽게 크기를 조정할 수 있지만, 크기가 작아질 때 풍선의 화살표와 모서리가 보이지 않게 되는 등 원하는 결과를 얻기 어렵습니다:

    scled-down speech bubble shape

    이 도형을 shape() 함수로 만들기 위해 path 함수에서 사용된 픽셀 값을 모두 백분율로 변환해보겠습니다. shape() 함수는 from으로 시작하는 점에 유의하세요:

    .bubble { clip-path: shape(  from 5% 0%,
                  hline to 95%,
                  curve to 100% 5% with 100% 0%,
                  vline to 92%,
                  curve to 95% 97% with 100% 97%,
                  hline to 70%,
                  line by -2% 3%,
                  line by -2% -3%,
                  hline to 5%,
                  curve to 0% 92% with 0% 97%,
                  vline to 5%,
                  curve to 5% 0% with 0% 0%); }
    

    이 경로를 반응형으로 만들기 위해, 즉 크기 변화에 잘 대응하도록 일부 단위를 px 값으로 변환합니다. 특히 곡선과 화살표 부분을 px로 지정합니다:

    .bubble { clip-path: shape(  from 5px 0%,
                  hline to calc(100% - 5px),
                  curve to 100% 5px with 100% 0%,
                  vline to calc(100% - 8px),
                  curve to calc(100% - 5px) calc(100% - 3px) with 100% calc(100% - 3px),
                  hline to 70%,
                  line by -2px 3px,
                  line by -2px -3px,
                  hline to 5px,
                  curve to 0% calc(100% - 8px) with 0% calc(100% - 3px),
                  vline to 5px,
                  curve to 5px 0% with 0% 0%); }
    

    clip-path으로 적용하면 다음과 같이 보입니다:

    A speech bubble shape, using clip-path

    전체 말풍선은 reference box에 맞춰 크기가 조정되며, 곡선과 화살표는 일정하게 유지됩니다.

    shape() 함수는 CSS 단위를 사용하므로, 일부 모서리를 position 값으로 바꿀 수도 있습니다:

    .bubble { clip-path: shape(from 5px 0,
                  hline to calc(100% - 5px),
                  curve to right 5px with right top,
                  vline to calc(100% - 8px),
                  curve to calc(100% - 5px) calc(100% - 3px) with right calc(100% - 3px),
                  hline to 70%,
                  line by -2px 3px,
                  line by -2px -3px,
                  hline to 5px,
                  curve to left calc(100% - 8px) with left calc(100% - 3px),
                  vline to 5px,
                  curve to 5px top with left top); }
    

    shape()의 또 다른 장점은 CSS 속성과 함께 사용할 수 있다는 점입니다. 이 경우 화살표와 반지름을 매개변수화할 수 있습니다:

    :root {
      --radius: 5px;
      --arrow-length: 3px;
      --arrow-half-width: 2px;
      --arrow-position: 70%;
      --arrow-bottom-offset: calc(100% - var(--radius) - var(--arrow-length));
    }
    
    .bubble {
      animation: bubble 100ms;
      clip-path: shape(from var(---radius) top,
        hline to calc(100% - var(---radius)),
        curve to right var(---radius) with right top,
        vline to var(---arrow-bottom-offset),
        curve to calc(100% - var(---radius)) calc(100% - var(---arrow-length))
                  with right calc(100% - var(---arrow-length)),
        hline to var(---arrow-position),
        line by var(---arrow-half-width) var(---arrow-length),
        line by var(---arrow-half-width) calc(0px - var(---arrow-length)),
        hline to var(---radius),
        curve to left var(---arrow-bottom-offset) with left calc(100% - var(---arrow-length)),
        vline to var(---radius),
        curve to var(---radius) top with left top); }
    
    3.1.1.2. shape() 함수의 보간(Interpolation)

    shape()path() 함수는 경로 데이터 명령 목록의 길이가 같고, 명령의 순서가 같으며, path() 함수의 첫 번째 명령이 shape() 함수의 초기 <coordinate-pair>와 보간될 때, 서로 보간(interpolated)될 수 있습니다.

    참고: path() 함수의 첫 번째 명령은 반드시 move 명령입니다. 자세한 내용은 moveTo를 참조하세요.

    시작 값과 끝 값이 모두 path() 함수일 경우, 보간 결과는 path() 함수가 됩니다. 그렇지 않은 경우에는 shape() 함수가 됩니다. 두 경우 모두, 보간 결과는 동일한 경로 데이터 명령 목록을 나타내야 하며, 각 명령의 수치 성분은 시작 목록과 끝 목록의 대응 성분 간에서 보간됩니다.

    이때, 명령은 같은 명령어 키워드를 사용하고, 동일한 <by-to> 키워드를 사용할 때 "같은 것"으로 간주합니다. curvesmooth의 경우, 제어점의 개수도 같아야 합니다.

    arc 명령에서 시작과 끝의 <arc-sweep>이 다르면, 보간 결과는 0과 1 사이의 진행 값에 대해 항상 cw를 사용합니다. <arc-size> 키워드가 다르면, 보간 결과는 0과 1 사이의 진행 값에 대해 항상 large를 사용합니다.

    참고: arc 키워드의 보간 규칙은 기존 SVG path 보간 규칙과 일치하도록 설계되었습니다.

    3.2. 기본 도형의 계산된 값

    <basic-shape> 함수의 값은 아래 예외를 제외하고 명시된 대로 계산됩니다:

    테스트

    3.3. 기본 도형의 직렬화

    <basic-shape> 함수들을 직렬화하려면, 각 함수의 별도 문법에 따라 직렬화하며, 문법에 작성된 순서대로 직렬화합니다. 공백으로 구분된 토큰은 하나의 공백으로 연결하고, 직렬화된 쉼표 뒤에는 하나의 공백을 붙입니다. 계산된 값을 직렬화할 때, 구성 값들은 계산된 값이며, 의미에 변화가 없다면 생략할 수 있습니다.

    명시된 값 기준으로 shape 함수 직렬화는 비교적 단순하므로, 계산된 값 직렬화의 예시를 아래에 제시합니다. circle() 표기법이 shape-outside에서 사용된 경우입니다:

    테스트

    3.4. 기본 도형의 보간

    한 기본 도형에서 다른 도형으로 보간할 때, 아래의 규칙을 적용합니다. shape 함수의 값은 계산된 값 기준으로 보간됩니다. 목록 값들은 가능하다면 길이, 백분율, calc 단위로 보간됩니다. 목록 값이 해당 타입이 아니지만 동일하다면 (예: 두 목록에서 같은 위치에 nonzero가 있을 경우) 해당 값도 보간됩니다.

    테스트

    4. 이미지로부터 도형 만들기

    도형을 정의하는 또 다른 방법은 소스 <image>를 지정하여, 알파 채널을 이용해 도형을 계산하는 것입니다. 도형은 경로 또는 경로 집합으로 계산되며, 지정된 이미지의 불투명도가 shape-image-threshold 값보다 큰 영역을 감싸는 형태가 됩니다. 지정된 임계값보다 높은 알파 값을 가진 픽셀이 전혀 없으면, 빈 float 영역이 생성되어 래핑에 영향을 주지 않습니다. shape-image-threshold가 지정되지 않은 경우, 초기 값은 0.0으로 간주됩니다.

    이미지는 대체(replaced) 요소처럼 크기와 위치가 지정되며, 지정된 너비와 높이가 요소의 사용된 콘텐츠 박스 크기와 동일하게 맞춰집니다.

    애니메이션 래스터 이미지 포맷(예: GIF)의 경우, 애니메이션 시퀀스의 첫 번째 프레임이 사용됩니다.

    이미지가 단락 왼쪽에 플로팅되어 있습니다. 이미지는 투명 배경 위에 3D 버전의 CSS 로고를 보여줍니다. 로고는 알파 채널로 그림자가 있습니다.

    이미지는 float areashape-outside 속성으로 정의합니다.

    
      <p>
        <img id="CSSlogo" src="CSS-logo1s.png"/>
        blah blah blah blah...
      </p>
    
      <style>
        #CSSlogo {
          float: left;
          shape-outside: attr(src url);
          shape-image-threshold: 0.1;
        }
      </style>
    

    shape-outside 속성은 img 요소의 src 속성에서 url을 재사용합니다.

    이미지를 표시하면서 float area에는 다른 이미지를 사용할 수도 있습니다.

    아래 그림에서, 알파 채널 임계값은 CSS 로고의 점선으로 표시된 경계로 나타납니다.

    단락의 줄이 어디서 시작하는지 3가지 방법으로 조정할 수 있습니다:

    1. 이미지의 알파 채널 수정
    2. shape-image-threshold 속성 값 변경
    3. shape-margin 속성 값 변경(예시 8 참고)
    A float shape around an image using its alpha-channel
    알파 채널을 이용한 이미지 주변 float 도형 예시
    테스트

    5. 박스 값으로부터 도형 만들기

    도형은 CSS 박스 모델의 엣지를 참조하여 정의할 수 있습니다. 이러한 엣지에는 사용된 border-radius 값에서 유도된 border-radius 곡률 [CSS3BG] 등이 포함됩니다. <shape-box> 값은 <visual-box> 값을 확장하여 margin-box를 포함합니다. 그 문법은 다음과 같습니다:

    <shape-box> = <visual-box> | margin-box
    

    각 값의 정의는 다음과 같습니다:

    margin-box 값은 외부 마진 엣지에 의해 둘러싸인 도형을 정의합니다. 이 도형의 코너 반지름은 해당 border-radius 및 margin 값에 의해 결정됩니다. border-radius/margin의 비율이 1 이상이거나, margin이 음수 또는 0이면, margin-box의 코너 반지름은 max(border-radius + margin, 0)입니다. border-radius/margin의 비율이 1 미만이고, margin이 양수인 경우, margin-box의 코너 반지름은 border-radius + margin * (1 + (ratio-1)^3)입니다.

    border-box 값은 외부 보더 엣지에 의해 둘러싸인 도형을 정의합니다. 이 도형은 보더 외부에 대한 일반적인 border-radius 모양 규칙을 모두 따릅니다.

    padding-box 값은 외부 패딩 엣지에 의해 둘러싸인 도형을 정의합니다. 이 도형은 보더 내부에 대한 일반적인 border-radius 모양 규칙을 모두 따릅니다.

    content-box 값은 외부 콘텐츠 엣지에 의해 둘러싸인 도형을 정의합니다. 이 박스의 각 코너 반지름은 0과 border-radius - border-width - padding 중 더 큰 값입니다.

    아래 100px 정사각형에 10px 패딩, 보더, 마진이 있을 때, 박스 값은 다음 도형을 정의합니다:

    Colored boxes representing simple box edges
    단순 CSS 박스 모델 엣지

    그리고 동일한 100px 정사각형에 대해, 다음과 같은 border, padding, margin 속성을 사용한 좀 더 복잡한 예시에도 동일한 정의가 적용됩니다:

    
      border-radius: 20px 20px 20px 40px;
      border-width: 30px 10px 20px 10px;
      padding: 10px 20px 10px 10px;
      margin: 20px 10px 10px 10px;
    
    Colored boxes representing complex box edges
    복잡한 CSS 박스 모델 엣지

    일반적인 float 래핑과 margin-box 값으로 정의된 도형을 따라 래핑하는 것의 차이는 margin-box 도형이 코너 모양을 포함한다는 점입니다. 10px 패딩, 보더, 마진을 가진 100px 정사각형에 border-radius가 60px인 경우를 생각해봅시다. 이를 왼쪽 float로 만들면, 콘텐츠는 일반적으로 다음과 같이 래핑됩니다:

    Text wrapping around float with no shape
    일반 float 래핑

    float에 margin-box 도형을 추가하면, 콘텐츠가 둥근 margin-box 코너를 따라 래핑됩니다.

    
      shape-outside: margin-box;
    
    Text wrapping around float with margin-box shape
    margin-box가 적용된 float 래핑
    테스트

    6. 도형 선언

    도형은 shape-outside 속성으로 선언하며, shape-margin 속성으로 수정할 수 있습니다. shape-outsideshape-margin 속성에 의해 정의된 도형은 float 요소의 float area의 기하학적 구조를 변경합니다.

    6.1. Float 영역 도형: shape-outside 속성

    이름: shape-outside
    값: none | [ <basic-shape> || <shape-box> ] | <image>
    초기값: none
    적용 대상: float 요소 및 initial letter box
    상속 여부: 아니오
    백분율: 해당 없음
    계산된 값: 정의된 대로 <basic-shape> (추가로 <shape-box>가 있다면 뒤에 붙음); 그렇지 않으면 계산된 <image>; 아니면 명시된 키워드
    정규 순서: 문법에 따름
    애니메이션 타입: 정의된 대로 <basic-shape>일 경우, 아니면 불연속

    이 속성의 값의 의미는 다음과 같습니다:

    none
    float area에 아무런 영향을 주지 않습니다.
    <shape-box>
    이 값들 중 하나만 지정되면, 도형은 margin-box, border-box, padding-box 또는 content-box 중 하나의 박스를 기반으로 계산됩니다. 각 박스는 border-radius의 곡률을 포함하여 정의되며, background-clip과 유사하게 동작합니다 [CSS3BG].
    <basic-shape>
    도형은 <basic-shape> 함수 중 하나를 기반으로 계산됩니다. <shape-box>가 함께 제공되면, 이는 reference box를 정의합니다. <shape-box>가 제공되지 않으면, reference box는 기본적으로 margin-box로 지정됩니다.
    <image>
    도형은 지정된 <image>의 알파 채널을 기반으로 추출 및 계산됩니다. shape-image-threshold에 의해 정의됩니다.

    사용자 에이전트는 CORS 프로토콜 [FETCH] 명세에 따라 shape-outside 값의 모든 URL을 처리해야 합니다. 가져올 때, 사용자 에이전트는 "Anonymous" 모드를 사용해야 하며, referrer 소스를 스타일시트의 URL로 설정하고, origin을 포함 문서의 URL로 지정해야 합니다. 네트워크 오류로 인해 유효한 대체 이미지가 없으면, none 값이 지정된 것과 동일한 효과를 가집니다.

    테스트

    6.2. 이미지 픽셀 선택: shape-image-threshold 속성

    shape-image-threshold는 이미지로 도형을 추출할 때 사용되는 알파 채널 임계값을 정의합니다. 값이 0.5인 경우, 도형은 불투명도가 50%를 넘는 모든 픽셀을 감싸게 됩니다.

    이름: shape-image-threshold
    값: <opacity-value>
    초기값: 0
    적용 대상: float 요소
    상속 여부: 아니오
    백분율: 해당 없음
    계산된 값: 지정된 숫자, [0,1] 범위로 제한됨
    정규 순서: 문법에 따름
    애니메이션 타입: 계산된 값 기준

    이 속성의 값의 의미는 다음과 같습니다:

    <number>
    이미지를 통해 도형을 추출할 때 사용되는 임계값을 설정합니다. 도형은 알파 값이 임계값을 초과하는 픽셀에 의해 정의됩니다. 임계값이 0.0(완전 투명)에서 1.0(완전 불투명) 범위를 벗어나면, 해당 범위로 제한되어 적용됩니다.

    참고: 앞으로의 CSS Shapes 버전에서는 알파 데이터 대신 이미지의 휘도(luminance) 데이터를 사용할 수 있는 스위치가 정의될 수 있습니다. 그 경우 shape-image-threshold는 스위치 상태에 따라 알파 또는 휘도에 임계값을 적용할 수 있도록 확장될 예정입니다.

    테스트

    6.3. 도형 확장: shape-margin 속성

    shape-margin 속성은 shape-outside에 마진을 더합니다. 이는 가장 작은 외곽선(수축 포장 관점에서) 즉, 기본 도형 위 한 점에서 수직 방향으로 shape-margin 거리만큼 바깥쪽으로 포함하는 모든 점을 커버하는 새로운 도형을 정의합니다. 여기에는 기본 도형의 어떤 엣지나 선 부분도 포함됩니다. 수직선이 정의되지 않는 점(예: 뾰족한 꼭짓점이나 선 끝)에서는 해당 점을 중심으로 반지름이 shape-margin인 원 위의 모든 점을 포함합니다.

    shape-outside가 적용되어 생성된 새로운 도형이 float area를 결정하며, 어떤 줄 감싸기(wrap) 결정을 내리기 전에 반드시 생성되어야 합니다.

    이 속성은 0 이상의 값만 허용합니다.

    이름: shape-margin
    값: <length-percentage [0,∞]>
    초기값: 0
    적용 대상: float 요소 및 initial letter box
    상속 여부: 아니오
    백분율: 포함 블록의 inline size 기준
    계산된 값: 계산된 <length-percentage>
    정규 순서: 문법에 따름
    애니메이션 타입: 계산된 값 기준
    <length-percentage [0,∞]>
    도형의 margin을 지정된 값으로 설정합니다.

    참고: shape-margin을 추가해도 float area가 float의 margin-box를 벗어날 수 없습니다. 클리핑을 방지하려면 shape-margin과 함께 추가 margin을 적용해야 할 수도 있습니다.

    shape-margin을 polygon 형태의 shape-outside에 적용하여 오프셋을 만든 예시입니다. 밝은 파란색 영역은 100x100px float에서의 도형을, 어두운 파란색 영역은 10px 오프셋을 보여줍니다.

    
      .float {
          width: 100px;
          height: 100px;
        shape-outside: polygon(10px 10px, 90px 50px, 40px 50px, 90px 90px, 10px 90px);
        shape-margin: 10px;
      }
    

    Example of a shape-margin offset

    예시 6의 CSS 로고에 shape-margin을 추가하면, 도형 주위로 줄 감싸기가 더 짧아집니다. 이미지의 알파 채널이 이미지의 오른쪽 엣지까지 닿아 있는 경우 도형이 margin-box에 의해 잘리지 않도록 추가적인 margin-right를 적용해야 합니다.

    
      #CSSlogo {
        shape-margin: 35px;
        margin-right: 35px;
      }
    
    A float shape around an image using its alpha-channel with a 35 pixels shape-margin
    알파 채널 기반 이미지 주변 float 도형에 35px shape-margin이 적용된 예시
    테스트

    7. 개인정보 보호 고려사항

    이 명세에 대해 개인정보 보호와 관련된 이슈는 제기되지 않았습니다.

    8. 보안 고려사항

    <image> 값이 shape-outside에 사용될 때, 이미지 데이터가 새로운 방식으로 노출될 수 있으므로, CORS 승인이 된 이미지에 한해 사용이 제한됩니다.

    감사의 글

    이 명세는 다음 분들의 의견과 참여 덕분에 가능했습니다: Tab Atkins Jr., Amelia Bellamy-Royds, Oriol Brufau, Andrei Bucur, Alexandru Chiculita, Boris Chiou, Emilio Cobos Álvarez, Elika Etemad, Arron Eicholz, Sylvain Galineau, Daniel Glazman, Arno Gourdol, Zoltan Horvath, Chris Jones, Bem Jones-Bey, Ian Kilpatrick, Guillaume Lebas, Ting-Yu Lin, Eric Meyer, Marcus Mielke, Alex Mogilevsky, Hans Muller, Mihnea Ovidenie, Virgil Palanciuc, Noam Rosenthal, Robert Sanderson, Dirk Schulze, Jen Simmons, Peter Sorotokin, Bear Travis, Lea Verou, Eugene Veselov, Brad Werth, Stephen Zilles 그리고 CSS 작업 그룹 멤버 여러분.

    변경 기록

    2022년 11월 15일 이후 (링크)

    2014년 3월 20일 이후 (링크)

    2014년 2월 11일 이후 (링크)

    2013년 12월 3일 이후 (링크)

    2013년 6월 20일 이후 (링크)

    2012년 5월 3일 이후 (링크)

    2011년 12월 13일 이후 (링크)

    적합성(Conformance)

    문서 관례(Document conventions)

    적합성 요구사항은 설명적 단언과 RFC 2119 용어의 조합으로 표현됩니다. “MUST”, “MUST NOT”, “REQUIRED”, “SHALL”, “SHALL NOT”, “SHOULD”, “SHOULD NOT”, “RECOMMENDED”, “MAY”, “OPTIONAL”이라는 주요 용어는 본 명세의 규범적 부분에서 RFC 2119에 정의된 대로 해석되어야 합니다. 그러나 가독성을 위해, 이 용어들은 본 명세에서 모두 대문자로 표기되지 않습니다.

    이 명세의 모든 텍스트는 규범적이며, 명시적으로 비규범적이라고 표시된 섹션, 예시, 참고를 제외합니다. [RFC2119]

    예시는 “예를 들어(for example)”라는 문구로 시작하거나 class="example"로 규범적 텍스트와 구분됩니다. 예시:

    이것은 참고용 예시입니다.

    참고(Informative notes)는 “Note”라는 단어로 시작하며, class="note"로 규범적 텍스트와 구분됩니다. 예시:

    참고: 이것은 참고용 노트입니다.

    권고(advisement)는 특별한 주의를 유도하기 위해 스타일링된 규범적 섹션이며, <strong class="advisement">로 구분됩니다. 예시: UA는 접근성 대안을 반드시 제공해야 합니다.

    테스트

    이 명세의 내용과 관련된 테스트는 이와 같은 “테스트” 블록으로 문서화될 수 있습니다. 이러한 블록은 모두 비규범적입니다.


    적합성 클래스(Conformance classes)

    이 명세에 대한 적합성은 세 가지 적합성 클래스로 정의됩니다:

    style sheet
    CSS 스타일 시트.
    renderer
    UA로, 스타일 시트의 의미를 해석하고 이를 사용하는 문서를 렌더링합니다.
    authoring tool
    UA로, 스타일 시트를 작성합니다.

    스타일 시트가 이 명세에 적합하려면, 이 모듈에서 정의된 문법을 사용하는 모든 선언이 일반 CSS 문법과 이 모듈의 각 기능별 문법에 따라 유효해야 합니다.

    렌더러가 이 명세에 적합하려면, 스타일 시트를 해당 명세에 따라 해석할 뿐만 아니라, 이 명세에서 정의한 모든 기능을 올바르게 파싱하고 문서를 그에 맞게 렌더링해야 합니다. 단, 기기 제한으로 인해 UA가 문서를 올바르게 렌더링하지 못한다고 해서 비적합한 것은 아닙니다. (예: UA는 흑백 모니터에서 색상을 렌더링할 필요는 없습니다.)

    저작 도구가 이 명세에 적합하려면, 스타일 시트를 일반 CSS 문법과 각 기능별 문법에 따라 문법적으로 올바르게 작성하고, 이 모듈에서 설명한 스타일 시트의 모든 적합성 요구사항을 충족해야 합니다.

    부분 구현(Partial implementations)

    작성자가 미래 호환 파싱 규칙을 활용해 대체 값을 지정할 수 있도록, CSS 렌더러는 반드시 지원하지 않는 at-규칙, 속성, 속성값, 키워드, 기타 문법 요소를 무효로 처리하고 (적절히 무시해야 합니다.) 특히 사용자 에이전트는 부분적으로 지원하지 않는 구성값을 무시하고, 하나의 멀티값 속성 선언에서 지원되는 값만 적용해서는 안 됩니다: 어떤 값이 무효(지원하지 않는 값 포함)로 간주된다면, CSS는 전체 선언을 무시해야 함을 요구합니다.

    불안정 및 독점 기능의 구현

    향후 안정적인 CSS 기능과의 충돌을 피하기 위해, CSSWG는 베스트 프랙티스에 따라 불안정 기능 및 독점 확장을 구현할 것을 권장합니다.

    비실험적 구현(Non-experimental implementations)

    명세가 Candidate Recommendation 단계에 도달하면, 비실험적 구현이 가능해지며, 구현자는 스펙에 따라 올바르게 구현된 CR 수준의 기능에 대해 접두어 없는 구현을 공개해야 합니다.

    CSS의 상호운용성을 확립하고 유지하기 위해, CSS 작업 그룹은 비실험적 CSS 렌더러가 W3C에 구현 보고서(필요한 경우 해당 테스트케이스 포함)를 제출한 후 CSS 기능에 대한 접두어 없는 구현을 공개할 것을 요청합니다. W3C에 제출된 테스트케이스는 CSS 작업 그룹에 의해 검토 및 수정될 수 있습니다.

    테스트케이스와 구현 보고서 제출에 대한 추가 정보는 CSS 작업 그룹 웹사이트 https://www.w3.org/Style/CSS/Test/에서 확인할 수 있습니다. 문의는 public-css-testsuite@w3.org 메일링 리스트로 하십시오.

    CR 종료 기준(CR exit criteria)

    본 명세가 Proposed Recommendation으로 진행되려면, 각 기능별로 두 개 이상의 독립적이고 상호운용 가능한 구현이 있어야 합니다. 각 기능은 서로 다른 제품군에서 구현될 수 있으며, 모든 기능을 하나의 제품이 구현할 필요는 없습니다. 이를 위한 용어를 다음과 같이 정의합니다:

    independent
    각 구현은 서로 다른 당사자가 개발해야 하며, 다른 적합 구현에서 사용된 코드를 공유, 재사용, 파생할 수 없습니다. 이 명세 구현과 관련 없는 코드 부분은 예외로 합니다.
    interoperable
    공식 CSS 테스트 스위트의 해당 테스트케이스를 통과하는 것, 또는 구현체가 웹 브라우저가 아니라면 동등한 테스트를 통과하는 것. 모든 관련 테스트는 동등한 테스트가 만들어져야 하며 해당 UA가 상호운용성을 주장하려면 반드시 필요합니다. 또한 그러한 UA가 상호운용성을 주장하려면, 동일한 방식으로 해당 동등 테스트를 통과할 수 있는 추가 UA가 하나 이상 있어야 합니다. 동등 테스트는 동료 검토(peer review)를 위해 공개되어야 합니다.
    implementation
    사용자 에이전트로서:
    1. 명세를 구현함
    2. 일반 대중에게 공개됨. 구현은 출시 제품이나 공개 베타, 프리뷰 릴리즈, "nightly build"일 수 있습니다. 출시되지 않은 제품 릴리즈의 경우, 최소 한 달간 해당 기능을 구현해야 안정성을 증명한 것으로 인정됩니다.
    3. 실험적인 제품이 아님(즉, 테스트 스위트만 통과하도록 설계된, 앞으로 정상적으로 사용될 의도가 없는 버전이 아님)

    이 명세는 최소 6개월 동안 Candidate Recommendation 상태를 유지합니다.

    색인

    이 명세에서 정의된 용어

    참조로 정의된 용어

    참고 문헌

    규범적 참고 문헌

    [CSS-BOX-4]
    Elika Etemad. CSS Box Model Module Level 4. 2024년 8월 4일. WD. URL: https://www.w3.org/TR/css-box-4/
    [CSS-CASCADE-5]
    Elika Etemad; Miriam Suzanne; Tab Atkins Jr.. CSS Cascading and Inheritance Level 5. 2022년 1월 13일. CR. URL: https://www.w3.org/TR/css-cascade-5/
    [CSS-COLOR-4]
    Chris Lilley; Tab Atkins Jr.; Lea Verou. CSS Color Module Level 4. 2025년 4월 24일. CRD. URL: https://www.w3.org/TR/css-color-4/
    [CSS-IMAGES-3]
    Tab Atkins Jr.; Elika Etemad; Lea Verou. CSS Images Module Level 3. 2023년 12월 18일. CRD. URL: https://www.w3.org/TR/css-images-3/
    [CSS-IMAGES-4]
    Tab Atkins Jr.; Elika Etemad; Lea Verou. CSS Images Module Level 4. 2023년 2월 17일. WD. URL: https://www.w3.org/TR/css-images-4/
    [CSS-INLINE-3]
    Elika Etemad. CSS Inline Layout Module Level 3. 2024년 12월 18일. WD. URL: https://www.w3.org/TR/css-inline-3/
    [CSS-MASKING]
    Dirk Schulze; Brian Birtles; Tab Atkins Jr.. CSS Masking Module Level 1. 2021년 8월 5일. CRD. URL: https://www.w3.org/TR/css-masking-1/
    [CSS-SYNTAX-3]
    Tab Atkins Jr.; Simon Sapin. CSS Syntax Module Level 3. 2021년 12월 24일. CRD. URL: https://www.w3.org/TR/css-syntax-3/
    [CSS-TRANSFORMS-1]
    Simon Fraser; et al. CSS Transforms Module Level 1. 2019년 2월 14일. CR. URL: https://www.w3.org/TR/css-transforms-1/
    [CSS-VALUES-3]
    Tab Atkins Jr.; Elika Etemad. CSS Values and Units Module Level 3. 2024년 3월 22일. CRD. URL: https://www.w3.org/TR/css-values-3/
    [CSS-VALUES-4]
    Tab Atkins Jr.; Elika Etemad. CSS Values and Units Module Level 4. 2024년 3월 12일. WD. URL: https://www.w3.org/TR/css-values-4/
    [CSS-VALUES-5]
    Tab Atkins Jr.; Elika Etemad; Miriam Suzanne. CSS Values and Units Module Level 5. 2024년 11월 11일. WD. URL: https://www.w3.org/TR/css-values-5/
    [CSS-VARIABLES-1]
    Tab Atkins Jr.. CSS Custom Properties for Cascading Variables Module Level 1. 2022년 6월 16일. CR. URL: https://www.w3.org/TR/css-variables-1/
    [CSS-WRITING-MODES-4]
    Elika Etemad; Koji Ishii. CSS Writing Modes Level 4. 2019년 7월 30일. CR. URL: https://www.w3.org/TR/css-writing-modes-4/
    [CSS2]
    Bert Bos; et al. Cascading Style Sheets Level 2 Revision 1 (CSS 2.1) Specification. 2011년 6월 7일. REC. URL: https://www.w3.org/TR/CSS2/
    [CSS3BG]
    Elika Etemad; Brad Kemper. CSS Backgrounds and Borders Module Level 3. 2024년 3월 11일. CRD. URL: https://www.w3.org/TR/css-backgrounds-3/
    [CSS3BOX]
    Elika Etemad. CSS Box Model Module Level 3. 2024년 4월 11일. REC. URL: https://www.w3.org/TR/css-box-3/
    [FETCH]
    Anne van Kesteren. Fetch Standard. Living Standard. URL: https://fetch.spec.whatwg.org/
    [RFC2119]
    S. Bradner. Key words for use in RFCs to Indicate Requirement Levels. 1997년 3월. Best Current Practice. URL: https://datatracker.ietf.org/doc/html/rfc2119
    [SVG2]
    Amelia Bellamy-Royds; et al. Scalable Vector Graphics (SVG) 2. 2018년 10월 4일. CR. URL: https://www.w3.org/TR/SVG2/

    참고용 참고 문헌

    [CSS3-EXCLUSIONS]
    Rossen Atanassov; Vincent Hardy; Alan Stearns. CSS Exclusions Module Level 1. 2015년 1월 15일. WD. URL: https://www.w3.org/TR/css3-exclusions/

    속성 색인

    이름 초기값 적용 대상 상속 백분율 애니메이션 타입 정규 순서 계산값
    shape-image-threshold <opacity-value> 0 float 요소 아니오 해당 없음 계산된 값 기준 문법에 따름 지정된 숫자, [0,1] 범위로 제한됨
    shape-margin <length-percentage [0,∞]> 0 float 요소 및 initial letter box 아니오 포함 블록의 inline size 기준 계산된 값 기준 문법에 따름 계산된 <length-percentage> 값
    shape-outside none | [ <basic-shape> || <shape-box> ] | <image> none float 요소 및 initial letter box 아니오 해당 없음 <basic-shape>에 정의된 대로, 아니면 불연속 문법에 따름 <basic-shape>에 정의된 대로(추가로 <shape-box>가 있으면 뒤에 붙음); 아니면 계산된 <image>; 아니면 명시된 키워드