作为第二部分的头一章,本章将主要介绍一些常用的基本CSS布局工具,如浮动和定位。本章主要探索了如何将这些工具应用到基本元素。理解这些关键概念后,就可以很好地处理CSS布局中的各类问题了。
本章主要包括以下内容:
q 浮动和清理;
q 定位。
10.1 浮动和清理
浮动(float)是使用CSS实施布局的关键概念。浮动使得你可以在一个页面不遵守元素流的线性特性的情况下实施布局,如图10-1所示。如果不采用浮动,元素将一个接一个地往下排列,这必然会导致整个页面非常长,也将不存在列和内联图像,从而我们只能依赖表格来实现布局。
如果你浮动一个元素,该元素就变成了一个块级元素,这样它就可以在当前的线上左右移动。一个浮动的框按元素的正常流来放置。但是它自身可以在元素流之外,只要包含它的元素允许,它就可以左右移动。像文本之类的内容可以按流水顺序放置在左浮动的框的右边,也可以放置在右浮动的框的左边。为了实现在特定上下文中放置图像,或者是为了创建列,或者是为了支持一般情况下设计人员的水平考虑,浮动都必不可少。
因此,浮动非常重要!但是,也有一些不好的效果。在浮动元素之后的元素将环绕在浮动元素的周围。如果你不希望看到这种状况,这些后面的元素需要清理(clear),以恢复页面元素的自然流。
为了确保包含元素的元素能够正常工作,并且在其中确实包含了浮动元素,浮动也是需要的。如果没有清理这些浮动元素,那么容器将和在它所包含的子元素之后的元素相冲突(如图10-2所示)。关于清理将在本章稍后详细介绍,并且清理将贯穿于本书第二部分的所有例子。

