1. 소개
각 CSS 속성의 값 정의 필드는 키워드, 데이터 타입(<와 > 사이에 나타남), 그리고 이들이 어떻게 조합될 수 있는지에 대한 정보를 포함할 수 있습니다. 여러 속성에서 사용할 수 있는 일반 데이터 타입(<length>가 가장 널리 사용됨)은 이 명세에서 설명하고, 더 구체적인 데이터 타입(예: <spacing-limit>)은 해당 모듈에서 설명합니다.
1.1. 모듈 상호작용
이 모듈은 [CSS2]의 1.4.2.1, 4.3, 그리고 A.2 섹션의 데이터 타입 정의를 대체하고 확장합니다.
2. 값 정의 구문
여기서 설명하는 값 정의 구문은 CSS 속성(및 CSS의 다른 여러 부분)의 유효한 값 집합(및 유효한 구문)을 정의하는 데 사용됩니다. 이렇게 정의된 값은 하나 이상의 구성 요소를 가질 수 있습니다.
2.1. 구성 값 유형
구성 값 유형은 여러 방식으로 지정됩니다:
-
기본 데이터 타입은 <와 > 사이에 나타납니다(예: <length>, <percentage> 등). 숫자 데이터 타입의 경우, 이 타입 표기법은 아래에 설명된 대괄호 범위 표기법을 사용하여 범위 제한을 주석으로 달 수 있습니다.
-
속성 값 범위는 동일한 이름의 속성이 가지는 값 패턴과 동일합니다. 이는 속성 이름을 작은따옴표로 감싸고 <와 >로 둘러싸서 작성합니다. 예: <'border-width'>, <'background-attachment'> 등.
이러한 타입에는 CSS 전역 키워드(예: inherit)가 포함되지 않습니다. 또한, 만약 속성의 값 문법이 쉼표로 구분된 반복이라면, 해당 타입에는 최상위 쉼표 구분 목록 수량자가 포함되지 않습니다. (예: pairing 속성이 [ <custom-ident> <integer>? ]#로 정의되어 있다면, <'pairing'>은 [ <custom-ident> <integer>? ]과 같고, [ <custom-ident> <integer>? ]#와는 다릅니다.)
왜 수량자를 제거하나요?
최상위 수량자는 이러한 값 타입에서 제거됩니다. 그 이유는 최상위 쉼표 구분 반복이 주로 목록 조정 속성에 사용되며, 여러 속성을 단축 속성으로 결합할 때, 자체 쉼표 구분 반복 구문이 필요하기 때문입니다.
이런 특별 처리가 없다면, 각 longhand 속성마다 내부 값만을 위한 임시 production을 정의해야 하므로, 전체적으로 문법을 이해하기 어려워집니다.
-
함수 표기와 그 인자. 이는 함수 이름 다음 빈 괄호쌍을 <와 > 사이에 작성합니다. 예: <calc()>. 이는 해당 이름의 함수 표기를 참조합니다.
-
기타 비단말(non-terminal). 이는 비단말의 이름을 <와 > 사이에 작성합니다. 예: <spacing-limit>. <border-width>와 <'border-width'>의 차이를 참고하세요: 후자는 border-width 속성의 문법을 나타내고, 전자는 다른 곳에서 명시적으로 확장되어야 합니다. 비단말 정의는 명세서에서 처음 등장하는 근처에 위치하는 것이 일반적입니다.
일부 속성 값 정의에는 슬래시(/), 쉼표(,), 괄호와 같은 리터럴도 포함될 수 있습니다. 이는 해당 토큰을 의미합니다. 구성 값에 나타날 수 있는 그 외의 키워드가 아닌 리터럴 문자(예: "+")는 반드시 작은따옴표로 감싸야 합니다.
문법에 명시된 콤마(,) 는 일부 상황에서 암묵적으로 생략 가능합니다. 이는 문법에서 선택적 항목을 구분할 때 사용된 경우입니다. 속성이나 기타 CSS 값에서 최상위 리스트 내, 또는 함수의 인수 리스트에서, 문법에 명시된 콤마는 다음과 같은 경우 반드시 생략해야 합니다:
- 쉼표 앞의 모든 항목이 생략된 경우
- 쉼표 뒤의 모든 항목이 생략된 경우
- 쉼표 사이 항목이 생략되어, 여러 쉼표가 인접하게 되는 경우(공백/주석 무시)
example ( first?, second?, third?)
이 문법에서는 example(first, second, third)도, example(first, second)도, example(first, third)나 example(second)도 모두 유효합니다. 하지만 example(first, , third)는 더 이상 쉼표가 두 옵션을 구분하지 않으므로 잘못된 구문입니다; 마찬가지로 example(,second)와 example(first,)도 잘못된 구문입니다. example(first second) 역시 쉼표가 실제로 옵션을 구분하는 데 필요하므로 잘못된 구문입니다.
쉼표가 암시적으로 생략 불가능하다면, 인자를 생략하는 다양한 방법을 제대로 표현하기 위해 문법이 훨씬 더 복잡해져야 하며, 기능의 단순성이 크게 가려집니다.
모든 CSS 속성은 CSS 전역 키워드 값을 속성 값의 유일한 구성요소로도 허용합니다.
가독성을 위해 속성 값 구문 정의에는 이를 명시적으로 나열하지 않습니다.
예를 들어, border-color의 전체 값 정의는 CSS Cascading and Inheritance
Level 3에서 <color>
이지만,
실제로는 <color>
로
나열되어 있습니다.
참고: 이는 일반적으로, 이러한 키워드를 같은 선언 내에 다른 구성 값과 함께 사용하는 것은 잘못된 선언이 됨을 의미합니다. 예를 들어, background: url(corner.png) no-repeat, inherit;는 올바르지 않습니다.
2.2. 구성 값 조합자
구성 값들은 다음과 같이 속성 값으로 배열될 수 있습니다:
- 나란히 배치(juxtaposition)된 구성 요소는 모두 주어진 순서대로 반드시 나타나야 합니다.
- 이중 앰퍼샌드(&&)는 둘 이상의 구성 요소를 구분하며, 모두 등장해야 하지만 순서는 상관없습니다.
- 이중 바(||) 는 둘 이상의 옵션을 구분합니다: 그 중 하나 이상이 등장해야 하며, 순서는 상관없습니다.
- 바(|)는 둘 이상의 대안을 구분합니다: 그 중 정확히 하나만 등장해야 합니다.
- 대괄호([ ])는 그룹화에 사용됩니다.
나란히 배치는 이중 앰퍼샌드보다 강하고, 이중 앰퍼샌드는 이중 바보다 강하며, 이중 바는 바보다 강합니다. 따라서 다음 줄들은 동등합니다:
a b | c || d && e f[ a b] |[ c ||[ d &&[ e f]]]
재배열 가능한 조합자(||, &&)의 경우, 문법 내의 순서는 중요하지 않습니다: 동일 그룹 내 구성 요소들은 어떤 순서로든 섞일 수 있습니다. 따라서 다음 줄들은 동등합니다:
a || b || c b || a || c
참고: 조합자는 결합법칙을 따르지 않으므로 그룹화가 중요합니다. 예를 들어, a || b || c와 a || [ b || c ]는 서로 다른 문법입니다: 첫 번째는 b a c와 같은 값을 허용하지만, 두 번째는 그렇지 않습니다.
2.3. 구성 값 수량자
모든 타입, 키워드, 또는 괄호로 묶인 그룹 뒤에는 다음 수정자 중 하나가 올 수 있습니다:
- 별표(*) 는 앞의 타입, 단어, 그룹이 0회 이상 등장함을 의미합니다.
- 플러스(+) 는 앞의 타입, 단어, 그룹이 1회 이상 등장함을 의미합니다.
- 물음표(?) 는 앞의 타입, 단어, 그룹이 선택사항임(0회 또는 1회 등장)을 의미합니다.
- 중괄호 안의 단일 숫자({A}) 는 앞의 타입, 단어, 그룹이 A번 등장함을 의미합니다.
- 중괄호 안의 쉼표로 구분된 두 숫자({A,B}) 는 앞의 타입, 단어, 그룹이 최소 A번, 최대 B번 등장함을 의미합니다. B를 생략할 수 있으며({A,}), 이 경우 A번 이상 반복되어야 하며 최대 반복 횟수 제한은 없습니다.
- 샵 기호(#) 는 앞의 타입, 단어, 그룹이 1회 이상 반복되며, 각 반복이 쉼표 토큰(공백/주석이 들어갈 수 있음)으로 구분됨을 의미합니다. 위의 중괄호 형태와 조합하여 반복 횟수를 명확히 나타낼 수 있습니다(예: <length>#{1,4}).
- 느낌표(!)는 그룹 뒤에 오며, 그룹이 반드시 최소한 하나의 값을 생성해야 함을 의미합니다; 그룹 내 항목의 문법이 전체 생략을 허용하더라도, 최소 하나의 구성 값이 생략되지 않아야 합니다.
+와 # 수량자는 +#처럼 중첩할 수 있습니다; 마찬가지로 #와 ?도 #?처럼 중첩할 수 있습니다. 이 중첩은 각각 뒤의 수량자가 앞 수량자 결과에 적용되는 것을 의미합니다. (이러한 중첩은 그룹화로도 표현할 수 있지만, 복잡한 문법에서는 괄호 수가 너무 많아 가독성이 떨어질 수 있습니다.)
반복 구성 값(*, +, #로 표시)의 경우, UA는 해당 구성 요소를 최소 20회까지 지원해야 합니다. 속성 값에 지원 횟수보다 많은 반복이 있다면, 해당 선언은 잘못된 것으로 간주하여 무시해야 합니다.
2.4. 조합자 및 수량자 패턴
여러 개의 독립적인 구성 값을 특정 개수와 순서로 조합하는 일반적인 방법이 몇 가지 있습니다. 특히, 여러 구성 값 중 0개 이상, 1개 이상, 또는 모두를 선택하게 하고, 문법에서 지정된 순서 또는 임의의 순서로 나타내고자 하는 경우가 많습니다.
이 모든 것은 간단한 조합자와 수량자 패턴을 사용하여 쉽게 표현할 수 있습니다:
순서대로 | 임의 순서 | |
---|---|---|
0개 이상 | A? B? C?
| A? || B? || C?
|
1개 이상 |
| A || B || C
|
모두 | A B C
| A && B && C
|
"임의 순서"의 모든 경우가 조합자를 사용하여 표현되는 반면, "순서대로"는 모두 나란히 배치의 변형임에 주의하세요.
2.5. 구성 값과 공백
별도로 명시되지 않는 한, 공백 및/또는 주석은 위 조합자 및 수량자로 조합된 구성 요소 앞, 뒤, 사이에 올 수 있습니다.
참고: 많은 경우, 구성 요소를 서로 구분하기 위해 실제로 공백이 필요합니다. 예를 들어, 1em2em은 숫자 1과 식별자 em2em으로 해석되어 잘못된 단위가 되기 때문에, 이 경우 2 앞에 공백이 꼭 필요하며, 1em과 2em이라는 두 개의 길이로 올바르게 파싱됩니다.
2.6. 함수 표기 정의
함수 표기의 구문은 다음 순서로 정의됩니다:
-
함수 이름을 식별자로 작성하고, 그 뒤에 여는 괄호를 붙입니다(예: example(). 또는 <function-token> production을 사용하여 임의의 함수 이름을 나타낼 수 있습니다.
-
함수의 인자(있는 경우)는 값 정의 구문을 사용하여 표현합니다.
-
리터럴 닫는 괄호.
함수의 인자는 암시적으로 그룹화되어, 마치 대괄호([ ... ])로 둘러싸인 것처럼 동작합니다.
example ( <length>, <length>)
이 문법은 이름이 "example"이고 인자가 "<length> , <length>"인 함수를 일치시킵니다.
<pseudo-class-selector> =':' <ident-token> |':' <function-token> <any-value>')'
이는 임의의 함수 이름을 나타내며, <any-value>를 함수 인자로 사용합니다.
2.7. 속성 값 예시
아래는 속성과 그에 해당하는 값 정의 필드 예시 몇 가지입니다.
속성 | 값 정의 필드 | 예시 값 |
---|---|---|
orphans | <integer> | 3 |
text-align | left | right | center | justify | center |
padding-top | <length> | <percentage> | 5% |
outline-color | <color> | invert | #fefefe |
text-decoration | none | underline || overline || line-through || blink | overline underline |
font-family | [ <family-name> | <generic-family> ]# | "Gill Sans", Futura, sans-serif |
border-width | [ <length> | thick | medium | thin ]{1,4} | 2px medium 4px |
box-shadow | [ inset? && <length>{2,4} && <color>? ]# | none | 3px 3px rgba(50%, 50%, 50%, 50%), lemonchiffon 0 0 4px inset |
2.8. 비단말 정의 및 문법 production 블록
<position> 또는 <calc()>와 같은 비단말의 정확한 문법은 종종 CSS 문법 production 블록으로 명시됩니다. 이러한 블록은 보통 다음과 같이 정의된 각 항목을 별도의 preformatted 블록으로 나타냅니다:
<foo> = keyword | <bar> | some-really-long-pattern-of-stuff <bar> = <length>
각 정의는 별도의 줄에서 시작하며,
정의하고자 하는 비단말과,
=
다음에,
확장될 값
정의 구문 조각으로 이루어집니다.
정의는 여러 줄에 걸칠 수 있으며,
다음 문법 production을 시작하는 줄이나
production 블록의 끝에서 종료됩니다(둘 중 먼저 오는 것).
=
은 값 정의 구문에서는 단독으로 쓰이지 않으므로,
새 줄이 새로운 정의의 시작임을 명확히 알 수 있습니다.) 3. 값 결합: 보간, 덧셈, 누적
일부 프로시저(예: 트랜지션 및 애니메이션)는 두 개의 CSS 속성 값을 결합합니다. 아래의 결합 연산들은 두 계산된 값 VA와 VB에 대해 계산된 값 Vresult를 산출하는 방식으로 정의됩니다. 교환 법칙이 성립하지 않는 연산(예: 행렬 곱셈, 또는 서로 다른 변환 리스트의 누적)의 경우 VA는 연산의 첫 번째 항을, VB는 두 번째 항을 나타냅니다.
- 보간(interpolation)
-
두 속성 값 VA와 VB가 주어졌을 때,
VA와 VB 사이 구간에서 p 거리만큼 떨어진 중간값
Vresult를 생성합니다. p = 0이면 VA를, p = 1이면
VB를 생성합니다.
p의 범위는 타이밍 함수의 영향으로 (−∞, ∞)입니다. 따라서, 이 절차는 p가 [0, 1] 범위를 벗어날 때의 외삽 동작도 정의해야 합니다.
- 덧셈(addition)
-
두 속성 값 VA와 VB를 받아
두 속성의 합 Vresult를 반환합니다.
참고: 덧셈은 종종 보간을 정의하는 가중 합(weighted sum) 함수로 표현할 수 있지만, 항상 그런 것은 아닙니다. 예를 들어, 변환 행렬의 보간은 행렬 성분을 분해 및 보간하는 반면, 덧셈은 행렬 곱셈에 의존합니다.
값 타입이 덧셈에 대한 특정 절차를 정의하지 않거나, 덧셈 불가(not additive)로 정의되었다면, 해당 덧셈 연산은 단순히 Vresult = VB가 됩니다.
- 누적(accumulation)
- 두 속성 값 VA와 VB를 받아, VA에서 VB를 델타로 취급하여 결합한 결과 Vresult를 반환합니다.
이러한 연산은 계산된 값에만 정의됩니다. (따라서 예를 들어, <length> 값 15pt와 5em을 더하는 방법을 정의할 필요가 없습니다. 이러한 값들은 위 절차에 전달되기 전에 표준 단위로 변환됩니다.)
3.1. 범위 검사
보간 결과가 속성의 유효 범위를 벗어날 수 있으며, 입력값 모두가 유효하더라도 마찬가지입니다. 특히 p가 [0, 1] 범위를 벗어날 때 자주 발생하며, 일부 타이밍 함수는 해당 범위 내에서도 이를 야기할 수 있습니다. 보간, 덧셈, 누적 후 최종적으로 결과가 사용 대상 컨텍스트의 범위를 벗어나더라도 선언이 무효가 되지는 않습니다. 대신, 값은 대상 컨텍스트에서 허용되는 범위로 클램프(clamp)되어야 하며, 수학 함수(§ 10.12 범위 검사 참조)와 동일하게 처리됩니다.
참고: 보간 결과가 범위를 벗어나더라도, 덧셈/누적이 결과를 다시 범위 내로 "교정"할 수 있습니다. 따라서, 클램프는 보간 관련 연산을 모두 적용한 최종 결과에만 적용됩니다.
4. 텍스트 데이터 타입
텍스트 데이터 타입은 다양한 키워드와 식별자, 그리고 문자열(<string>), URL(<url>) 등을 포함합니다. 사전 정의된 키워드의 대소문자나 특정 속성에서 명시적으로 정의된 경우를 제외하고, 어떠한 정규화도 수행하지 않습니다(유니코드 정규화 역시 하지 않음). 즉, 해당 속성의 명시값과 계산된 값은 파싱 후(문자 집합 변환 및 이스케이프 포함) 제공된 유니코드 값 그대로입니다. [UNICODE] [CSS-SYNTAX-3]
CSS 식별자(identifier)는, 일반적으로 <ident>로 표기합니다. 이는 <ident-token> 문법을 따르는 문자 시퀀스입니다. [CSS-SYNTAX-3] 식별자는 따옴표로 감싸면 안 됩니다. 그렇지 않으면 문자열로 해석됩니다. CSS 속성은 두 종류의 식별자를 허용합니다: 사전 정의 키워드와 작성자 정의 식별자.
참고: <ident> production은 속성 값 정의용이 아니며, <custom-ident>를 대신 사용해야 합니다. 이는 기타 구문 구조 정의를 위해 제공됩니다.
모든 텍스트 데이터 타입은 불연속(discrete) 보간을 하며 덧셈 불가입니다.
4.1. 사전 정의 키워드
값 정의 필드에서, 키워드는 사전 정의된 의미를 갖고 문자 그대로 나타납니다. 키워드는 식별자이며, ASCII 대소문자 구분 없이 해석됩니다([a-z]와 [A-Z]는 동일하게 간주).
Value : collapse | separate
그리고 사용 예시는 다음과 같습니다:
table{ border-collapse : separate}
4.1.1. CSS 전역 키워드: initial, inherit 및 unset
위에서 정의한 대로, 모든 속성은 CSS 전역 키워드를 허용합니다. 이는 모든 CSS 속성에 공통적인 값 연산을 나타냅니다. 이러한 키워드는 CSS Cascading and Inheritance Module에서 규범적으로 정의됩니다.
다른 CSS 명세에서도 추가적인 CSS 전역 키워드를 정의할 수 있습니다.
4.2. 접두사 없는 작성자 정의 식별자: <custom-ident> 타입
일부 속성은 임의의 작성자 정의 식별자를 구성 값으로 허용합니다. 이 일반 데이터 타입은 <custom-ident>로 표기하며, 해당 속성 값 정의에서 사전 정의된 키워드로 잘못 해석되지 않는 유효한 CSS 식별자를 의미합니다. 이러한 식별자는 완전히 대소문자를 구분합니다 ("동일함" 연산으로 비교). ASCII 범위 내에서도 (예: example와 EXAMPLE은 서로 다른 식별자입니다).
CSS 전역 키워드는 <custom-ident>로 사용할 수 없습니다. default 키워드도 예약되어 있어 <custom-ident>이 될 수 없습니다. <custom-ident>를 사용하는 명세는, <custom-ident>에서 제외되는 키워드가 있다면 명확히 명시해야 합니다—예를 들어, 해당 속성의 값 정의에서 사전 정의된 키워드는 모두 제외한다고 밝히는 식입니다. 제외된 키워드는 모든 ASCII 대소문자 조합에서 제외됩니다.
속성 값에서 위치적으로 모호한 키워드를 파싱할 때, <custom-ident> production은 다른 미충족 production이 해당 키워드를 가져갈 수 없는 경우에만 키워드를 가져갈 수 있습니다.
참고: <custom-ident>가 포함된 문법을 설계할 때, <custom-ident>는 항상 "위치적으로 모호하지 않게" 해야 하며, 속성 내 키워드 값과 충돌이 불가능해야 합니다. 이러한 충돌은 <dashed-ident>를 사용하여도 방지할 수 있습니다.
4.3. 접두사 있는 작성자 정의 식별자: <dashed-ident> 타입
일부 컨텍스트에서는 작성자 정의 식별자와 CSS 정의 식별자를 모두 허용합니다. 이를 조심스럽게 처리하지 않으면, 새로운 CSS 정의 값을 추가할 때 어려움이 생길 수 있습니다; UA는 기존 사용 현황을 조사하고, 새 CSS 정의 값과 일치하는 작성자 정의 식별자가 충분히 적다고 판단해야 하며, 새 값을 CSS에서 특별한 의미로 부여해도 기존 페이지가 깨지지 않을지 모험해야 합니다.
CSS에는 이 두 값 공간이 섞여 있는 레거시 사례가 많지만, <dashed-ident> 타입은 작성자 정의 식별자와 CSS 정의 식별자를 쉽게 구분할 수 있도록 고안되었습니다.
<dashed-ident> production은 <custom-ident>이며, 그만큼 대소문자를 구분하고, 추가로 반드시 두 개의 대시(U+002D HYPHEN-MINUS)로 시작해야 합니다.
<dashed-ident>는 오직 작성자 정의 이름 용도로만 예약되어 있습니다. CSS가 자체적으로 <dashed-ident>를 정의하는 일은 없습니다.
.foo{ --fg-color : blue; }
@color-profile --foo{ src : url ( https://example.com/foo.icc ); } .foo{ color : color ( --foo1 0 .5 /.2 ); }
예를 들어, CSS 전처리기가 새 "커스텀" at-규칙을 추가한다면, @custom이라고 작성해서는 안 됩니다. 이는 향후 CSS에서 공식 @custom 규칙과 충돌할 수 있기 때문입니다. 대신 @--custom을 사용해야 하며, 이는 CSS에서 정의하는 것과 절대 충돌하지 않습니다.
더 나아가 @--library1-custom처럼 작성하면, Library2가 @--library2-custom을 추가하더라도 충돌 가능성이 없습니다. 이상적으로는 이 접두사를 도구에서 설정 가능하게 하여, 작성자가 직접 충돌을 피할 수 있도록 해야 합니다.
4.4. 따옴표 문자열: <string> 타입
문자열은 <string>으로 표시됩니다. 문자 그대로 작성할 때는, 큰따옴표나 작은따옴표로 둘러싼 일련의 문자들로 이루어지며, 이는 <string-token> production에 해당합니다. 자세한 내용은 CSS 구문 모듈 [CSS-SYNTAX-3]를 참고하세요.
"\" "
또는 "\22"
).
작은따옴표도 마찬가지입니다('\' '
또는 '\27'
).
content : "this is a 'string'." ; content : "this is a \" string\"." ; content : 'this is a "string".' ; content : 'this is a \' string\'.'
미관이나 기타 이유로 문자열을 여러 줄에 걸쳐 쓸 수 있지만, 이 경우 줄바꿈 문자 자체를 역슬래시(\)로 이스케이프해야 합니다. 줄바꿈 문자는 문자열에서 제거됩니다. 예를 들어, 다음 두 선택자는 완전히 동일합니다:
문자열은 줄바꿈 문자를 직접 표현할 수 없으므로, 문자열 내에서 줄바꿈을 포함하려면 이스케이프 "\A"를 사용하세요. (16진수 A는 유니코드에서 줄바꿈 문자(U+000A)이지만, CSS에서는 일반적인 "newline"을 의미합니다.)
4.5. 리소스 위치: <url> 타입
<url> 타입은, url() 및 src() 함수로 작성되며, URL을 나타냅니다. URL은 리소스를 가리키는 포인터입니다.
<url>의 구문은 다음과 같습니다:
<url> = <url () > | <src () > <url () > =url ( <string> <url-modifier> * ) | <url-token> <src () > =src ( <string> <url-modifier>*)
레거시 이유로, url()은 URL 자체를 따옴표 없이 쓸 수 있습니다. 이 경우 특별히 파싱되어 <url-token>이 됩니다. [CSS-SYNTAX-3] 이러한 특별한 파싱 때문에 url()은 URL만 직접 지정할 수 있습니다; src()에는 이러한 파싱 규칙이 없으므로, var()와 같은 함수로 URL을 전달할 수 있습니다.
background : url ( "http://www.example.com/pinkish.gif" ); background : url ( http://www.example.com/pinkish.gif );
다음 선언들도 의미가 같습니다:
background : src ( "http://www.example.com/pinkish.gif" ); --foo : "http://www.example.com/pinkish.gif" ; background : src ( var ( --foo));
그러나 다음은 동작하지 않습니다:
--foo : "http://www.example.com/pinkish.gif" ; background : url ( var(--foo ));
...왜냐하면 값에 있는 이스케이프되지 않은 "("가 파싱 오류를 일으키기 때문에, 전체 선언이 잘못된 것으로 처리되기 때문입니다.
따옴표 없는 url() 구문의 정확한 파싱 요구사항은 [CSS-SYNTAX-3]에 규범적으로 정의되어 있습니다.
일부 CSS 문맥(예: @import)에서는 <url>을 함수 없이 맨 <string>으로도 나타낼 수 있습니다. 이 경우 문자열은 해당 url() 함수와 동일하게 동작합니다.
4.5.1. 상대 URL
리소스의 절대 위치에 의존하지 않는 모듈형 스타일시트를 만들기 위해, 작성자는 상대 URL을 사용해야 합니다. 상대 URL([URL]에서 정의됨)은 기준(base) URL을 이용해 전체 URL로 변환됩니다. RFC 3986, 섹션 3에 이 과정의 규범적 알고리즘이 정의되어 있습니다. CSS 스타일시트의 경우, 기준 URL은 스타일시트 자체의 URL이며, 스타일된 소스 문서의 URL이 아닙니다. 문서 내에 삽입된 스타일시트는 해당 컨테이너의 기준 URL을 가집니다.
참고: HTML 문서의 경우, 기준(base) URL이 동적으로 변경될 수 있습니다.
<url>이 속성의 계산값(computed value)으로 나타날 때, 앞에서 설명한 대로 절대 URL로 변환됩니다. UA가 절대 URL로 변환할 수 없는 URL의 계산값은 지정된 값(specified value)입니다.
body{ background : url ( "tile.png" ) }
이 규칙이 위치한 스타일시트의 URL:
http : //www.example.org/style/basic.css
소스 문서의 <body>
배경은 다음 URL로 지정된 리소스 이미지로 채워집니다:
http : //www.example.org/style/tile.png
<body>
를 포함하는 소스 문서의 URL과 관계없이 동일한 이미지가 사용됩니다.
4.5.1.1. 프래그먼트 URL
기준 URL이 바뀌거나 섀도우 DOM이 적용되어도 요소 ID 참조가 CSS에서 동작하도록, <url>은 프래그먼트만 포함할 때 특별한 동작을 합니다.
<url>의 값이
U+0023 숫자 기호(#
) 문자로 시작하면,
해당 URL은 local url flag가 설정되며,
URL의 프래그먼트에 대해 트리 스코프 참조(tree-scoped reference)가 됩니다.
<url>에 local url flag가 설정된 경우:
-
프래그먼트가 요소 ID 참조라면 (예: 미디어 프래그먼트가 아닌 경우), 해당 트리의 ID 집합을 트리 스코프 네임으로 하여 트리 스코프 참조로 해석합니다: 즉, 해당 프래그먼트와 ID가 같은 노드 트리 내에서 트리 순서상 가장 먼저 나오는 요소를 가리킵니다. (트리 스코프 참조의 일반 규칙에 따라, 필요시 호스트 트리로 계속 올라감.)
해당 요소가 없으면, URL은 해석에 실패합니다.
-
그 외의 경우, 프래그먼트를 현재 문서 기준으로 해석합니다.
find a potential indicated element를 참조할 수 있지만,
이는 Document
에만
정의되어 있고,
ShadowRoot
에는
적용되지 않습니다.
참고: 이런 프래그먼트는
(섀도우 DOM의 경우에는 스타일시트가 속한 노드 트리 등)
항상 현재 문서(또는 해당 트리) 기준으로 해석된다는 의미입니다.
즉, 다른 상황에서 상대 URL이 해석되는 방식(base
요소로 기준 URL이 바뀌거나,
연결된 스타일시트의 상대 URL이 스타일시트 URL 기준으로 해석되는 것 등)을 무시합니다.
#anchor
는 http : //example.com/
기준으로 해석되고,
#image
는 HTML 문서 내의 요소들을 기준으로 해석됩니다:
<!DOCTYPE html> < base href = "http://example.com/" > ...< a href = "#anchor" style = "background-image: url(#image)" > link</ a >
직렬화할 때, url()에 local url flag가 설정되어 있으면, 프래그먼트만 직렬화해야 합니다.
4.5.2. 빈 URL
<url>의 값이 빈 문자열인 경우 (예: url("") 또는 url()), 해당 url은 잘못된 리소스(예: about:invalid와 유사)로 해석되어야 합니다.
계산값은 지정된 형태(url("") 또는 src("")) 그대로이며, 직렬화도 동일하게 해야 합니다.
참고: 이는 웹 플랫폼 내 임베디드 리소스의 빈 url 동작과 일치하며, url() 값이 비어 있을 때(편집 실수 등) 스타일시트나 호스트 문서에 대한 불필요한 재요청을 방지해줍니다. 거의 항상 해당 url()이 사용되는 맥락에서는 잘못된 리소스이기 때문입니다. 웹 플랫폼의 링크는 빈 url을 허용하므로, 향후 CSS가 하이퍼링크 제어 기능을 갖게 된다면, 이 제한은 그런 맥락에서는 완화될 수 있습니다.
4.5.3. URL 수정자
<url>는 추가적인 <url-modifier>를 지정할 수 있으며, 이는 URL의 의미나 해석을 변경합니다. <url-modifier>는 <ident> 또는 함수 표기가 될 수 있습니다.
이 명세는 <url-modifier>를 정의하지 않지만, 다른 명세에서 정의할 수 있습니다.
참고: 따옴표 없는 <url>나 url()으로 감싸지 않은 경우, <url-modifier>를 사용할 수 없습니다.
4.5.4. URL 처리 모델
CSSStyleSheet
sheet,
RequestDestination
과 일치하는 문자열 destination,
"no-cors" 또는 "cors" corsMode,
response와 null, 실패 또는 바이트 스트림을 인자로 받는 알고리즘 processResponse를
받아 다음과 같이 동작합니다:
-
environmentSettings를 sheet의 관련 설정 객체로 설정합니다.
-
base를 sheet의 스타일시트 기준 URL(null이 아니면)로, 아니면 environmentSettings의 API 기준 URL로 설정합니다. [CSSOM]
-
parsedUrl을 URL 파서 단계의 결과로 설정합니다. 인자로는 urlValue의 url과 base를 사용합니다. 알고리즘이 오류를 반환하면, 중단합니다.
-
req를 새 request로, url은 parsedUrl, destination은 destination, mode는 corsMode, origin은 environmentSettings의 origin, credentials mode는 "same-origin", use-url-credentials flag는 설정, client는 environmentSettings, referrer는 environmentSettings의 API 기준 URL로 설정합니다.
-
이 요청에 적용되는 모든 URL 요청 수정 단계(URL request modifier steps)를 적용합니다.
참고: 이 명세는 URL 요청 수정 단계를 정의하지 않지만, 다른 명세에서 정의할 수 있습니다.
-
req의 mode가 "cors"라면, req의 referrer를 sheet의 location으로 설정합니다. [CSSOM]
-
sheet의 origin-clean flag가 설정되어 있으면, req의 initiator type을 "css"로 설정합니다. [CSSOM]
-
Fetch req를 실행하고, processresponseconsumebody를 processResponse로 설정합니다.
CSS에서 표현된 URL을 해석할 때는, URL 파서의 encoding 인자를 생략해야 하며 (즉, 기본값인 UTF-8 사용), 스타일시트 인코딩과 관계없이 항상 적용됩니다.
참고: 다시 말해, CSS에 작성된 URL은 항상 퍼센트 인코딩을 통해 비ASCII 코드 포인트를 URL 객체에서 UTF-8로 인코딩합니다 (따라서 URL 값을 네트워크 요청 등에서 사용할 때에도 마찬가지입니다), 스타일시트 자체의 인코딩과 무관하게 적용됩니다. 이 처리는 스타일시트를 유니코드로 디코딩한 후 코드 포인트로 변환된 뒤에 이루어진다는 점에 유의하세요.
5. 숫자 데이터 타입
숫자 데이터 타입은 양, 인덱스, 위치 및 이와 유사한 값을 나타내는 데 사용됩니다. 특정 숫자 값에서 양(숫자적 측면)을 표현하는 구문은 여러 가지 변형이 있을 수 있지만, 명시값과 계산값은 이러한 변형을 구분하지 않습니다: 추상적인 값의 양만을 표현하며, 구문적 표현 방식은 구분하지 않습니다.
숫자 데이터 타입에는 <integer>, <number>, <percentage>, 그리고 차원에 해당하는 다양한 값(예: <length>, <angle>, <time>, <frequency>, <resolution>)이 포함됩니다.
참고: 범용 차원은 여기서 정의되지만, 일부 다른 모듈에서는 추가 데이터 타입을 정의합니다 (예: [css-grid-1]은 fr 단위 도입) 이들은 보다 국소적으로 사용됩니다.
CSS에서 숫자 값의 정밀도와 지원 범위는 구현 정의이며, 값이 사용되는 속성이나 다른 문맥에 따라 달라질 수 있습니다. 그러나 CSS 명세 내에서는 무한한 정밀도와 범위를 가정합니다. 범위/정밀도 한계로 인해 명시적으로 지원할 수 없는 값은 구현에서 지원하는 가장 가까운 값으로 변환되어야 하며, "가장 가까운 값"의 정의 또한 구현 정의입니다.
<angle> 값이 구현 정의 범위를 초과해 변환이 필요할 때에는, 지원 가능한 360deg의 가장 가까운 배수에 맞춰 클램프(clamp)되어야 합니다.
5.1. 범위 제한 및 범위 정의 표기법
속성은 숫자 값을 특정 범위로 제한할 수 있습니다.
값이 허용 범위를 벗어나면,
별도의 명시가 없는 한,
선언은 잘못된 것으로 간주되어 무시되어야 합니다.
범위 제한은 숫자 타입 표기법에서
CSS 대괄호 범위 표기법—
—을 각도 괄호 내 식별
키워드 뒤에 사용하여
min과 max를 포함하는 닫힌 범위를 나타냅니다.
예를 들어, <integer [0,10]>는 0 이상 10 이하의 정수를 의미하고,
<angle
[0,180deg]>는 0deg에서 180deg 사이(어떤 단위로든)의 각도를 의미합니다.
참고: CSS 값은 일반적으로 열린 범위를 허용하지 않으므로, 대괄호 표기법만 사용됩니다.
이론적으로 CSS는 모든 값 타입에 대해 무한한 정밀도와 무한한 범위를 지원하지만, 실제로 구현에는 한계가 있습니다. UA는 실용적 범위와 정밀도를 지원해야 합니다. 이상적으로 무제한이어야 하는 범위의 극값은 ∞ 또는 −∞로 표시합니다. 예를 들어, <length [0,∞]>는 음수가 아닌 길이를 의미합니다.
대괄호 범위 표기법이나 속성 설명에 별도의 범위가 표시되지 않았다면,
가 기본값으로 간주됩니다.
−∞ 또는 ∞ 값은 단위가 있는 값 타입이라도 단위 없이 작성해야 합니다. 0 값은 "단위 없는 0"을 허용하지 않는 타입(예: <time>)이어도 단위 없이 쓸 수 있습니다.
참고: 이 문서 작성 시점에서
대괄호
범위 표기법은 새롭게 도입된 것이며,
대부분의 CSS 명세에서는
범위 제한이 산문으로만 서술되어 있습니다.
(예: "음수 값은 허용되지 않는다" 또는
"음수 값은 잘못된 값이다"는
범위를 의미)
이런 서술 역시 동일하게 구속력을 갖습니다.
5.2. 정수: <integer> 타입
정수 값은 <integer>로 표기합니다.
문자 그대로 작성할 때, 정수는 10진수 숫자 0~9 하나 이상으로 이루어지며, CSS 구문 모듈의 <number-token> production의 부분 집합에 해당합니다. 정수의 첫 숫자 앞에는 - 또는 +가 바로 올 수 있으며, 이는 정수의 부호를 나타냅니다.
별도 명시가 없는 한, CSS 명세에서 가장 가까운 정수로 반올림은 소수 부분이 정확히 0.5일 때 +∞ 방향으로 반올림함을 의미합니다. (예: 1.5는 2로, -1.5는 -1로 반올림합니다.)
5.2.1. <integer>의 계산 및 결합
별도 명시가 없는 한, 명시된 <integer>의 계산값은 명시된 추상 정수입니다.
보간은 <integer>에 대해 Vresult = round((1 - p) × VA + p × VB);로 정의되며, 즉, 실수 공간에서 보간한 후 <number>와 동일하게 계산하고, 가장 가까운 정수로 반올림하여 <integer>로 변환합니다.
덧셈은 <integer>에 대해 Vresult = VA + VB로 정의됩니다.
5.3. 실수: <number> 타입
실수 값은 <number>로 표기하며, 소수 부분이 있을 수 있는 실수를 나타냅니다.
문자 그대로 작성할 때, 실수는 정수이거나, 10진수 숫자 0개 이상 뒤에 점(.) 및 10진수 숫자 하나 이상이 뒤따르는 형태입니다; 선택적으로, "e" 또는 "E" 뒤에 정수(지수)를 붙여 과학적 표기법도 허용합니다. 이는 <number-token> production에 해당합니다. 정수와 마찬가지로, 실수의 첫 글자 앞에도 - 또는 +가 바로 올 수 있습니다.
<zero> 값은 값이 0인 리터럴 실수를 나타냅니다. (예: calc(0) 등 0으로 평가되는 식은 <zero>와 일치하지 않으며, 리터럴 <number-token>만 해당됩니다.)
5.3.1. <number>의 계산 및 결합
별도 명시가 없는 한, 명시된 <number>의 계산값은 명시된 추상 실수입니다.
보간은 <number>에 대해 Vresult = (1 - p) × VA + p × VB로 정의됩니다.
덧셈은 <number>에 대해 Vresult = VA + VB로 정의됩니다.
5.4. 단위가 있는 숫자: 차원 값
차원은 단위가 붙은 숫자를 의미하며, <dimension>으로 표기됩니다.
문자 그대로 작성할 때, 차원은 단위 식별자가 즉시 뒤따르는 실수이며, 단위 식별자는 식별자입니다. 이는 <dimension-token> production에 해당합니다. 키워드와 마찬가지로, 단위 식별자는 ASCII 대소문자 구분 없이 해석됩니다.
CSS는 <dimension>을 이용해 거리(<length>), 기간(<time>), 주파수(<frequency>), 해상도(<resolution>), 기타 양을 지정합니다.
5.4.1. 호환 단위
계산값(computed value)을 [CSSOM]에서 직렬화할 때, 호환 단위(정적 곱셈 계수로 변환 가능한 단위, 예: px와 in 사이 96:1, 또는 font-size에 따라 변하는 em과 px)는 하나의 정준 단위(canonical unit)로 변환됩니다. 각 호환 단위 그룹마다 직렬화에 사용할 정준 단위가 정해집니다.
해결된 값(resolved value)을 직렬화할 때, 길이를 나타내는 모든 값 타입(백분율, 숫자, 키워드 등)은 길이와 호환되는 것으로 간주합니다. 앞으로 도입될 API 역시 거리/시간/주파수 등과 관련된 값을 차원의 해당 클래스와 호환되는 것으로 보고, 정준화해야 합니다.
5.4.2. 차원 값의 결합
보간은 호환 차원(예: 두 <length> 값)에서 Vresult = (1 - p) × VA + p × VB로 정의됩니다.
덧셈은 호환 차원에 대해 Vresult = VA + VB로 정의됩니다.
5.5. 백분율: <percentage> 타입
백분율 값은 <percentage>로 표기하며, 다른 기준값의 일정 비율을 의미합니다.
문자 그대로 작성할 때, 백분율은 실수 뒤에 퍼센트 기호 %가 바로 붙는 형태입니다. 이는 <percentage-token> production에 해당합니다.
백분율 값은 항상 다른 양에 상대적입니다. 각 속성마다 백분율이 참조하는 양이 정의되어 있습니다. 이 양은 동일 요소의 다른 속성 값, 조상 요소의 속성 값, 포매팅 컨텍스트의 측정값(예: 포함 블록의 너비), 또는 기타 다른 것일 수 있습니다.
5.5.1. <percentage>의 계산 및 결합
별도 명시가 없는 한 (예: font-size는 <percentage>를 <length>로 계산), 백분율의 계산값은 명시된 백분율입니다.
보간은 <percentage>에 대해 Vresult = (1 - p) × VA + p × VB로 정의됩니다.
덧셈은 <percentage>에 대해 Vresult = VA + VB로 정의됩니다.
5.6. 백분율과 차원 혼합
<percentage>가 동일 차원과 같은 구성 값 위치를 나타낼 수 있고, 따라서 calc() 식에서 함께 결합될 수 있는 경우, 다음과 같은 편의 표기법을 속성 문법에서 사용할 수 있습니다:
- <length-percentage>
-
와 같으며, <percentage>는 <length>로 환산됨을 의미합니다.[ <length> | <percentage>] - <frequency-percentage>
-
와 같으며, <percentage>는 <frequency>로 환산됨을 의미합니다.[ <frequency> | <percentage>] - <angle-percentage>
-
와 같으며, <percentage>는 <angle>로 환산됨을 의미합니다.[ <angle> | <percentage>] - <time-percentage>
-
와 같으며, <percentage>는 <time>으로 환산됨을 의미합니다.[ <time> | <percentage>]
반면, hsl() 함수의 두 번째와 세 번째 인자는 <percentage>로만 표현할 수 있습니다. calc() production도 가능하지만, 백분율끼리만 결합할 수 있습니다. 예: calc(10% + 20%).
참고: 명세에서 <percentage>를 차원 대신 교대로 쓰지 않아야 하며, 반드시 호환되는 경우에만 허용해야 합니다.
참고: 필요한 경우 앞으로 더 많은 <type-percentage> production이 추가될 수 있습니다. <number-percentage>는 추가되지 않으며, <number>와 <percentage>는 calc()에서 결합할 수 없기 때문입니다.
5.6.1. 백분율-차원 혼합의 계산 및 결합
백분율-차원 혼합의 계산값은 다음과 같이 정의됩니다.
-
백분율 성분이 0이거나, 백분율이 명확히 차원값으로 계산되도록 정의된 경우 계산된 차원값
-
차원 성분이 0인 경우 계산된 백분율
-
그 외에는 계산된 calc() 식
백분율-차원 혼합(<length-percentage>, <frequency-percentage>, <angle-percentage>, <time-percentage> 등)에서의 보간은 다음과 같이 정의됩니다.
- 두 값이 모두 순수 <length> 값이면 길이 보간과 동일
- 두 값이 모두 순수 <percentage> 값이면 백분율 보간과 동일
- 둘 다 아니면, 두 값을 calc() 표현으로 변환한 뒤, 차원(및 각 경우에 따라 <length>/<frequency>/<angle>/<time>)와 백분율(<percentage>)을 각각 개별적으로 보간함
더하기(Addition)는 <percentage>에 대해 보간(interpolation)과 동일하게 정의되지만, 각 구성요소를 보간하는 대신 더하는 점만 다릅니다.
5.7. 비율: <ratio> 타입
비율 값은 <ratio>로 표기하며, 두 숫자 값의 비율을 의미합니다. 보통 가로:세로 비율 등에서 사용됩니다.
문자 그대로 작성할 때, 비율의 구문은 다음과 같습니다:
<ratio> = <number[ 0 , ∞] >[ / <number[ 0 , ∞] >] ?
두 번째 <number>는 선택사항이며, 기본값은 1입니다. 단, <ratio>는 항상 두 개의 성분으로 직렬화됩니다.
<ratio>의 계산값은 제공된 두 숫자의 쌍입니다.
<ratio>의 두 숫자 중 하나라도 0 또는 무한이면, 특이 비율(degenerate ratio)을 의미하며(일반적으로 아무 동작도 하지 않음),
두 <ratio>를 비교하려면, 첫 번째 숫자를 두 번째 숫자로 나눈 값을 비교하면 됩니다. 예를 들어, 3/2는 2/1보다 작으며, 각각 1.5와 2로 해석됩니다. (즉, "세로로 긴" 비율이 "가로로 넓은" 비율보다 작습니다.)
5.7.1. <ratio>의 결합
<ratio>의 보간은 각 <ratio>를 첫 번째 값을 두 번째 값으로 나누어 숫자로 변환한 후 (예: 3 / 2 → 1.5), 그 결과의 로그를 취하고 (예: 1.5 → 약 0.176), 이 값을 보간합니다. 보간 중 결과는 로그를 다시 역산(invert)하여, 결과를 첫 번째 값, 1을 두 번째 값으로 하는 <ratio>로 해석합니다.
두 <ratio> 중 하나라도 특이 비율이면, 보간이 불가능합니다.
start =log ( 5 ); // ≈0.69897 end =log ( 1.5 ); // ≈0.17609 interp =0.69897 *.5 +0.17609 *.5 ; // ≈0.43753 final =10 ^interp; // ≈2.73
참고: 비율의 로그로 보간하면 결과가 스케일 독립적이 되며 (5 / 1에서 300 / 200으로 보간해도 위와 동일한 결과), "가로"와 "세로" 변형에 대해 대칭적이며 (예: 1 / 5에서 2 / 3으로 보간하면 중간에 대략 1 / 2.73이 됨), 가로 고정/세로 고정 여부와 무관하게 대칭적이 됩니다. 이런 성질은 다른 보간 전략에서는 얻기 어렵습니다.
참고: 로그의 특성상 어떤 로그를 써도 무방합니다; 이 예시는 10진수 로그를 사용했지만, 자연로그(e) 등을 사용해도 중간 결과는 달라질 수 있지만 최종 결과는 같습니다.
<ratio>의 덧셈은 불가능합니다.
6. 거리 단위: <length> 타입
길이는 거리 측정값을 의미하며, 속성 정의에서 <length>로 표시됩니다. 길이는 차원입니다.
길이가 0일 때 단위 식별자는 선택사항입니다 (즉, <number> 0으로 구문적으로 표현될 수 있습니다). 하지만, 0이 <number> 또는 <length>로 해석될 수 있는 속성 (예: line-height)에서는, 반드시 <number>로 해석해야 합니다.
속성은 길이 값을 특정 범위로 제한할 수 있습니다. 허용된 범위를 벗어난 값은 선언이 무효가 되어 무시되어야 합니다.
일부 속성에서는 음수 길이 값을 허용하지만, 이는 포매팅을 복잡하게 만들 수 있고 구현별 한계가 있을 수 있습니다. 음수 길이 값이 허용되지만 지원할 수 없는 경우, 지원 가능한 가장 가까운 값으로 변환되어야 합니다.
사용된 길이 값을 지원할 수 없는 경우에는, 사용자 에이전트는 실제 값에서 근사치를 사용해야 합니다.
길이 단위는 상대적과 절대적 두 가지가 있습니다. 길이의 지정 값(지정 길이)은 그 수치와 단위로 표현됩니다. 길이의 계산 값(계산 길이)은 지정 길이를 절대 길이로 변환한 값이며, 단위는 구분하지 않습니다: 어떤 절대 길이 단위로도 표현될 수 있지만(직렬화 시에는 정준 단위, px로 직렬화됩니다).
숫자 값의 지원 정밀도와 해당 정밀도에 맞추어 반올림하는 방법은 일반적으로 구현 정의이지만, <length>는 border-width 등 일부 속성에서 특정 방식으로 반올림되어 적절한 시각적 표시를 보장합니다. (이 알고리듬은 개별 속성에서 명시적으로 호출됩니다.)
6.1. 상대 길이
상대 길이 단위는 다른 길이에 상대적인 값을 지정합니다. 상대 단위를 사용하는 스타일 시트는 출력 환경에 따라 더 쉽게 확장할 수 있습니다.
상대 단위는 다음과 같습니다:
단위 | 상대 기준 |
---|---|
em | 요소의 글꼴 크기 |
ex | 요소 글꼴의 x-높이 |
cap | 요소 글꼴의 대문자 높이(대문자 기준 높이) |
ch | 요소 글꼴에서 좁은 글리프의 문자 전진폭 (U+0030 “0” 글리프로 측정) |
ic | 요소 글꼴에서 전폭 글리프의 문자 전진폭 (U+6C34 “水” 글리프로 측정) |
rem | 루트 요소의 글꼴 크기 |
lh | 요소의 줄 높이 |
rlh | 루트 요소의 줄 높이 |
vw | 뷰포트 너비의 1% |
vh | 뷰포트 높이의 1% |
vi | 루트 요소의 인라인 축 기준 뷰포트 크기의 1% |
vb | 루트 요소의 블록 축 기준 뷰포트 크기의 1% |
vmin | 뷰포트의 더 짧은 변의 1% |
vmax | 뷰포트의 더 긴 변의 1% |
자식 요소는 부모에 대해 지정된 상대 값을 상속하지 않으며, 계산 값을 상속합니다.
6.1.1. 글꼴-상대 길이: em, rem, ex, rex, cap, rcap, ch, rch, ic, ric, lh, rlh 단위
글꼴-상대 길이는 사용되는 요소의 글꼴 지표 (로컬 글꼴-상대 길이) 또는 루트 요소의 (루트 글꼴-상대 길이)를 참조합니다.
- em
- 해당 요소의 font-size 속성의 계산 값과 같습니다.
- rem
- 루트 요소의 em 단위의 계산 값과 같습니다.
- ex
- 첫 번째 사용 가능한 폰트의 사용된 x-높이와 같습니다 [CSS3-FONTS]. x-높이는 보통 소문자 "x"의 높이와 같습니다. 하지만 ex는 "x"가 없는 폰트에도 정의됩니다. x-높이는 여러 방법으로 찾을 수 있습니다. 일부 폰트는 x-높이에 대한 신뢰할 수 있는 메트릭을 포함합니다. 신뢰할 수 있는 폰트 메트릭이 없으면, UA는 소문자 글리프의 높이로 x-높이를 결정할 수 있습니다. 한 가지 휴리스틱은 소문자 "o"가 기준선 아래로 얼마나 내려가는지 확인하고, 그 값을 바운딩 박스 상단에서 빼는 것입니다. x-높이를 결정할 수 없거나 비현실적인 경우, 0.5em 값을 사용해야 합니다.
- rex
- 루트 요소의 ex 단위 값과 같습니다.
- cap
- 첫 번째 사용 가능한 폰트의 사용된 대문자 높이와 같습니다 [CSS3-FONTS]. 대문자 높이는 일반적으로 라틴 대문자 높이와 비슷합니다. 하지만 cap은 라틴 문자가 없는 폰트에도 정의됩니다. 대문자 높이는 여러 방법으로 찾을 수 있습니다. 일부 폰트는 대문자 높이에 대한 신뢰할 수 있는 메트릭을 포함합니다. 신뢰할 수 있는 폰트 메트릭이 없으면, UA는 대문자 글리프의 높이로 대문자 높이를 결정할 수 있습니다. 한 가지 휴리스틱은 대문자 "O"가 기준선 아래로 얼마나 내려가는지 확인하고, 그 값을 바운딩 박스 상단에서 빼는 것입니다. 대문자 높이를 결정할 수 없거나 비현실적인 경우, 폰트의 상승선을 사용해야 합니다.
- rcap
- 루트 요소의 cap 단위 값과 같습니다.
- ch
-
유럽계 영숫자 문자의 일반적인 전진폭(advance measure)을 나타내며,
사용된 폰트에서 “0”(제로, U+0030) 글리프의 전진폭으로 측정됩니다.
(글리프의 전진폭은 인라인 축의 폭 또는 높이입니다.)
참고: 이 측정값은 대략적인 값이며(모노스페이스 폰트에서는 정확한 값), 예상 글리프 개수를 바탕으로 한 측정에 사용할 수 있습니다.
참고: 글리프의 전진폭은 writing-mode와 text-orientation, 그리고 폰트 설정, text-transform, 기타 글리프 선택 또는 방향에 영향을 주는 속성에 따라 달라질 수 있습니다.
“0” 글리프의 측정값을 결정할 수 없거나 비현실적인 경우, 0.5em 너비, 1em 높이로 간주해야 합니다. 따라서 ch 단위는 일반적으로 0.5em을, 위로 세워질 때(즉, writing-mode가 vertical-rl 또는 vertical-lr이고 text-orientation이 upright일 때) 1em으로 대체됩니다.
- rch
- 루트 요소의 ch 단위 값과 같습니다.
- ic
-
CJK 문자(한중일)의 일반적인 전진폭(advance measure)을 나타내며,
사용된 폰트에서 “水”(CJK 물 글리프, U+6C34)의 전진폭으로 측정됩니다.
참고: 이 측정값은 일반적으로 정확한 값이며 (프로포셔널 전폭 글리프가 있는 일부 폰트에서는 대략적인 값), 예상 글리프 개수를 바탕으로 한 측정에 사용할 수 있습니다.
이데오그램 전진폭을 결정할 수 없거나 비현실적인 경우, 1em으로 간주해야 합니다.
- ric
- 루트 요소의 ic 단위 값과 같습니다.
- lh
- 해당 요소의 line-height 속성의 계산 값과 같으며, normal은 첫 번째 사용 가능한 폰트의 메트릭만을 사용하여 절대 길이로 변환됩니다.
- rlh
-
루트 요소의 lh 단위 값과 같습니다.
참고: height 속성에 lh나 rlh 단위를 사용해도 실제 줄 수를 제어할 수 없습니다. 이 단위는 이상적인 빈 줄의 이론적 크기에 따라 길이 계산만 가능하며, 실제 줄 박스의 크기는 내용에 따라 다를 수 있습니다. 실제 줄 수를 제한하려면 max-lines 속성을 대신 사용할 수 있습니다.
해당 요소의 font-* 속성 값에 사용될 때, 글꼴-상대 길이는 부모 요소의 계산된 메트릭을 기준으로 해석됩니다(또는 부모가 없는 경우 font 및 line-height 속성의 초기값). 마찬가지로, lh 또는 rlh 단위가 line-height 속성이나 font-* 속성 값에 사용될 때, 부모 요소의 계산된 line-height 및 글꼴 메트릭을 기준으로 해석됩니다(또는 부모가 없으면 font 및 line-height 초기값의 계산된 메트릭). (다른 글꼴-상대 길이 단위는 line-height에 사용될 때 요소 자신의 메트릭에 대해 계속 해석됩니다.)
요소 컨텍스트 외부에서 사용될 때 (예: 미디어 쿼리), 글꼴-상대 길이 단위는 font 및 line-height 초기값의 메트릭을 참조합니다. 마찬가지로, 루트 요소가 없는 문서에서 지정된 경우, 루트 글꼴-상대 길이는 font 및 line-height 초기값의 메트릭을 기준으로 해석됩니다.
참고: ch 및 ic와 같은 글꼴-상대 단위는 필요한 폰트가 아직 로드되지 않은 경우 폰트 다운로드를 유발할 수 있습니다.
글꼴-상대 길이는 셰이핑 없이 계산됩니다.
일부 사용자 에이전트는 문서 내 글꼴 크기에 추가 제한(예: 가독성을 위해 최소 글꼴 크기 설정)을 허용합니다. 이러한 제한은 영향을 받는 속성의 사용된 값에만 적용되어야 하며, 글꼴-상대 길이의 해석에는 영향을 주면 안 됩니다. 그러나 다른 컨텍스트(예: 미디어 쿼리)에서는, 사용된 글꼴 메트릭에 영향을 주는 한, 이러한 제한이 글꼴-상대 길이의 해석에 영향을 줍니다.
참고: 일반적으로 사용자의 선호(예: 최소 글꼴 크기)를 존중하는 것이 바람직합니다. (min-width: 40em)과 같은 미디어 쿼리는 문서가 실제로 표시될 글꼴 크기를 사용하는 것이 유용합니다. 하지만 이러한 선호가 요소의 속성에서 글꼴-상대 길이에 영향을 주는 것은 웹 호환성에 문제가 있으므로, 많은 페이지가 이 단위가 지정된 font-size의 정확한 배수임을 기대하기 때문입니다. (실제) 사용자의 선호가 적용된 후의 font-size가 아니라.
일부 사용자 에이전트는 폼 컨트롤의 line-height 값에 제한을 둘 수 있습니다. 이러한 제한은 lh 및 rlh 단위에는 영향을 주지 않아야 합니다. 다만, 이들의 자손에 미치는 영향은 구현 정의입니다.
6.1.2. 뷰포트-백분율 길이: *vw, *vh, *vi, *vb, *vmin, *vmax 단위
뷰포트-백분율 길이는 초기 포함 블록의 크기를 기준으로 하며, 이는 연속 매체의 경우 뷰포트 크기, 페이지 영역의 경우 페이징 매체의 크기를 기준으로 합니다. 초기 포함 블록의 높이나 너비가 변경되면, 이에 따라 스케일됩니다.
6.1.2.1. 대형, 소형, 동적 뷰포트 크기
뷰포트-백분율 길이 단위에는 네 가지 변형이 있으며, 세 가지(동일할 수도 있는) 뷰포트 크기 개념에 대응합니다.
- 대형 뷰포트
-
대형 뷰포트-백분율
단위 (lv*)
와 기본
뷰포트-백분율 단위 (v*)
는 대형 뷰포트 크기 기준으로
정의됩니다:
사용자 에이전트 인터페이스가 동적으로 확장 및 축소되는 경우,
모두 축소된 상태를 기준으로 한 뷰포트 크기입니다.
이로써, 저자들은 컨텐츠가 뷰포트를 확실하게 채우도록 할 수 있으며,
이러한 UI가 확장되어 있을 때 컨텐츠가 가려질 수 있음을 알 수 있습니다.
대형 뷰포트-백분율 단위의 크기는 고정되어 있으며 (따라서 안정적임), 뷰포트 자체가 크기 조정되지 않는 한 유지됩니다.
예를 들어, 휴대폰에서는 화면 공간이 제한적이기 때문에, 사용자가 페이지를 스크롤하면 브라우저가 타이틀/주소 표시줄의 일부 또는 전체를 숨기는 경우가 많습니다. 대형 뷰포트-백분율 단위는 이 모든 UI가 축소된 더 큰 공간을 기준으로 하므로, 이러한 단위를 사용하는 컨텐츠는 UI가 모두 숨겨져 있을 때 전체 페이지를 채웁니다. 하지만 UI가 표시될 때, 이러한 단위를 사용하여 크기가 지정된 컨텐츠는 UI에 가려질 수 있습니다. - 소형 뷰포트
-
소형 뷰포트-백분율
단위 (sv*)
는 소형 뷰포트 크기 기준으로
정의됩니다:
사용자 에이전트 인터페이스가 동적으로 확장 및 축소되는 경우,
모두 확장된 상태를 기준으로 한 뷰포트 크기입니다.
이로써 저자들은 UI가 표시된 상태에서도 컨텐츠가 뷰포트 내에 들어가도록 할 수 있으며,
UI가 숨겨지면 컨텐츠가 뷰포트를 완전히 채우지 않을 수 있습니다.
소형 뷰포트-백분율 단위의 크기는 고정되어 있으며 (따라서 안정적임), 뷰포트 자체가 크기 조정되지 않는 한 유지됩니다.
예를 들어, height: 100svh로 크기가 지정된 요소는 모든 동적 UI가 표시된 상태에서는 화면을 완전히 채워서 컨텐츠가 가려지지 않게 됩니다.하지만 UI가 숨겨지면, 요소 주변에 여백이 생깁니다. 소형 뷰포트-백분율 단위는 일반적으로 “더 안전”하지만, 사용자가 페이지와 상호작용하기 시작하면 가장 매력적인 레이아웃은 아닐 수 있습니다.
- 동적 뷰포트
-
동적
뷰포트-백분율 단위 (dv*)
는 동적 뷰포트 크기
기준으로 정의됩니다:
사용자 에이전트 인터페이스의 동적 확장/축소를 실시간 반영한 뷰포트 크기입니다.
이로써 저자들은 UI가 표시되거나 숨겨졌을 때 모두 정확히 뷰포트에 맞도록 컨텐츠 크기를 지정할 수 있습니다.
동적 뷰포트-백분율 단위의 크기는 동일한 뷰포트에서도 안정적이지 않습니다. 이러한 단위를 사용하면 사용자가 페이지를 스크롤하는 동안 컨텐츠 크기가 변할 수 있습니다. 사용 용도에 따라 이는 사용자에게 혼란을 주거나 성능에 부담을 줄 수 있습니다.
사용자 에이전트는 UI를 확장/축소하는 동안 동적 뷰포트-백분율 단위를 애니메이션할 필요는 없으며, 대신 UI 애니메이션 중에 UI가 완전히 확장 또는 축소된 상태로 계산할 수 있습니다. (이 기간에는 UI가 축소된 크기를 가정하는 것이 권장됩니다.)
특정 UI의 확장/축소(A)가 모든 뷰포트-백분율 길이(그리고 초기 포함 블록)의 크기를 동시에 바꾸는지, 아니면(B) 대형 뷰포트 크기와 소형 뷰포트 크기의 차이에만 영향을 주는지는 대부분 사용자 에이전트에 달려 있습니다. 하지만:
-
스크롤 등 자주 발생하는 페이지 상호작용으로 인해 UI가 바뀌는 경우, 레이아웃 변화로 인해 사용자가 방해받지 않도록 (B)로 분류해야 합니다.
-
충분히 안정적인 상태에 도달하는 UI 변경은 문서를 조정된 공간에 재배치하는 것이 사용자에게 이로울 때 (A)로 분류해야 합니다.
-
또한, 사용자 에이전트는 일부 동적 UI가 의도적으로 컨텐츠 위에 오버레이되어 레이아웃 변화가 발생하지 않도록 할 수 있습니다—이 경우, 뷰포트-백분율 길이에는 아무런 영향이 없습니다. (보통 온스크린 키보드가 이에 해당합니다.)
모든 경우, overflow나 scrollbar-gutter 속성이 루트 요소에서 어느 축이든 무조건 스크롤바가 나타나거나(또는 공간이 예약되는) 경우 (예: overflow: scroll이지만 overflow: auto는 해당하지 않음), 해당 축의 계산 값 뷰포트-백분율 길이는 초기 포함 블록에 따라 줄어듭니다. 그 외의 경우(및 항상 미디어 쿼리의 경우), 뷰포트-백분율 길이는 스크롤바가 존재하지 않는다고 가정하고 크기가 지정됩니다 (설령 이것이 초기 포함 블록과 다를지라도).
참고: overflow 속성이 body 요소에 적용된 경우, 루트 요소의 스크롤바에 영향을 줄 수 있습니다. 그러나 이것이 뷰포트 단위의 크기에는 영향을 주지 않습니다.
6.1.2.2. 다양한 뷰포트-상대 단위
뷰포트-백분율 길이 단위는 다음과 같습니다:
- vw
- svw
- lvw
- dvw
- svw
- 각각 대형 뷰포트 크기, 소형 뷰포트 크기, 대형 뷰포트 크기, 그리고 동적 뷰포트 크기의 너비의 1%와 같습니다.
- vh
- svh
- lvh
- dvh
- svh
- 각각 대형 뷰포트 크기, 소형 뷰포트 크기, 대형 뷰포트 크기, 그리고 동적 뷰포트 크기의 높이의 1%와 같습니다.
- vi
- svi
- lvi
- dvi
- svi
- 각각 대형 뷰포트 크기, 소형 뷰포트 크기, 대형 뷰포트 크기, 그리고 동적 뷰포트 크기의 (각각) 박스의 인라인 축 크기의 1%와 같습니다.
- vb
- svb
- lvb
- dvb
- svb
- 각각 초기 포함 블록의 대형 뷰포트 크기, 소형 뷰포트 크기, 대형 뷰포트 크기, 그리고 동적 뷰포트 크기의 (각각) 박스의 블록 축 크기의 1%와 같습니다.
- vmin
- svmin
- lvmin
- dvmin
- svmin
- *vw와 *vh 중 더 작은 값과 같습니다.
- vmax
- svmax
- lvmax
- dvmax
- svmax
- *vw와 *vh 중 더 큰 값과 같습니다.
참고: 원래(접두사 없는) 뷰포트 단위는 정의되었으며, 초기 포함 블록을 기준으로 했습니다. 연속 매체에서는 항상 단일 뷰포트 크기와 일치했습니다. 스크롤 중 브라우저 크롬이 나타났다 사라지는 동적 동작은 나중에 도입되었고, Safari를 따라 대부분의 UA가 이 단위를 더 큰 크기와 매핑했습니다. 이런 방식이 여러 상황에서 보기에는 더 낫지만, 다른 상황에서는 툴바, 헤더, 푸터 등 중요한 컨텐츠를 가릴 수 있습니다. 이 매핑이 최선이었는지는 확실하지 않으므로, 이전 명세에서는 UA가 기본 단위의 매핑을 선택할 수 있도록 허용했습니다. 하지만 이제는 대형 뷰포트-백분율 단위로 매핑하는 것이 웹 호환성을 위해 필수로 간주됩니다.
요소가 없거나 아직 스타일링되지 않은 상황(예: 미디어 쿼리 평가 시)에서는, *vi와 *vb 단위가 writing-mode 속성의 초기값을 사용하여 어느 축을 참조할지 결정합니다.
6.2. 절대 길이: cm, mm, Q, in, pt, pc, px 단위
절대 길이 단위는 서로 간에 고정된 비율을 가지며, 기준 단위가 실제 물리적 측정값에 연결되어 있습니다. 출력 환경이 알려진 경우에 주로 유용합니다. 절대 단위는 물리 단위 (in, cm, mm, pt, pc, Q) 와 시각각 단위(픽셀 단위) (px)로 구성됩니다:
단위 | 이름 | 동등 관계 |
---|---|---|
cm | 센티미터 | 1cm = 96px/2.54 |
mm | 밀리미터 | 1mm = 1cm의 1/10 |
Q | 쿼터밀리미터 | 1Q = 1cm의 1/40 |
in | 인치 | 1in = 2.54cm = 96px |
pc | 파이카 | 1pc = 1in의 1/6 |
pt | 포인트 | 1pt = 1in의 1/72 |
px | 픽셀 | 1px = 1in의 1/96 |
h1{ margin : 0.5 in } /* 인치 */ h2{ line-height : 3 cm } /* 센티미터 */ h3{ word-spacing : 4 mm } /* 밀리미터 */ h3{ letter-spacing : 1 Q } /* 쿼터밀리미터 */ h4{ font-size : 12 pt } /* 포인트 */ h4{ font-size : 1 pc } /* 파이카 */ p{ font-size : 12 px } /* px */
참고: 출판 컨텍스트에서는
길이를
처럼 표기하기도 하며,
이는 2 파이카와 3 포인트의 길이를 의미합니다.
이런 표기는 CSS에서 calc(2pc + 3pt)로 쓸 수 있습니다(자세한 내용은 § 10.1
기본 산술: calc() 참고).
모든 절대 길이 단위는 호환되며, px가 이들의 정준 단위입니다.
CSS 장치에서, 이 치수는 기준 단위로 고정(anchor)되는데,
인쇄 매체의 일반적인 읽기 거리에서는, 기준 단위가 물리 단위(인치, 센티미터 등)여야 합니다. 화면 매체(고해상도 장치 포함), 저해상도 장치, 특이한 읽기 거리를 가진 장치에서는, 기준 단위로 픽셀 단위를 사용하는 것이 권장됩니다. 이런 장치에서는 픽셀 단위가 기준 픽셀에 가장 근접한 정수 개수의 디바이스 픽셀을 참조하는 것이 좋습니다.
참고: 기준 단위가 픽셀 단위라면, 물리 단위는 실제 측정값과 일치하지 않을 수 있습니다. 반대로 기준 단위가 물리 단위라면, 픽셀 단위가 정수 개수의 디바이스 픽셀에 대응되지 않을 수 있습니다.
참고: 픽셀 단위와 물리 단위에 대한 정의는 CSS1, CSS2의 이전 판과 다릅니다. 특히, 이전 CSS에서는 픽셀 단위와 물리 단위가 고정된 비율로 연결되지 않았으며, 물리 단위는 항상 실제 측정값에 묶여 있었고, 픽셀 단위는 기준 픽셀에 최대한 가깝게 변동되었습니다. (이 변경은 96dpi 전제를 가정하는 기존 콘텐츠가 너무 많아, 해당 전제를 깨면 콘텐츠가 깨지는 일이 많았기 때문에 불가피하게 이루어졌습니다.)
참고: 단위는 ASCII 대소문자 구분 없이 소문자로 직렬화됩니다. 예: 1Q는 1q로 직렬화됩니다.
기준 픽셀은 96dpi의 디바이스 픽셀 밀도와 팔 길이(28인치) 거리에서 읽을 때 한 픽셀의 시각각을 의미합니다. 28인치(약 71cm) 거리에서는 시각각이 약 0.0213도입니다. 팔 길이에서 읽을 때 1px는 약 0.26mm(1/96인치)에 해당합니다.
아래 이미지는 읽기 거리에 따라 기준 픽셀의 크기가 어떻게 달라지는지를 보여줍니다: 71cm(28인치) 거리에서는 기준 픽셀이 0.26mm, 3.5m(12피트) 거리에서는 기준 픽셀이 1.3mm가 됩니다.

두 번째 이미지는 장치의 해상도가 픽셀 단위에 미치는 영향을 보여줍니다: 1px × 1px 영역이 저해상도 장치(예: 일반 모니터)에서는 점 하나로, 고해상도 장치(예: 프린터)에서는 16개의 점으로 채워집니다.

디바이스 픽셀은 장치 출력에서 색상의 전체 범위를 표시할 수 있는 가장 작은 면적 단위입니다. 일반적인 컬러 디스플레이에서는 빨강, 초록, 파랑 서브픽셀을 포함하는 정사각형 또는 직사각형 영역입니다. 일부 비전통적 출력 장치는 이 정의를 흐릴 수 있으며, 어떤 색상은 더 높은 해상도로 표시될 수도 있습니다. 이런 장치들도 "디바이스 픽셀"과 동등한 개념을 제공합니다.
7. 기타 수량
7.1. 각도 단위: <angle> 타입과 deg, grad, rad, turn 단위
각도 값은 <dimension>으로, <angle>로 표시됩니다. 각도 단위 식별자는 다음과 같습니다:
- deg
- 도(degree). 원 한 바퀴는 360도입니다.
- grad
- 그라디안(gradian). "gon" 또는 "grade"라고도 합니다. 원 한 바퀴는 400그라디안입니다.
- rad
- 라디안(radian). 원 한 바퀴는 2π 라디안입니다.
- turn
- 턴(turn). 원 한 바퀴는 1턴입니다.
예를 들어, 직각은 90deg 또는 100grad 또는 0.25turn 또는 약 1.57rad입니다.
모든 <angle> 단위는 호환되며, deg가 이들의 정준 단위입니다.
예를 들어, linear-gradient() 함수에서 그라디언트의 방향을 결정하는 <angle>도 방위 각으로 해석됩니다.
참고: 레거시 이유로, 일부 <angle> 사용처에서는 단위 없는 0을 0deg로 해석할 수 있습니다. 그러나 이는 일반적으로 적용되지 않으며, 앞으로 <angle> 타입의 신규 사용처에서는 허용되지 않습니다.
7.2. 지속 시간 단위: <time> 타입과 s, ms 단위
시간 값은 차원이며, <time>으로 표시됩니다. 시간 단위 식별자는 다음과 같습니다:
- s
- 초(second).
- ms
- 밀리초(millisecond). 1초는 1000밀리초입니다.
모든 <time> 단위는 호환되며, s가 이들의 정준 단위입니다.
속성에 따라 시간 값이 특정 범위로 제한될 수 있습니다. 허용된 범위를 벗어난 값은 선언이 무효가 되어 무시되어야 합니다.
7.3. 주파수 단위: <frequency> 타입과 Hz, kHz 단위
주파수 값은 차원이며, <frequency>로 표시됩니다. 주파수 단위 식별자는 다음과 같습니다:
- Hz
- 헤르츠(Hertz). 1초당 발생 횟수를 나타냅니다.
- kHz
- 킬로헤르츠(KiloHertz). 1킬로헤르츠는 1000헤르츠입니다.
예를 들어, 소리의 피치를 나타낼 때 200Hz(또는 200hz)는 저음, 6kHz(또는 6khz)는 고음입니다.
모든 <frequency> 단위는 호환되며, hz가 이들의 정준 단위입니다.
참고: 단위는 ASCII 대소문자 구분 없이 소문자로 직렬화됩니다. 예: 1Hz는 1hz로 직렬화됩니다.
7.4. 해상도 단위: <resolution> 타입과 dpi, dpcm, dppx 단위
해상도 단위는 차원이며, <resolution>로 표시됩니다. 해상도 단위 식별자는 다음과 같습니다:
- dpi
- 인치당 점(Dots per inch).
- dpcm
- 센티미터당 점(Dots per centimeter).
- dppx
- x
- CSS px 단위당 점.
<resolution> 단위는 한 "점"의 크기를 나타내며, CSS in, cm, px 중 몇 개에 몇 개의 점이 들어가는지로 표시됩니다. 사용 예시는 resolution 미디어 쿼리([MEDIAQ])나 image-resolution 속성([CSS3-IMAGES])을 참고하세요.
모든 <resolution> 단위는 호환되며, dppx가 이들의 정준 단위입니다.
<resolution> 값의 허용 범위는 항상 음수를 제외하며, 추가적으로 명시된 범위도 적용됩니다.
CSS in과 CSS px의 1:96 고정 비율로 인해, 1dppx는 96dpi와 동일합니다. 이는 CSS에서 이미지를 표시할 때의 기본 해상도와 일치합니다. image-resolution을 참고하세요.
@media ( min-resolution:2 dppx ) { ...}
8. 별도 정의된 데이터 타입
일부 데이터 타입은 자체 모듈에서 정의됩니다. 이 예시는 여러 명세에서 사용되는 가장 일반적인 데이터 타입 몇 가지를 다룹니다.
8.1. 색상: <color> 타입
<color> 데이터 타입은 [CSS-COLOR-4]에서 정의됩니다. UA는 <color>를 그 정의대로 해석해야 합니다.
8.1.1. <color>의 조합
보간(Interpolation)은 <color>에 대해 CSS Color 4 § 12. 색상 보간에서 정의되어 있습니다. 보간은 CSS Color 4 § 12.3 알파와 함께 보간에 정의된 대로 프리멀티플라이드 컬러 사이에서 수행됩니다.
<color> 타입은 가산적이 아님(not additive)입니다.
참고: CSS WG는 이슈를 통해 <color>의 더하기(addition) 사용 사례를 받고 있으며, 향후 <color>를 가산적으로 만드는 것을 고려할 수 있습니다.
8.2. 이미지: <image> 타입
<image> 데이터 타입은 [CSS3-IMAGES]에서 정의됩니다. UA가 CSS Images Level 3 또는 후속 명세를 지원하는 경우 <image>를 그 정의대로 해석해야 하며, 아직 CSS Images Level 3를 지원하지 않는 UA는 <image>를 <url>로 해석해야 합니다.
8.2.1. <image>의 조합
참고: <image>의 보간은 CSS Images 3 § 6 보간에 정의되어 있습니다.
이미지는 가산적이 아닙니다.
8.3. 2D 위치 지정: <position> 타입
<position> 값은 오브젝트 영역(예: 배경 이미지)의 위치를 위치 지정 영역(예: 배경 위치 지정 영역) 내에서 지정합니다. 이는 background-position에 대해 명세된 대로 계산 및 해석됩니다. [CSS3-BACKGROUND]
<position> =[ [ left | center | right | top | bottom | <length-percentage>] |[ left | center | right] &&[ top | center | bottom] |[ left | center | right | <length-percentage>] [ top | center | bottom | <length-percentage>] |[ [ left | right] <length-percentage>] &&[ [ top | bottom] <length-percentage>] ]
참고: background-position 속성은 세 값 구문(three-value syntax)도 허용합니다. 하지만 길이 또는 백분율 구성요소가 있는 속성 값과 결합될 때 파싱의 모호함을 초래하므로, 일반적으로는 허용되지 않습니다.
8.3.1. <position> 파싱
다른 키워드, <length>, <percentage> 등과 함께 문법에 명시된 경우, <position>은 그리디(greedy)하게 파싱되어, 가능한 많은 구성요소를 소비합니다.
8.3.2. <position> 직렬화
지정 값의 <position>을 직렬화할 때:
- 구성요소가 하나만 지정된 경우:
-
-
암시된 center 키워드가 추가되어, 2-구성요소 값으로 직렬화됩니다.
-
- 구성요소가 두 개인 경우:
-
-
키워드는 키워드로 직렬화됩니다.
-
<length-percentage>는 <length-percentage>로 직렬화됩니다.
-
구성요소는 가로, 그 다음 세로 순서로 직렬화됩니다.
-
- 구성요소가 네 개인 경우:
-
-
키워드와 오프셋 모두 직렬화됩니다.
-
구성요소는 가로, 그 다음 세로 순서로 직렬화됩니다.
-
참고: <position> 값은 단일 값으로 직렬화되지 않으며, 비록 단일 값이 같은 동작을 한다 해도, 일부 문법에서 <position> 바로 옆에 <length>가 오는 경우 파싱의 모호함을 피하기 위해서입니다. 예: transform-origin.
참고: 계산 값은 항상 오프셋 두 개(키워드 없이)로 직렬화되며, 계산 값에는 구문 구분이 보존되지 않기 때문입니다.
8.3.3. <position>의 조합
보간은 <position> 각 구성요소(x, y)를 좌상단으로부터의 오프셋으로 정규화된 <length-percentage>로 독립적으로 보간하는 것으로 정의됩니다.
더하기(addition)도 <position> 각 구성요소(x, y)를 좌상단으로부터의 오프셋으로 정규화된 <length-percentage>로 독립적으로 더하는 것으로 정의됩니다.
9. 함수 표기법
함수 표기법은 더 복잡한 타입을 표현하거나 특별한 처리를 호출할 수 있는 컴포넌트 값의 한 종류입니다. 구문은 함수 이름 다음에 바로 왼쪽 괄호가 오며 (즉, <function-token>), 이어서 표기법의 인수들이 오고, 그 다음 오른쪽 괄호가 옵니다. 키워드처럼, 함수 이름은 ASCII 대소문자 구분 없이 사용됩니다. 공백은 괄호 바로 안쪽에 허용되지만, 선택사항입니다. 함수는 여러 인수를 받을 수 있으며, 인수들은 CSS 속성 값과 유사하게 포맷됩니다. 자세한 내용은 § 2.6 함수 표기법 정의를 참조하세요.
참고: 함수 표기법 중 일부 레거시 표기(예: rgba())는 불필요하게 콤마를 사용하지만, 일반적으로 콤마는 리스트의 항목을 구분하거나 문법상 모호한 부분을 구분할 때만 사용됩니다. 콤마로 인수를 구분할 때는 공백이 콤마 앞뒤에 있어도 되고 없어도 됩니다.
background : url ( http://www.example.org/image ); color : rgb ( 100 , 200 , 50 ); content : counter ( list-item) ". " ; width : calc ( 50 % -2 em );
수학 함수들은 아래에서 정의되어 있습니다. 그 외의 함수 표기법은 각자의 모듈에서 정의되어 있습니다. 예를 들어, <color> 함수는 [CSS-COLOR-4] 및 [CSS-COLOR-5]에서 정의되어 있습니다.
10. 수학식
수학 함수 (calc(), clamp(), sin() 등 이 장에서 정의된 함수) 는 CSS의 수치 값을 수학식으로 작성할 수 있게 해줍니다.
수학 함수는 다음 중 하나의 수치 값을 나타냅니다:
...또는 <length-percentage> 등 혼합 타입도 가능하며, 해당 값이 유효한 모든 곳에서 사용할 수 있습니다.
10.1. 기본 산술: calc()
calc() 함수는 덧셈(+), 뺄셈(-), 곱셈(*), 나눗셈(/), 괄호를 사용해 수치 값에 기본 산술 연산을 할 수 있게 하는 수학 함수입니다.
calc() 함수는 하나의 계산식(calculation)을 포함하며, 값과 연산자가 섞여 있는 시퀀스이고, 괄호로 묶일 수도 있으며 (<calc-sum> 문법과 일치), 표현식을 표준 연산자 우선순위 규칙에 따라 평가한 결과를 나타냅니다 (*와 /가 +와 -보다 우선, 그렇지 않으면 연산자는 왼쪽에서 오른쪽 순으로 평가). calc() 함수는 내부 계산식의 결과를 나타냅니다.
계산식의 구성요소는 (5px처럼) 리터럴 값, 다른 수학 함수, 또는 var()와 같은 다른 표현식(예: <length>에 유효한 값)을 포함할 수 있습니다.
수학 함수는 서로 다른 단위를 사용하는 값을 결합할 때 사용할 수 있습니다. 아래 예시에서 저자는 각 section의 마진 박스가 전체 공간의 1/3을 차지하도록 하고 싶으므로 우선 100%/3에서 시작해, 요소의 테두리와 마진을 빼줍니다. (box-sizing만으로는 테두리와 패딩까지 자동으로 처리 가능하지만, 마진까지 포함하려면 수학 함수가 필요합니다.)
section{ float : left; margin : 1 em ; border : solid1 px ; width : calc ( 100 % /3 -2 *1 em -2 *1 px ); }
마찬가지로, 아래 예시에서는 그라디언트가 요소의 처음과 마지막 20px에서만 색상 전환을 보여줍니다:
.fade{ background-image : linear-gradient ( silver0 % , white20 px , whitecalc ( 100 % -20 px ), silver100 % ); }
수학 함수는 값을 더 자연스럽고 읽기 쉽게 표현하는 데에도 쓸 수 있습니다. 예를 들어, 아래는 font-size를 뷰포트 안에 정확히 35em이 들어가도록 설정해서, 어떤 화면 크기에서도 대략 같은 양의 텍스트가 항상 화면을 채우게 합니다.
:root{ font-size : calc ( 100 vw /35 ); }
기능적으로는 font-size: 2.857vw와 같지만, 코드를 읽는 사람에게 35em이 뷰포트에 딱 맞는다는 의도가 훨씬 더 명확하게 전달됩니다. 반면 2.857이 100/35의 근삿값임을 나중에 읽는 사람이 직접 역산해야 합니다.
연산자에 대해 표준 수학적 우선순위 규칙이 적용됩니다: calc(2 + 3 * 4)는 14와 같고, 20이 아닙니다.
괄호로 우선순위를 조절할 수 있습니다: calc((2 + 3) * 4)는 20과 같습니다.
괄호와 중첩된 calc() 함수 사용은 동등합니다; 위 식은 calc(calc(2 + 3) * 4)로도 쓸 수 있습니다. var()로 값 조합을 점진적으로 만들 때 유용합니다. 예시:
.aspect-ratio-box{ --ar : calc ( 16 /9 ); --w : calc ( 100 % /3 ); --h : calc ( var ( --w) /var ( --ar)); width : var ( --w); height : var ( --h); }
--ar는 사실 --ar: (16 / 9);로 단순히 쓸 수도 있지만, --w는 (아래 width)에서 단독으로도, --h에서 calc()의 구성요소로도 사용되기 때문에, 전체를 calc() 함수로 써야 합니다.
10.2. 비교 함수: min(), max(), clamp()
min(), max(), clamp() 비교 함수는 여러 계산식을 비교하여 그 중 하나의 값을 나타냅니다.
min() 또는 max() 함수는 하나 이상의 콤마로 구분된 계산식을 가지며, 각각 가장 작은 값(가장 음수) 또는 가장 큰 값(가장 양수)을 나타냅니다.
clamp() 함수는 세 개의 계산식—최소값, 중심값, 최대값—을 받아, 중심 계산값을 최소와 최대 계산값에 따라 제한(clamp)합니다. 만약 상한/하한이 충돌하면 하한(min) 쪽을 우선합니다. (즉, clamp(MIN, VAL, MAX)는 max(MIN, min(VAL, MAX))와 정확히 같은 값을 나타냅니다.)
최소 또는 최대 계산식 (또는 둘 다) 대신 키워드 none을 쓸 수 있으며, 이 경우 해당 방향(상한/하한)에서 제한하지 않음을 의미합니다. (즉, clamp(MIN, VAL, none)는 max(MIN, VAL)과 같고, clamp(none, VAL, MAX)는 min(VAL, MAX)과 같으며, clamp(none, VAL, none)은 그냥 calc(VAL)과 같습니다.)
세 함수 모두에서, 인수 계산식은 <number>, <dimension>, <percentage> 등 어떤 것이든 가능하지만, 반드시 일관된 타입이어야 하며, 그렇지 않으면 함수는 무효가 됩니다. 결과 타입은 일관된 타입이 됩니다.
min(), max(), clamp()는 값이 "안전"한 한계를 넘지 않도록 보장할 때 쓸 수 있습니다: 예를 들어, 뷰포트 단위로 font-size를 지정할 때도 최소 크기를 설정해 가독성을 보장할 수 있습니다:
.type{ /* font-size를 vw와 vh 평균의 10배로 지정하지만, 12px보다 작아지지 않게 합니다. */ font-size:max ( 10 *( 1 vw +1 vh ) /2 , 12 px ); }
참고: 각 인수에 전체 수학식을 쓸 수 있으므로, calc()를 중첩할 필요가 없습니다! 적용해야 할 제약이 많으면 인수를 두 개 이상 줄 수도 있습니다.
.type{ /* font-size가 12px~100px 사이에만 머물게 강제 */ font-size:clamp ( 12 px , 10 *( 1 vw +1 vh ) /2 , 100 px ); }
최소값만 강제하고, font-size가 얼마든 커질 수 있게 하려면:
.type{ /* font-size가 최소 12px이 되도록 강제 */ font-size:clamp ( 12 px , 10 *( 1 vw +1 vh ) /2 , none); }
다른 해석 방식이 필요하다면 clamp()와 min(), max()를 조합해 구현할 수 있습니다:
- MAX가 MIN을 이기게 하려면:
-
clamp(min(MIN, MAX), VAL, MAX). MAX 계산을 반복하지 않으려면, clamp() 정의에 맞게 함수의 중첩 순서를 바꿔 min(MAX, max(MIN, VAL))로 쓸 수 있습니다.
- MAX와 MIN이 "순서가 바뀌면" 서로 교환하게 하려면:
-
clamp(min(MIN, MAX), VAL, max(MIN, MAX)). 아쉽게도 이 방법은 MIN, MAX를 반복하는 수밖에 없습니다.
10.3. 계단값 함수: round(), mod(), rem()
계단값 함수인 round(), mod(), rem()는 모두 주어진 값을 또 다른 "스텝 값"에 따라 각각 다른 방식으로 변환합니다.
round(<rounding-strategy>?, A, B?) 함수는 선택적인 반올림 전략과 두 개의 계산식 A, B를 포함하며, A의 값을 B의 정수 배수 중 A에 가장 가깝게, 반올림 전략에 따라 위 또는 아래로 반올림하여 반환합니다. 인수 계산식은 <number>, <dimension>, <percentage>가 될 수 있지만, 반드시 일관된 타입이어야 하며, 그렇지 않으면 함수가 무효가 됩니다. 결과의 타입은 일관된 타입입니다.
A가 B의 정수 배수와 정확히 같으면, round()는 A를 그대로 반환합니다 (A가 0⁻인지 0⁺인지도 그대로 유지). 그렇지 않으면, A와 가장 가까운 B의 두 정수 배수 lower B (−∞ 쪽)와 upper B (+∞ 쪽)가 존재합니다. 아래 <rounding-strategy>가 두 값 중 어떤 것을 선택할지 결정합니다:
- nearest
-
lower B와 upper B 중 A와의 차이(절대값)가 더 작은 쪽을 선택합니다. 만약 둘 다 차이가 같으면 (A가 두 값의 정중앙에 있으면), upper B를 선택합니다.
- up
-
upper B를 선택합니다.
- down
-
lower B를 선택합니다.
- to-zero
-
lower B와 upper B 중 0과의 차이(절대값)가 더 작은 쪽을 선택합니다.
lower B가 0이 되면, 반드시 0⁺입니다; upper B가 0이 되면, 반드시 0⁻입니다.
<rounding-strategy>가 생략되면, 기본값은 nearest입니다. (즉, 가장 가까운 정수로 반올림.) A의 타입이 <number>와 일치하면, B를 생략할 수 있고, 기본값은 1입니다. 그렇지 않으면 B를 생략하면 무효입니다.
CSSOM이 어떻게 반올림하는지 명확히 해야 하고, CSS 함수도 기본적으로 동일한 방식으로 반올림하는 것이 좋습니다. 어떤 동작을 기본값으로 해야 할까요? [Issue #5689]
참고: JavaScript 등 다른 프로그래밍 언어는
반올림 전략을 별도의 함수로 분리하기도 합니다.
JS의 Math
는 CSS의 round(down,
...)와 같고,
JS의 Math
는 CSS의 round(up,
...)와 같으며,
JS의 Math
는 CSS의 round(to-zero,
...)와 같고,
JS의 Math
는 CSS의 round(nearest,
...) 또는 round(...)와 같습니다.
참고: <rounding-strategy> 키워드는 block-step-size의 키워드와 동일하며, 동작도 같습니다. (block-step-size에는 to-zero가 없는데, 블록 크기는 항상 0 이상이므로 to-zero와 down이 동일합니다.)
나머지 함수 mod(A, B)와 rem(A, B)도 두 개의 계산식 A, B를 포함하며, A에서 B의 정수 배수 중 A에 가장 가까운 값을 빼서 반환합니다. 인수 계산식은 <number>, <dimension>, <percentage> 중 하나여야 하며, 반드시 같은 타입이어야 하며, 그렇지 않으면 함수가 무효입니다. 결과도 인수와 같은 타입입니다.
두 함수는 매우 비슷하며, 두 인수가 모두 양수이거나 모두 음수일 때는 결과가 완전히 같습니다: 함수의 값은 A에서 적절한 정수배의 B를 더하거나 빼서 값을 0과 B 사이로 이동시킨 값입니다. (구체적으로, 범위는 0을 포함하고 B는 포함하지 않습니다. 더 구체적으로 B가 양수면 0⁺에서 시작, B가 음수면 0⁻에서 시작합니다.)
마찬가지로, mod(-140deg, -90deg)는 -50deg가 되며, -140deg에 -90deg * 1을 더하면 -50deg이 되고, 이 값이 0deg과 -90deg 사이의 유일한 값입니다.
이 예시를 rem()으로 평가해도 결과는 동일합니다.
A값과 B스텝이 0의 양쪽에 있으면 두 함수의 동작이 달라집니다: mod()(modulus 약자)는 위에서 설명한 대로 값을 0과 B 사이로 이동시키는 B의 정수배를 선택합니다 (즉 결과는 0이거나, B의 부호를 가짐. A의 부호가 아님), rem()(remainder 약자)는 값을 0과 -B 사이로 이동시키는 B의 정수배를 선택해서 결과의 부호가 바뀌지 않도록 합니다.
반면 rem(-18px, 5px)는 -3px이 되며, -18px에 5px * 3을 더하면 -3px이 되고, 이는 -18px과 부호가 같으면서 0px과 -5px 사이에 있습니다.
마찬가지로, mod(140deg, -90deg)는 -40deg이 되고(140deg에 -90deg * 2를 더해 0deg과 -90deg 사이로 옮김), rem(140deg, -90deg)는 50deg이 됩니다.
언제 mod()와 rem()을 선택해야 하나요?
일반적으로 이 연산을 사용하는 쪽이 스텝 값(B)을 제어하며, 알 수 없는 값 A를 조정합니다. 결과적으로, 결과가 0과 B 사이(부호와 관계없이)로 나오는 것이 보통 더 기대에 부합하므로 mod()를 써야 합니다.
예시로, 값이 짝수 픽셀인지 홀수 픽셀인지 확인하려면 mod(A, 2px)는 값이 전체 픽셀일 때 0px 또는 1px만 반환하고, a의 부호와 무관합니다. rem(A, 2px)는 A가 짝수면 0px을, 홀수면 1px 또는 -1px을 A의 부호에 따라 반환합니다.
반대 상황도 가끔 있으므로
rem()도 제공됩니다.
또한 rem()은 JavaScript
연산자의 동작과 동일하므로,
CSS와 JS의 결과를 완전히 일치시키고 싶다면 rem()을 사용할 수 있습니다.
참고: mod() 및 rem()는 다른 함수로 직접 정의할 수도 있습니다: mod(A, B)는 calc(A - sign(B)*round(down, A*sign(B), B))와 같고(즉, B가 양수일 때는 round(down), 음수일 때는 round(up)), rem(A, B)는 calc(A - round(to-zero, A, B))와 같습니다. (이 식은 0⁺, 0⁻를 항상 제대로 처리하지는 않는데, 0⁻ 의미가 덧셈에서 교환법칙이 아니기 때문입니다.)
10.3.1. 인수 범위
round(A, B)에서, B가 0이면, 결과는 NaN입니다. A와 B가 모두 무한대이면, 결과는 NaN입니다.
A가 무한대이고 B가 유한이면, 결과는 같은 무한대입니다.
A가 유한이고 B가 무한이면, 결과는 <rounding-strategy>와 A의 부호에 따라 달라집니다:
- nearest
- to-zero
-
A가 양수거나 0⁺이면 0⁺를 반환, 그렇지 않으면 0⁻를 반환합니다.
- up
-
A가 양수(0 제외)면 +∞ 반환, A가 0⁺면 0⁺, 그렇지 않으면 0⁻ 반환.
- down
-
A가 음수(0 제외)면 −∞ 반환, A가 0⁻면 0⁻, 그렇지 않으면 0⁺ 반환.
mod(A, B) 또는 rem(A, B)에서, B가 0이면, 결과는 NaN입니다. A가 무한대이면, 결과는 NaN입니다.
mod(A, B)에서만, B가 무한대이면서 A와 B의 부호가 반대(0도 포함)인 경우, 결과는 NaN입니다.
참고: 그 외 "무한대 B" 경우는 모두 유효하며, 결과는 즉시 A를 반환합니다.
10.4. 삼각함수: sin(), cos(), tan(), asin(), acos(), atan(), atan2()
삼각함수 sin(), cos(), tan(), asin(), acos(), atan(), atan2()는 기본적인 삼각관계를 계산합니다.
sin(A), cos(A), tan(A) 함수는 모두 단일 계산식을 포함하며, 이 값은 <number> 또는 <angle>이어야 하고, 인수의 결과를 라디안으로 해석하여 해당 함수 값을 계산합니다. (즉, sin(45deg), sin(.125turn), sin(3.14159 / 4) 모두 약 .707로 동일한 값을 나타냅니다.) 이 함수들은 모두 <number>를 반환하며, 반환 타입은 입력 계산식의 타입에 일관성 있게 맞춰집니다. sin()과 cos()는 항상 -1~1 사이의 값을 반환하고, tan()은 −∞~+∞ 어떤 값도 반환할 수 있습니다. (§ 10.9 타입체크에서 수학 함수가 ∞를 다루는 법 설명.)
asin(A), acos(A), atan(A) 함수는 "아크" 또는 "역" 삼각함수로, 각각의 "정방향" 삼각함수의 역함수입니다. 모두 단일 계산식을 가지며, <number>여야 하며, 결과도 라디안으로 해석하여 함수 값을 계산, <angle>을 나타내며 반환 타입은 입력 계산식 타입에 일관성 있게 맞춰집니다. asin()의 각도는 [-90deg, 90deg] 범위로, acos()는 [0deg, 180deg], atan()은 [-90deg, 90deg]로 정규화되어야 합니다.
atan2(A, B) 함수는 콤마로 구분된 두 계산식 A, B를 받습니다. 둘 다 <number>, <dimension>, <percentage>가 될 수 있지만, 반드시 일관된 타입이어야 하며, 그렇지 않으면 함수가 무효입니다. 이 함수는 양의 X축과 점 (B,A) 사이의 <angle>을 반환하며, 반환 타입은 입력 계산식 타입에 일관성 있게 맞춰집니다. 반환 각도는 (-180deg, 180deg] 범위(즉, -180deg 초과 180deg 이하)로 정규화되어야 합니다.
참고: atan2(Y, X)는 일반적으로 atan(Y / X)와 동일하지만, 음수 성분이 포함될 수 있는 점에서 더 정확한 결과를 줍니다. atan2(1, -1)은 (-1, 1)에 대응하며 135deg를 반환하고, atan2(-1, 1)은 (1, -1)에 대응하며 -45deg를 반환합니다. 반면 atan(1 / -1), atan(-1 / 1)은 둘 다 내부 계산이 -1이므로 -45deg만 반환합니다.
10.4.1. 인수 범위
sin(A), cos(A), tan(A)에서 A가 무한대이면, 결과는 NaN입니다. (§ 10.9 타입체크에서 수학 함수가 NaN을 다루는 법 설명.)
sin(A) 또는 tan(A)에서 A가 0⁻이면, 결과도 0⁻입니다.
tan(A)에서, A가 비분연점(예: 90deg, 270deg
등)이면,
수치 결과는 구현 정의입니다.
만약 구현체가 이런 입력을 정확히 표현할 수 있으면,
에서는 +∞,
에서는 −∞를 반환
해야 하지만,
구현체가 정확히 표현할 필요는 없으며,
(그럴 수 없으면 입력에 가장 근접한 값에 대한 결과를 반환)
저자는 tan()이 이런 입력에 어떤
값을 반환할지 기대해서는 안 됩니다.
왜 이 경우가 구현 정의인가요?
탄젠트 함수는 비분연점에서 불연속이며, 한쪽에서는 무한대로, 다른 쪽에서는 음의 무한대로 발산하며, 정확한 비분연점에서는 정의되지 않습니다.
또한 비분연점이 구현체에서 정확히 표현 가능한지는, 내부적으로 각도를 어떻게 저장/계산하냐에 따라 다릅니다. 도 단위로 쓰면 단순하지만(90deg 등), 라디안으로 쓰면 초월수(pi / 2 등)라 정확히 표현할 수 없습니다. 따라서 특정 입력값에 대한 동작을 정의하는 것도 어렵습니다. 라디안을 내부적으로 쓰는 경우, 입력이 충분히 근접할 때 정의된 값을 반환하도록 퍼지 매칭이 필요합니다.
웹의 다른 주요 언어인 JS도 이 함수들은 라디안만 받으므로 정확히 비분연점을 맞출 수 없고 (다른 대부분의 언어도 마찬가지), JS로 코딩하는 저자도 이런 입력에 특정 결과를 기대할 수 없으니 CSS에서도 크게 다를 이유가 없습니다.
비분연점 값을 정확히 표현 가능한 구현체라면 atan() 함수와의 왕복 일관성도 보장됩니다: tan(atan(X))과 atan(tan(X))이 모든 X에 대해 (대략) X를 반환하게 됩니다. 또한 atan() 반환 범위 내에서는 함수가 연속됩니다.
asin(A) 또는 acos(A)에서, A가 -1 미만이거나 1 초과이면, 결과는 NaN입니다.
acos(A)에서, A가 정확히 1이면, 결과는 0입니다.
asin(A) 또는 atan(A)에서, A가 0⁻이면, 결과도 0⁻입니다.
atan(A)에서, A가 +∞이면 90deg를, A가 −∞이면 -90deg를 반환합니다.
atan2(Y, X)에서, 아래 표는 모든 특이 인수 조합에 대한 결과를 나타냅니다:
X | |||||||
---|---|---|---|---|---|---|---|
−∞ | -유한 | 0⁻ | 0⁺ | +유한 | +∞ | ||
Y | −∞ | -135deg | -90deg | -90deg | -90deg | -90deg | -45deg |
-유한 | -180deg | (일반) | -90deg | -90deg | (일반) | 0⁻deg | |
0⁻ | -180deg | -180deg | -180deg | 0⁻deg | 0⁻deg | 0⁻deg | |
0⁺ | 180deg | 180deg | 180deg | 0⁺deg | 0⁺deg | 0⁺deg | |
+유한 | 180deg | (일반) | 90deg | 90deg | (일반) | 0⁺deg | |
+∞ | 135deg | 90deg | 90deg | 90deg | 90deg | 45deg |
참고: 이 모든 동작은 대부분의 프로그래밍 언어(특히 JS)의 "표준" 함수 정의와 일치하도록 설계되었습니다.
10.5. 지수 함수: pow(), sqrt(), hypot(), log(), exp()
지수 함수—pow(), sqrt(), hypot(), log(), exp()—는 인수를 이용해 다양한 지수 계산을 수행합니다.
pow(A, B) 함수는 콤마로 구분된 두 개의 계산식 A와 B를 포함하며, 둘 다 <number>로 계산되어야 하며, A의 B 제곱을 반환합니다. 반환 값의 타입은 <number>입니다. 입력 계산식의 타입이 일관되지 않으면 함수는 무효가 되며, 결과 타입은 일관된 타입입니다.
sqrt(A) 함수는 하나의 계산식을 포함하며, <number>로 계산되어야 합니다. 해당 값의 제곱근을 반환하며, 반환 타입은 <number>이고, 반환 타입은 입력 계산식 타입에 일관성 있게 맞춥니다. (sqrt(X)와 pow(X, .5)는 거의 동일하지만, 오류 처리에서만 차이가 있습니다. sqrt()는 자주 쓰이기 때문에 편의상 별도로 제공합니다.)
hypot(A, …) 함수는 하나 이상의 콤마로 구분된 계산식을 포함하며, 각각의 계산식 값으로 이루어진 N차원 벡터의 크기(길이)를 반환합니다. (즉, 인수 각각의 제곱의 합의 제곱근) 인수 계산식은 <number>, <dimension>, <percentage>가 될 수 있으나, 일관된 타입이어야 하며, 그렇지 않으면 함수는 무효입니다. 결과 타입은 일관된 타입입니다.
왜 hypot()은 단위값을 허용하고, pow(), sqrt()는 숫자만 쓸 수 있을까요?
hypot(30px, 40px)처럼 쓸 수 있으며, 이 값은 50px이 됩니다. 하지만 sqrt(pow(30px, 2) + pow(40px, 2))처럼 쓸 수는 없습니다. 둘은 수학적으로는 동일한 값이지만, CSS에서는 다릅니다.
이유는 두 가지입니다: 지수 연산의 수치 정밀도, 그리고 저자의 기대와의 충돌입니다.
첫째, 수치 정밀도. CSS production(<length> 등)에 타입이 일치(match)하려면, 단위 지수가 정확히 1이어야 합니다. 이론적으로 pow(pow(30px, 3), 1/3)은 내부 pow(30px, 3)이 27000, 타입은 «[ "length" → 3 ]»(즉 <length>³), pow(X, 1/3)이 1/3 제곱하여 지수도 곱해 «[ "length" → 1 ]»이 되어 일치해야 합니다.
수학적으로는 항상 잘 맞지만,
컴퓨터의 이진 부동소수점 현실에서는
제곱/제곱근이 정확히 상쇄되지 않아 예기치 않게 무효가 될 수 있습니다.
(JS 예시: Math.
결과는 정확히 30이 아니며,
이 3/10이 아니기 때문입니다.
는 실제로 1보다 약간 큽니다.)
값을 number로 변환해 계산 후 원하는 단위로 다시 바꾸도록 요구하는 것은 불편하지만, 수치 정밀도 문제로 인한 오류를 막을 수 있습니다: calc(pow(pow(30px / 1px, 3), 1/3) * 1px)는 <length>로 평가되며, 수치가 정확히 30은 아닐지라도 매우 근접합니다.
둘째, 기대 충돌. 많은 저자는 pow(30px, 2)가 900px이 되리라 기대합니다(Sass 이슈 예시). 하지만 이 방식은 인수의 단위에 따라 결과가 달라지므로, pow(1em, 2)는(16px 기준) 1em, pow(16px, 2)는 256px 또는 16em이 되어, 동일한 입력이라도 단위에 따라 결과가 완전히 달라집니다. 이런 입력 의존성은 CSS의 자유로운 정준화에 문제를 일으키고, pow(2em + 10px, 2) 같은 복잡한 식도 해석이 어렵게 됩니다.
따라서, 값을 숫자로 변환해서 연산 후 다시 단위로 바꾸도록 요구하면 이러한 문제를 회피할 수 있습니다. pow(30, 2)는 900이 되고, 저자가 원하는 해석대로 쓸 수 있습니다.
반면, hypot()는 이런 문제가 없습니다. 단위의 수치 정밀도 영향도 없고, 입력과 출력이 모두 같은 타입이므로 결과가 단위에 의존하지 않습니다. 예: hypot(3em, 4em), hypot(48px, 64px)은 1em = 16px일 때 각각 5em, 80px이 됩니다. 즉 hypot()에는 단위값을 허락해도 안전합니다.
log(A, B?) 함수는 하나 혹은 두 개의 계산식(값, 로그의 밑, 기본값은 e)을 포함하며, 모두 <number>여야 하며, 로그(base B) A의 값을 반환합니다. 반환 타입은 <number>이며, 입력 계산식 타입에 일관성 있게 맞춥니다.
exp(A) 함수는 하나의 계산식을 포함하며, <number>여야 하며, pow(e, A)와 동일한 값을 반환합니다. 반환 타입은 <number>이고, 입력 계산식 타입에 일관성 있게 맞춥니다.
이러한 크기는 아래처럼 커스텀 속성에 쉽게 정의할 수 있습니다:
:root{ --h6 : calc ( 1 rem *pow ( 1.5 , -1 )); --h5 : calc ( 1 rem *pow ( 1.5 , 0 )); --h4 : calc ( 1 rem *pow ( 1.5 , 1 )); --h3 : calc ( 1 rem *pow ( 1.5 , 2 )); --h2 : calc ( 1 rem *pow ( 1.5 , 3 )); --h1 : calc ( 1 rem *pow ( 1.5 , 4 )); }
...미리 계산된 5.0625rem(calc(1rem * pow(1.5, 4))의 결과) 등의 값을 직접 쓰는 것보다, 스타일시트에서 값의 출처가 더 명확합니다.
여러 인수를 주면, 각 인수만큼의 길이를 가진 박스의 주대각선 길이를 반환합니다. 대상 요소가 X, Y, Z만큼 변환될 때 실제 이동 거리를 구하는 등, 트랜스폼 관련 계산에 유용할 수 있습니다.
예: hypot(30px, 40px)는 50px이 되며, translate(30px, 40px) 트랜스폼으로 요소가 이동하는 거리를 의미합니다. 워드클라우드 등에서 원점에서 멀어질수록 요소를 작게 만들고 싶을 때, 이 거리를 스케일 계산에 쓸 수 있습니다.
밑이 10인 로그(예: 자리수 카운트)나, 밑이 2인 로그(예: 비트수 카운트)가 필요하면 log(X, 10) 또는 log(X, 2)를 사용하면 됩니다.
10.5.1. 인수 범위
pow(A, B)에서, A가 음수 유한값이고, B도 유한값이면, B는 반드시 정수여야 하며, 아니면 결과는 NaN입니다.
A 또는 B가 무한대이거나 0인 경우, 아래 표에 따라 결과가 정해집니다:
A가 −∞ | A가 0⁻ | A가 0⁺ | A가 +∞ | |
---|---|---|---|---|
B가 −유한 | 홀수 정수면 0⁻, 아니면 0⁺ | 홀수 정수면 −∞, 아니면 +∞ | +∞ | 0⁺ |
B가 0 | 항상 1 | |||
B가 +유한 | 홀수 정수면 −∞, 아니면 +∞ | 홀수 정수면 0⁻, 아니면 0⁺ | 0⁺ | +∞ |
A < -1 | A = -1 | -1 < A < 1 | A = 1 | A > 1 | |
---|---|---|---|---|---|
B = +∞ | +∞ | NaN | 0⁺ | NaN | +∞ |
B = −∞ | 0⁺ | NaN | +∞ | NaN | 0⁺ |
sqrt(A)에서, A가 +∞면, 결과는 +∞. A가 0⁻면, 결과는 0⁻. A가 0보다 작으면, 결과는 NaN.
hypot(A, …)에서, 입력 중 하나라도 무한대이면, 결과는 +∞.
log(A, B)에서, B가 1이거나 음수면 B가 0~1 사이이거나 1보다 큰 값은 허용됩니다. 결과는 NaN. A가 음수면, 결과는 NaN. A가 0⁺ 또는 0⁻면, 결과는 −∞. A가 1이면, 결과는 0⁺. A가 +∞면, 결과는 +∞.
exp(A)에서, A가 +∞면, 결과는 +∞. A가 −∞면, 결과는 0⁺.
(§ 10.9 타입체크에서 수학 함수가 NaN과 무한대를 처리하는 방법을 참고하세요.)
동일한 JS 함수와의 유일한 차이점은, NaN이 모든 함수에서 "전염성"이 있다는 점이며, 인수 중 하나라도 NaN이면 무조건 NaN을 반환합니다.
JS 동작의 세부사항
JS에서는 NaN이 함수에 "전염"되지 않는 경우가 두 가지 있습니다:
-
Math
는. hypot( Infinity , NaN )
를 반환합니다.Infinity -
Math
는. pow( NaN , 0 )
을 반환합니다.1
논리는 NaN을 어떤 숫자로 바꿔도 반환값이 같기 때문입니다.
하지만 이 논리는 Math
함수 전체에 일관되게 적용되지 않습니다: Math
는
을 반환하며, Math
도 마찬가지입니다.
이것은 에러 코너케이스이기 때문에 JS에서는 일관성이 없으며, CSS에서는 더 높은 레벨에서 NaN 인식/처리가 이루어지는 경우가 많으므로, CSS에서는 일관성을 위해 모든 함수에서 NaN이 전염성을 가지도록 정의합니다.
10.6. 부호 관련 함수: abs(), sign()
부호 관련 함수—abs(), sign()—는 인수의 부호와 관련된 다양한 함수를 계산합니다.
abs(A) 함수는 하나의 계산식 A를 포함하고, A의 절댓값을 입력과 동일한 타입으로 반환합니다: A의 값이 양수이거나 0⁺이면 그대로, 아니면 -1 * A로 반환.
sign(A) 함수는 하나의 계산식 A를 포함하고, A의 값이 음수면 -1, 양수면 +1, 0⁺면 0⁺, 0⁻면 0⁻를 반환합니다. 반환 타입은 <number>이고, 입력 계산식 타입에 일관성 있게 맞춥니다.
참고: 두 함수 모두 인수의 완전히 단순화/해결된 형태에 동작하므로, 처음엔 직관적이지 않을 수 있습니다. 예를 들어 10%는 실제로 계산되는 값에 따라 양수 또는 음수가 될 수 있습니다. 예를 들어 background-position에서 양의 백분율은 배경 이미지가 배경 영역보다 큰 경우 음수 길이로 계산되고, 반대도 마찬가지입니다. 따라서 sign(10%)의 결과는 백분율이 어떻게 계산되는지에 따라 1 또는 -1이 될 수 있습니다. (또는 길이가 0이면 0이 될 수도 있습니다.)
10.7. 수치 키워드
계산식 내의 키워드는 리터럴로 표현하기 어렵거나 불가능한 값에 접근할 수 있게 해줍니다. 각 키워드마다 값, 타입, 언제 해석되는지(파싱 시, 계산값 시, 사용값 시)를 정의합니다.
10.7.1. 수치 상수: e, pi
삼각함수, 지수함수로 많은 복잡한 수치 연산이 가능하지만, 일부 계산은 수동으로 조합해야 하며, 이때 e나 π 같이 잘 알려진 상수를 포함할 때가 많습니다.
이러한 상수를 매번 여러 자리로 입력하게 하지 않기 위해, 일부는 미리 제공됩니다:
- e
-
자연로그의 밑, 약 2.7182818284590452354
- pi
-
원의 둘레와 지름의 비율, 약 3.1415926535897932
이 키워드들은 모두 <number>이며, 파싱 시점에 해석됩니다.
참고: 이 키워드는 반드시 계산식 내에서만 사용할 수 있습니다. (calc(pow(e, pi) - pi) 또는 min(pi, 5, e) 등) 계산식 밖에서 쓰면 일반 키워드처럼 처리되어 animation-name: pi;는 "pi"라는 애니메이션명을 의미하고, line-height: e;는 무효입니다. (line-height: 2.7와 같지 않음, line-height: calc(e);처럼 써야 함)
10.7.2. 특이 수치 상수: infinity, -infinity, NaN
계산식(또는 그 하위 트리)가 무한대거나 NaN이 될 때, 수치값으로 표현할 수 없습니다. 이런 특이값의 직렬화를 돕기 위해 다음 수학 상수가 추가 정의됩니다:
- infinity
-
양의 무한대(+∞) 값
- -infinity
-
음의 무한대(−∞) 값
- NaN
-
NaN 값
이 키워드들은 모두 <number>이며, 파싱 시 해석됩니다.
CSS 키워드답게 이들은 ASCII 대소문자 무시입니다. 따라서 calc(InFiNiTy)도 유효합니다. 단, NaN은 반드시 이 표준 대소문자로 직렬화해야 합니다.
참고: 이 키워드가 <number>이므로, 예를 들어 무한대 길이를 얻으려면 calc(infinity * 1px)처럼 써야 합니다.
참고: 이 상수는 주로 무한/NaN 값의 직렬화를 단순화하려고 정의된 것이지만, 최대값 표시 등에도 쓸 수 있습니다. 실무에서는 드물지만, 그런 경우 infinity를 쓰면 거대한 수를 직접 쓰는 것보다 의도가 명확합니다.
10.7.3. 수치 변수
다른 명세에서는 특정 상황에서 계산식에 사용할 수 있는 추가 키워드를 정의할 수 있습니다. 예: 상대 색상 문법은 각 색상 채널 값을 <number>로 나타내는 여러 키워드를 정의합니다.
이런 키워드를 정의하는 명세마다, 각 키워드에 대해 반드시 아래를 정의해야 합니다:
10.8. 구문
수학 함수의 구문은 다음과 같습니다:
<calc () > =calc ( <calc-sum>) <min () > =min ( <calc-sum>#) <max () > =max ( <calc-sum>#) <clamp () > =clamp ( [ <calc-sum> | none] , <calc-sum>, [ <calc-sum> | none] ) <round () > =round ( <rounding-strategy>?, <calc-sum>, <calc-sum>?) <mod () > =mod ( <calc-sum>, <calc-sum>) <rem () > =rem ( <calc-sum>, <calc-sum>) <sin () > =sin ( <calc-sum>) <cos () > =cos ( <calc-sum>) <tan () > =tan ( <calc-sum>) <asin () > =asin ( <calc-sum>) <acos () > =acos ( <calc-sum>) <atan () > =atan ( <calc-sum>) <atan2 () > =atan2 ( <calc-sum>, <calc-sum>) <pow () > =pow ( <calc-sum>, <calc-sum>) <sqrt () > =sqrt ( <calc-sum>) <hypot () > =hypot ( <calc-sum>#) <log () > =log ( <calc-sum>, <calc-sum>?) <exp () > =exp ( <calc-sum>) <abs () > =abs ( <calc-sum>) <sign () > =sign ( <calc-sum>) <calc-sum> = <calc-product>[ [ '+' |'-' ] <calc-product>] * <calc-product> = <calc-value>[ [ '*' |'/' ] <calc-value>] * <calc-value> = <number> | <dimension> | <percentage> | <calc-keyword> |( <calc-sum>) <calc-keyword> = e | pi | infinity | -infinity | NaN <rounding-strategy> = nearest | up | down | to-zero
일부 컨텍스트에서는 추가적인 <calc-keyword> 값이 유효하도록 정의될 수 있습니다. (예를 들어, relative color 문법에서는 적절한 채널 키워드가 허용됩니다.)
또한, 공백은 + 및 - 연산자 양쪽에 반드시 필요합니다. (*와 / 연산자는 공백 없이 사용할 수 있습니다.)
위의 여러 수학 함수들은 인수 <calc-sum>에 대해 추가적인 제약을 가집니다. 자세한 내용은 각 함수의 정의를 확인하세요.
UA는 최소 32개의 계산식 <calc-value> 항, 그리고 최소 32단계의 중첩(괄호 및/또는 함수)을 지원해야 합니다. 임의 개수 인수를 지원하는 함수(예: min())의 경우, 최소 32개의 인수도 지원해야 합니다. 계산식이 지원 개수를 초과하는 항, 인수, 중첩을 포함하면 무효로 처리해야 합니다.
10.9. 타입 검사
수학 함수는 아래에 정의된 대로, 포함하는 계산식에 따라 <length>, <number> 등 여러 타입이 될 수 있습니다. 해당 타입이 허용되는 곳이라면 어디서든 사용할 수 있습니다.
또한, 수학 함수가 <number>로 계산되면, <integer>만 허용되는 곳에서도 사용할 수 있습니다. 이 값은 해석 시 가장 가까운 정수로 반올림됩니다.
연산자는 하위 식(sub-expression)을 형성하며, 인수에 따라 타입을 가집니다.
참고: 이전 명세에서는, 곱셈과 나눗셈이 인수에 제한이 있었는데, 이는 더 복잡한 중간 결과(예: 1px * 1em은 <length>²이 됨)를 방지하고, 0으로 나누기를 파싱 시점에 감지하게 하기 위함이었습니다. 현 버전에서는 이런 제한이 완화되었습니다.
-
+ 또는 - 하위 식에서, 좌우 인수의 타입을 더하도록 시도합니다. 실패하면 전체 계산식의 타입은 실패가 됩니다. 그렇지 않으면 하위 식의 타입은 반환된 타입입니다.
-
/ 하위 식에서는, left type은 좌 인수의 타입, right type은 우 인수의 타입을 구한 뒤, 반전시켜 구합니다.
-
그 외는 터미널 값이며, 타입은 CSS 타입에 따라 결정됩니다. (별도 명시가 없는 한, 타입의 percent hint는 null입니다.)
- <number>
- <integer>
-
타입은 «[ ]» (빈 맵)
- <length>
-
타입은 «[ "length" → 1 ]»
- <angle>
-
타입은 «[ "angle" → 1 ]»
- <time>
-
타입은 «[ "time" → 1 ]»
- <frequency>
-
타입은 «[ "frequency" → 1 ]»
- <resolution>
-
타입은 «[ "resolution" → 1 ]»
- <flex>
-
타입은 «[ "flex" → 1 ]»
- <calc-keyword>
-
타입은 해당 키워드 정의에 따름
- <percentage>
-
해당 수학 함수가 있는 문맥에서 이 계산식의 <percentage>가 다른 타입에 대해 해석되면 (예: width에서 <percentage>는 <length>를 기준으로 해석), 그 타입이 <number>가 아니면, 타입은 그 타입이 되며, percent hint는 그 타입이 됨.
그렇지 않으면, 타입은 «[ "percent" → 1 ]».
- 그 외
-
계산식의 타입은 실패입니다.
- <number>
-
base와 input 모두에 서로 다른 null이 아닌 percent hint가 있으면, 일관성 있게 만들 수 없습니다. 실패를 반환합니다.
-
base의 percent hint가 null이면 base의 percent hint를 input의 percent hint로 설정합니다.
-
base를 반환합니다.
수학 함수 자체도 포함하는 계산식에 따라 타입을 가집니다:
- calc()
- abs()
-
내부 계산식의 타입.
- min()
- max()
- clamp()
- hypot()
- round()
- mod()
- rem()
- max()
-
콤마로 구분된 계산식 타입 더하기의 결과.
- asin()
- acos()
- atan()
- atan2()
- acos()
-
«[ "angle" → 1 ]».
- sign()
- sin()
- cos()
- tan()
- pow()
- sqrt()
- log()
- exp()
- sin()
-
«[ ]» (빈 맵).
위 항목 중, 타입이 실패이면, 수학 함수는 무효입니다.
수학 함수는 <number>, <length>, <angle>, <time>, <frequency>, <resolution>, <flex>, <percentage> 중 타입이 매칭되는 것에 따라 해당 타입으로 해석됩니다. (이들 카테고리는 상호배타적입니다.) 어느 것도 매칭되지 않으면, 수학 함수는 무효입니다.
참고: 대수적 단순화는 수학 함수의 유효성이나 결정된 타입에 영향을 주지 않습니다. 예: calc(5px - 5px + 10s)와 calc(0 * 5px + 10s) 모두, 길이와 시간을 더하려 했기 때문에 무효입니다.
참고: <percentage>가 <number>에 대해 상대적인 경우 (예: opacity에서), 이 둘은 결합할 수 없습니다—opacity: calc(.25 + 25%)는 무효입니다. 이를 허용하면 "단위 대수(unit algebra)"에 심각한 문제(특히 <dimension>의 곱셈/나눗셈)와, 실질적으로는 새로운 기능을 제공하지 않는 문제가 발생합니다. (예: opacity: 25%와 opacity: .25는 완전히 동일하므로, 단순한 문법 변환일 뿐입니다.) 이런 경우에도 opacity: calc(100% / 3); 같은 연산은 유효합니다.
참고: <number-token>은 항상 <number> 또는 <integer>로 해석되어, "단위 없는 0" <length>는 수학 함수에서 지원되지 않습니다. 즉, width: calc(0 + 5px);는 <number>와 <length>를 더하려 했으므로 무효이며, width: 0;, width: 5px; 자체는 유효합니다.
참고: 일부 속성에서는 <number>가 사용값(used-value) 단계에서 <length>로 변환되지만 (예: line-height, tab-size), <number>는 calc() 내에서 "길이처럼" 되지 않습니다. 항상 <number>로 유지됩니다.
참고: Quirks Mode [QUIRKS]에서는, 보통 <length>만 허용하는 일부 속성도 <number>를 허용하며, 이 경우 px 길이로 해석합니다. 단위 없는 0과 마찬가지로, 이것이 수학 함수의 파싱/동작에는 영향을 주지 않지만, 수학 함수가 <number> 값으로 계산되면 Quirks 모드에서는 유효해지고 px 길이로 해석될 수 있습니다.
10.9.1. 무한대, NaN, 부호 있는 0
수학 함수는 IEEE-754 의미론을 따릅니다. 즉, 양/음수 0, 양/음수 무한대, NaN(not a number) 개념을 인식합니다.
하지만, 이 개념들은 계산 트리 내부에서만 유지됩니다; 만약 최상위 계산(다른 수학 함수 안에 직접 중첩되지 않은 수학 함수) 이 이러한 특수값이 되면, 아래 정의된 대로 "표준 표현 가능한 값"으로 검열(censor)됩니다.
부호 있는 0(여기서는 0⁺, 0⁻로 표기)은 CSS에서 직접 쓸 수 없습니다; 0, +0, -0 모두 표준 "무부호" 0이 되며, 규칙상 양수(0⁺)로 간주합니다.
부호 있는 0은 다음과 같이 생성됩니다:
-
음수 0(0⁻)은 곱셈/나눗셈에서 정확히 하나의 인수가 음수이고 결과가 0이 될 때 생성됩니다 (예: -5 * 0, 1 / -infinity 등).
-
0⁻ + 0⁻ 또는 0⁻ - 0⁺는 0⁻을 생성. 그 외의 덧셈/뺄셈에서 0이 나오면 0⁺을 생성.
-
0⁻에 양수(0⁺ 포함) 곱셈/나눗셈은 음수 결과(0⁻ 또는 −∞), 0⁻에 음수 곱셈/나눗셈은 양수 결과가 나옵니다.
(즉, 표준 부호 규칙을 따름)
-
0⁺와 0⁻를 비교하면 0⁻이 더 작습니다. 예: min(0⁺, 0⁻)은 0⁻, max(0⁺, 0⁻)은 0⁺, clamp(0⁺, 0⁻, 1)은 0⁺를 반환해야 합니다.
-
특정 수학 함수의 인수 조합이 0⁻을 생성한다고 정의됨 (예: round(-1, infinity)). 그 외 0을 생성하는 연산은 모두 0⁺을 반환.
부호 있는 0은 최상위 계산을 벗어나지 않습니다; "무부호" 0으로 검열됩니다.
무한대 (+∞, −∞로 표기)는 수학 상수 infinity, -infinity를 사용해 직접 쓸 수 있으며, 다음과 같은 계산 결과로도 생성됩니다:
-
0으로 나누기는 표준 부호 규칙에 따라 +∞ 또는 −∞을 반환.
-
±∞를 더하거나 빼면 해당 무한대를 반환.
-
어떤 값이든 ±∞을 곱하면 해당 무한대를 반환.
-
어떤 값을 ±∞로 나누면 0을 반환.
참고: 아래 NaN 생성 규칙이 위 무한대 생성 규칙보다 우선합니다.
무한대는 최상위 계산을 벗어나지 않으며, § 10.12 범위 검사에서 정의된 대로 해당 컨텍스트의 최소/최대값으로 클램프 됩니다.
NaN ("not a number"의 약자)은 명확히 정의할 수 없는 연산의 결과입니다. 수학 상수 NaN으로 직접 쓸 수 있고, 다음과 같은 계산 결과로도 생성됩니다:
-
0 / 0, ±∞ / ±∞, 0 * ±∞, +∞ + -∞, 같은 부호의 무한대끼리의 뺄셈 등은 NaN을 반환합니다.
이 규칙은 다른 결과 규칙보다 우선합니다. 예: 0 / 0은 NaN, +∞가 아님.
-
NaN 인수가 포함된 어떤 연산이든 결과는 NaN.
NaN은 최상위 계산을 벗어나지 않으며, 0값으로 검열됩니다.
반면, calc(1 / calc(-5 * 0))은 −∞, calc(1 / (-5 * 0))과 동일—내부 calc는 0⁻을 반환하고, 이는 최상위 계산이 아니므로 변경 없이 외부 calc에 전달되어 −∞이 됩니다. 만약 무부호 0으로 검열된다면, +∞이 되었을 것입니다.
10.10. 내부 표현
내부 표현은 수학 함수의 계산 트리입니다: 이 트리는 가지 노드가 연산자 노드로, 수학 함수(Min, Cos, Sqrt 등)나 계산식의 연산자(Sum, Product, Negate, Invert, calc-operator 노드)에 해당하며, 잎 노드는 숫자 값(숫자, 치수, 백분율 등)이나 수치 타입으로 해석되는 비-수학 함수입니다.
-
values의 <whitespace-token>들을 모두 버린다.
-
values의 항목이 <delim-token>이며 값이 "+", "-", "*", "/"이면 "연산자", 아니면 "값"으로 간주.
-
Product, Invert 노드로 자식들을 묶는다.
연속된 값 항목 사이에 "*" 또는 "/" 연산자가 있는 구간마다:
-
해당 구간의 "/" 연산자마다, 우측 값 항목 rhs를 Invert 노드(rhs를 자식으로 가짐)로 대체.
-
해당 구간 전체를 Product 노드(값 항목들을 자식으로)로 대체.
-
-
Sum, Negate 노드로 자식들을 묶는다.
-
values의 "-" 연산자마다, 우측 값 항목 rhs를 Negate 노드(rhs를 자식으로)로 대체.
-
values가 Product 노드 하나 또는 괄호친 simple block 하나뿐이면, values를 그 항목으로 대체.
그 외에는, values 전체를 Sum 노드(값 항목들을 자식으로)로 대체.
-
-
이 시점의 values는 Sum, Product, Negate, Invert 트리이며, 잎 노드는 기타 값 타입. 잎 노드를 처리:
values의 모든 잎 노드 leaf에 대해:
-
leaf가 괄호친 simple block이면, leaf 내용을 계산식 파싱 결과로 대체.
-
-
values에 대해 계산 트리 단순화 결과 반환.
10.10.1. 단순화
내부 표현은 수학 함수에 대해 가능한 한 미리 단순화되며, 표준 대수 단순화(곱의 분배, 동일 단위 결합 등)를 사용합니다.
속성 외의 컨텍스트(예: @font-face 설명자 등)에서는, 수학 함수를 지정 값처럼 단순화합니다.
-
root가 숫자 값이면:
-
root가 다른 값에 대해 해석될 백분율이고, 해석 가능한 정보가 있으면, 해석 후 결과 값을 적절한 정준 단위로 표현해 반환.
-
root가 정준 단위가 아닌 치수이고, 정준 단위로 변환할 정보가 있으면, 변환 후 값을 반환.
-
root가 해석 가능한 <calc-keyword>면, 해석 결과를 단순화해서 반환.
-
그 외에는 root 반환.
-
-
root가 그 외 잎 노드(연산자 노드 아님)라면:
-
값을 정할 정보가 있으면, 값을 해당 정준 단위로 표현해 반환.
-
그 외에는 root 반환.
-
-
root가 연산자 노드이나 calc-operator 노드가 아니고, 모든 계산식 자식이 숫자 값이며, 연산을 계산할 정보가 충분하면, 자식들을 사용해 연산 수행 결과를 해당 정준 단위로 표현해 반환.
이 시점에 백분율이 남아 있으면, 보통 그 노드의 단순화를 막게 됩니다. (다른 값에 대해 해석될 때까지 정보가 충분하지 않기 때문) min 등 연산도 마찬가지로, 백분율이 음수 기반으로 해석될 수 있기 때문에 원래 값과 비교 결과가 달라질 수 있습니다.
하지만 "raw" 백분율—다른 값에 대해 해석되지 않는 것(opacity 등)은 단순화를 막지 않을 수 있습니다.
-
root가 Min 또는 Max 노드면, 부분적으로 단순화 시도:
-
각 자식 노드 child에 대해:
child가 숫자 값이며, 다른 동일 단위 자식과 비교할 정보가 충분하고, 그런 자식이 더 있으면, 해당 자식들과 적절한 연산자(Min/Max)로 결합해 child를 결과로 대체, 결합된 나머지 자식 노드는 제거.
-
root 자식이 하나면 그 자식 반환, 아니면 root 반환.
-
-
root가 Negate 노드면:
-
자식이 숫자 값이면, 동등한 숫자 값(값을 반전, 0 - 값) 반환.
-
자식이 Negate 노드면, 그 자식의 자식을 반환.
-
root 반환.
-
-
root가 Invert 노드면:
-
자식이 숫자(백분율, 치수 아님)면, 역수 반환.
-
자식이 Invert 노드면, 그 자식의 자식을 반환.
-
root 반환.
-
-
root가 Sum 노드면:
-
자식 중 Sum 노드는 그 자식들로 대체.
-
동일 단위의 숫자 값 자식들을 묶어 합산 결과만 남기고, 나머지 해당 자식은 제거.
(예: 숫자, 백분율, px 값 각각 합산)
-
이 시점에 자식이 하나면 그 자식 반환, 아니면 root 반환.
참고: 0 값 항목은 단순히 Sum에서 삭제할 수 없으며, 동일 단위끼리만 합쳐집니다. (0이라도 단위가 있으면 동작에 영향을 줄 수 있기 때문)
-
-
root가 Product 노드면:
-
자식 중 Product 노드는 그 자식들로 대체.
-
여러 숫자(백분율, 치수 아님) 자식이 있으면, 곱한 결과만 남기고 해당 자식은 삭제.
-
자식이 두 개뿐이고, 한쪽이 숫자(백분율, 치수 아님), 다른 쪽이 모든 자식이 숫자인 Sum이면, Sum의 자식 모두에 숫자를 곱해 Sum 반환.
-
모든 자식이 숫자 값과/또는 숫자 값이 든 Invert 노드뿐이고, (Invert 노드 타입은 자식의 타입의 반전임) 모든 자식 타입 곱셈 결과가 수학 함수가 반환 가능한 타입과 매칭되면, 모든 값 곱셈 결과(역수 포함)를 해당 정준 단위로 반환.
-
root 반환.
-
10.11. 계산 값
계산 값은 수학 함수의 계산 트리를 단순화한 결과로, 계산 값 시점에서 얻을 수 있는 모든 정보를 사용합니다. (예: em과 px 비율, 일부 속성에서 백분율 해석 방법 등)
백분율이 계산값 시점에 해석되지 않으면, 수학 함수 내에서도 해석되지 않습니다. 예: calc(100% - 100% + 1px)은 calc(0% + 1px)이 되고, 1px이 되지 않습니다. 값에서 백분율 계산에 특별 규칙이 있으면 (예: height 속성), 수학 함수가 백분율을 포함하면 이 규칙이 적용됩니다.
계산 트리는 사용 값 시점에도 다시 단순화됩니다. 사용 값 시점 정보로, 수학 함수는 반드시 단일 수치값으로 단순화됩니다.
이로 인해 background-position 계산에서는 calc() 안에 백분율이 남지만, font-size는 그런 식을 길이로 직접 계산합니다.
테이블 셀/요소의 width, height 계산 복잡성 때문에, 표의 열, colgroup, 행, rowgroup, 셀 등에서 width, height에 백분율과 0이 아닌 길이가 혼합된 수학식은 auto/fixed 레이아웃 구분 없이 auto가 지정된 것처럼 처리해야 합니다.
10.12. 범위 검사
파싱 시점의 범위 검사는 수학 함수 내부에서는 수행되지 않으므로, 범위를 벗어난 값이 선언을 무효로 만들지 않습니다. 단, 최상위 계산 결과 값은 대상 컨텍스트의 허용 범위에 클램프(clamp)되어야 합니다. 클램프는 계산 값에서 가능한 한 수행되며, 계산이 충분히 단순화되지 않았다면 사용 값에서도 클램프됩니다. (클램프는 지정 값에는 수행되지 않습니다.)
참고: 이를 위해 calc()를 허용하는 모든 컨텍스트는 허용 값을 닫힌 구간(열린 구간 아님)으로 정의해야 합니다.
참고: 정의상, ±∞는 어떤 속성의 허용 범위 밖이므로, 최소/최대값으로 클램프됩니다. 무한대 키워드를 명시적으로 지원하는 속성(예: animation-iteration-count 등)도 ±∞는 클램프 처리합니다. 수학 함수는 키워드 값으로 해석될 수 없으므로, 속성의 수치 부분 문법엔 최소/최대값이 항상 존재합니다.
또한 수학 함수가 <number>로 해석되고, <integer>만 허용되는 곳에 쓰이면, 계산 값과 사용 값도 위와 같은 방식으로 가장 가까운 정수로 반올림됩니다.
width : calc ( 5 px -10 px ); width : calc ( -5 px ); width : 0 px ;
하지만 width: -5px는 width: calc(-5px)와 동일하지 않다는 점에 주의! 범위를 벗어난 값이 calc() 밖에 있으면 문법상 무효이며, 전체 선언이 무시됩니다.
10.13. 직렬화
이 섹션은 아직 논의 중입니다.
-
계산 트리 fn의 루트가 숫자 값(숫자, 백분율, 치수)이면서, 직렬화가 computed value 또는 이후라면, 값을 해당 컨텍스트의 허용 범위로 클램프(clamp)한 뒤, 값을 평소대로 직렬화하여 그 결과를 반환.
-
fn이 무한대 또는 NaN 값을 나타내면:
-
계산 트리의 루트 노드가 숫자 값이거나, calc-operator 노드라면, s를 "calc("로 시작하는 문자열로 둔다.
그 외의 경우, s를 루트 노드 이름(예: "sin"이나 "max")을 소문자로, 이어서 "("로 시작하는 문자열로 둔다.
-
루트 노드의 각 자식에 대해, 계산 트리 직렬화를 수행. 직렬화 결과가 "("로 시작하고 ")"로 끝나면 그 괄호를 제거. 결과를 모두 , (콤마+공백)로 이어붙여 s에 추가.
-
s에 ")"를 추가.
-
s 반환.
-
root를 계산 트리의 루트 노드로 둔다.
-
root가 숫자 값이거나, 비-수학 함수라면, 평소 규칙에 따라 root를 직렬화해 그 결과 반환.
-
root가 Sum, Negate, Product, Invert 노드가 아니면, 해당 노드 타입의 함수에 대해 수학 함수 직렬화를 수행, 노드의 자식을 함수의 콤마로 구분된 계산식 인수로 보고, 결과 반환.
-
root가 Negate 노드라면, s를 "(-1 * "로 시작하는 문자열로 둔다.
계산 트리 직렬화로 root의 자식을 직렬화해 s에 추가.
s에 ")"를 추가 후 반환.
-
root가 Invert 노드라면, s를 "(1 / "로 시작하는 문자열로 둔다.
계산 트리 직렬화로 root의 자식을 직렬화해 s에 추가.
s에 ")"를 추가 후 반환.
-
root가 Sum 노드라면, s를 "("로 시작하는 문자열로 둔다.
root의 자식 정렬을 수행.
계산 트리 직렬화로 첫 번째 자식을 직렬화해 s에 추가.
각 첫 번째 이후 child에 대해:
-
child가 Negate 노드면, s에 " - " 추가 후, Negate의 자식을 직렬화하여 추가.
-
child가 음수 숫자 값이면, s에 " - " 추가 후, child의 반전값을 평소대로 직렬화하여 추가.
-
그 외에는 s에 " + " 추가 후, 직렬화 결과를 추가.
마지막으로 s에 ")" 추가 후 반환.
-
-
root가 Product 노드라면, s를 "("로 시작하는 문자열로 둔다.
root의 자식 정렬을 수행.
계산 트리 직렬화로 첫 번째 자식을 직렬화해 s에 추가.
각 첫 번째 이후 child에 대해:
마지막으로 s에 ")" 추가 후 반환.
-
ret을 빈 리스트로 둔다.
-
nodes에 숫자가 있으면, nodes에서 제거해 ret에 추가.
-
nodes에 백분율이 있으면, nodes에서 제거해 ret에 추가.
-
nodes에 치수가 있으면, nodes에서 제거 후, 단위별로 ASCII 대소문자 구분 없이 정렬, ret에 추가.
-
nodes에 남은 항목이 있으면, 원래 순서대로 ret에 추가.
-
ret 반환.
calc(20px + 0%)는 calc(0% + 20px)로 직렬화되어 두 항이 모두 직렬화된 값에 남아있습니다. (0 값 항목을 유지하는 것이 중요합니다. 그래야 calc()가 트랜지션 중 값이 잠시 0이 되었다고 "모양이 바뀌는" 일이 없습니다. 또한 모든 항이 0일 때 단위를 "선택"할 필요도 없습니다.)
calc(20px + 2em)는 지정 값에서는 calc(2em + 20px)로 (단위가 호환되지 않으므로 모두 유지, 알파벳순으로 정렬), 계산 값에서는 52px과 같이 직렬화됩니다. (em 값은 계산값 시점에 절대 길이로 변환되어, 1em = 16px일 때 52px이 되고, 이때 calc() 래퍼는 사라집니다.)
속성 외의 컨텍스트(예: @font-face 설명자 등)에서는, 수학 함수를 지정 값처럼 단순화합니다.
직렬화에 대한 자세한 내용은 [CSSOM]을 참고하세요.
10.14. 수학 함수의 결합
보간은 수학 함수끼리, 혹은 숫자 값 및 다른 수치 함수와 결합 시, Vresult = calc((1 - p) * VA + p * VB)로 정의됩니다. (단순화를 거치면 표현식이 더 간단해질 수 있습니다.)
더하기도 수학 함수끼리, 혹은 숫자 값 및 다른 수치 함수와 결합 시, Vresult = calc(VA + VB)로 정의됩니다. (단순화를 거치면 표현식이 더 간단해질 수 있습니다.)
부록 A: 리스트 값 속성의 연동
일부 리스트 값 속성은 연동 효과가 있습니다: 값 리스트의 각 항목이 별도의 효과에 적용되며, 각 속성 리스트의 같은 위치에 있는 값들이 모두 같은 효과를 참조합니다. 종종 이렇게 연동되는 값들은 리스트 값 축약형 속성에서 하나의 항목으로 함께 지정할 수도 있습니다.
대표적인 예로 리스트 값 background-* 속성들이 있습니다. 여러 개의 배경 이미지 레이어를 지정할 수 있습니다. 이미지의 크기, 타일, 위치 등을 제어하는 각 속성마다, 리스트의 N번째 항목은 N번째 배경 이미지에 적용되는 효과를 설명합니다.
연동 리스트 속성 그룹은 연동 값 리스트를 만듭니다. 이는 각 항목마다 그룹 내 각 속성의 값을 가지며, 이 값들을 함께 사용해 하나의 효과(예: 배경 이미지 레이어, 애니메이션 등)를 정의합니다. 연동 값 리스트는 아래처럼 조립됩니다:
-
연동 값 리스트의 길이는 특정 연동 리스트 속성, 즉 연동 리스트 기준 속성에 지정된 항목 수로 결정됩니다. (배경의 경우 background-image 속성이 이에 해당합니다.)
부록 B: IANA 관련
about : invalid
URL 스킴 등록
이 섹션은
URL을 정의하고 등록하며,
[RFC6694]의 등록
절차를 따릅니다.
이 등록의 공식 기록은 http://www.iana.org/assignments/about-uri-tokens/about-uri-tokens.xhtml에서 확인할 수 있습니다.
등록된 토큰 | invalid
|
---|---|
의도된 용도 | URL은
일반적인 에러 조건의 존재하지 않는 문서를 참조합니다.
URL이 필요하지만, 기본값이 어떤 문서 유형으로도 해석되지 않아야 할 때 사용할 수 있습니다.
|
연락처/변경 담당자 | CSS WG <www-style@w3.org> (W3C 대리) |
명세(Specification) | CSS Values and Units Module Level 3 |
부록 C: 쿼크 길이(Quirky Lengths)
CSS가 쿼크 모드로 파싱될 때, <quirky-length>는 특정 속성에서만 유효한 <length>의 한 종류입니다:
아래와 같이 해당 속성들을 포함하거나 참조하는 속성에서는 유효하지 않습니다: 예를 들어 background 축약형, 또는 함수 표기 (예: calc()) 안에서는 유효하지 않습니다. 단, rect()가 clip 속성에서 사용될 때는 허용해야 합니다.
또한, <quirky-length>는 <length>로 파싱되어야 하며,
@supports 규칙 내에서 해당 속성을 파싱할 때 허용되어야 합니다.
하지만,
CSS.supports()
메서드에서는 해당 속성에 대해 유효하지 않습니다.
<quirky-length>는 구문상 <number-token>과 동일하며, 동일한 값을 갖는 px 길이로 해석됩니다.
(즉, 쿼크 모드에서는 해당 속성의 모든 px 단위 길이를 단위 없이 쓸 수 있습니다. 이는 단위 없는 0 길이와 유사합니다.)
감사의 글
우선, 이 모듈 이전 레벨의 모든 기여자들에게 감사드립니다.
또한, Anthony Frehner, Emilio Cobos Álvarez, Koji Ishii, Noam Rosenthal, Xidorn Quan 님의 피드백과 제안에 감사드리며, 이로 인해 Level 4가 향상될 수 있었습니다.
변경 사항
최근 변경사항
(이는 Level 3 이후 추가사항의 일부입니다.)
2023년 12월 18일 WD(원문) 이후 주요 변경 사항:
-
퍼센트 타입 추론 방식 전반 수정 (이슈 10017)
-
viewport-percentage 길이가 overflow: scroll 및 scrollbar-gutter에 따라 실제로 100 단위가 초기 포함 블록과 일치할 수 있도록 종속성을 복원 (이슈 6026)
2023년 10월 27일 WD(원문) 이후 주요 변경 사항:
-
기본 viewport-percentage 단위를 large viewport-percentage units로 고정 (기존 웹 호환성 유지 목적) (이슈 6452)
-
CSS 문법 production block 명시적 정의 추가 (이슈 2921)
-
percent-encoded URL의 문자 인코딩 명확화 (이슈 9301)
2023년 4월 6일 WD(원문) 이후 주요 변경 사항:
-
색상 타입을 비가산적(non-additive)으로 정의 (이슈 8576)
-
CSS의 URL 전송은 항상 UTF-8로 함을 명시 (이슈 9301)
-
두 값이 덧셈/누적 불가 시 두 번째 값을 사용하도록 addition/accumulation 정의 수정 (이슈 9070)
2022년 10월 19일 WD(원문) 이후 주요 변경 사항:
- § 2.6 함수 표기법 정의를 추가하여 함수 표기법 문법 정의 방식 명시 (이슈 2921)
- 테두리 두께로 snap 알고리즘 추가(일관된 스트로크 두께 렌더링 반영) (이슈 5210)
- mix() 문법 및 계산 값 명확화 (이슈 8096)
- tan()의 비분연점 동작 미정의로 변경 (이슈 8527)
- 음수 <resolution> 값은 정의상 범위 밖으로 명시 (이슈 8532)
- mix()의 완전 생략 인수도 허용 명확화 (이슈 8556)
- 범위 클램프가 최상위 계산에만 적용됨을 명확화 (이슈 8158)
- <url()> 및 <src()> 공식 정의 추가(<url> 포함)
- fragment-only URL을 tree-scoped reference로 재정의 (이슈 3320)
2021년 12월 16일 WD(원문) 이후 주요 변경 사항:
- url()에 local url flag가 있는 경우 현재 노드 트리를 참조하도록 변경 (이슈 3320)
- NaN이 수학 함수에서 벗어났을 때 infinity가 아닌 0으로 검열하도록 변경 (이슈 7067)
- 부록 A: 리스트 값 속성 연동 추가 (이슈 7164)
- mix()는 반드시 선언의 유일한 값이어야 함을 명시 (이슈 6700)
- 최신 Fetch 용어 반영 (Fetch PR 1413, CSS PR 7160)
- font-relative 길이는 텍스트 셰이핑 없이 계산됨을 명확화
- 빈 url 직렬화는
로 정의 (이슈 6447)url ( "" ) - <position> 지정 값 직렬화 정의 (이슈 2274)
- 숫자 정의를 소수점+지수 표기도 허용하도록 수정 ([CSS-SYNTAX-3] 참고, 이슈 7248)
- 여러 함수의 type 반환값을 «[ "number" → 1 ]» 대신 빈 맵으로 수정 (이슈 7486)
- line-height에 대한 UA 제한이 lh, rlh에 미치는 영향 명확화 (이슈 3257)
-
<
표기법이 함수 표기 전체를 지칭함을 명시 (이슈 5728)function () >
2021년 10월 16일 WD(원문) 이후 주요 변경 사항:
- *vi, *vb 단위가 요소 자체의 계산된 writing mode 기준으로 해석되도록 변경 (이슈 6873)
- § 4.5.4 URL 처리 모델 추가(CORS 등 통합) (이슈 562)
-
viewport-percentage 길이의 A/B 분류가 반대로 배정된 부분 수정
-
스크롤 등 사용자에게 레이아웃 변화가 빈번하게 발생해선 안 되는 인터페이스 변화는
전자(A)후자(B) 로 분류해야 함. -
안정적인 상태에서 레이아웃 변경이 사용자의 경험에 이로운 변화는
후자(B)전자(A) 로 분류해야 함.
-
스크롤 등 사용자에게 레이아웃 변화가 빈번하게 발생해선 안 되는 인터페이스 변화는
- calc()의 항, 인수, 중첩 최소 개수를 32로 명시 (이슈 3462)
- mod(-0, infinity)는 NaN 반환 명시 (이슈 4723)
- toggle(), attr()를 Level 5로 이관
2021년 9월 30일 WD(원문) 이후 변경:
- rex, rcap, rch, ric 단위 추가
- toggle()가 세미콜론 사용하도록 변경, mix()와 일치 (이슈 6701)
- calc() 정의의 일부 문구 오류 수정 (이슈 6506)
- <quirky-length> 정의를 [QUIRKS]에서 가져옴 (이슈 6100)
2021년 7월 15일 WD(원문) 이후 변경:
- mix() 표기 추가
- <integer>, <number>, <percentage>, <length>의 계산 방식 범용 정의
- 0이 아닌 길이만 백분율+길이 혼합에서 테이블 셀을 auto로 전환하게 함을 명확화
2020년 11월 11일 WD(원문) 이후 변경:
- 색상 보간 참조를 [CSS-COLOR-4]로 변경
- svh, svw, svi, svb, svmin, svmax small viewport-percentage units 및 lvh, lvw, lvi, lvb, lvmin, lvmax large viewport-percentage units, dvh, dvw, dvi, dvb, dvmin, dvmax dynamic viewport-percentage units 추가 (이슈 4329, 이슈 6113)
- <angle> 값이 너무 클 때 360deg 배수로 클램프하도록 명시 (이슈 6105)
- 결합된 값의 범위 검사 규칙을 CSS Transitions 명세 이동 과정에서 누락된 부분 복원 (이슈 6097)
- UA 최소 글꼴 크기는 font-size에만 적용된다는 점 명확화 (이슈 5858)
- min() 및 max()의 퍼센트 부분 단순화 명확화 (이슈 6293)
Level 3 이후 추가사항
CSS Values and Units Level 3 이후 변경 사항:
- 숫자 정밀도/범위를 명확하게 정의하지 않음.
- 값 타입별 보간 규칙 및 계산값 명확화.
- 색상 보간을 [CSS-COLOR-4]를 참조하도록 업데이트.
CSS Values and Units Level 3 이후 추가된 사항:
- <dashed-ident> 타입 정의.
- <ratio> 타입 정의.
- src()를 <url> 타입에 추가.
- vi, vb, ic, cap, lh 및 rlh 길이 단위 추가.
- svh, svw, svi, svb, svmin, svmax 소형 뷰포트 백분율 단위 및 dvh, dvw, dvi, dvb, dvmin, dvmax 동적 뷰포트 백분율 단위 추가.
- x 별칭을 dppx에 추가.
- min(), max(), clamp() 비교 함수 추가.
- round(), mod(), rem(), sin(), cos(), tan(), asin(), acos(), atan(), atan2(), pow(), sqrt(), hypot(), log(), exp(), abs(), sign() 수학 함수 추가.
- e, pi, infinity, -infinity, NaN 상수 추가 (calc()에서 사용).
- unit algebra를 calc()에 추가하여 치수의 곱/나눗셈 허용.
- calc() 내에서 정수가 아닌 값이 <integer>가 필요한 곳에 사용되면 자동으로 가장 가까운 정수로 반올림.
- 수학 함수의 직렬화 정의.
- 연동 리스트 속성 그룹의 범용 정의 추가, background 속성군의 연동 동작 참조를 용이하게 함.
보안 고려사항
이 명세는 새로운 보안 고려사항을 제시하지 않습니다.
이 명세는 url() 및 src() 함수(<url>)를 정의하며, CSS가 네트워크 요청을 할 수 있게 합니다. 사용되는 기능에 따라, 사용자가 네트워크 상의 리소스에 접근 가능한지 여부나 해당 리소스의 정보(예: 스타일시트 내 규칙, 이미지 크기, 폰트 메트릭 등) 노출될 수 있습니다. URL을 통한 데이터 유출도 가능할 수 있습니다.
프라이버시 고려사항
이 명세는 사용자의 화면 크기(뷰포트 백분율 길이), 기본 글꼴 크기, 그리고 사용자의 시스템에 어떤 글꼴이 설치되어 있는지에 대한 일부 정보를 (글꼴 상대 길이) 노출할 수 있는 단위를 정의합니다.
이 명세는 url() 및 src() 함수(<url>)를 정의하며, CSS가 네트워크 요청을 할 수 있게 합니다. 사용되는 기능에 따라, 사용자가 네트워크 상의 리소스에 접근 가능한지 여부나 해당 리소스의 정보(예: 스타일시트 내 규칙, 이미지 크기, 폰트 메트릭 등) 노출될 수 있습니다. URL을 통한 데이터 유출도 가능할 수 있습니다.