@@ -1612,11 +1612,6 @@ Mathematical Expressions: ''calc()'', ''min()'', and ''max()''</h3>
1612
1612
or other expressions, such as ''attr()'' ,
1613
1613
that evaluate to a valid argument type (like <<length>> ).
1614
1614
1615
- Issue: Per WG resolution, [=math functions=] will be extended to handle arbitrary unit algebra,
1616
- like ''calc(1px / 1em)'' resolving to a <<number>> .
1617
- This is already fully specified in [[css-typed-om]] ;
1618
- it just needs to be converted over to raw CSS values for this spec.
1619
-
1620
1615
<div class="example">
1621
1616
<pre>
1622
1617
section {
@@ -1686,11 +1681,8 @@ Syntax</h4>
1686
1681
<<min()>> = min( <<calc-sum>> # )
1687
1682
<<max()>> = max( <<calc-sum>> # )
1688
1683
<dfn><calc-sum></dfn> = <<calc-product>> [ [ '+' | '-' ] <<calc-product>> ]*
1689
- <dfn><calc-product></dfn> = <<calc-value>> [ '*' <<calc-value>> | '/' <<calc-number -value>> ]*
1684
+ <dfn><calc-product></dfn> = <<calc-value>> [ [ '*' | '/' ] <<calc-value>> ]*
1690
1685
<dfn><calc-value></dfn> = <<number>> | <<dimension>> | <<percentage>> | ( <<calc-sum>> )
1691
- <dfn><calc-number-sum></dfn> = <<calc-number-product>> [ [ '+' | '-' ] <<calc-number-product>> ]*
1692
- <dfn><calc-number-product></dfn> = <<calc-number-value>> [ '*' <<calc-number-value>> | '/' <<calc-number-value>> ]*
1693
- <dfn><calc-number-value></dfn> = <<number>> | ( <<calc-number-sum>> )
1694
1686
</pre>
1695
1687
1696
1688
In addition, [=whitespace=]
@@ -1769,46 +1761,71 @@ Type Checking</h4>
1769
1761
<<number>> s never become "length-like" in ''calc()'' .
1770
1762
They always stay as <<number>> s.
1771
1763
1772
- Operators form sub-expressions, which gain types based on their arguments.
1773
- To make expressions simpler,
1774
- operators have restrictions on the types they accept.
1775
- At each operator,
1776
- the types of the left and right argument are checked for these restrictions.
1777
- If compatible, the type resolves as described below
1778
- (the following ignores precedence rules on the operators for simplicity):
1779
-
1780
- <ul>
1781
- <li>
1782
- At ''+'' or ''-'' ,
1783
- check that both sides have the same type,
1784
- or that one side is a <<number>> and the other is an <<integer>> .
1785
- If both sides are the same type,
1786
- resolve to that type.
1787
- If one side is a <<number>> and the other is an <<integer>> ,
1788
- resolve to <<number>> .
1764
+ <h5 id="type-checking-exprs">
1765
+ Type-Checking Expressions</h5>
1789
1766
1790
- <li>
1791
- At ''*'' ,
1792
- check that at least one side is <<number>> .
1793
- If both sides are <<integer>> ,
1794
- resolve to <<integer>> .
1795
- Otherwise,
1796
- resolve to the type of the other side.
1797
-
1798
- <li>
1799
- At ''/'' ,
1800
- check that the right side is <<number>> .
1801
- If the left side is <<integer>> ,
1802
- resolve to <<number>> .
1803
- Otherwise,
1804
- resolve to the type of the left side.
1805
- </ul>
1806
-
1807
- If an operator does not pass the above checks, the expression is invalid.
1808
- Also, division by zero is invalid. This includes both dividing by the
1809
- literal number zero, as well as any numeric expression that evaluates to zero
1810
- (as purely-numeric expressions can be evaluated without any additional
1811
- information at parse time).
1767
+ Operators form sub-expressions, which gain types based on their arguments.
1768
+ In previous versions of this specification,
1769
+ multiplication and division were limited in what arguments they could take,
1770
+ to avoid producing more complex intermediate results
1771
+ (such as ''1px * 1em'' , which is <<length>> ²)
1772
+ and to make division-by-zero detectable at parse time.
1773
+
1774
+ This version now relaxes those restrictions,
1775
+ allowing arbitrary expressions,
1776
+ so long as the expression as a whole resolves to a singular unit
1777
+ according to the following rules:
1778
+
1779
+ * At a ''+'' or ''-'' sub-expression,
1780
+ attempt to [=add two types|add the types=] of the left and right arguments.
1781
+ If this returns failure,
1782
+ the entire [=math function=] is invalid.
1783
+ Otherwise, the sub-expression's [=CSSNumericValue/type=] is the returned type.
1784
+
1785
+ * At a ''*'' or ''/'' sub-expression,
1786
+ attempt to [=multiply two types|multiply the types=] of the left and right arguments.
1787
+ If this returns failure,
1788
+ the entire [=math function=] is invalid.
1789
+ Otherwise, the sub-expression's [=CSSNumericValue/type=] is the returned type.
1790
+
1791
+ * The [=CSSNumericValue/type=] of a literal
1792
+ is the result of [=creating a type=]
1793
+ from the literal's unit,
1794
+ if it's a <<dimension>> ,
1795
+ or from "number"
1796
+ if it's a <<number>> .
1797
+ For <<percentage>> s,
1798
+ if they're relative to another type
1799
+ (as defined in the previous section),
1800
+ their type is [=create a type|created=]
1801
+ from the [=canonical unit=] of the type they're resolved to;
1802
+ otherwise it's [=create a type|created=] from "percentage".
1803
+
1804
+ * The [=CSSNumericValue/type=] of a ''calc()'' expression
1805
+ is the [=CSSNumericValue/type=] of its contained expression.
1806
+ The [=CSSNumericValue/type=] of a ''min()'' or ''max()'' expression
1807
+ is the result of [=adding two types|adding the types=]
1808
+ of its comma-separated expressions.
1809
+ If the result is failure,
1810
+ the entire [=math function=] is invalid.
1811
+
1812
+ The [=math function=] resolves to <<length>> , <<angle>> , <<time>> , <<frequency>> , <<resolution>> , <<flex>> , or <<percentage>>
1813
+ according to which of those productions its [=CSSNumericValue/type=] [=CSSNumericValue/matches=] .
1814
+ (These categories are mutually exclusive.)
1815
+ If it can't [=CSSNumericValue/match=] any of these,
1816
+ the [=math function=] is invalid.
1817
+
1818
+ As a further breaking change from the previous version of this specification,
1819
+ division by zero is now allowed.
1820
+ Expressions must follow IEEE-754 semantics for recognition and propagation
1821
+ of infinities and NaN values,
1822
+ including tracking the difference between +0 and -0.
1823
+ (However, CSS treats both zeroes as the same,
1824
+ if a [=math function=] resolves to one of them.)
1825
+ Infinities are, by definition, out-of-range for any property,
1826
+ and trigger appropriate clamping at used-value time per [[#calc-range]] .
1827
+ If a [=math function=] would resolve to NaN,
1828
+ it instead resolves to positive infinity.
1812
1829
1813
1830
Note: Algebraic simplifications do not affect the validity of a [=math function=] or its resolved type.
1814
1831
For example, ''calc(5px - 5px + 10s)'' and ''calc(0 * 5px + 10s)'' are both invalid
0 commit comments