图10-1 More Than Doodles(http://doodles.cssmastery.com)为整个布局使用了浮动,所有图像和分栏都一定程度上浮动了

图10-2 如果浮动元素没有正确清理,包含元素的元素可能并不能识别它,因此它将和后面不浮动的元素相冲突
10.1.1 float属性
如果一个元素需要在元素自然流之外考虑,那么它就可以浮动。float属性有3个可能值:
![]()
前两个值的含义非常明显,但是none就不一样了。在本章后续部分将会详细介绍这个值。有了对浮动的基本理解,现在可以学习用于布局的浮动列了。在继续下面的内容之前,有必要先看几个例子。看看几个浮动的一般应用。
10.1.2 浮动图像
本例是为了实现一个小图像和相应的文本块对齐。该方法经常用来将一个小图像与针对某篇文章的基本介绍文本内联地放在一起。
为了继续这些例子,需要建立一个新的(X)HTML文件和相应的外部样式表。可以看出,我非常渴望成为世界上最伟大的摇滚乐队的一员。将下面的(X)HTML标记放在一个的新的文件内,并命名为floats.html:

保存该文件。注意,在文档的<head>元素中使用了一个float.css的外部样式表。创建文件float.css,并将如下代码粘贴到文件中:


保存float.css,并在浏览器上加载(X)HTML。现在,它还非常普通——仅有一个容器元素和一个二级标题。
下面,创建一个小图像,大约80×80像素,并将该图像放置在图像目录下。现在,拷贝并粘贴如下针对简单传记的(X)HTML到文件的内容区域,并确定添加了到图像的相应路径。


保存并加载该文件,其效果如图10-3所示。就它本身来说,这个布局并不丑。但是由于图像单独在一条线上,它占用了宝贵的页面空间。

图10-3 包括一个标题、一幅图像和一个段落的基本页面
现在是时候浮动图像了。首先,应用一个简单的<div>元素作为父元素来定义图像元素。

由于拥有<div>元素,图像现在可以通过使用简单的浮动来方便操作。在此,你也可以通过将image_float声明为<img>元素中的一个类来浮动图像。

一般认为,第二种方法更好,因为它使用较少的标记。但是,由于将来第一种方法能为我们在<img>元素上添加更多样式提供更多的控制,因此,在本例中我们使用第一种方法,将<img>元素包含在一个<div>元素中。
左浮动
正如前面所提到的,float属性具有不同值:left、right和none(对于例外情况下,需要覆盖任何已有的浮动时最后一个非常有用)。我们首先将图像浮动在左边。
在float.css样式表中添加如下的CSS块,并保存该文件:

在这个例子中,除定义了浮动外,还通过缩写定义了右外边距和下外边距。这样就保证了环绕在图像周围的文本和它的边缘保持一定距离,如图10-4所示:

图10-4 图像成功地浮动在左边,但是为什么容器不垂直拉伸以包含整个图像呢?
效果不错,但是并不完美。浮动确实生效了,因为图像确实已经浮动在左边,而文本紧跟其后放在右边,它们之间的距离为声明的外边距。但是,现在的问题是包含图像的<div>(container)并没有识别浮动,因此,container没有进行垂直扩展,以包含<image_float>元素,而不是与段落一样高。因此,现在是时候看看清理浮动了。当然,在你继续阅读之前,不妨泡一杯浓茶。
10.1.3 清理浮动
在浮动元素之后的元素将环绕在浮动元素周围。例如,如果一个图像浮动在左边,并且其后紧跟一个段落文本,那么只要段落够长,文本环绕在图像周围。如果你不希望看到这种情况的话,那么在浮动之后将需要对这些元素应用clear属性。
clear属性有4个不同的值:

通常,如果一般情况下都需要清理的元素,现在由于某种原因不需要清理的话,那么就使用clear:none。例如,有这么一个场景,你需要多次重用一个被清理的元素,但是现在你希望文本环绕在该元素周围,而不是出现在它的下方,那么就使用该属性。在这种情况下,需要向该元素添加一个新类,在该类中声明clear:none以覆盖父元素的clear属性。现在来仔细看一下其他的clear属性值。
1. clear:left
通过设定clear:left,元素将移动到左浮动的元素的下边界之外。
考虑如下的(X)HTML。该(X)HTML文件各个例子中可能会稍有不同,但是在结构上并没有什么改变。稍后,我们会再次使用这些技术来实现在Introducing the Band例子中关于音乐家简介的布局。但是现在,我们还是从一个比较一般的角度来看看各个值。

使用了一些简单的CSS为给这段代码加样式。第1行CSS定义了段落的属性。第2行CSS则定义了一个将要浮动在左边的灰框:

该CSS设定了一个如图10-5所示的布局。

图10-5 没有将段落清理,文本紧贴在灰框的右边
文本“说谎”了,因为文本明显仍然环绕在框周围。因此,我们需要段落来清理浮动的灰框。为了达到这个目的,在段落选择器中设定了clear属性,如下所示:

注意,框仍然浮动在左边,而段落现在清理了左边。这将迫使段落在框下面另起一行(如图10-6所示)。

图10-6 灰框浮动在左边,而段落的左边被清理了
2. clear:right
通过设定clear:right,元素将移动到右浮动的元素的下边界以下。
我们考虑另外一个例子,这个例子是建立在上面例子基础之上的。在CSS中,所需要的改动就是将所有的left改成right。


如图10-7所示,现在,框浮动在右边。由于段落清理了右边,段落仍然保持上例中的位置另起一行。

图10-7 灰框浮动在右边,段落清理了右边以确保出现在框的下方另起一行
如果没有将段落的clear值从left改成right,那么段落文本将出现在浮动框的左边,并处于同一行。这样的结果当然在某些情况下也需要。
3. clear:both
通过设定clear:both,元素将移到所有的浮动元素之下,而不管它们是浮动在左边还是浮动在右边。在本例中,框是浮动在左边,而段落的clear属性则设定为both。

在(X)HTML中,在浮动框之后添加了一个简单的三级标题。该标题没有float和clear属性。如图10-8所示,标题将环绕在浮动框周围,而段落将清理所有在它之前的元素。

图10-8 灰框仍然浮动在左边。第二个标题没有设定clear值,因此环绕在框周围,而段落则设定了clear:both
10.1.4 清理浮动图像
现在,回到浮动图像问题。应该还记得,尽管图像浮动在左边,文本正确地环绕在它周围,但是包含元素的元素并没有识别浮动。因此,容器在段落之后就结束了,而不会扩展以包含比文本更高的图像(如前面的图10-5所示)。
清理浮动现在将解决这个问题。但是由于它需要应用一些额外元素,因此这个方法并不完美。
1. 额外的spacer <div>
如果在段落元素之后还有别的元素(比如说另一个三级标题),clear属性可以在该元素中定义,而不需要定义一个额外的元素来实现清理。稍后,我们将会这样处理,但是现在由于后面没有其他元素,所以需要额外的spacer <div>。
注意 CSS设计中比较恐怖的一点是,在某些情况下,为了实现某种效果,可以违背我们所遵循的一些原则。为了达到表现的目的,添加一些没有意义的标记是不可取的。但是如果我们想在不同的平台下得到相同的结果,在某些情况下,我们仍然需要这样做。这一点,在包含元素的元素内清理浮动就是正确的。
在<p>之后,直接添加如下的spacer <div>元素:

这个讨厌的元素无疑是和表现相关的,但是为了迫使容器垂直拉伸以包含图像,该元素是必需的。接下来就需要为spacer定义CSS规则:
![]()
通过设定clear值为left,间隔层被移到了image_float元素和段落元素的下边缘之下。尽管间隔层在最终显示结果中不可见(如图10-9所示),但是它可以使得容器垂直拉伸以包含该元素。
在很多相似的环境下,用这种方式清理浮动是必需的。因为并不知道到底有多少文本需要围绕在浮动元素周围。如果添加一些段落使得文本的高度超出了浮动图像的高度,那么间隔层就不再需要了。因为容器需要扩展以包含这些段落(如图10-10所示)。但是,为了安全起见,添加一个间隔层来避免将来文本减少,使得容器不再包含浮动图像是有必要的。

图10-9 现在,容器被迫垂直拉伸以容纳在该元素中的所有元素

图10-10 不管是否清理浮动,如果不浮动的元素(段落)比浮动元素“高”,容器就可以正常工作
2. 处理多个浮动
很显然,整个乐队并不止我一个人,需要介绍一些其他的成员,如:吉他手Hendrix先生。因此,在主容器内,需要在“我”下面添加其他人的简介。
如图10-11所示,没有使用spacer <div>,因此,网页显示不正常。除了容器不能识别浮动从而太早地结束外,Hendrix先生的简介将在我的图像旁边开始了。三级标题刚好环绕在我的浮动图像周围。这是正确的,但是很丑。

图10-11 第2个简介开始得太早,正好环绕在前一个简介的浮动图像周围
在此,第一种方法是需要在每段简介后添加一个spacer <div>,如下所示:

这样就比较好了,一切都正常了(如图10-12所示)。但是现在,布局中使用了两个额外的用于表现的间隔层元素。由于添加了不必要的标记,使得代码膨胀了。这个乐队现在有7个人,那么这意味着,简介部分最后将会有7个间隔层元素。不知道你会怎么想,反正我是很不满。当然,CSS提供了更好的方法来实现以上目的。

图10-12 通过利用spacer <div>,各个简介清晰地分开了,但是现在设计使用了太多额外的表现标记
3. 用现有的元素清理
那么,怎么样才能减少间隔层呢?前面已经提到过,如果在段落后跟了其他的元素(譬如另一个三级标题),那么可以在该元素中设定clear属性,而不使用spacer <div>。现在正好有多个人物简介,因此,每个简介信息块后面都有其他元素。
在本例中,每个简介都以一个三级标题开始。这样,该元素就可用于清理上面的浮动。现在再看看在容器内的标记,我们添加了很多简介,但是仅仅在最后加了一个spacer <div>。


由于最后一段简介没有后续元素,而又同样需要清理来迫使容器垂直扩展以包容该简介,所以最后一个间隔层还是需要的。
现在,例子使用三级标题来清理在它之前的浮动元素。因此,在间隔层选择器中设定的clear值同样应用到了h3选择器:

注意,为了在每两段简介之间保持一定间隔以使布局更漂亮一些,CSS中设定了padding-top。现在,三级标题负责完成原来间隔层所完成的工作,清理前面的浮动元素,并确保每段简介都另起一行(见图10-13)。
使用已有元素清理浮动的主要优点非常明显。表现标记的数量大大减少了,从7个变成了最后的1个。标记变得更小了,并且仍然可以完全实现浮动控制。
4. 右浮动
将一个图像浮动在右边也非常简单。由于该方法一般看上去都比较美观,有些设计人员喜欢使用这种方法。文本将不均衡地环绕(只要文本没有使用text-align:justified来限定相同的长度,一般情况下都不会这么做)以创造一个右边有凹口的边缘,从而将图像精确地放置在右边。

图10-13 介绍整个乐队,现在三级标题清理了所有在其之上的浮动元素,从而将spacer <div>实例从原来的7个减为现在的1个
第一步是需要将浮动的值设定为right,并在图像的左边设定相应的外边距,而不再是在右边。

其结果如图10-14所示。图像浮动在右边,但是清理不再起作用了。第二个三级标题环绕在第一幅图像周围,而且容器也不再拉伸以容纳所有元素了。

图10-14 图像浮动在右边,但是由于没有设定clear:right,浮动被后面的元素忽略
因此,需要对用来清理浮动的两个选择器进行简单的调整。在前面的例子中,我们采用了清理left,而现在我们需要的是清理right。

这样,三级标题就移到了右浮动图像的下端的外边缘的下边,之后返回自然元素流(如图10-15所示)。

图10-15 通过清理,浮动元素之后的自然元素流跟随在浮动图像下端的外边缘之下
这些浮动的方法仅仅简单涉及了和浮动相关的一些基础知识。实际应用中,我们可以通过将浮动应用于诸如日期、图标、链接等一些元素,以实现一个非常美观而且节省空间的效果。重要的是,这些基础知识是下一章实施列布局方法的关键所在。







