自适应内部元素

摘自《CSS揭秘》---LEA VEROU

难题

  众所周知,如果我们不给元素指定固定的高度(height),它会根据其内容的高度自适应。假如我们希望宽度(width)也具有类似的行为,该怎么做呢?举个例子,假设我们用HTML5来标记图片元素,结构代码可能是这样的:

<p>文本</p>
<figure>
    <img src="" alt="" width="" height="" />
    <figcaption>
     The great Sir Adam Catlace was named after Countess Ada Lovelace, the first programmer ever.
    </figcaption>
</figure>
<p>文本</P>

  假设还需要给它添加一些基本的样式,比如一道边框。在默认情况下,他看起来如下图所示。演示连接

  但我们实际上希望这个figure元素能跟它所包含的图片一样宽(图片的尺寸通常不是固定的),而且是水平居中的。目前这个渲染结果距离我们的期望还有不小的差距:文本行比图片要宽多了。如何让figure的宽度由它内部的图片来决定,而不是由它的父元素来决定呢?闯荡江湖这么多年,相信你已经积攒了一套顺手的CSS代码大全。在这个代码库里,你可能会找到几段可以满足这种宽度行为的代码,它们通常是以副作用的方式来实现的。

  (1)让<figure>元素浮动会让它得到正确的宽度,但同时也彻底改变了它的布局模式,这往往会导致我们不想要的结果。演示连接

  (2)对<figure>应用display:inline-block会让它根据内容来决定自身的尺寸,但跟我们想要的效果还是不一样(参见下图,演示连接)此外,即使它的宽度计算方式与我们所期望的一致,我们也很难继续完成水平居中的任务。我们需要对它的父元素应用text-align:center,然后对这个父元素的所有子元素(p,ul,ol,dl.....)都设置一遍text-align:left。

  (3)当开发者走投无路时,就只能对figure应用一个固定的width或max-width了,然后对figure>img应用max-100%。可是这个方法无法充分利用有效空间;对于过小的图片来说,布局效果也很突兀。此外,响应式也无从谈起。

  有没有一种合适的CSS技巧可以解决这个问题?我们是不是应该放弃这条路,改用脚本来动态地为每个figure设置宽度?

解决方案

  CSS内部与外部尺寸模型(第三版)是一个相对较新的的规范,它为width和height属性定义了一些新的关键字,其中最有用的应该就是min-content了。这个关键字将解析为这个容器内部最大的不可断行元素的宽度(即最宽的单词、图片或具有固定宽度的盒元素)。这正是我们梦寐以求的!现在,使用以下两行CSS代码就可以把figure设置为恰当的宽度,并让它水平居中:

figure {
    width: min-content;
    margin: auto;
}

  你可以在下图中看到效果。 演示连接

  为了给那些旧版浏览器提供一个平稳的回退样式,我们需要在使用这个技巧的同时,提供一个固定的max-width值,比如:

figure {
     max-width: 300px;
     max-width: min-content;
     margin: auto;
}
figure>img {
     max-width: inherit;
}

  对于现代浏览器来说,后一条max-width声明会覆盖前一条。如果figure的尺寸是由内部因素决定时,第二条规则中的max-inherit就不会生效了。

原文地址:https://www.cnblogs.com/yaotome/p/8926089.html