clamp()

Baseline 已广泛支持

此特性已经十分成熟,可在许多设备和浏览器版本上使用。自 2020 年 7 月以来,它已在各大浏览器中可用。

clamp() 这个 CSS 函数将一个值限制在一个定义的最小边界和最大边界之间。该函数接受三个参数:一个最小值、一个首选值和一个最大允许值。

试一试

font-size: clamp(1rem, 2.5vw, 2rem);
font-size: clamp(1.5rem, 2.5vw, 4rem);
font-size: clamp(1rem, 10vw, 2rem);
<section class="default-example" id="default-example">
  <div class="transition-all" id="example-element">
    The font-size of this text varies depending on the base font of the page,
    and the size of the viewport.
  </div>
</section>

注意,像这些示例中一样,使用 clamp() 设置字体大小,可以使字体大小随视口大小增长,但不会低于最小字体大小或超过最大字体大小。它与流式排版中的代码效果相同,但只需一行,且无需使用媒体查询。

语法

css
/* Static values */
width: clamp(200px, 40%, 400px);
width: clamp(20rem, 30vw, 70rem);
width: clamp(10vw, 20em, 100vw);

/* Calculated values */
width: clamp(min(10vw, 20rem), 300px, max(90vw, 55rem));
width: clamp(100px, calc(30% / 2rem + 10px), 900px);

参数

clamp(min, val, max) 函数接受三个逗号分隔的表达式作为其参数。

min

最小值是最小(最负)的值。这是允许值范围内的下限。如果首选值小于此值,将使用最小值。

val

首选值是表达式的值,只要结果在最小值和最大值之间,就会使用该值。

max

最大值是最大(最正)的表达式值,如果首选值大于此上限,属性的值将被赋予此值。

表达式可以是数学函数(更多信息请参见 calc())、字面量值、其他可解析为有效参数类型的表达式(如 <length>),或嵌套的 min()max() 函数。对于数学表达式,你可以使用加、减、乘、除,而无需使用 calc() 函数本身。你也可以在需要时使用括号来确定计算顺序。

你可以在表达式中的每个值使用不同的单位,也可以在构成任何参数的任何数学函数中使用不同的单位。

在使用此函数时,请牢记以下几点:

  • 在自动和固定布局的表格中,涉及表格列、列表、行、行组和单元格宽度和高度百分比的数学表达式可能会被视为指定了 auto
  • 允许将 max()min() 函数作为表达式值嵌套,此时内部的函数被视为基本括号。表达式是完整的数学表达式,因此你可以直接使用加、减、乘、除,而无需使用 calc() 函数本身。
  • 表达式可以是结合了加法(+)、减法(-)、乘法(*)和除法(/)运算符的值,并使用标准的运算符优先级规则。请确保在 +- 操作数的两边都加上一个空格。表达式中的操作数可以是任何 <length> 语法值。你可以在表达式中的每个值使用不同的单位。你也可以在需要时使用括号来确定计算顺序。
  • 通常你会想在 clamp() 函数中使用 min()max()

返回值

clamp(MIN, VAL, MAX) 会被解析为 max(MIN, min(VAL, MAX))

根据提供的参数,该函数返回 <length><frequency><angle><time><percentage><number><integer>

正式语法

<clamp()> = 
clamp( [ <calc-sum> | none ] , <calc-sum> , [ <calc-sum> | none ] )

<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

示例

min()、max() 和 clamp() 的比较

在此示例中,我们有一个使用 min()max()clamp() 来响应式设置大小的网页。

该示例通过三种方式调整页面元素的大小:

  • 文本行的长度
  • 段落文本的字体大小
  • 标题文本的字体大小

在这三种情况下,页面都使用了相对于视口的单位(vw<percentage>)与非相对于视口的值(rempx)的组合,来设置一个随视口宽度变化的大小,并实现最小和/或最大尺寸。

