css line-height 详解

Last Modified: 2022/10/29

概述

内联元素的高度是由行高决定的。line-height 可以应用于任意元素,当应用于块级元素时,则定义了该块级元素内部的行高(两行文本基线之间的距离)。行高定义了最小行间距,实际的行间距可能更大。

行高的默认值是 normal,浏览器必须计算出行之间的垂直距离,各个浏览器计算的值可能不同,通常是字体大小的 1.2 倍。

基本概念

1. Leading

leading 翻译过来就是行间距~

/*行高通常应该是font size的1.2倍*/
leading = line_height - font_size /*leading可以是负值*/

2. 再说 Leading

leading = line_height - font_size
height(content_area) = font-size
/*将leading一分为二,分别加到content-area的上下,就形成了inline-box。*/
  • Top - The maximum distance above the baseline for the tallest glyph in the font at a given text size.
  • Ascent - The recommended distance above the baseline for singled spaced text.
  • Descent - The recommended distance below the baseline for singled spaced text.
  • Bottom - The maximum distance below the baseline for the lowest glyph in the font at a given text size.
  • Leading - The recommended additional space to add between lines of text.

Note that the Baseline is what the first four are measured from.

究竟什么是font-size?字体的em框又是什么鬼?

3. 内容区域

对于行内替换元素而言,内容区域就是的高等于 font-size,而行内非替换元素,内容区域等于元素的固有大小+内外间距+边框。

4. 行内框(inline box)

将 leading 一分为二,分别加到内容区域的上下就形成了元素的行内框。

/*以下推导是针对行内非替换元素而言的,行内替换元素,如img是没有leading概念的*/
leading+height(content-area)=height(inline-box)
因为height(content-area)=font_size
所以leading+font_size=height(inline-box)
因为line_height=leading+font_size
所以height(inline-box)=line-height

行内替换元素的行内框高度正好等于元素内容区域的高度。

/*总结*/
inlineBoxHeight(non-replaced-inline-element)=line-height=height(content-area)+leading
inlineBoxHeight(replaced-inline-element)=height(content-area)=(元素的固有高度+padding+margin+border)

5. line box(行框盒子)

内联元素在水平方向上从左到右排列,垂直方向上通过某种对齐方式(baseline/top/bottom)对齐之后所形成的一块矩形区域就是行框盒子(这个矩形区域正好包含最高的行内框和最低的 inline-box)。

6. 行框盒子(line box)的高度

行框盒子的高度由以下条件决定:

  • 计算每个行框盒子内每个 inline-level-box 的高度。replaced elements,inline-block elements and inline-table elements,盒子的高度就是元素的 margin 盒子高度;none replaced inline boxes 的高度是它们的 line-height。
  • 通过 vertical-align 属性对齐 inline-level 盒子。
  • 行框盒子的高度等于最高的盒子的顶部到最低盒子的底部的距离。

7. padding/margin/border对元素行内框的影响

padding/margin/border 不会影响行内非替换元素的行内框的高度,换句话说对行框高度的计算也不会产生影响;然而 padding/margin/border 却会影响行内替换元素的行内框的高度,从而影响整个行框高度的计算。

行高和继承

当一个块级元素从父元素继承行高的时候,问题就变得蹊跷了,行高会继承父元素的计算值(当父元素的行高为具体的长度值时),而不是默认情况下的字体大小的 1.2 倍了。以下代码说明了这一问题。

body {font-size: 10px;}
div {line-height: 1em;}
p {font-size: 18px;}
/* computes to '10px' */
<div>
<p>This paragraph's 'font-size' is 18px, but the inherited 'line-height'
value is only 10px. This may cause the lines of text to overlap each
other by a small amount.</p>
</div>

这种情况,可以通过将父元素的行高设置为缩放因子,此时,子元素将会继承这个缩放因子而不是计算值。

line_height = scale_factor * font_size

vertical-align

该属性只是能应用于行内元素和替换元素,不可继承。该属性值支持以下关键字:

1. baseline

使元素的基线和父元素的基线对齐。如果元素的没有基线(如img元素),就使元素的底边和父元素的基线对齐。

2. sup

使元素成为上标,这不会导致文本尺寸的变化,只是提高元素的基线,使元素的基线高于父元素的基线。

3. sub

使元素成为上标,这不会导致文本尺寸的变化,只是提高元素的基线,使元素的基线低于父元素的基线。

4. bottom

使元素的行内框的底部和行框的底部对齐。

5. top

和bottom相反。

6. middle

将元素行内框的垂直方向的中点和父元素基线上方 0.5ex位置对齐。这里的 1ex 是相对于父元素的 font-size 定义的。大多数浏览器会将 1ex 处理为 0.5em,因此大多数浏览器会将元素行框的中点和父元素基线上方 0.25em 的一个点对齐。

// 使span元素基线提高9px,而不是7px。
<div style="font-size: 14px; line-height: 18px;">
I felt that, if nothing else, I deserved a
<span style="vertical-align: 50%;">raise</span> for my efforts.
</div>

vertical-align 的值为具体数值

应当明确的是,垂直对齐的文本不会和其他行重叠也不会,更不会成为其他行的一部分,只是影响了行高而已。

Recall the description of a line box, which is exactly as tall as necessary to enclose the top of the tallest inline box and the bottom of the lowest inline box. This includes inline boxes that have been shifted up or down by vertical alignment.

行框正好的高度正好包含最高的行内框和最低的行内框。

行高的计算

line-height = leading + font-size
font-size = height-above-baseline + height-below-baseline(depth)

inline-box 包裹了文字以及文字上方和下方的 half-leading,因此 inline box 的高度恰好等于 line-height。尽管外边距,内边距和边框不会纳入行框的计算,但是这些组件仍然会被渲染在 line-box 的周围,如果行高比行内元素的盒子内容的高度小,那么会导致边框、内边距溢出到上一行。

行内非替换元素的 margin-top 和 margin-bottom

CSS2.1 规范,margin-top 和 margin-bottom 对于行内元素来说应该被忽略。

替换元素

替换元素可以增加行框的高度(参考行框高度的计算),但是不影响 line-height 的值的计算。

行内替换元素和行内非替换元素的区别?

  • 行内框高度计算方式不同;
  • 不要妄想给行内非替换元素设置宽和高;
  • any others?

行内非替换元素的行内框

行内框的内容区域由 font-size 决定,如果 font-size 是 15px,那么内容区高度就 15px,如果 line-height 是 21px,那么用户代理将 (21-15)/2 分别加到内容区域的上下,就得到了行内框。

内容区域+行间距=line-height=行内框高度

行内替换元素

一般认为行内替换元素有固有的高度和宽度。

margin 属性

/*记忆方法:逆时针tr,或者简单记为trouble*/
p{margin: top right bottom left;}

百分比和 margin

div{width:100px;}/*注意这里是width*/
p{margin-top:10%;}/*此时p的margin-top是100px乘以10%*/
<div><p>test p</p></div>

margin 为百分比的时候,是相对于父元素的宽度计算的。对于 positioned 元素来说,百分比 margin 的计算方式是不同的,啥不同呢?。。。

有问题吗?点此反馈!

温馨提示:反馈需要登录