示例位于 https://mdn.github.io/css-examples/min-max-clamp/。请在新窗口中打开它,并尝试调整窗口宽度。

行长(由 <body> 元素的 width 控制)会随着窗口宽度的增加而增加,但只增加到某个点(1000px),超过该点后,它将不再增加。我们使用 min() 来设置最大行长:它可以小于 1000px,但不会超过。这很有用,因为长行更难阅读,所以我们常常希望限制行的长度。为实现这一点,我们使用 min(1000px, calc(70% + 100px)):当基于百分比的计算结果超过 1000px 时,我们切换到固定的 1000px 值。

段落文本的大小(由 <p> 元素的 font-size 控制)会随着窗口变窄而减小,但只减小到某个点,超过该点(即 1.2vw 小于 1.2rem 的点)后,它不会再变小:它保持在 1.2rem。我们使用 max() 来设置最小字体大小:字体可以大于 1.2rem,但绝不会小于它。这很有用,因为非常小的文本很难阅读。为实现这一点,我们使用 max(1.2rem, 1.2vw)。这意味着 font-size 将被设置为 1.2rem,除非 1.2vw 的计算值大于 1.2rem,在这种情况下,它将被设置为 1.2vw

标题文本的大小(由 <h1> 元素的 font-size 控制)有一个相对于视口的值,同时具有最大和最小阈值。为实现这一点,我们使用 clamp(1.8rem, 2.5vw, 2.8rem)。相对于视口的值是 2.5vw,但它被限制在 1.8rem2.8rem 之间,所以:

  • 如果 2.5vw 的计算值小于 1.8rem,则将使用 1.8rem
  • 如果 2.5vw 的计算值大于 2.8rem,则将使用 2.8rem

这可以防止标题文本在非常窄的窗口中变得太小,或在非常宽的窗口中变得太大。

HTML

html
<h1>Basic responsive test</h1>
<p>
  Lorem ipsum dolor sit amet, consectetur adipiscing elit. In orci orci,
  eleifend id risus nec, mattis rutrum velit. Suspendisse fringilla egestas erat
  eu convallis. Phasellus eu velit ut magna dapibus elementum cursus at ligula.
  Ut tempus varius nibh, nec auctor sapien iaculis sit amet. Fusce iaculis,
  libero quis elementum viverra, nulla ante accumsan lectus, sit amet convallis
  lacus ipsum vel est. Curabitur et urna non est consectetur pulvinar vel id
  risus. Ut vestibulum, sem in semper aliquet, felis arcu euismod sapien, ac
  imperdiet massa nisl quis sem. Vestibulum ac elementum felis, in tempor velit.
  Pellentesque purus ex, mattis at ornare quis, porta condimentum mi. Donec
  vestibulum ligula vel nulla blandit, quis euismod nulla vestibulum.
  Suspendisse potenti. Nunc neque mauris, tempor sed facilisis at, ultrices eget
  nulla. Pellentesque convallis ante nec augue porttitor, id tempus ante luctus.
</p>

<p>
  Integer rutrum sollicitudin tellus, quis cursus nulla scelerisque nec. Nunc eu
  facilisis lorem. Maecenas faucibus sapien eleifend, semper tellus at, pharetra
  quam. Cras feugiat vulputate tortor at rhoncus. Class aptent taciti sociosqu
  ad litora torquent per conubia nostra, per inceptos himenaeos. Nam non felis
  quis sem lobortis sodales vel id libero. Phasellus sit amet placerat lorem.
</p>

CSS

css
html {
  font-family: sans-serif;
}

body {
  margin: 0 auto;
  width: min(1000px, calc(70% + 100px));
}

h1 {
  letter-spacing: 2px;
  font-size: clamp(1.8rem, 2.5vw, 2.8rem);
}

p {
  line-height: 1.5;
  font-size: max(1.2rem, 1.2vw);
}

规范

规范
CSS 值和单位模块第 4 级
# funcdef-clamp

浏览器兼容性

另见